relaxed parsing of usercss @version

fixes #821
This commit is contained in:
tophf 2021-02-26 10:02:21 +03:00
parent 9b46da5846
commit 53c71614fc
25 changed files with 98 additions and 142 deletions

View File

@ -672,12 +672,7 @@
}
},
"meta_invalidVersion": {
"message": "Ungültige Versionsnummer: Der Wert entspricht nicht dem SemVer Schema: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Ungültige Versionsnummer"
},
"meta_invalidWord": {
"message": "Erwarte ein Wort"

View File

@ -916,12 +916,7 @@
"description": "Error displayed when the protocol of the URL is invalid"
},
"meta_invalidVersion": {
"message": "Invalid version number. The value doesn't match SemVer pattern: $version$",
"placeholders": {
"version": {
"content": "$1"
}
},
"message": "Invalid version number",
"description": "Error displayed when @version is invalid"
},
"meta_invalidWord": {

View File

@ -662,12 +662,7 @@
}
},
"meta_invalidVersion": {
"message": "Número de versión no válido. El valor no coincide con el patrón SemVer: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Número de versión no válido"
},
"meta_invalidWord": {
"message": "Se espera una palabra"

View File

@ -669,12 +669,7 @@
}
},
"meta_invalidVersion": {
"message": "Numéro de version invalide. La valeur ne correspond pas au motif SemVer : $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Numéro de version invalide"
},
"meta_invalidWord": {
"message": "Mot attendu"

View File

@ -654,12 +654,7 @@
}
},
"meta_invalidVersion": {
"message": "Érvénytelen verziószám. Az érték nem illeszkedik a SemVer mintájához: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Érvénytelen verziószám"
},
"meta_invalidWord": {
"message": "Várt elem: szó"

View File

@ -684,12 +684,7 @@
}
},
"meta_invalidVersion": {
"message": "不正なバージョン番号。値がバージョン番号のパターンに合っていません: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "不正なバージョン番号"
},
"meta_invalidWord": {
"message": "単語を入力してください"

View File

@ -672,12 +672,7 @@
}
},
"meta_invalidVersion": {
"message": "유효하지 않은 버전 숫자입니다. $version$은(는) 유의적 버전 패턴과 일치하지 않습니다.",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "유효하지 않은 버전 숫자입니다"
},
"meta_invalidWord": {
"message": "단어를 입력하세요"

View File

@ -691,12 +691,7 @@
}
},
"meta_invalidVersion": {
"message": "Ongeldig versienummer. De waarde komt niet overeen met het SemVer-patroon:$version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Ongeldig versienummer"
},
"meta_invalidWord": {
"message": "Woord verwacht"

View File

@ -719,12 +719,7 @@
}
},
"meta_invalidVersion": {
"message": "Nieprawidłowy numer wersji. Wartość nie pasuje do wzorca SemVer: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Nieprawidłowy numer wersji"
},
"meta_invalidWord": {
"message": "Spodziewane słowo"

View File

@ -675,12 +675,7 @@
}
},
"meta_invalidVersion": {
"message": "Неверный номер версии. Значение не соответствует шаблону SemVer: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Неверный номер версии"
},
"meta_invalidWord": {
"message": "Ожидание слова"

View File

@ -648,12 +648,7 @@
}
},
"meta_invalidVersion": {
"message": "Ogiltigt versionsnummer. Värdet matchar inte SemVer-mönstret: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "Ogiltigt versionsnummer"
},
"meta_invalidWord": {
"message": "Förvänta dig ett ord"

View File

@ -725,12 +725,7 @@
}
},
"meta_invalidVersion": {
"message": "无效的版本号. 值与 SemVer 规则不匹配: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "无效的版本号"
},
"meta_invalidWord": {
"message": "需要一个单词"

View File

@ -719,12 +719,7 @@
}
},
"meta_invalidVersion": {
"message": "无效的版本号. 值与 SemVer 规则不匹配: $version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "无效的版本号"
},
"meta_invalidWord": {
"message": "需要一个单词"

View File

@ -719,12 +719,7 @@
}
},
"meta_invalidVersion": {
"message": "無效的版本號。值不符合 SemVer 模式:$version$",
"placeholders": {
"version": {
"content": "$1"
}
}
"message": "無效的版本號"
},
"meta_invalidWord": {
"message": "預期為單字"

View File

@ -2,6 +2,7 @@
/* global RX_META URLS debounce download ignoreChromeError */// toolbox.js
/* global calcStyleDigest styleJSONseemsValid styleSectionsEqual */ // sections-util.js
/* global chromeLocal */// storage-util.js
/* global compareVersion */// cmpver.js
/* global db */
/* global prefs */
'use strict';
@ -25,10 +26,10 @@ const updateMan = (() => {
const RH_ETAG = {responseHeaders: ['etag']}; // a hashsum of file contents
const RX_DATE2VER = new RegExp([
/^(\d{4})/,
/(1(?:0|[12](?=\d\d))?|[2-9])/, // in ambiguous cases like yyyy123 the month will be 1
/([1-2][0-9]?|3[0-1]?|[4-9])/,
/\.(0|1[0-9]?|2[0-3]?|[3-9])/,
/\.(0|[1-5][0-9]?|[6-9])$/,
/(0[1-9]|1(?:0|[12](?=\d\d))?|[2-9])/, // in ambiguous cases like yyyy123 the month will be 1
/(0[1-9]|[1-2][0-9]?|3[0-1]?|[4-9])/,
/\.([01][0-9]?|2[0-3]?|[3-9])/,
/\.([0-5][0-9]?|[6-9])$/,
].map(rx => rx.source).join(''));
const ALARM_NAME = 'scheduledUpdate';
const MIN_INTERVAL_MS = 60e3;
@ -213,14 +214,8 @@ const updateMan = (() => {
}
// TODO: when sourceCode is > 100kB use http range request(s) for version check
const {headers: {etag}, response} = await tryDownload(style.updateUrl, RH_ETAG);
/* There's a bug? in Chrome which occurs only in a packaged crx:
* DOM script for semver fires 'load' event before the script actually runs.
* Since the conditions for the bug are rare we'll simply load in parallel */
const [json] = await Promise.all([
API.usercss.buildMeta({sourceCode: response, etag}),
require(['/vendor/semver-bundle/semver']), /* global semverCompare */
]);
const delta = semverCompare(json.usercssData.version, ucd.version);
const json = await API.usercss.buildMeta({sourceCode: response, etag});
const delta = compareVersion(json.usercssData.version, ucd.version);
let err;
if (!delta && !ignoreDigest) {
// re-install is invalid in a soft upgrade

View File

@ -56,7 +56,7 @@ setTimeout(() => {
'/vendor/codemirror/addon/selection/active-line',
'/vendor/codemirror/lib/codemirror.css',
'/vendor/codemirror/addon/fold/foldgutter.css',
'/vendor/semver-bundle/semver', /* global semverCompare */
'/js/cmpver', /* global compareVersion */
'/js/sections-util', /* global styleCodeEmpty */
'/js/color/color-converter',
'/edit/codemirror-default.css',
@ -89,7 +89,7 @@ setTimeout(() => {
}
const data = style.usercssData;
const dupData = dup && dup.usercssData;
const versionTest = dup && semverCompare(data.version, dupData.version);
const versionTest = dup && compareVersion(data.version, dupData.version);
updateMeta(style, dup);
@ -144,7 +144,7 @@ function updateMeta(style, dup = installedDup) {
installedDup = dup;
const data = style.usercssData;
const dupData = dup && dup.usercssData;
const versionTest = dup && semverCompare(data.version, dupData.version);
const versionTest = dup && compareVersion(data.version, dupData.version);
cm.setPreprocessor(data.preprocessor);

42
js/cmpver.js Normal file
View File

@ -0,0 +1,42 @@
'use strict';
/**
Copied from https://github.com/violentmonkey/violentmonkey/blob/master/src/common/util.js
A couple of trivial changes: switched to Math.sign, removed the default radix from parseInt
*/
/* exported compareVersion */
const VERSION_RE = /^(.*?)-([-.0-9a-z]+)|$/i;
const DIGITS_RE = /^\d+$/; // using regexp to avoid +'1e2' being parsed as 100
/** @return -1 | 0 | 1 */
function compareVersion(ver1, ver2) {
const [, main1 = ver1 || '', pre1] = VERSION_RE.exec(ver1);
const [, main2 = ver2 || '', pre2] = VERSION_RE.exec(ver2);
const delta = compareVersionChunk(main1, main2)
|| !pre1 - !pre2 // 1.2.3-pre-release is less than 1.2.3
|| pre1 && compareVersionChunk(pre1, pre2, true); // if pre1 is present, pre2 is too
return Math.sign(delta);
}
function compareVersionChunk(ver1, ver2, isSemverMode) {
const parts1 = ver1.split('.');
const parts2 = ver2.split('.');
const len1 = parts1.length;
const len2 = parts2.length;
const len = (isSemverMode ? Math.min : Math.max)(len1, len2);
let delta;
for (let i = 0; !delta && i < len; i += 1) {
const a = parts1[i];
const b = parts2[i];
if (isSemverMode) {
delta = DIGITS_RE.test(a) && DIGITS_RE.test(b)
? a - b
: a > b || a < b && -1;
} else {
delta = (parseInt(a) || 0) - (parseInt(b) || 0);
}
}
return delta || isSemverMode && (len1 - len2);
}

View File

@ -5,6 +5,12 @@ const metaParser = (() => {
require(['/vendor/usercss-meta/usercss-meta.min']); /* global usercssMeta */
const {createParser, ParseError} = usercssMeta;
const PREPROCESSORS = new Set(['default', 'uso', 'stylus', 'less']);
/** Relaxed semver:
* dot-separated digits sequence e.g. 1 or 1.2 or 1.2.3.4.5
* optional pre-release chunk: "-" followed by dot-separated word characters, "-"
* optional build chunk: "+" followed by dot-separated word characters, "-"
*/
const RX_VER = /^\d+(\.\d+)*(?:-(\w[-\w]*(\.[-\w]+)*))?(?:\+(\w[-\w]*(\.[-\w]+)*))?$/;
const options = {
validateKey: {
preprocessor: state => {
@ -16,6 +22,15 @@ const metaParser = (() => {
});
}
},
version: state => {
if (!RX_VER.test(state.value)) {
throw new ParseError({
code: 'invalidVersion',
message: 'Invalid @version',
index: state.valueIndex,
});
}
},
},
validateVar: {
select: state => {

View File

@ -32,6 +32,7 @@
"js/storage-util.js",
"js/sections-util.js",
"js/worker-util.js",
"js/cmpver.js",
"background/common.js",

34
package-lock.json generated
View File

@ -14,7 +14,6 @@
"jsonlint": "^1.6.3",
"less-bundle": "github:openstyles/less-bundle#v0.1.0",
"lz-string-unsafe": "^1.4.4-fork-1",
"semver-bundle": "^0.1.1",
"stylelint-bundle": "^13.8.0",
"stylus-lang-bundle": "github:openstyles/stylus-lang-bundle#v0.54.7",
"usercss-meta": "^0.10.0",
@ -644,6 +643,7 @@
"espree": "7.3.0",
"esprima": "4.0.1",
"fluent-syntax": "0.13.0",
"fsevents": "2.2.1",
"glob": "7.1.6",
"is-mergeable-object": "1.1.1",
"jed": "1.1.1",
@ -1853,6 +1853,12 @@
"engines": [
"node >=0.10.0"
],
"dependencies": {
"dtrace-provider": "~0.8",
"moment": "^2.19.3",
"mv": "~2",
"safe-json-stringify": "~1"
},
"bin": {
"bunyan": "bin/bunyan"
},
@ -2136,6 +2142,7 @@
"dependencies": {
"anymatch": "~3.1.1",
"braces": "~3.0.2",
"fsevents": "~2.3.1",
"glob-parent": "~5.1.0",
"is-binary-path": "~2.1.0",
"is-glob": "~4.0.1",
@ -4570,6 +4577,9 @@
"resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz",
"integrity": "sha1-h3Gq4HmbZAdrdmQPygWPnBDjPss=",
"dev": true,
"dependencies": {
"graceful-fs": "^4.1.6"
},
"optionalDependencies": {
"graceful-fs": "^4.1.6"
}
@ -7009,6 +7019,7 @@
"integrity": "sha512-ssHt0dkljEDaKmTgQ04DQgx2ag6G2gMPxA5hpcsoeTbfDgRf2fC2gNSRc6kISjD7ckCpHwwQvXxuTBK8402fXg==",
"dev": true,
"dependencies": {
"encoding": "^0.1.12",
"minipass": "^3.1.0",
"minipass-pipeline": "^1.2.2",
"minipass-sized": "^1.0.3",
@ -9110,14 +9121,6 @@
"resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz",
"integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg=="
},
"node_modules/semver-bundle": {
"version": "0.1.1",
"resolved": "https://registry.npmjs.org/semver-bundle/-/semver-bundle-0.1.1.tgz",
"integrity": "sha512-AXZEjNFlP6BzqRlWQNF3NBGsDw/clPcuUAk1mUl+ypnSplG20CDLQj5ofmaj40vlUHt40duxH3d/x/RXItLAHA==",
"dependencies": {
"semver": "^5.5.0"
}
},
"node_modules/semver-diff": {
"version": "3.1.1",
"resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-3.1.1.tgz",
@ -11267,8 +11270,10 @@
"integrity": "sha512-9P3MWk6SrKjHsGkLT2KHXdQ/9SNkyoJbabxnKOoJepsvJjJG8uYTR3yTPxPQvNDI3w4Nz1xnE0TLHK4RIVe/MQ==",
"dev": true,
"dependencies": {
"chokidar": "^3.4.1",
"graceful-fs": "^4.1.2",
"neo-async": "^2.5.0"
"neo-async": "^2.5.0",
"watchpack-chokidar2": "^2.0.1"
},
"optionalDependencies": {
"chokidar": "^3.4.1",
@ -11352,6 +11357,7 @@
"anymatch": "^2.0.0",
"async-each": "^1.0.1",
"braces": "^2.3.2",
"fsevents": "^1.2.7",
"glob-parent": "^3.1.0",
"inherits": "^2.0.3",
"is-binary-path": "^1.0.0",
@ -19458,14 +19464,6 @@
"resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz",
"integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg=="
},
"semver-bundle": {
"version": "0.1.1",
"resolved": "https://registry.npmjs.org/semver-bundle/-/semver-bundle-0.1.1.tgz",
"integrity": "sha512-AXZEjNFlP6BzqRlWQNF3NBGsDw/clPcuUAk1mUl+ypnSplG20CDLQj5ofmaj40vlUHt40duxH3d/x/RXItLAHA==",
"requires": {
"semver": "^5.5.0"
}
},
"semver-diff": {
"version": "3.1.1",
"resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-3.1.1.tgz",

View File

@ -11,7 +11,6 @@
"jsonlint": "^1.6.3",
"less-bundle": "github:openstyles/less-bundle#v0.1.0",
"lz-string-unsafe": "^1.4.4-fork-1",
"semver-bundle": "^0.1.1",
"stylelint-bundle": "^13.8.0",
"stylus-lang-bundle": "github:openstyles/stylus-lang-bundle#v0.54.7",
"usercss-meta": "^0.10.0",

View File

@ -44,9 +44,6 @@ const files = {
'lz-string-unsafe': [
'lz-string-unsafe.min.js',
],
'semver-bundle': [
'dist/semver.js → semver.js',
],
'stylelint-bundle': [
'dist/stylelint-bundle.min.js → stylelint-bundle.min.js',
'https://github.com/stylelint/stylelint/raw/{VERSION}/LICENSE → LICENSE',

View File

@ -1,15 +0,0 @@
The ISC License
Copyright (c) Isaac Z. Schlueter and Contributors
Permission to use, copy, modify, and/or distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.

View File

@ -1,5 +0,0 @@
## semver-bundle v0.1.1
Following files are copied from npm (node_modules):
* semver.js: dist\semver.js

View File

@ -1 +0,0 @@
var semverCompare=function(){"use strict";var s=256,i=Number.MAX_SAFE_INTEGER||9007199254740991,a=[],e=[],r=0,t=r++;e[t]="0|[1-9]\\d*";var n=r++;e[n]="[0-9]+";var h=r++;e[h]="\\d*[a-zA-Z-][a-zA-Z0-9-]*";var o=r++;e[o]="("+e[t]+")\\.("+e[t]+")\\.("+e[t]+")";var p=r++;e[p]="("+e[n]+")\\.("+e[n]+")\\.("+e[n]+")";var l=r++;e[l]="(?:"+e[t]+"|"+e[h]+")";var c=r++;e[c]="(?:"+e[n]+"|"+e[h]+")";var v=r++;e[v]="(?:-("+e[l]+"(?:\\."+e[l]+")*))";var f=r++;e[f]="(?:-?("+e[c]+"(?:\\."+e[c]+")*))";var m=r++;e[m]="[0-9A-Za-z-]+";var u=r++;e[u]="(?:\\+("+e[m]+"(?:\\."+e[m]+")*))";var g=r++,w="v?"+e[o]+e[v]+"?"+e[u]+"?";e[g]="^"+w+"$";var d="[v=\\s]*"+e[p]+e[f]+"?"+e[u]+"?",$=r++;e[$]="^"+d+"$";var y=r++;e[y]="((?:<|>)?=?)";var E=r++;e[E]=e[n]+"|x|X|\\*";var j=r++;e[j]=e[t]+"|x|X|\\*";var b=r++;e[b]="[v=\\s]*("+e[j]+")(?:\\.("+e[j]+")(?:\\.("+e[j]+")(?:"+e[v]+")?"+e[u]+"?)?)?";var k=r++;e[k]="[v=\\s]*("+e[E]+")(?:\\.("+e[E]+")(?:\\.("+e[E]+")(?:"+e[f]+")?"+e[u]+"?)?)?",e[r++]="^"+e[y]+"\\s*"+e[b]+"$",e[r++]="^"+e[y]+"\\s*"+e[k]+"$",e[r++]="(?:^|[^\\d])(\\d{1,16})(?:\\.(\\d{1,16}))?(?:\\.(\\d{1,16}))?(?:$|[^\\d])";var T=r++;e[T]="(?:~>?)";var x=r++;e[x]="(\\s*)"+e[T]+"\\s+",a[x]=new RegExp(e[x],"g"),e[r++]="^"+e[T]+e[b]+"$",e[r++]="^"+e[T]+e[k]+"$";var I=r++;e[I]="(?:\\^)";var A=r++;e[A]="(\\s*)"+e[I]+"\\s+",a[A]=new RegExp(e[A],"g"),e[r++]="^"+e[I]+e[b]+"$",e[r++]="^"+e[I]+e[k]+"$",e[r++]="^"+e[y]+"\\s*("+d+")$|^$",e[r++]="^"+e[y]+"\\s*("+w+")$|^$";var R=r++;e[R]="(\\s*)"+e[y]+"\\s*("+d+"|"+e[b]+")",a[R]=new RegExp(e[R],"g"),e[r++]="^\\s*("+e[b]+")\\s+-\\s+("+e[b]+")\\s*$",e[r++]="^\\s*("+e[k]+")\\s+-\\s+("+e[k]+")\\s*$",e[r++]="(<|>)?=?\\s*\\*";for(var N=0;N<35;N++)a[N]||(a[N]=new RegExp(e[N]));function z(e,r){if(e instanceof z){if(e.loose===r)return e;e=e.version}else if("string"!=typeof e)throw new TypeError("Invalid Version: "+e);if(e.length>s)throw new TypeError("version is longer than "+s+" characters");if(!(this instanceof z))return new z(e,r);this.loose=r;var t=e.trim().match(r?a[$]:a[g]);if(!t)throw new TypeError("Invalid Version: "+e);if(this.raw=e,this.major=+t[1],this.minor=+t[2],this.patch=+t[3],this.major>i||this.major<0)throw new TypeError("Invalid major version");if(this.minor>i||this.minor<0)throw new TypeError("Invalid minor version");if(this.patch>i||this.patch<0)throw new TypeError("Invalid patch version");t[4]?this.prerelease=t[4].split(".").map(function(e){if(/^[0-9]+$/.test(e)){var r=+e;if(0<=r&&r<i)return r}return e}):this.prerelease=[],this.build=t[5]?t[5].split("."):[],this.format()}z.prototype.format=function(){return this.version=this.major+"."+this.minor+"."+this.patch,this.prerelease.length&&(this.version+="-"+this.prerelease.join(".")),this.version},z.prototype.toString=function(){return this.version},z.prototype.compare=function(e){return e instanceof z||(e=new z(e,this.loose)),this.compareMain(e)||this.comparePre(e)},z.prototype.compareMain=function(e){return e instanceof z||(e=new z(e,this.loose)),X(this.major,e.major)||X(this.minor,e.minor)||X(this.patch,e.patch)},z.prototype.comparePre=function(e){if(e instanceof z||(e=new z(e,this.loose)),this.prerelease.length&&!e.prerelease.length)return-1;if(!this.prerelease.length&&e.prerelease.length)return 1;if(!this.prerelease.length&&!e.prerelease.length)return 0;var r=0;do{var t=this.prerelease[r],s=e.prerelease[r];if(void 0===t&&void 0===s)return 0;if(void 0===s)return 1;if(void 0===t)return-1;if(t!==s)return X(t,s)}while(++r)},z.prototype.inc=function(e,r){switch(e){case"premajor":this.prerelease.length=0,this.patch=0,this.minor=0,this.major++,this.inc("pre",r);break;case"preminor":this.prerelease.length=0,this.patch=0,this.minor++,this.inc("pre",r);break;case"prepatch":this.prerelease.length=0,this.inc("patch",r),this.inc("pre",r);break;case"prerelease":0===this.prerelease.length&&this.inc("patch",r),this.inc("pre",r);break;case"major":0===this.minor&&0===this.patch&&0!==this.prerelease.length||this.major++,this.minor=0,this.patch=0,this.prerelease=[];break;case"minor":0===this.patch&&0!==this.prerelease.length||this.minor++,this.patch=0,this.prerelease=[];break;case"patch":0===this.prerelease.length&&this.patch++,this.prerelease=[];break;case"pre":if(0===this.prerelease.length)this.prerelease=[0];else{for(var t=this.prerelease.length;0<=--t;)"number"==typeof this.prerelease[t]&&(this.prerelease[t]++,t=-2);-1===t&&this.prerelease.push(0)}r&&(this.prerelease[0]===r?isNaN(this.prerelease[1])&&(this.prerelease=[r,0]):this.prerelease=[r,0]);break;default:throw new Error("invalid increment argument: "+e)}return this.format(),this.raw=this.version,this};var M=/^[0-9]+$/;function X(e,r){var t=M.test(e),s=M.test(r);return t&&s&&(e=+e,r=+r),t&&!s?-1:s&&!t?1:e<r?-1:r<e?1:0}return function(e,r,t){return new z(e,t).compare(new z(r,t))}}();