Hacker News new | ask | show | jobs
by vbezhenar 1082 days ago
People just love LTS and backwards compatibility too much. I'm one of them. But it slows the industry, when you can't do API refactors and have to keep bad decisions forever.

I think library authors should be more relentless and break compatibility every few years. We just need some conventions to not do so very often. Like new major version every year, deprecate API on the next major version, remove deprecated API on the following major version. So you have 1 year to rewrite your app if necessary.

And supporting old versions for those enterprises who would rather pay than upgrade might be a good source of income.

11 comments

> So you have 1 year to rewrite your app if necessary

Multiply this by the thousands of dependencies modern apps have and the only thing you will ever do is rewrites.

Most applications (even large ones) do not have thousands of direct dependencies.
Good point. It's even better when a dependency multiple levels down gets a breaking change and the direct one is unmaintained.
Who keeps unmaintained, direct dependencies in their projects? Seems like basic hygiene to replace them.
*Node.js & Python developers enter the chat*
> People just love LTS and backwards compatibility too much. I'm one of them. But it slows the industry, when you can't do API refactors and have to keep bad decisions forever.

Hard disagree. API churn is (one of) the real cost of using libraries / external dependencies, so people would just rather reimplement them themselves or copy the library code directly into their project.

> I think library authors should be more relentless and break compatibility every few years. We just need some conventions to not do so very often.

I indeed did this years ago---I'm the original author of Chrono [1]---and it wasn't well received [2] [3] [4]. To be fair, I knew it was a clear violation of semantic versioning but I didn't see any point of strictly obeying that until we've reached 1.0 so I went ahead. People complained a lot and I had to yank the release in question. By then I realized many enough people religiously expect semantic versioning (for good reasons though) and it's wiser to avoid useless conflict.

[1] https://github.com/chronotope/chrono

[2] https://github.com/chronotope/chrono/issues/146#issuecomment...

[3] https://github.com/chronotope/chrono/issues/156

[4] https://github.com/chronotope/chrono/blob/main/CHANGELOG.md#...

I understand from the author perspective that everything below 1.0 is subject to change, from the hobby user perspective I see 0.3 to 0.3.1 and think "oh bug fix, that means I won't read it" without expecting semver.
All those things happened when the Rust crate ecosystem was still much in flux (back in 2017), and I had some good reasons:

- Serde had made a very slight but breaking change in 1.0, and at that time I think it was impossible to support both Serde 0.9 and 1.0 in a single crate without a hacky workaround (which I only learned much later). So if I had to pick only one version to support, it ought to be 1.0 as the change was trivial to resolve.

- Cargo's use of semantic versioning is, while documented, not strictly conforming because 0.x.y is considered compatible with 0.x.z where x > 0 and y < z [1].

- People complained a lot when Chrono went 0.2.x to 0.3.0 as well. This is IMO the biggest reason to issue a breaking change; if people would complain in either way, I wanted to make a choice that benefits the whole Rust ecosystem more.

If this happen today I would agree that I shouldn't have done that, but I think it was not that clear cut at that time.

[1] https://semver.org/#spec-item-4

OTOH you, as a library supplier, may be somewhat hamstrung to improve things you think ought to be improved but consider the productivity hit to your downstream consumers if you constantly break things for them. Stepping back to consider all parties, for even moderately popular projects the balance is obviously tipped in the favor of the consumers.

There are libraries out there (such as FFMpeg iirc) that will do a yearly major version with breaking changes. This is a good approach imo. FFmpeg consumers know what to expect and when to expect it.

> But it slows the industry, when you can't do API refactors and have to keep bad decisions forever.

It slows the industry when you're spending all your time rewriting code that already works.

The question is, who is slowed down: API creators or API users? If you make regular breaking changes to APIs, it's API users who get slowed down, if you don't it's API creators who get slowed down.

Given the entire point of things that have APIs (libraries, frameworks, centralized services, etc.) is that there are many users and few creators, it's pretty clear which slows down more people.

Additionally, with good API design, you can often maintain namespaced APIs in tandem with very little additional cost. I've got a /v1/blah API and a /v2/blah API on one of my clients' websites--the v1 directory hasn't been touched in 7 years, because all the bugs anyone cares about have been fixed. It still has users (at least officially, I haven't looked at the reporting to see how often they're actually hitting those APIs). The users simply don't care about the new features in the new API, and it's not our place to force them to care.

You can do similar things with libraries (think sqlite vs. sqlite3) but this is obviously harder with frameworks (which is one of the reasons to not like frameworks). It doesn't work everywhere but it works often.

It takes 3 years minimum, often 5, for non LTS Debian, to cycle through a library revision.

IMO, if you think distros are a thing of the past, or 3 years support of the biggest base distro is slowing things down, you're living in a bubble.

I know you prepended this with a statement saying you love LTS too, but to many, LTS is a decade or more.

And really, I have no interest running 'new shiny'. That is the absolute opposite of stable. That is where horrible, life altering mistakes live. If you want to increase your workload 100x, run bleeding edge.

And bleeding edge is anything that has any code change, outside of bug fixes and security fixes.

I know my position is not popular, but that doesn't make it wrong.

Like software that requires some time to master. I can't recount all the times when i invested much time into doing it properly, only to have it all become useless and invalidated because upstream decided to throw it all away.

With you having an attitude like you do, why should i even bother with reading your documentation? Give it 2 years and it will all be obsolete. Waste of time.

Fuck innovation. I want tools that exist long enough that i can master them.

> But it slows the industry, when you can't do API refactors and have to keep bad decisions forever.

That's not true. You can simply put any breaking changes into separate namespaces. Now you have limitless backwards compatibility and yet users can selectively upgrade whenever they want the new features.

Maintain a non-trivial node project for a while and you will see why some people like stability.

Libraries are not really a problem, as you can have multiple major versions alongside, so i can have gtk2, gtk3 and gtk4 alongside, each offering its API for applications that use it, while actively developed code (in library) does not need to handle deprecated API.

Bigger problems are demons with API, where it is usually not possible to run multiple versions alongside (as they would compete on the same resources or data), so one code have to offer multiple API versions internally.

> I think library authors should be more relentless and break compatibility every few years.

...isn't it just how most LTSs work? LTS is long-term support, not life-time support.

I don't think you should be afraid of removing backwards compatibility. Look at WordPress that has maintained backwards compatibility for too long. It will happily run plugins that were abandoned ten years ago.

When you break compatibility, you force out abandoned crap. I agree you don't want to do it too often; but not doing it at all is (IMHO) worse.