diff --git a/lib/util/regex.ts b/lib/util/regex.ts new file mode 100644 index 0000000000000000000000000000000000000000..b109ffde07580ed0a8f042f363947d0b5519e0ca --- /dev/null +++ b/lib/util/regex.ts @@ -0,0 +1,22 @@ +import { logger } from '../logger'; + +export interface RegExConstructor { + new (pattern: RegExp | string): RegExp; + new (pattern: string, flags?: string): RegExp; +} + +const RegEx: RegExConstructor = (() => { + try { + // eslint-disable-next-line + const RE2 = require('re2'); + // Test if native is working + new RE2('.*').exec('test'); + logger.debug('Using RE2 as regex engine'); + return RE2; + } catch (err) { + logger.warn({ err }, 'RE2 not usable, falling back to RegExp'); + return RegExp; + } +})(); + +export { RegEx }; diff --git a/lib/versioning/regex/index.ts b/lib/versioning/regex/index.ts index 2f201f35bce8a09c18d695bbcc6fa2d9712cec94..94e2c1c672b671ba6f62b56db12de3f3e3bf2647 100644 --- a/lib/versioning/regex/index.ts +++ b/lib/versioning/regex/index.ts @@ -1,8 +1,8 @@ import { compare, satisfies, ltr, minSatisfying, maxSatisfying } from 'semver'; -import RE2 from 're2'; import { VersioningApiConstructor } from '../common'; import { GenericVersion, GenericVersioningApi } from '../loose/generic'; import { logger } from '../../logger'; +import { RegEx } from '../../util/regex'; export interface RegExpVersion extends GenericVersion { /** prereleases are treated in the standard semver manner, if present */ @@ -50,7 +50,7 @@ export class RegExpVersioningApi extends GenericVersioningApi<RegExpVersion> { // capture groups? try { - this._config = new RE2(new_config); + this._config = new RegEx(new_config); } catch (e) { logger.debug({ err: e }, 'regex error'); const error = new Error('config-validation'); diff --git a/package.json b/package.json index 808ebd05870f05b60ff6479d31724c84c5c4853d..d3d24f7430eeef32ae1eff9359de4609dd4d0b26 100644 --- a/package.json +++ b/package.json @@ -137,7 +137,6 @@ "parse-diff": "0.5.1", "parse-link-header": "1.0.1", "pnpm": "3.7.5", - "re2": "1.10.0", "registry-auth-token": "4.0.0", "safe-regex": "2.0.2", "semver": "6.3.0", @@ -155,6 +154,9 @@ "yarn": "1.17.3", "yawn-yaml": "1.4.0" }, + "optionalDependencies": { + "re2": "1.10.0" + }, "devDependencies": { "@babel/cli": "7.5.5", "@babel/core": "7.5.5", diff --git a/test/util/regex.spec.ts b/test/util/regex.spec.ts new file mode 100644 index 0000000000000000000000000000000000000000..f99dd325108d5d7ac63fba704713e709b71a6ff9 --- /dev/null +++ b/test/util/regex.spec.ts @@ -0,0 +1,21 @@ +import RE2 from 're2'; +import { RegEx } from '../../lib/util/regex'; + +describe('util/regex', () => { + beforeEach(() => { + jest.resetModules(); + }); + + it('uses RE2', () => { + expect(RegEx).toEqual(RE2); + }); + + it('Falls back to RegExp', () => { + jest.doMock('re2', () => { + throw new Error(); + }); + + const regex = require('../../lib/util/regex'); + expect(regex.RegEx).toEqual(RegExp); + }); +});