UNPKG

renovate

Version:

Automated dependency updates. Flexible so you don't need to be.

100 lines 4.35 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.MSBUILD_CENTRAL_FILE = exports.NUGET_CENTRAL_FILE = void 0; exports.getDependentPackageFiles = getDependentPackageFiles; const tslib_1 = require("tslib"); const is_1 = tslib_1.__importDefault(require("@sindresorhus/is")); const graph_data_structure_1 = require("graph-data-structure"); const upath_1 = tslib_1.__importDefault(require("upath")); const logger_1 = require("../../../logger"); const minimatch_1 = require("../../../util/minimatch"); const scm_1 = require("../../platform/scm"); const util_1 = require("./util"); exports.NUGET_CENTRAL_FILE = 'Directory.Packages.props'; exports.MSBUILD_CENTRAL_FILE = 'Packages.props'; /** * Get all leaf package files of ancestry that depend on packageFileName. */ async function getDependentPackageFiles(packageFileName, isCentralManagement = false) { const packageFiles = await getAllPackageFiles(); const graph = new graph_data_structure_1.Graph(); if (isCentralManagement) { graph.addNode(packageFileName); } const parentDir = packageFileName === exports.NUGET_CENTRAL_FILE || packageFileName === exports.MSBUILD_CENTRAL_FILE ? '' : upath_1.default.dirname(packageFileName); for (const f of packageFiles) { graph.addNode(f); if (isCentralManagement && upath_1.default.dirname(f).startsWith(parentDir)) { graph.addEdge(packageFileName, f); } } for (const f of packageFiles) { const doc = await (0, util_1.readFileAsXmlDocument)(f); if (!doc) { continue; } const projectReferenceAttributes = doc .childrenNamed('ItemGroup') .map((ig) => ig.childrenNamed('ProjectReference')) .flat() .map((pf) => pf.attr.Include) .filter(is_1.default.nonEmptyString); const projectReferences = projectReferenceAttributes.map((a) => upath_1.default.normalize(a)); const normalizedRelativeProjectReferences = projectReferences.map((r) => reframeRelativePathToRootOfRepo(f, r)); for (const ref of normalizedRelativeProjectReferences) { graph.addEdge(ref, f); } if ((0, graph_data_structure_1.hasCycle)(graph)) { throw new Error('Circular reference detected in NuGet package files'); } } const deps = new Map(); recursivelyGetDependentPackageFiles(packageFileName, graph, deps); if (isCentralManagement) { // remove props file, as we don't need it deps.delete(packageFileName); } // deduplicate return Array.from(deps).map(([name, isLeaf]) => ({ name, isLeaf })); } /** * Traverse graph and find dependent package files at any level of ancestry */ function recursivelyGetDependentPackageFiles(packageFileName, graph, deps) { if (deps.has(packageFileName)) { // we have already visited this package file return; } const dependents = graph.adjacent(packageFileName); if (!dependents || dependents.size === 0) { deps.set(packageFileName, true); return; } deps.set(packageFileName, false); for (const dep of dependents) { recursivelyGetDependentPackageFiles(dep, graph, deps); } } /** * Take the path relative from a project file, and make it relative from the root of the repo */ function reframeRelativePathToRootOfRepo(dependentProjectRelativePath, projectReference) { const virtualRepoRoot = '/'; const absoluteDependentProjectPath = upath_1.default.resolve(virtualRepoRoot, dependentProjectRelativePath); const absoluteProjectReferencePath = upath_1.default.resolve(upath_1.default.dirname(absoluteDependentProjectPath), projectReference); const relativeProjectReferencePath = upath_1.default.relative(virtualRepoRoot, absoluteProjectReferencePath); return relativeProjectReferencePath; } /** * Get a list of package files in localDir */ async function getAllPackageFiles() { const allFiles = await scm_1.scm.getFileList(); const filteredPackageFiles = allFiles.filter((0, minimatch_1.minimatchFilter)('*.{cs,vb,fs}proj', { matchBase: true, nocase: true })); logger_1.logger.trace({ filteredPackageFiles }, 'Found package files'); return filteredPackageFiles; } //# sourceMappingURL=package-tree.js.map