Hacker News new | ask | show | jobs
by pas 27 days ago
Rust's stdlib is small, Go took more of Python's "batteries included" strategy.

So in that sense it seems like a category error to try to look for crypto stuff in the standard library. Of course this brings the well known problem of "okay, but then which one should I use?". Nowadays this is largely solved by a few web searches and LLM queries, and people are quite helpful at https://old.reddit.com/r/rust/ .

Go was shaped by the needs of Google, Rust is a wildly successful amazing experiment in programming language and compiler design that really got out of hand :) (A bit like JavaScript! Or even C#! Or Python. Same growing pains (async/await!), but arguably on different levels.)

2 comments

It turns out that the needs of Google overlaps significantly with the needs of software engineers outside Google. That argument could have been valid for a while after its initial release. But now it is just a lazy argument today.

I think batteries included is a better strategy. To the degree where I think Rust should reconsider this decision.

Rust likes to do things neat and proper and inclusive and community and zero-cost (or ALARA [as low as reasonably achievable]), and so on.

But there's no theory of standard library that they could implement. Shipping things together makes sense, but the maintenance burden is already significant, and there's also no theory of "ethically cloning open source maintainers".

I'm also quite squeamish when I think about all the unvetted dependencies, so yes, there's definitely a need, but I don't think slapping a stdlib tag on millions of lines of code would lead to great things.

But sure, I think someone could champion the case to introduce a process for adding projects to the standard packages. The projects would need to show some competence, commitment to quality and security. And the process obviously needs to have an orderly procedure for deprecation, and for "non maintainer updates" (like Debian has, for example).

It also means that everything is (over) optimised for Google's usecases, but not general purpose applications

I came across this problem pretty directly a couple of weeks ago - I wanted to see if I could port a small C program to Go, where one of the needs is to create gzip archives. But the Go stdlib insists on extraneous padding that breaks the backwards compatibility requirements of my program.

The padding isn't needed, it isn't useful, and you can't opt out of it. So the whole program went in the bin and I have resumed maintaining it in C

This is one of dozens of situations I've experienced where Go's allegedly pristine stdlib design has kicked me in the nuts

How is this «optimized for Google»?
Somebody at Google decided this is how they wanted it to work. They don't have to explain why and they don't have to fix this deficiency until it becomes a problem for Google
It seems the problem here is that they didn’t “fix” whatever you thought was “broken” and you are upset. And somehow you extrapolated that to mean that Go only follows Google’s needs.

Be a bit more precise. What exactly are you talking about and and what do you think Go does wrong and why have they chosen to do it that way?

Your tone seems hostile. I'm not obliged to answer you.
Have you argued yourself to "it's a bad thing that the Go standard library has a cryptography library"?
Rust has clearly opined that they prefer a small standard library and a "choose your own libraries" vs "batteries included" approach.

If Rust included a crypto lib and a vulnerability was discovered, many fixes are backwards incompatible. Rust maintains strict backwards compatibility, which means updating the relevant crypto functions in the std lib would necessitate a major version bump. By keeping crypto outside of std, it allows the community to make backwards incompatible changes at a higher pace.

Python handles backward incompatibility changes via multi-year deprecations. I'm not familiar with Golang but a quick Google search reveals that it deals with this by using feature flags via GODEBUG. Excessive feature flag use is a bad pattern in my experience years ago, but I don't know if that's applicable here.

I prefer the trade-offs of a "choose your own lib" approach, but I understand the advantages and preferences of those who prefer a "batteries included" approach.

In general, I get your argument, but cryptography is the perfect example for something so well-specified, well-understood, and extremely widely used, that these arguments do not really apply. You are not going to have to make backwards-incompatible changes to SHA256 or Poly1305, etc. It has minimal API surface too, and is not going to be a large maintenance burden. But nearly everybody is going to need crypto at some point. It is great to have blessed and well-audited standard implementations that people can rely on, without even having to make a choice. This it is not something where you want “the community to make backwards incompatible changes at a higher pace.”.

Crypto is something any modern language should include in the stdlib, imo.

Proviso: you do cryptography in the stdlib if you have the means to do it well. Go did; Filippo Valsorda has built a whole company practice on keeping that library excellent.

Certainly, that's a better outcome than just providing bindings to OpenSSL, which is what most other languages do.

I think I agree, but I am not sure I understand what "the means to do it well" actually means. I would think of it more as a community decision: let's focus efforts on doing X well in the standard library since X is important and people shouldn't have to ask "ok, so which third party library is the best choice right now".

Let me be the first to point out that this is not an easy thing to do since it depends heavily on the community/team/maintainer dynamics. Even agreeing on the goal or scope can be really hard. But if the Rust community is as good as people say it is, that should be doable, right?

On the other hand it wouldn't have to be definitive and exhaustive. Just a safe default. Like http muxers in Go: the one that came with the standard library was fine for a lot of uses, but people generally used third party muxers. I certainly did. And then one of the most used third party ones became shaky as it was no longer being maintained (now it is again, I think). Eventually the one in Go was improved to where I'd prefer to use that since it represents a "safe default" (and I am probably not going to need whatever extra features or performance third parties can provide).

Also note that I see myself first and foremost as an _engineer_. I care less about purity in theory than what things mean in practical terms. And in practical terms I appreciate Go for having so much useful stuff in the standard library. Stuff I kind of think we should take for granted in any serious language today.