5 ms·
I see a lot of discussion on Rust vs $LANG, but nobody seems to be discussing what I think is the meat of this announcement: 1. Fewer tradeoffs for third-p
by d4mi3n 5y ago
I see a lot of discussion on Rust vs $LANG, but nobody seems to be discussing what I think is the meat of this announcement:
1. Fewer tradeoffs for third-party dependencies
Most JavaScript/npm packages have to balance a lot of different concerns for many different kinds of users. They are forced to make tradeoffs around code size and performance that we aren’t interested in. Rust crates, on the other hand, are generally making tradeoffs that much closer align to our needs.
2. Correctness is built-in to the standard library and in most popular crates
We were creating our own APIs that focused on correctness instead of using third-party JavaScript dependencies. Rust, and its community, places a lot more focus on correctness without paving over edge cases that we need to worry about for Rome.
3. Trait/Module system allows us to make better use of dependencies
Rust’s trait system is a powerful way to create abstractions over any piece of data without overhead. It allows us to deeply integrate third party libraries. It also allows libraries to create APIs that are much more incremental, safely exposing more surface area without creating a need to make breaking changes.
My takeaway here is that the Rome team was getting tired of rewriting stuff from scratch but the nature of the JS/NPM ecosystem made it hard to use 3rd party code without losing control over Rome's performance.
I'm not sure how valid this claim is, but it is well known that the history of NPM modules puts the ecosystem in a weird place where libraries are expected to optimize for usage on both server environments (Node, Deno, etc) and browser environments (Firefox, Chrome, etc).
This tradeoff is not without costs--I believe it's one of the big reasons we see dependency bloat in the NPM ecosystem. I'd love to see more discussion around this topic and what other folks' experiences with these kinds of problems are.
- thejameskyle 5y agoSomething I didn't mention in the post that might deserve calling out specifically is that Rust maintainers actively decide to work in crates instead of in std for many things. This means that you have the language designers themselves maintaining some of the most important crates in the ecosystem, and baking it into their process to iterate on the language itself. The result is really high quality crates and the community is better for it. I'm not trying to dunk on JavaScript/npm packages though, or anyone involved in developing the language. Clearly the JS community has found success and is meeting a lot of people's needs. We can accept that Rome's requirements are different than most people using JavaScript.
- d4mi3n 5y agoHi Jamie! I thought the article was pretty thoughtful and I'm sorry it's gotten such a mixed response in the comments here. It was interesting seeing your commentary on Red-Green trees and how they're used. I'm excited at the prospect of a rust-analyzer level of type-checking and correction for TS/JS. As a technical security person, I also see a lot of potential for such tooling to do things like data-flow analysis, which is pretty much the gold standard for detecting things like untrusted input or dangerous interpolation. Are there plans to support that kind of security tooling in Rome? If not, is there any interest in supporting something like that in it's eventual feature-set?
- lhorie 5y agoOne big issue with NPM is that JS stdlib is extremely bare bones and the ecosystem swings far into the other direction to compensate, which leads to many libraries pulling in convenience utils that pull in their own convenience utils ad infinitum. So you, as a consumer of a toolkit like Rome, might be forced to download crap like function-bind@1.0.1 even though that is only pulled in as a deep transitive dep for some ancient obscure thing that wanted to support IE6 or something. With Rust and other compiled languages, this isn't as much of an issue since even a "bloated" binary for a single architecture is still orders of magnitude faster to download than a constellation of packages each supporting an arbitrary subset of Node runtime versions. with this said, there may also be a novelty factor in play here. Rust can definitely be considered the "new shiny thing" for this team, and with only a few weeks of Rust under their belt, they might still be well within the honeymoon phase. I can think of at least one major aspect in this space that becomes harder with a move to Rust: the only fully complete Typescript type checking implementation in existence is written in JS/TS, and I expect that type-aware tooling is going to sprout there first. The Typescript team in particular seems fairly uniquely positioned to be able to deliver some sort of type-aware compiler mode similar to google closure advanced mode. In comparison, IMHO it's not a super compelling story for Rome to say they're going to provide a fast, unified web dev toolkit that... doesn't typecheck (due to poor interop with the JS ecosystem/community). The esbuild ecosystem is already there today and forging ahead with the force of the OSS community behind it. Bun.sh is taking a completely different approach by standing on the shoulders of giants. Last I heard, they were leveraging the ubiquity of C ABI - via zig - to leverage JavascriptCore, and looking into V8 bindings, and focusing on lightning fast hot reloading instead of reinventing parsing. Rome seems to be approaching implementation from a first-principles angle, which seems most similar to esbuild's approach, but that first movers advantage is long gone though.
- pornel 5y agoRust's stdlib is similarly bare-bones. Rust/Cargo has the same mindset of many small packages as JS/npm. The difference is that in JS abstraction and indirection has a run-time cost, so doing things via packages adds overhead. In Rust, you can have zero-cost abstractions that optimize away. The runtime and code-size cost is often the same whether you call code from a generic 3rd party crate or write it yourself inline in your function.