mirror of
https://github.com/semver/semver.git
synced 2026-07-11 03:53:53 -05:00
[GH-ISSUE #1148] ✨ Proposal: Clarify SemVer handling of build metadata and equality #5810
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Originally created by @erify-world on GitHub (Sep 7, 2025).
Original GitHub issue: https://github.com/semver/semver/issues/1148
Context
While SemVer 2.0.0 specifies that build metadata (+...) does not affect precedence, there’s ambiguity in how equality should be interpreted across implementations.
For example:
• 1.0.0+build.1 vs. 1.0.0+exp.sha.5114f85
• Should these be considered equal (since build metadata is ignored for precedence), or distinct (since the metadata differs)?
⸻
Problem
• Different tooling ecosystems (npm, Maven, Cargo, etc.) treat equality and metadata differently.
• This creates interoperability issues when comparing, caching, or distributing artifacts.
⸻
Proposal
1. Clarify Equality Rule:
Explicitly state whether two versions differing only by build metadata should be considered equal.
2. Reference Examples:
Add normative examples to the specification, e.g.:
• 1.0.0+abc == 1.0.0+xyz (if build metadata is ignored)
• Or explicitly declare them distinct (if metadata counts).
3. Impact Assessment:
• How will this affect existing package managers?
• Should metadata equality be left implementation-defined, or standardized?
⸻
Motivation
• Ensures cross-tool consistency.
• Reduces ambiguous comparisons across ecosystems.
• Provides clear guidance for future spec versions (e.g., SemVer 3.0).
⸻
🔗 Related Issues:
• Equality and build metadata
• Proposed v2.0.1
@ljharb commented on GitHub (Sep 7, 2025):
I'm not sure why there's ambiguity -
1.0.0+build.1is objectively not equal to1.0.0+exp.sha.5114f85.However, in a system like npm that ignores build metadata,
1.0.0+build.1is reduced to1.0.0, as is1.0.0+exp.sha.5114f85- so they resolve to the same version.@norman-abramovitz commented on GitHub (Oct 20, 2025):
The spec makes it clear that information after the + does not play a role in comparing semver strings. if you want the information to compared it needs to be in the - section. Think the + section as comments.
@ljharb commented on GitHub (Oct 22, 2025):
The spec says
Comparing two versions for equality is not for determining version precedence.
@norman-abramovitz commented on GitHub (Oct 23, 2025):
I cannot tell if we are agreeing or not. The spec allows for version comparison only. The prerelease section is lower precedence.
The spec intentionally does not define whole string comparison. Just like adding a v in front of the major number is not a semver string.
Whole string comparison is out of scope for this version of the spec.
@ljharb commented on GitHub (Oct 23, 2025):
Right - this issue is asking about whole string comparison of the semver string - in which case, regardless of the spec's silence on the matter, I'd say the only possible interpretation is that
1.0.0+build.1is not equal to1.0.0+exp.sha.5114f85@norman-abramovitz commented on GitHub (Oct 29, 2025):
I am playing devil's advocate here (i.e., proposing a different interpretation on purpose to see where it leads).
Given your example strings
1.0.0+build.1
1.0.0+exp.sha.5114f85
Your two strings are providing different information. One gives build information, and the other gives exp. sha information.
Performing a whole string comparison would be invalid even if you want to compare the complete strings.
As some people say, it is like comparing apples to oranges., They are both fruits, but they are totally different things.
Nothing in the specification stops you from having multiple version strings for a project.
So, staying within the specification, these two strings are equal, but convey different information. I believe that is what npm is doing.
@smilly-boy commented on GitHub (Dec 29, 2025):
@Aranmobinarann commented on GitHub (Jan 27, 2026):
Hello
Ok🙂
Formally define 'semantic equality' where build metadata is entirely ignored. Two versions are considered equal if their major.minor.patch-pre-release identifiers are identical..
Justification:
Aligns with SemVer philosophy
Follows common existing behavior..
Prevents duplicate versions with different build metadata.
Improves tooling interoperability..👍🙂
@jwdonahue commented on GitHub (Mar 10, 2026):
@Aranmobinarann
That depends on the infrastructure you are using. Some packaging tools are perfectly happy to apply multiple version strings, with differing metadata, to the same content. Some aren't quite that picky, and will allow multiple entries that vary only in metadata (useful in massively parallel build systems), whether their content is the same or not, but they require you to be explicit regarding which package you want to pull, if there is more than one.
For compliance purposes, there should never be 2 package content hashes in the wild, with the same version string (ignoring meta). Most tool chains don't actually work hard enough to prevent this.
Some, like NPM, simply toss the metadata. Or at least they used to, and that makes it a little harder for multiple devs working in the same code space, to silently bifurcate their customer base.