semver 7.2.2 → 7.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +10 -0
- package/README.md +26 -23
- package/classes/range.js +50 -36
- package/index.js +1 -0
- package/internal/re.js +3 -0
- package/package.json +2 -2
- package/ranges/subset.js +155 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,15 @@
|
|
|
1
1
|
# changes log
|
|
2
2
|
|
|
3
|
+
## 7.3.0
|
|
4
|
+
|
|
5
|
+
* Add `subset(r1, r2)` method to determine if `r1` range is entirely
|
|
6
|
+
contained by `r2` range.
|
|
7
|
+
|
|
8
|
+
## 7.2.3
|
|
9
|
+
|
|
10
|
+
* Fix handling of `includePrelease` mode where version ranges like `1.0.0 -
|
|
11
|
+
2.0.0` would include `3.0.0-pre` and not `1.0.0-pre`.
|
|
12
|
+
|
|
3
13
|
## 7.2.2
|
|
4
14
|
|
|
5
15
|
* Fix bug where `2.0.0-pre` would be included in `^1.0.0` if
|
package/README.md
CHANGED
|
@@ -79,6 +79,7 @@ const semverGtr = require('semver/ranges/gtr')
|
|
|
79
79
|
const semverLtr = require('semver/ranges/ltr')
|
|
80
80
|
const semverIntersects = require('semver/ranges/intersects')
|
|
81
81
|
const simplifyRange = require('semver/ranges/simplify')
|
|
82
|
+
const rangeSubset = require('semver/ranges/subset')
|
|
82
83
|
```
|
|
83
84
|
|
|
84
85
|
As a command-line utility:
|
|
@@ -255,8 +256,8 @@ inclusive range, then all versions that start with the supplied parts
|
|
|
255
256
|
of the tuple are accepted, but nothing that would be greater than the
|
|
256
257
|
provided tuple parts.
|
|
257
258
|
|
|
258
|
-
* `1.2.3 - 2.3` := `>=1.2.3 <2.4.0`
|
|
259
|
-
* `1.2.3 - 2` := `>=1.2.3 <3.0.0`
|
|
259
|
+
* `1.2.3 - 2.3` := `>=1.2.3 <2.4.0-0`
|
|
260
|
+
* `1.2.3 - 2` := `>=1.2.3 <3.0.0-0`
|
|
260
261
|
|
|
261
262
|
#### X-Ranges `1.2.x` `1.X` `1.2.*` `*`
|
|
262
263
|
|
|
@@ -264,28 +265,28 @@ Any of `X`, `x`, or `*` may be used to "stand in" for one of the
|
|
|
264
265
|
numeric values in the `[major, minor, patch]` tuple.
|
|
265
266
|
|
|
266
267
|
* `*` := `>=0.0.0` (Any version satisfies)
|
|
267
|
-
* `1.x` := `>=1.0.0 <2.0.0` (Matching major version)
|
|
268
|
-
* `1.2.x` := `>=1.2.0 <1.3.0` (Matching major and minor versions)
|
|
268
|
+
* `1.x` := `>=1.0.0 <2.0.0-0` (Matching major version)
|
|
269
|
+
* `1.2.x` := `>=1.2.0 <1.3.0-0` (Matching major and minor versions)
|
|
269
270
|
|
|
270
271
|
A partial version range is treated as an X-Range, so the special
|
|
271
272
|
character is in fact optional.
|
|
272
273
|
|
|
273
274
|
* `""` (empty string) := `*` := `>=0.0.0`
|
|
274
|
-
* `1` := `1.x.x` := `>=1.0.0 <2.0.0`
|
|
275
|
-
* `1.2` := `1.2.x` := `>=1.2.0 <1.3.0`
|
|
275
|
+
* `1` := `1.x.x` := `>=1.0.0 <2.0.0-0`
|
|
276
|
+
* `1.2` := `1.2.x` := `>=1.2.0 <1.3.0-0`
|
|
276
277
|
|
|
277
278
|
#### Tilde Ranges `~1.2.3` `~1.2` `~1`
|
|
278
279
|
|
|
279
280
|
Allows patch-level changes if a minor version is specified on the
|
|
280
281
|
comparator. Allows minor-level changes if not.
|
|
281
282
|
|
|
282
|
-
* `~1.2.3` := `>=1.2.3 <1.(2+1).0` := `>=1.2.3 <1.3.0`
|
|
283
|
-
* `~1.2` := `>=1.2.0 <1.(2+1).0` := `>=1.2.0 <1.3.0` (Same as `1.2.x`)
|
|
284
|
-
* `~1` := `>=1.0.0 <(1+1).0.0` := `>=1.0.0 <2.0.0` (Same as `1.x`)
|
|
285
|
-
* `~0.2.3` := `>=0.2.3 <0.(2+1).0` := `>=0.2.3 <0.3.0`
|
|
286
|
-
* `~0.2` := `>=0.2.0 <0.(2+1).0` := `>=0.2.0 <0.3.0` (Same as `0.2.x`)
|
|
287
|
-
* `~0` := `>=0.0.0 <(0+1).0.0` := `>=0.0.0 <1.0.0` (Same as `0.x`)
|
|
288
|
-
* `~1.2.3-beta.2` := `>=1.2.3-beta.2 <1.3.0` Note that prereleases in
|
|
283
|
+
* `~1.2.3` := `>=1.2.3 <1.(2+1).0` := `>=1.2.3 <1.3.0-0`
|
|
284
|
+
* `~1.2` := `>=1.2.0 <1.(2+1).0` := `>=1.2.0 <1.3.0-0` (Same as `1.2.x`)
|
|
285
|
+
* `~1` := `>=1.0.0 <(1+1).0.0` := `>=1.0.0 <2.0.0-0` (Same as `1.x`)
|
|
286
|
+
* `~0.2.3` := `>=0.2.3 <0.(2+1).0` := `>=0.2.3 <0.3.0-0`
|
|
287
|
+
* `~0.2` := `>=0.2.0 <0.(2+1).0` := `>=0.2.0 <0.3.0-0` (Same as `0.2.x`)
|
|
288
|
+
* `~0` := `>=0.0.0 <(0+1).0.0` := `>=0.0.0 <1.0.0-0` (Same as `0.x`)
|
|
289
|
+
* `~1.2.3-beta.2` := `>=1.2.3-beta.2 <1.3.0-0` Note that prereleases in
|
|
289
290
|
the `1.2.3` version will be allowed, if they are greater than or
|
|
290
291
|
equal to `beta.2`. So, `1.2.3-beta.4` would be allowed, but
|
|
291
292
|
`1.2.4-beta.2` would not, because it is a prerelease of a
|
|
@@ -307,15 +308,15 @@ However, it presumes that there will *not* be breaking changes between
|
|
|
307
308
|
`0.2.4` and `0.2.5`. It allows for changes that are presumed to be
|
|
308
309
|
additive (but non-breaking), according to commonly observed practices.
|
|
309
310
|
|
|
310
|
-
* `^1.2.3` := `>=1.2.3 <2.0.0`
|
|
311
|
-
* `^0.2.3` := `>=0.2.3 <0.3.0`
|
|
312
|
-
* `^0.0.3` := `>=0.0.3 <0.0.4`
|
|
313
|
-
* `^1.2.3-beta.2` := `>=1.2.3-beta.2 <2.0.0` Note that prereleases in
|
|
311
|
+
* `^1.2.3` := `>=1.2.3 <2.0.0-0`
|
|
312
|
+
* `^0.2.3` := `>=0.2.3 <0.3.0-0`
|
|
313
|
+
* `^0.0.3` := `>=0.0.3 <0.0.4-0`
|
|
314
|
+
* `^1.2.3-beta.2` := `>=1.2.3-beta.2 <2.0.0-0` Note that prereleases in
|
|
314
315
|
the `1.2.3` version will be allowed, if they are greater than or
|
|
315
316
|
equal to `beta.2`. So, `1.2.3-beta.4` would be allowed, but
|
|
316
317
|
`1.2.4-beta.2` would not, because it is a prerelease of a
|
|
317
318
|
different `[major, minor, patch]` tuple.
|
|
318
|
-
* `^0.0.3-beta` := `>=0.0.3-beta <0.0.4` Note that prereleases in the
|
|
319
|
+
* `^0.0.3-beta` := `>=0.0.3-beta <0.0.4-0` Note that prereleases in the
|
|
319
320
|
`0.0.3` version *only* will be allowed, if they are greater than or
|
|
320
321
|
equal to `beta`. So, `0.0.3-pr.2` would be allowed.
|
|
321
322
|
|
|
@@ -323,16 +324,16 @@ When parsing caret ranges, a missing `patch` value desugars to the
|
|
|
323
324
|
number `0`, but will allow flexibility within that value, even if the
|
|
324
325
|
major and minor versions are both `0`.
|
|
325
326
|
|
|
326
|
-
* `^1.2.x` := `>=1.2.0 <2.0.0`
|
|
327
|
-
* `^0.0.x` := `>=0.0.0 <0.1.0`
|
|
328
|
-
* `^0.0` := `>=0.0.0 <0.1.0`
|
|
327
|
+
* `^1.2.x` := `>=1.2.0 <2.0.0-0`
|
|
328
|
+
* `^0.0.x` := `>=0.0.0 <0.1.0-0`
|
|
329
|
+
* `^0.0` := `>=0.0.0 <0.1.0-0`
|
|
329
330
|
|
|
330
331
|
A missing `minor` and `patch` values will desugar to zero, but also
|
|
331
332
|
allow flexibility within those values, even if the major version is
|
|
332
333
|
zero.
|
|
333
334
|
|
|
334
|
-
* `^1.x` := `>=1.0.0 <2.0.0`
|
|
335
|
-
* `^0.x` := `>=0.0.0 <1.0.0`
|
|
335
|
+
* `^1.x` := `>=1.0.0 <2.0.0-0`
|
|
336
|
+
* `^0.x` := `>=0.0.0 <1.0.0-0`
|
|
336
337
|
|
|
337
338
|
### Range Grammar
|
|
338
339
|
|
|
@@ -455,6 +456,8 @@ strings that they parse.
|
|
|
455
456
|
programmatically, to provide the user with something a bit more
|
|
456
457
|
ergonomic. If the provided range is shorter in string-length than the
|
|
457
458
|
generated range, then that is returned.
|
|
459
|
+
* `subset(subRange, superRange)`: Return `true` if the `subRange` range is
|
|
460
|
+
entirely contained by the `superRange` range.
|
|
458
461
|
|
|
459
462
|
Note that, since ranges may be non-contiguous, a version might not be
|
|
460
463
|
greater than a range, less than a range, *or* satisfy a range! For
|
package/classes/range.js
CHANGED
|
@@ -68,7 +68,7 @@ class Range {
|
|
|
68
68
|
range = range.trim()
|
|
69
69
|
// `1.2.3 - 1.2.4` => `>=1.2.3 <=1.2.4`
|
|
70
70
|
const hr = loose ? re[t.HYPHENRANGELOOSE] : re[t.HYPHENRANGE]
|
|
71
|
-
range = range.replace(hr, hyphenReplace)
|
|
71
|
+
range = range.replace(hr, hyphenReplace(this.options.includePrerelease))
|
|
72
72
|
debug('hyphen replace', range)
|
|
73
73
|
// `> 1.2.3 < 1.2.5` => `>1.2.3 <1.2.5`
|
|
74
74
|
range = range.replace(re[t.COMPARATORTRIM], comparatorTrimReplace)
|
|
@@ -92,6 +92,7 @@ class Range {
|
|
|
92
92
|
.map(comp => parseComparator(comp, this.options))
|
|
93
93
|
.join(' ')
|
|
94
94
|
.split(/\s+/)
|
|
95
|
+
.map(comp => replaceGTE0(comp, this.options))
|
|
95
96
|
// in loose mode, throw out any that are not valid comparators
|
|
96
97
|
.filter(this.options.loose ? comp => !!comp.match(compRe) : () => true)
|
|
97
98
|
.map(comp => new Comparator(comp, this.options))
|
|
@@ -191,11 +192,11 @@ const parseComparator = (comp, options) => {
|
|
|
191
192
|
const isX = id => !id || id.toLowerCase() === 'x' || id === '*'
|
|
192
193
|
|
|
193
194
|
// ~, ~> --> * (any, kinda silly)
|
|
194
|
-
// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0
|
|
195
|
-
// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0
|
|
196
|
-
// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0
|
|
197
|
-
// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0
|
|
198
|
-
// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0
|
|
195
|
+
// ~2, ~2.x, ~2.x.x, ~>2, ~>2.x ~>2.x.x --> >=2.0.0 <3.0.0-0
|
|
196
|
+
// ~2.0, ~2.0.x, ~>2.0, ~>2.0.x --> >=2.0.0 <2.1.0-0
|
|
197
|
+
// ~1.2, ~1.2.x, ~>1.2, ~>1.2.x --> >=1.2.0 <1.3.0-0
|
|
198
|
+
// ~1.2.3, ~>1.2.3 --> >=1.2.3 <1.3.0-0
|
|
199
|
+
// ~1.2.0, ~>1.2.0 --> >=1.2.0 <1.3.0-0
|
|
199
200
|
const replaceTildes = (comp, options) =>
|
|
200
201
|
comp.trim().split(/\s+/).map((comp) => {
|
|
201
202
|
return replaceTilde(comp, options)
|
|
@@ -210,18 +211,18 @@ const replaceTilde = (comp, options) => {
|
|
|
210
211
|
if (isX(M)) {
|
|
211
212
|
ret = ''
|
|
212
213
|
} else if (isX(m)) {
|
|
213
|
-
ret = `>=${M}.0.0 <${+M + 1}.0.0`
|
|
214
|
+
ret = `>=${M}.0.0 <${+M + 1}.0.0-0`
|
|
214
215
|
} else if (isX(p)) {
|
|
215
|
-
// ~1.2 == >=1.2.0 <1.3.0
|
|
216
|
-
ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0`
|
|
216
|
+
// ~1.2 == >=1.2.0 <1.3.0-0
|
|
217
|
+
ret = `>=${M}.${m}.0 <${M}.${+m + 1}.0-0`
|
|
217
218
|
} else if (pr) {
|
|
218
219
|
debug('replaceTilde pr', pr)
|
|
219
220
|
ret = `>=${M}.${m}.${p}-${pr
|
|
220
|
-
} <${M}.${+m + 1}.0`
|
|
221
|
+
} <${M}.${+m + 1}.0-0`
|
|
221
222
|
} else {
|
|
222
|
-
// ~1.2.3 == >=1.2.3 <1.3.0
|
|
223
|
+
// ~1.2.3 == >=1.2.3 <1.3.0-0
|
|
223
224
|
ret = `>=${M}.${m}.${p
|
|
224
|
-
} <${M}.${+m + 1}.0`
|
|
225
|
+
} <${M}.${+m + 1}.0-0`
|
|
225
226
|
}
|
|
226
227
|
|
|
227
228
|
debug('tilde return', ret)
|
|
@@ -230,11 +231,11 @@ const replaceTilde = (comp, options) => {
|
|
|
230
231
|
}
|
|
231
232
|
|
|
232
233
|
// ^ --> * (any, kinda silly)
|
|
233
|
-
// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0
|
|
234
|
-
// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0
|
|
235
|
-
// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0
|
|
236
|
-
// ^1.2.3 --> >=1.2.3 <2.0.0
|
|
237
|
-
// ^1.2.0 --> >=1.2.0 <2.0.0
|
|
234
|
+
// ^2, ^2.x, ^2.x.x --> >=2.0.0 <3.0.0-0
|
|
235
|
+
// ^2.0, ^2.0.x --> >=2.0.0 <3.0.0-0
|
|
236
|
+
// ^1.2, ^1.2.x --> >=1.2.0 <2.0.0-0
|
|
237
|
+
// ^1.2.3 --> >=1.2.3 <2.0.0-0
|
|
238
|
+
// ^1.2.0 --> >=1.2.0 <2.0.0-0
|
|
238
239
|
const replaceCarets = (comp, options) =>
|
|
239
240
|
comp.trim().split(/\s+/).map((comp) => {
|
|
240
241
|
return replaceCaret(comp, options)
|
|
@@ -251,40 +252,40 @@ const replaceCaret = (comp, options) => {
|
|
|
251
252
|
if (isX(M)) {
|
|
252
253
|
ret = ''
|
|
253
254
|
} else if (isX(m)) {
|
|
254
|
-
ret = `>=${M}.0.0${z} <${+M + 1}.0.0
|
|
255
|
+
ret = `>=${M}.0.0${z} <${+M + 1}.0.0-0`
|
|
255
256
|
} else if (isX(p)) {
|
|
256
257
|
if (M === '0') {
|
|
257
|
-
ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0
|
|
258
|
+
ret = `>=${M}.${m}.0${z} <${M}.${+m + 1}.0-0`
|
|
258
259
|
} else {
|
|
259
|
-
ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0
|
|
260
|
+
ret = `>=${M}.${m}.0${z} <${+M + 1}.0.0-0`
|
|
260
261
|
}
|
|
261
262
|
} else if (pr) {
|
|
262
263
|
debug('replaceCaret pr', pr)
|
|
263
264
|
if (M === '0') {
|
|
264
265
|
if (m === '0') {
|
|
265
266
|
ret = `>=${M}.${m}.${p}-${pr
|
|
266
|
-
} <${M}.${m}.${+p + 1}
|
|
267
|
+
} <${M}.${m}.${+p + 1}-0`
|
|
267
268
|
} else {
|
|
268
269
|
ret = `>=${M}.${m}.${p}-${pr
|
|
269
|
-
} <${M}.${+m + 1}.0
|
|
270
|
+
} <${M}.${+m + 1}.0-0`
|
|
270
271
|
}
|
|
271
272
|
} else {
|
|
272
273
|
ret = `>=${M}.${m}.${p}-${pr
|
|
273
|
-
} <${+M + 1}.0.0
|
|
274
|
+
} <${+M + 1}.0.0-0`
|
|
274
275
|
}
|
|
275
276
|
} else {
|
|
276
277
|
debug('no pr')
|
|
277
278
|
if (M === '0') {
|
|
278
279
|
if (m === '0') {
|
|
279
280
|
ret = `>=${M}.${m}.${p
|
|
280
|
-
}${z} <${M}.${m}.${+p + 1}
|
|
281
|
+
}${z} <${M}.${m}.${+p + 1}-0`
|
|
281
282
|
} else {
|
|
282
283
|
ret = `>=${M}.${m}.${p
|
|
283
|
-
}${z} <${M}.${+m + 1}.0
|
|
284
|
+
}${z} <${M}.${+m + 1}.0-0`
|
|
284
285
|
}
|
|
285
286
|
} else {
|
|
286
287
|
ret = `>=${M}.${m}.${p
|
|
287
|
-
} <${+M + 1}.0.0
|
|
288
|
+
} <${+M + 1}.0.0-0`
|
|
288
289
|
}
|
|
289
290
|
}
|
|
290
291
|
|
|
@@ -357,12 +358,15 @@ const replaceXRange = (comp, options) => {
|
|
|
357
358
|
}
|
|
358
359
|
}
|
|
359
360
|
|
|
361
|
+
if (gtlt === '<')
|
|
362
|
+
pr = '-0'
|
|
363
|
+
|
|
360
364
|
ret = `${gtlt + M}.${m}.${p}${pr}`
|
|
361
365
|
} else if (xm) {
|
|
362
|
-
ret = `>=${M}.0.0${pr} <${+M + 1}.0.0
|
|
366
|
+
ret = `>=${M}.0.0${pr} <${+M + 1}.0.0-0`
|
|
363
367
|
} else if (xp) {
|
|
364
368
|
ret = `>=${M}.${m}.0${pr
|
|
365
|
-
} <${M}.${+m + 1}.0
|
|
369
|
+
} <${M}.${+m + 1}.0-0`
|
|
366
370
|
}
|
|
367
371
|
|
|
368
372
|
debug('xRange return', ret)
|
|
@@ -379,32 +383,42 @@ const replaceStars = (comp, options) => {
|
|
|
379
383
|
return comp.trim().replace(re[t.STAR], '')
|
|
380
384
|
}
|
|
381
385
|
|
|
386
|
+
const replaceGTE0 = (comp, options) => {
|
|
387
|
+
debug('replaceGTE0', comp, options)
|
|
388
|
+
return comp.trim()
|
|
389
|
+
.replace(re[options.includePrerelease ? t.GTE0PRE : t.GTE0], '')
|
|
390
|
+
}
|
|
391
|
+
|
|
382
392
|
// This function is passed to string.replace(re[t.HYPHENRANGE])
|
|
383
393
|
// M, m, patch, prerelease, build
|
|
384
394
|
// 1.2 - 3.4.5 => >=1.2.0 <=3.4.5
|
|
385
|
-
// 1.2.3 - 3.4 => >=1.2.0 <3.5.0 Any 3.4.x will do
|
|
386
|
-
// 1.2 - 3.4 => >=1.2.0 <3.5.0
|
|
387
|
-
const hyphenReplace = ($0,
|
|
395
|
+
// 1.2.3 - 3.4 => >=1.2.0 <3.5.0-0 Any 3.4.x will do
|
|
396
|
+
// 1.2 - 3.4 => >=1.2.0 <3.5.0-0
|
|
397
|
+
const hyphenReplace = incPr => ($0,
|
|
388
398
|
from, fM, fm, fp, fpr, fb,
|
|
389
399
|
to, tM, tm, tp, tpr, tb) => {
|
|
390
400
|
if (isX(fM)) {
|
|
391
401
|
from = ''
|
|
392
402
|
} else if (isX(fm)) {
|
|
393
|
-
from = `>=${fM}.0.0`
|
|
403
|
+
from = `>=${fM}.0.0${incPr ? '-0' : ''}`
|
|
394
404
|
} else if (isX(fp)) {
|
|
395
|
-
from = `>=${fM}.${fm}.0`
|
|
396
|
-
} else {
|
|
405
|
+
from = `>=${fM}.${fm}.0${incPr ? '-0' : ''}`
|
|
406
|
+
} else if (fpr) {
|
|
397
407
|
from = `>=${from}`
|
|
408
|
+
} else {
|
|
409
|
+
from = `>=${from}${incPr ? '-0' : ''}`
|
|
398
410
|
}
|
|
399
411
|
|
|
400
412
|
if (isX(tM)) {
|
|
401
413
|
to = ''
|
|
402
414
|
} else if (isX(tm)) {
|
|
403
|
-
to = `<${+tM + 1}.0.0`
|
|
415
|
+
to = `<${+tM + 1}.0.0-0`
|
|
404
416
|
} else if (isX(tp)) {
|
|
405
|
-
to = `<${tM}.${+tm + 1}.0`
|
|
417
|
+
to = `<${tM}.${+tm + 1}.0-0`
|
|
406
418
|
} else if (tpr) {
|
|
407
419
|
to = `<=${tM}.${tm}.${tp}-${tpr}`
|
|
420
|
+
} else if (incPr) {
|
|
421
|
+
to = `<${tM}.${tm}.${+tp + 1}-0`
|
|
408
422
|
} else {
|
|
409
423
|
to = `<=${to}`
|
|
410
424
|
}
|
package/index.js
CHANGED
package/internal/re.js
CHANGED
|
@@ -177,3 +177,6 @@ createToken('HYPHENRANGELOOSE', `^\\s*(${src[t.XRANGEPLAINLOOSE]})` +
|
|
|
177
177
|
|
|
178
178
|
// Star ranges basically just allow anything at all.
|
|
179
179
|
createToken('STAR', '(<|>)?=?\\s*\\*')
|
|
180
|
+
// >=0.0.0 is like a star
|
|
181
|
+
createToken('GTE0', '^\\s*>=\\s*0\.0\.0\\s*$')
|
|
182
|
+
createToken('GTE0PRE', '^\\s*>=\\s*0\.0\.0-0\\s*$')
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "semver",
|
|
3
|
-
"version": "7.
|
|
3
|
+
"version": "7.3.2",
|
|
4
4
|
"description": "The semantic version parser used by npm.",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"scripts": {
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
"postpublish": "git push origin --follow-tags"
|
|
12
12
|
},
|
|
13
13
|
"devDependencies": {
|
|
14
|
-
"tap": "^14.10.
|
|
14
|
+
"tap": "^14.10.7"
|
|
15
15
|
},
|
|
16
16
|
"license": "ISC",
|
|
17
17
|
"repository": "https://github.com/npm/node-semver",
|
package/ranges/subset.js
ADDED
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
const Range = require('../classes/range.js')
|
|
2
|
+
const { ANY } = require('../classes/comparator.js')
|
|
3
|
+
const satisfies = require('../functions/satisfies.js')
|
|
4
|
+
const compare = require('../functions/compare.js')
|
|
5
|
+
|
|
6
|
+
// Complex range `r1 || r2 || ...` is a subset of `R1 || R2 || ...` iff:
|
|
7
|
+
// - Every simple range `r1, r2, ...` is a subset of some `R1, R2, ...`
|
|
8
|
+
//
|
|
9
|
+
// Simple range `c1 c2 ...` is a subset of simple range `C1 C2 ...` iff:
|
|
10
|
+
// - If c is only the ANY comparator
|
|
11
|
+
// - If C is only the ANY comparator, return true
|
|
12
|
+
// - Else return false
|
|
13
|
+
// - Let EQ be the set of = comparators in c
|
|
14
|
+
// - If EQ is more than one, return true (null set)
|
|
15
|
+
// - Let GT be the highest > or >= comparator in c
|
|
16
|
+
// - Let LT be the lowest < or <= comparator in c
|
|
17
|
+
// - If GT and LT, and GT.semver > LT.semver, return true (null set)
|
|
18
|
+
// - If EQ
|
|
19
|
+
// - If GT, and EQ does not satisfy GT, return true (null set)
|
|
20
|
+
// - If LT, and EQ does not satisfy LT, return true (null set)
|
|
21
|
+
// - If EQ satisfies every C, return true
|
|
22
|
+
// - Else return false
|
|
23
|
+
// - If GT
|
|
24
|
+
// - If GT is lower than any > or >= comp in C, return false
|
|
25
|
+
// - If GT is >=, and GT.semver does not satisfy every C, return false
|
|
26
|
+
// - If LT
|
|
27
|
+
// - If LT.semver is greater than that of any > comp in C, return false
|
|
28
|
+
// - If LT is <=, and LT.semver does not satisfy every C, return false
|
|
29
|
+
// - If any C is a = range, and GT or LT are set, return false
|
|
30
|
+
// - Else return true
|
|
31
|
+
|
|
32
|
+
const subset = (sub, dom, options) => {
|
|
33
|
+
sub = new Range(sub, options)
|
|
34
|
+
dom = new Range(dom, options)
|
|
35
|
+
let sawNonNull = false
|
|
36
|
+
|
|
37
|
+
OUTER: for (const simpleSub of sub.set) {
|
|
38
|
+
for (const simpleDom of dom.set) {
|
|
39
|
+
const isSub = simpleSubset(simpleSub, simpleDom, options)
|
|
40
|
+
sawNonNull = sawNonNull || isSub !== null
|
|
41
|
+
if (isSub)
|
|
42
|
+
continue OUTER
|
|
43
|
+
}
|
|
44
|
+
// the null set is a subset of everything, but null simple ranges in
|
|
45
|
+
// a complex range should be ignored. so if we saw a non-null range,
|
|
46
|
+
// then we know this isn't a subset, but if EVERY simple range was null,
|
|
47
|
+
// then it is a subset.
|
|
48
|
+
if (sawNonNull)
|
|
49
|
+
return false
|
|
50
|
+
}
|
|
51
|
+
return true
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
const simpleSubset = (sub, dom, options) => {
|
|
55
|
+
if (sub.length === 1 && sub[0].semver === ANY)
|
|
56
|
+
return dom.length === 1 && dom[0].semver === ANY
|
|
57
|
+
|
|
58
|
+
const eqSet = new Set()
|
|
59
|
+
let gt, lt
|
|
60
|
+
for (const c of sub) {
|
|
61
|
+
if (c.operator === '>' || c.operator === '>=')
|
|
62
|
+
gt = higherGT(gt, c, options)
|
|
63
|
+
else if (c.operator === '<' || c.operator === '<=')
|
|
64
|
+
lt = lowerLT(lt, c, options)
|
|
65
|
+
else
|
|
66
|
+
eqSet.add(c.semver)
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
if (eqSet.size > 1)
|
|
70
|
+
return null
|
|
71
|
+
|
|
72
|
+
let gtltComp
|
|
73
|
+
if (gt && lt) {
|
|
74
|
+
gtltComp = compare(gt.semver, lt.semver, options)
|
|
75
|
+
if (gtltComp > 0)
|
|
76
|
+
return null
|
|
77
|
+
else if (gtltComp === 0 && (gt.operator !== '>=' || lt.operator !== '<='))
|
|
78
|
+
return null
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// will iterate one or zero times
|
|
82
|
+
for (const eq of eqSet) {
|
|
83
|
+
if (gt && !satisfies(eq, String(gt), options))
|
|
84
|
+
return null
|
|
85
|
+
|
|
86
|
+
if (lt && !satisfies(eq, String(lt), options))
|
|
87
|
+
return null
|
|
88
|
+
|
|
89
|
+
for (const c of dom) {
|
|
90
|
+
if (!satisfies(eq, String(c), options))
|
|
91
|
+
return false
|
|
92
|
+
}
|
|
93
|
+
return true
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
let higher, lower
|
|
97
|
+
let hasDomLT, hasDomGT
|
|
98
|
+
for (const c of dom) {
|
|
99
|
+
hasDomGT = hasDomGT || c.operator === '>' || c.operator === '>='
|
|
100
|
+
hasDomLT = hasDomLT || c.operator === '<' || c.operator === '<='
|
|
101
|
+
if (gt) {
|
|
102
|
+
if (c.operator === '>' || c.operator === '>=') {
|
|
103
|
+
higher = higherGT(gt, c, options)
|
|
104
|
+
if (higher === c)
|
|
105
|
+
return false
|
|
106
|
+
} else if (gt.operator === '>=' && !satisfies(gt.semver, String(c), options))
|
|
107
|
+
return false
|
|
108
|
+
}
|
|
109
|
+
if (lt) {
|
|
110
|
+
if (c.operator === '<' || c.operator === '<=') {
|
|
111
|
+
lower = lowerLT(lt, c, options)
|
|
112
|
+
if (lower === c)
|
|
113
|
+
return false
|
|
114
|
+
} else if (lt.operator === '<=' && !satisfies(lt.semver, String(c), options))
|
|
115
|
+
return false
|
|
116
|
+
}
|
|
117
|
+
if (!c.operator && (lt || gt) && gtltComp !== 0)
|
|
118
|
+
return false
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
// if there was a < or >, and nothing in the dom, then must be false
|
|
122
|
+
// UNLESS it was limited by another range in the other direction.
|
|
123
|
+
// Eg, >1.0.0 <1.0.1 is still a subset of <2.0.0
|
|
124
|
+
if (gt && hasDomLT && !lt && gtltComp !== 0)
|
|
125
|
+
return false
|
|
126
|
+
|
|
127
|
+
if (lt && hasDomGT && !gt && gtltComp !== 0)
|
|
128
|
+
return false
|
|
129
|
+
|
|
130
|
+
return true
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
// >=1.2.3 is lower than >1.2.3
|
|
134
|
+
const higherGT = (a, b, options) => {
|
|
135
|
+
if (!a)
|
|
136
|
+
return b
|
|
137
|
+
const comp = compare(a.semver, b.semver, options)
|
|
138
|
+
return comp > 0 ? a
|
|
139
|
+
: comp < 0 ? b
|
|
140
|
+
: b.operator === '>' && a.operator === '>=' ? b
|
|
141
|
+
: a
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
// <=1.2.3 is higher than <1.2.3
|
|
145
|
+
const lowerLT = (a, b, options) => {
|
|
146
|
+
if (!a)
|
|
147
|
+
return b
|
|
148
|
+
const comp = compare(a.semver, b.semver, options)
|
|
149
|
+
return comp < 0 ? a
|
|
150
|
+
: comp > 0 ? b
|
|
151
|
+
: b.operator === '<' && a.operator === '<=' ? b
|
|
152
|
+
: a
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
module.exports = subset
|