/ utils / semver.ts
semver.ts
 1  /**
 2   * Semver comparison utilities that use Bun.semver when available
 3   * and fall back to the npm `semver` package in Node.js environments.
 4   *
 5   * Bun.semver.order() is ~20x faster than npm semver comparisons.
 6   * The npm semver fallback always uses { loose: true }.
 7   */
 8  
 9  let _npmSemver: typeof import('semver') | undefined
10  
11  function getNpmSemver(): typeof import('semver') {
12    if (!_npmSemver) {
13      // eslint-disable-next-line @typescript-eslint/no-require-imports
14      _npmSemver = require('semver') as typeof import('semver')
15    }
16    return _npmSemver
17  }
18  
19  export function gt(a: string, b: string): boolean {
20    if (typeof Bun !== 'undefined') {
21      return Bun.semver.order(a, b) === 1
22    }
23    return getNpmSemver().gt(a, b, { loose: true })
24  }
25  
26  export function gte(a: string, b: string): boolean {
27    if (typeof Bun !== 'undefined') {
28      return Bun.semver.order(a, b) >= 0
29    }
30    return getNpmSemver().gte(a, b, { loose: true })
31  }
32  
33  export function lt(a: string, b: string): boolean {
34    if (typeof Bun !== 'undefined') {
35      return Bun.semver.order(a, b) === -1
36    }
37    return getNpmSemver().lt(a, b, { loose: true })
38  }
39  
40  export function lte(a: string, b: string): boolean {
41    if (typeof Bun !== 'undefined') {
42      return Bun.semver.order(a, b) <= 0
43    }
44    return getNpmSemver().lte(a, b, { loose: true })
45  }
46  
47  export function satisfies(version: string, range: string): boolean {
48    if (typeof Bun !== 'undefined') {
49      return Bun.semver.satisfies(version, range)
50    }
51    return getNpmSemver().satisfies(version, range, { loose: true })
52  }
53  
54  export function order(a: string, b: string): -1 | 0 | 1 {
55    if (typeof Bun !== 'undefined') {
56      return Bun.semver.order(a, b)
57    }
58    return getNpmSemver().compare(a, b, { loose: true })
59  }