renovate
Version:
Automated dependency updates. Flexible so you don't need to be.
150 lines • 5.65 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.api = exports.isValid = exports.supportedRangeStrategies = exports.supportsRanges = exports.urls = exports.displayName = exports.id = void 0;
const semver_1 = require("semver");
const semver_stable_1 = require("semver-stable");
const logger_1 = require("../../../logger");
const regex_1 = require("../../../util/regex");
const npm_1 = require("../npm");
exports.id = 'cargo';
exports.displayName = 'Cargo';
exports.urls = [
'https://doc.rust-lang.org/cargo/reference/specifying-dependencies.html',
];
exports.supportsRanges = true;
exports.supportedRangeStrategies = [
'bump',
'pin',
'replace',
];
const isVersion = (input) => npm_1.api.isVersion(input);
function convertToCaret(item) {
// In Cargo, caret versions are used by default, so "1.2.3" actually means ^1.2.3.
// Similarly, "0.4" actually means ^0.4.
// See: https://doc.rust-lang.org/stable/cargo/reference/specifying-dependencies.html#caret-requirements
if (isVersion(item) || isVersion(item + '.0') || isVersion(item + '.0.0')) {
return '^' + item.trim();
}
return item.trim();
}
function cargo2npm(input) {
let versions = input.split(',');
versions = versions.map(convertToCaret);
return versions.join(' ');
}
function notEmpty(s) {
return s !== '';
}
function npm2cargo(input) {
// istanbul ignore if
if (!input) {
return input;
}
// Note: this doesn't remove the ^
const res = input
.split((0, regex_1.regEx)(/\s+,?\s*|\s*,?\s+/))
.map((str) => str.trim())
.filter(notEmpty);
const operators = ['^', '~', '=', '>', '<', '<=', '>='];
for (let i = 0; i < res.length - 1; i += 1) {
if (operators.includes(res[i])) {
const newValue = res[i] + ' ' + res[i + 1];
res.splice(i, 2, newValue);
}
}
return res.join(', ');
}
const isLessThanRange = (version, range) => !!npm_1.api.isLessThanRange?.(version, cargo2npm(range));
const isValid = (input) => npm_1.api.isValid(cargo2npm(input));
exports.isValid = isValid;
const matches = (version, range) => npm_1.api.matches(version, cargo2npm(range));
function getSatisfyingVersion(versions, range) {
return npm_1.api.getSatisfyingVersion(versions, cargo2npm(range));
}
function minSatisfyingVersion(versions, range) {
return npm_1.api.minSatisfyingVersion(versions, cargo2npm(range));
}
const isSingleVersion = (constraint) => constraint.trim().startsWith('=') &&
isVersion(constraint.trim().substring(1).trim());
function getNewValue({ currentValue, rangeStrategy, currentVersion, newVersion, }) {
if (!currentValue || currentValue === '*') {
return rangeStrategy === 'pin' ? `=${newVersion}` : currentValue;
}
// If the current value is a simple version, bump to fully specified newVersion
if (rangeStrategy === 'bump' && (0, regex_1.regEx)(/^\d+(?:\.\d+)*$/).test(currentValue)) {
return newVersion;
}
if (rangeStrategy === 'pin' || isSingleVersion(currentValue)) {
let res = '=';
if (currentValue.startsWith('= ')) {
res += ' ';
}
res += newVersion;
return res;
}
if (rangeStrategy === 'replace' && matches(newVersion, currentValue)) {
return currentValue;
}
const newSemver = npm_1.api.getNewValue({
currentValue: cargo2npm(currentValue),
rangeStrategy,
currentVersion,
newVersion,
});
let newCargo = newSemver
? npm2cargo(newSemver)
: /* istanbul ignore next: should never happen */ null;
// istanbul ignore if
if (!newCargo) {
logger_1.logger.info({ currentValue, newSemver }, 'Could not get cargo version from semver');
return currentValue;
}
// Keep new range precision the same as current
if ((currentValue.startsWith('~') || currentValue.startsWith('^')) &&
rangeStrategy === 'replace' &&
newCargo.split('.').length > currentValue.split('.').length) {
newCargo = newCargo
.split('.')
.slice(0, currentValue.split('.').length)
.join('.');
}
// Try to reverse any caret we added
if (newCargo.startsWith('^') && !currentValue.startsWith('^')) {
const withoutCaret = newCargo.substring(1);
// NOTE: We want the number of components in the new version to match the original.
// e.g. "5.0" should be updated to "6.0".
const components = currentValue.split('.').length;
newCargo = withoutCaret.split('.').slice(0, components).join('.');
}
return newCargo;
}
function isBreaking(current, version) {
// The change may be breaking if either version is unstable
if (!(0, semver_stable_1.is)(version) || !(0, semver_stable_1.is)(current)) {
return true;
}
const currentMajor = (0, semver_1.major)(current);
if (currentMajor === 0) {
if ((0, semver_1.minor)(current) === 0) {
// This can only be non-breaking if they're the same version
return current !== version;
}
// v0.x updates are breaking if x changes
return (0, semver_1.minor)(current) !== (0, semver_1.minor)(version);
}
// Otherwise, only major updates are breaking
return currentMajor !== (0, semver_1.major)(version);
}
exports.api = {
...npm_1.api,
getNewValue,
isBreaking,
isLessThanRange,
isSingleVersion,
isValid: exports.isValid,
matches,
getSatisfyingVersion,
minSatisfyingVersion,
};
exports.default = exports.api;
//# sourceMappingURL=index.js.map