@verifyhash/semver-lite
v0.1.1
Published
Zero-dependency SemVer 2.0.0 parse, precedence compare, and a documented practical subset of npm-style range matching for Node.js.
Downloads
32
Maintainers
Readme
semver-lite
A tiny, zero-dependency, zero-network Node.js library for Semantic Versioning 2.0.0: parse a version string, compare two versions by the exact SemVer precedence rules (including the fiddly pre-release ordering), and test whether a version satisfies a range using a documented, practical subset of npm-style range syntax.
It is a single CommonJS file (index.js) with no dependencies, no install step,
and no I/O. Drop it into any project.
Spec reference: https://semver.org/spec/v2.0.0.html
Install
npm install @verifyhash/semver-litePublished as @verifyhash/semver-lite;
source lives in the verifyhash/libs monorepo.
Zero runtime dependencies — you can also vendor the folder directly.
Who it's for
JavaScript/Node developers who need dependency- or version-logic — "is 1.4.2
inside ^1.2.0?", "which of these tags is newest?", "does this pre-release sort
before the release?" — without pulling in the full semver
package and its transitive footprint. Good for build scripts, CLIs, plugin
loaders, changelog tooling, and anywhere you want auditable, single-file version
math.
If you need the complete node-semver range grammar (coercion, x in the
middle of comparators, full prerelease-range semantics, loose mode, etc.), use
the real semver package. This library deliberately covers the common 95%.
Install / use
No install — copy index.js, or require it directly:
const semver = require('./index.js');
semver.parse('1.2.3-rc.1+build.5');
// { major: 1, minor: 2, patch: 3,
// prerelease: ['rc', 1], build: ['build', '5'],
// version: '1.2.3-rc.1' }
semver.gt('1.0.0', '1.0.0-rc.1'); // true (release > prerelease)
semver.lt('1.0.0-alpha.1', '1.0.0-alpha.beta'); // true (numeric < alphanumeric)
semver.eq('1.0.0+build.1', '1.0.0+build.9'); // true (build metadata ignored)
semver.satisfies('1.2.5', '^1.2.0'); // true
semver.satisfies('2.0.0', '^1.2.0'); // false
semver.sort(['1.0.0', '1.0.0-rc.1', '1.0.0-alpha']);
// ['1.0.0-alpha', '1.0.0-rc.1', '1.0.0']API
parse(v) → object | null
Parses a SemVer 2.0.0 string. Returns null on invalid input — it does not
throw. (Comparison functions below do throw on invalid input; see each.)
Returns:
{
major: Number,
minor: Number,
patch: Number,
prerelease: Array<string|number>, // numeric identifiers are Numbers
build: Array<string>, // always strings; ignored for precedence
version: String // "major.minor.patch[-prerelease]" (no build)
}Rejected (returns null): missing components (1, 1.2), a leading v
(v1.2.3), leading zeros in any numeric field (01.2.3, 1.2.3-01), empty
identifiers (1.2.3-, 1.0.0-a..b), and non-strings. Surrounding whitespace is
trimmed.
valid(v) → boolean
true iff parse(v) succeeds.
compare(a, b) → -1 | 0 | 1
Compares by SemVer precedence. Throws TypeError if either argument is not a
valid version. Precedence rules implemented (SemVer §11):
- Compare
major, thenminor, thenpatchnumerically. - A version with a pre-release has lower precedence than the same
version without one (
1.0.0-rc.1 < 1.0.0). - Pre-release identifiers are compared left-to-right:
- numeric identifiers are compared numerically (
beta.2 < beta.11); - a numeric identifier always has lower precedence than an alphanumeric
one (
alpha.1 < alpha.beta); - alphanumeric identifiers are compared by ASCII sort order;
- if all shared identifiers are equal, the version with more fields has
higher precedence (
alpha < alpha.1).
- numeric identifiers are compared numerically (
- Build metadata is ignored entirely (
1.0.0+a==1.0.0+b).
gt, lt, gte, lte, eq, neq (a, b) → boolean
Thin wrappers over compare; same throwing behaviour.
sort(list) → array
Returns a new array sorted ascending by precedence.
satisfies(version, range) → boolean
Returns true iff version matches range. Never throws for a bad
version (returns false); a malformed range token throws TypeError.
Supported range syntax
| Form | Example | Expands to |
| --------------- | -------------------- | ----------------------------- |
| exact | 1.2.3 | =1.2.3 |
| equals | =1.2.3 | =1.2.3 |
| comparators | >1.2.3 >=1.2.3 <2.0.0 <=1.2.3 | as written |
| caret | ^1.2.3 | >=1.2.3 <2.0.0 |
| caret (0.x) | ^0.2.3 | >=0.2.3 <0.3.0 |
| caret (0.0.x) | ^0.0.3 | >=0.0.3 <0.0.4 |
| tilde | ~1.2.3 | >=1.2.3 <1.3.0 |
| tilde (partial) | ~1.2 / ~1 | >=1.2.0 <1.3.0 / >=1.0.0 <2.0.0 |
| x-range | 1.2.x 1.x 1.2.* * 1 | e.g. 1.2.x → >=1.2.0 <1.3.0 |
| hyphen range | 1.2.3 - 2.3.4 | >=1.2.3 <=2.3.4 |
| AND (space) | >=1.2.0 <2.0.0 | intersection |
| OR (\|\|) | ^1.0.0 \|\| ^2.0.0 | union |
Partial operands are handled the node-semver way: >1 → >=2.0.0,
<=1.2 → <1.3.0, and a partial upper hyphen bound like 1.2.3 - 2.3 becomes
<2.4.0.
Pre-release handling in ranges
A version carrying a pre-release tag (e.g. 1.2.3-beta.2) satisfies a range
only if some comparator in the matched set names the same
major.minor.patch tuple and itself has a pre-release. So
1.2.3-beta.2 satisfies >=1.2.3-beta.1 <2.0.0 but not ^1.0.0. This
mirrors npm's default (non-includePrerelease) behaviour.
NOT supported (use the full semver package instead)
includePrereleasemode and advanced pre-release range edge cases beyond the single documented rule above.- Version coercion /
looseparsing (e.g.v1,1.2.3.4,=v1.2). x/*in the middle of a version (1.x.3) — only trailing wildcards.- Comparators glued to carets/tildes in one token, or ranges relying on operator precedence quirks.
- Any I/O, registry lookups, or
dist-tags.
If your input might use those, reach for semver.
Running the tests
One command, no framework, only Node's built-in assert:
node test/index.test.js
# or
npm testThe suite covers: parse (valid, prerelease/build, leading-zero rejection,
non-string input), the full SemVer spec precedence chain
(1.0.0-alpha < 1.0.0-alpha.1 < 1.0.0-alpha.beta < 1.0.0-beta < 1.0.0-beta.2 <
1.0.0-beta.11 < 1.0.0-rc.1 < 1.0.0), build-metadata-ignored equality,
invalid-input handling, and satisfies with both true and false cases for
every supported range form (exact, ^, ~, x-range, comparators, hyphen, and
||).
License
MIT — see LICENSE.
