Closed Tcc100 closed 2 years ago
Thank you...
I will add it to v2.51
Actually the suggested higherVersion_new function has problem, since it doesn't break early
function higherVersion_new(a, b) {
a = a.split('.').map(n => parseInt(n));
b = b.split('.').map(n => parseInt(n));
for (let i = 0; i < Math.max(a.length, b.length); i++) {
console.log(a[i] ?? 0, '>', b[i] ?? 0, (a[i] ?? 0) > (b[i] ?? 0));
if ((a[i] ?? 0) > (b[i] ?? 0)) { return true; }
}
return false;
}
console.log(higherVersion('1.1.1', '2.0.0'));
/*
1 > 2 false
1 > 0 true
true
*/
Indeed, seems that comparing versions is quite hard.
Here is an early-aborting version:
function higherVersion_new2(a, b) {
a = a.split('.').map(n => parseInt(n));
b = b.split('.').map(n => parseInt(n));
for (let i = 0, len = Math.max(a.length, b.length); i < len; i++) {
if ((a[i] ?? 0) !== (b[i] ?? 0)) {
return (a[i] ?? 0) > (b[i] ?? 0);
}
}
return false;
}
The tests seems OK. You can try more tests to make sure.
function higherVersion(a, b) {
a = a.split('.').map(n => parseInt(n));
b = b.split('.').map(n => parseInt(n));
for (let i = 0; i < Math.max(a.length, b.length); i++) {
const [x, y] = [a[i] ?? 0, b[i] ?? 0];
console.log(a.join('.'), '-', b.join('.'), x, '>', y, x === y ? 'continue' : x > y);
if (x !== y) { return x > y; }
}
return false;
}
for (const [a, b, t] of [
["3.0", "2.0", true ],
["3.0", "3.0", false],
["3.0.0", "3.0", false],
["3.0", "3.0.0", false],
["3.0", "3.0.1", false],
["3.0.1", "3.0", true ],
["0.3.0", "0.2.0", true ],
["0.3", "0.3.1", false],
["0.3.1", "0.3", true ],
["1.1.1", "2.0", false ],
["2.0.0", "2.0.rc1", ?? ], // <- it is troublesome here
]) {
const o = higherVersion(a, b);
console.log(`${a}\t${b}\t${t}\t` + (o === t ? o : ("" + o).toUpperCase()));
}
I just checked greasy fork and did not find a version using -rc1 or alike. Some use a description like "1.1.1 New Features".
You also may consider
return a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }) > 0;
(https://stackoverflow.com/a/65687141). This succeeds for -rc1, but considers "3.0.0" and "3.0" differently.
That is not too bad. Although it considers "3.0.0" and "3.0" differently, but that should be OK.. since the script has changed (it didn't have .0
before).
Update: localeCompare
seems to work better and there are less mismatches.
function higherVersion(a, b) {
a = a.split('.').map(n => parseInt(n));
b = b.split('.').map(n => parseInt(n));
for (let i = 0; i < Math.max(a.length, b.length); i++) {
const [x, y] = [a[i] ?? 0, b[i] ?? 0];
console.log(a.join('.'), '-', b.join('.'), x, '>', y, x === y ? 'continue' : x > y);
if (x !== y) { return x > y; }
}
return false;
}
for (const [a, b, t] of [
['3.0', '2.0', true ],
['3.0', '3.0', false],
['3.0.0', '3.0', false],
['3.0', '3.0.0', false],
['3.0', '3.0.1', false],
['3.0.1', '3.0', true ],
['0.3.0', '0.2.0', true ],
['0.3', '0.3.1', false],
['0.3.1', '0.3', true ],
['1.1.1', '2.0', false ],
['2.0.0', '2.0.rc1', false ],
['2.0.rc2', '2.0.rc1', true ],
['2.0.rc2', '2.0.rc3', false ],
['1.2.0', '1.10.0', false ],
['1.02.0', '1.1.0', true ],
['1.2.0', '1.10.0', false ],
['1.02.0', '1.1.0', true ],
['1.2.0', '1.10.0', false ],
['1.02.0', '1.1.0', true ],
['1.0.0.0.0.0', '1.0', true],
['1.0.0.0.0.0', '1.1', false],
['1.0', '1.0.1', false],
['1.0b1', '1.0', true],
['1.0a', '1.0b', false],
['1.1', '1.0.1b', true],
['1.1alpha', '1.1beta', false],
['1.1rc1', '1.1beta', true],
['1.0001', '1.00000.1.0.0.0.01', true],
['1.0.0', '1.0.0', false],
]) {
let o = higherVersion(a, b);
(o === t ? console.log : console.error)(`higherVersion: ${a}\t${b}\t${t}\t` + (o === t ? o : ('' + o).toUpperCase()));
o = a.localeCompare(b, undefined, { numeric: true, sensitivity: 'base' }) > 0;
(o === t ? console.log : console.error)(`localeCompare: ${a}\t${b}\t${t}\t` + (o === t ? o : ('' + o).toUpperCase()));
}
When I click Update on a script with a major version number of zero, FireMonkey incorrectly shows "There is no new update" regardless of the actual version differences.
I found that the
higherVersion
function reports incorrect results for some values:I suggest to use a function like this instead:
Thanks!