@nx/devkit 22.0.0-beta.4 → 22.0.0-beta.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nx/devkit",
3
- "version": "22.0.0-beta.4",
3
+ "version": "22.0.0-beta.6",
4
4
  "private": false,
5
5
  "description": "The Nx Devkit is used to customize Nx for different technologies and use cases. It contains many utility functions for reading and writing files, updating configuration, working with Abstract Syntax Trees(ASTs), and more. Learn more about [extending Nx by leveraging the Nx Devkit](https://nx.dev/extending-nx/intro/getting-started) on our docs.",
6
6
  "repository": {
@@ -28,6 +28,7 @@
28
28
  },
29
29
  "homepage": "https://nx.dev",
30
30
  "dependencies": {
31
+ "@zkochan/js-yaml": "0.0.7",
31
32
  "ejs": "^3.1.7",
32
33
  "tslib": "^2.3.0",
33
34
  "semver": "^7.5.3",
@@ -37,7 +38,7 @@
37
38
  },
38
39
  "devDependencies": {
39
40
  "jest": "^29.4.1",
40
- "nx": "22.0.0-beta.4"
41
+ "nx": "22.0.0-beta.6"
41
42
  },
42
43
  "peerDependencies": {
43
44
  "nx": ">= 21 <= 23"
package/public-api.d.ts CHANGED
@@ -39,7 +39,7 @@ export { readTargetOptions } from './src/executors/read-target-options';
39
39
  /**
40
40
  * @category Utils
41
41
  */
42
- export { addDependenciesToPackageJson, removeDependenciesFromPackageJson, ensurePackage, NX_VERSION, } from './src/utils/package-json';
42
+ export { addDependenciesToPackageJson, removeDependenciesFromPackageJson, ensurePackage, getDependencyVersionFromPackageJson, NX_VERSION, } from './src/utils/package-json';
43
43
  /**
44
44
  * @category Utils
45
45
  */
@@ -1 +1 @@
1
- {"version":3,"file":"public-api.d.ts","sourceRoot":"","sources":["../../../packages/devkit/public-api.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH;;GAEG;AACH,OAAO,EAAE,WAAW,EAAE,MAAM,+BAA+B,CAAC;AAE5D;;GAEG;AACH,OAAO,EACL,aAAa,EACb,iBAAiB,GAClB,MAAM,iCAAiC,CAAC;AAEzC;;GAEG;AACH,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AAE3D;;GAEG;AACH,OAAO,EAAE,mBAAmB,EAAE,MAAM,0CAA0C,CAAC;AAE/E;;GAEG;AACH,OAAO,EAAE,gBAAgB,EAAE,MAAM,sCAAsC,CAAC;AAExE;;GAEG;AACH,OAAO,EAAE,oBAAoB,EAAE,MAAM,0CAA0C,CAAC;AAEhF,OAAO,EACL,iBAAiB,EACjB,oBAAoB,GACrB,MAAM,qCAAqC,CAAC;AAE7C;;GAEG;AACH,OAAO,EAAE,iBAAiB,EAAE,MAAM,qCAAqC,CAAC;AAExE;;GAEG;AACH,OAAO,EACL,4BAA4B,EAC5B,iCAAiC,EACjC,aAAa,EACb,UAAU,GACX,MAAM,0BAA0B,CAAC;AAElC;;GAEG;AACH,OAAO,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AAExE;;GAEG;AACH,OAAO,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAE1C;;GAEG;AACH,OAAO,EACL,kBAAkB,EAClB,sBAAsB,GACvB,MAAM,kCAAkC,CAAC;AAE1C;;GAEG;AACH,YAAY,EACV,YAAY,EACZ,cAAc,EACd,eAAe,GAChB,MAAM,2BAA2B,CAAC;AAEnC;;GAEG;AACH,OAAO,EAAE,oBAAoB,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAE7E;;GAEG;AACH,OAAO,EAAE,cAAc,EAAE,MAAM,8BAA8B,CAAC;AAE9D;;GAEG;AACH,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAErE;;GAEG;AACH,OAAO,EAAE,iBAAiB,EAAE,MAAM,iCAAiC,CAAC;AAEpE;;GAEG;AACH,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAC"}
1
+ {"version":3,"file":"public-api.d.ts","sourceRoot":"","sources":["../../../packages/devkit/public-api.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH;;GAEG;AACH,OAAO,EAAE,WAAW,EAAE,MAAM,+BAA+B,CAAC;AAE5D;;GAEG;AACH,OAAO,EACL,aAAa,EACb,iBAAiB,GAClB,MAAM,iCAAiC,CAAC;AAEzC;;GAEG;AACH,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AAE3D;;GAEG;AACH,OAAO,EAAE,mBAAmB,EAAE,MAAM,0CAA0C,CAAC;AAE/E;;GAEG;AACH,OAAO,EAAE,gBAAgB,EAAE,MAAM,sCAAsC,CAAC;AAExE;;GAEG;AACH,OAAO,EAAE,oBAAoB,EAAE,MAAM,0CAA0C,CAAC;AAEhF,OAAO,EACL,iBAAiB,EACjB,oBAAoB,GACrB,MAAM,qCAAqC,CAAC;AAE7C;;GAEG;AACH,OAAO,EAAE,iBAAiB,EAAE,MAAM,qCAAqC,CAAC;AAExE;;GAEG;AACH,OAAO,EACL,4BAA4B,EAC5B,iCAAiC,EACjC,aAAa,EACb,mCAAmC,EACnC,UAAU,GACX,MAAM,0BAA0B,CAAC;AAElC;;GAEG;AACH,OAAO,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AAExE;;GAEG;AACH,OAAO,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAE1C;;GAEG;AACH,OAAO,EACL,kBAAkB,EAClB,sBAAsB,GACvB,MAAM,kCAAkC,CAAC;AAE1C;;GAEG;AACH,YAAY,EACV,YAAY,EACZ,cAAc,EACd,eAAe,GAChB,MAAM,2BAA2B,CAAC;AAEnC;;GAEG;AACH,OAAO,EAAE,oBAAoB,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAE7E;;GAEG;AACH,OAAO,EAAE,cAAc,EAAE,MAAM,8BAA8B,CAAC;AAE9D;;GAEG;AACH,OAAO,EAAE,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAErE;;GAEG;AACH,OAAO,EAAE,iBAAiB,EAAE,MAAM,iCAAiC,CAAC;AAEpE;;GAEG;AACH,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAC"}
package/public-api.js CHANGED
@@ -9,7 +9,7 @@
9
9
  * a. We might need to duplicate code instead of importing from nx until all supported versions of nx contain the file.
10
10
  */
11
11
  Object.defineProperty(exports, "__esModule", { value: true });
12
- exports.moveFilesToNewDirectory = exports.convertNxExecutor = exports.convertNxGenerator = exports.offsetFromRoot = exports.ChangeType = exports.applyChangesToString = exports.extractLayoutDirectory = exports.getWorkspaceLayout = exports.names = exports.installPackagesTask = exports.NX_VERSION = exports.ensurePackage = exports.removeDependenciesFromPackageJson = exports.addDependenciesToPackageJson = exports.readTargetOptions = exports.targetToTargetString = exports.parseTargetString = exports.visitNotIgnoredFiles = exports.runTasksInSerial = exports.updateTsConfigsToJs = exports.toJS = exports.OverwriteStrategy = exports.generateFiles = exports.formatFiles = void 0;
12
+ exports.moveFilesToNewDirectory = exports.convertNxExecutor = exports.convertNxGenerator = exports.offsetFromRoot = exports.ChangeType = exports.applyChangesToString = exports.extractLayoutDirectory = exports.getWorkspaceLayout = exports.names = exports.installPackagesTask = exports.NX_VERSION = exports.getDependencyVersionFromPackageJson = exports.ensurePackage = exports.removeDependenciesFromPackageJson = exports.addDependenciesToPackageJson = exports.readTargetOptions = exports.targetToTargetString = exports.parseTargetString = exports.visitNotIgnoredFiles = exports.runTasksInSerial = exports.updateTsConfigsToJs = exports.toJS = exports.OverwriteStrategy = exports.generateFiles = exports.formatFiles = void 0;
13
13
  /**
14
14
  * @category Generators
15
15
  */
@@ -56,6 +56,7 @@ var package_json_1 = require("./src/utils/package-json");
56
56
  Object.defineProperty(exports, "addDependenciesToPackageJson", { enumerable: true, get: function () { return package_json_1.addDependenciesToPackageJson; } });
57
57
  Object.defineProperty(exports, "removeDependenciesFromPackageJson", { enumerable: true, get: function () { return package_json_1.removeDependenciesFromPackageJson; } });
58
58
  Object.defineProperty(exports, "ensurePackage", { enumerable: true, get: function () { return package_json_1.ensurePackage; } });
59
+ Object.defineProperty(exports, "getDependencyVersionFromPackageJson", { enumerable: true, get: function () { return package_json_1.getDependencyVersionFromPackageJson; } });
59
60
  Object.defineProperty(exports, "NX_VERSION", { enumerable: true, get: function () { return package_json_1.NX_VERSION; } });
60
61
  /**
61
62
  * @category Utils
@@ -0,0 +1,10 @@
1
+ import { type Tree } from 'nx/src/devkit-exports';
2
+ import { getCatalogManager } from './manager-factory';
3
+ import type { CatalogManager } from './manager';
4
+ export { getCatalogManager };
5
+ /**
6
+ * Detects which packages in a package.json use catalog references
7
+ * Returns Map of package name -> catalog name (undefined for default catalog)
8
+ */
9
+ export declare function getCatalogDependenciesFromPackageJson(tree: Tree, packageJsonPath: string, manager: CatalogManager): Map<string, string | undefined>;
10
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../../packages/devkit/src/utils/catalog/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAY,KAAK,IAAI,EAAE,MAAM,uBAAuB,CAAC;AAC5D,OAAO,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AACtD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAEhD,OAAO,EAAE,iBAAiB,EAAE,CAAC;AAE7B;;;GAGG;AACH,wBAAgB,qCAAqC,CACnD,IAAI,EAAE,IAAI,EACV,eAAe,EAAE,MAAM,EACvB,OAAO,EAAE,cAAc,GACtB,GAAG,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CA+BjC"}
@@ -0,0 +1,38 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getCatalogManager = void 0;
4
+ exports.getCatalogDependenciesFromPackageJson = getCatalogDependenciesFromPackageJson;
5
+ const devkit_exports_1 = require("nx/src/devkit-exports");
6
+ const manager_factory_1 = require("./manager-factory");
7
+ Object.defineProperty(exports, "getCatalogManager", { enumerable: true, get: function () { return manager_factory_1.getCatalogManager; } });
8
+ /**
9
+ * Detects which packages in a package.json use catalog references
10
+ * Returns Map of package name -> catalog name (undefined for default catalog)
11
+ */
12
+ function getCatalogDependenciesFromPackageJson(tree, packageJsonPath, manager) {
13
+ const catalogDeps = new Map();
14
+ if (!tree.exists(packageJsonPath)) {
15
+ return catalogDeps;
16
+ }
17
+ try {
18
+ const packageJson = (0, devkit_exports_1.readJson)(tree, packageJsonPath);
19
+ const allDependencies = {
20
+ ...packageJson.dependencies,
21
+ ...packageJson.devDependencies,
22
+ ...packageJson.peerDependencies,
23
+ ...packageJson.optionalDependencies,
24
+ };
25
+ for (const [packageName, version] of Object.entries(allDependencies || {})) {
26
+ if (manager.isCatalogReference(version)) {
27
+ const catalogRef = manager.parseCatalogReference(version);
28
+ if (catalogRef) {
29
+ catalogDeps.set(packageName, catalogRef.catalogName);
30
+ }
31
+ }
32
+ }
33
+ }
34
+ catch (error) {
35
+ // If we can't read the package.json, return empty map
36
+ }
37
+ return catalogDeps;
38
+ }
@@ -0,0 +1,6 @@
1
+ import type { CatalogManager } from './manager';
2
+ /**
3
+ * Factory function to get the appropriate catalog manager based on the package manager
4
+ */
5
+ export declare function getCatalogManager(workspaceRoot: string): CatalogManager | null;
6
+ //# sourceMappingURL=manager-factory.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"manager-factory.d.ts","sourceRoot":"","sources":["../../../../../../packages/devkit/src/utils/catalog/manager-factory.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAGhD;;GAEG;AACH,wBAAgB,iBAAiB,CAC/B,aAAa,EAAE,MAAM,GACpB,cAAc,GAAG,IAAI,CASvB"}
@@ -0,0 +1,17 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getCatalogManager = getCatalogManager;
4
+ const devkit_exports_1 = require("nx/src/devkit-exports");
5
+ const pnpm_manager_1 = require("./pnpm-manager");
6
+ /**
7
+ * Factory function to get the appropriate catalog manager based on the package manager
8
+ */
9
+ function getCatalogManager(workspaceRoot) {
10
+ const packageManager = (0, devkit_exports_1.detectPackageManager)(workspaceRoot);
11
+ switch (packageManager) {
12
+ case 'pnpm':
13
+ return new pnpm_manager_1.PnpmCatalogManager();
14
+ default:
15
+ return null;
16
+ }
17
+ }
@@ -0,0 +1,40 @@
1
+ import type { Tree } from 'nx/src/devkit-exports';
2
+ import type { PnpmWorkspaceYaml } from 'nx/src/utils/pnpm-workspace';
3
+ import type { CatalogReference } from './types';
4
+ /**
5
+ * Interface for catalog managers that handle package manager-specific catalog implementations.
6
+ */
7
+ export interface CatalogManager {
8
+ readonly name: string;
9
+ isCatalogReference(version: string): boolean;
10
+ parseCatalogReference(version: string): CatalogReference | null;
11
+ /**
12
+ * Get catalog definitions from the workspace.
13
+ */
14
+ getCatalogDefinitions(workspaceRoot: string): PnpmWorkspaceYaml | null;
15
+ getCatalogDefinitions(tree: Tree): PnpmWorkspaceYaml | null;
16
+ /**
17
+ * Resolve a catalog reference to an actual version.
18
+ */
19
+ resolveCatalogReference(workspaceRoot: string, packageName: string, version: string): string | null;
20
+ resolveCatalogReference(tree: Tree, packageName: string, version: string): string | null;
21
+ /**
22
+ * Check that a catalog reference is valid.
23
+ */
24
+ validateCatalogReference(workspaceRoot: string, packageName: string, version: string): void;
25
+ validateCatalogReference(tree: Tree, packageName: string, version: string): void;
26
+ /**
27
+ * Updates catalog definitions for specified packages in their respective catalogs.
28
+ */
29
+ updateCatalogVersions(tree: Tree, updates: Array<{
30
+ packageName: string;
31
+ version: string;
32
+ catalogName?: string;
33
+ }>): void;
34
+ updateCatalogVersions(workspaceRoot: string, updates: Array<{
35
+ packageName: string;
36
+ version: string;
37
+ catalogName?: string;
38
+ }>): void;
39
+ }
40
+ //# sourceMappingURL=manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"manager.d.ts","sourceRoot":"","sources":["../../../../../../packages/devkit/src/utils/catalog/manager.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,uBAAuB,CAAC;AAClD,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,6BAA6B,CAAC;AACrE,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAEhD;;GAEG;AACH,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAEtB,kBAAkB,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC;IAE7C,qBAAqB,CAAC,OAAO,EAAE,MAAM,GAAG,gBAAgB,GAAG,IAAI,CAAC;IAEhE;;OAEG;IACH,qBAAqB,CAAC,aAAa,EAAE,MAAM,GAAG,iBAAiB,GAAG,IAAI,CAAC;IACvE,qBAAqB,CAAC,IAAI,EAAE,IAAI,GAAG,iBAAiB,GAAG,IAAI,CAAC;IAE5D;;OAEG;IACH,uBAAuB,CACrB,aAAa,EAAE,MAAM,EACrB,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,MAAM,GAAG,IAAI,CAAC;IACjB,uBAAuB,CACrB,IAAI,EAAE,IAAI,EACV,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,MAAM,GAAG,IAAI,CAAC;IAEjB;;OAEG;IACH,wBAAwB,CACtB,aAAa,EAAE,MAAM,EACrB,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,IAAI,CAAC;IACR,wBAAwB,CACtB,IAAI,EAAE,IAAI,EACV,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,IAAI,CAAC;IAER;;OAEG;IACH,qBAAqB,CACnB,IAAI,EAAE,IAAI,EACV,OAAO,EAAE,KAAK,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,OAAO,EAAE,MAAM,CAAC;QAChB,WAAW,CAAC,EAAE,MAAM,CAAC;KACtB,CAAC,GACD,IAAI,CAAC;IACR,qBAAqB,CACnB,aAAa,EAAE,MAAM,EACrB,OAAO,EAAE,KAAK,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,OAAO,EAAE,MAAM,CAAC;QAChB,WAAW,CAAC,EAAE,MAAM,CAAC;KACtB,CAAC,GACD,IAAI,CAAC;CACT"}
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,22 @@
1
+ import { type Tree } from 'nx/src/devkit-exports';
2
+ import type { PnpmWorkspaceYaml } from 'nx/src/utils/pnpm-workspace';
3
+ import type { CatalogManager } from './manager';
4
+ import { type CatalogReference } from './types';
5
+ /**
6
+ * PNPM-specific catalog manager implementation
7
+ */
8
+ export declare class PnpmCatalogManager implements CatalogManager {
9
+ readonly name = "pnpm";
10
+ readonly catalogProtocol = "catalog:";
11
+ isCatalogReference(version: string): boolean;
12
+ parseCatalogReference(version: string): CatalogReference | null;
13
+ getCatalogDefinitions(treeOrRoot: Tree | string): PnpmWorkspaceYaml | null;
14
+ resolveCatalogReference(treeOrRoot: Tree | string, packageName: string, version: string): string | null;
15
+ validateCatalogReference(treeOrRoot: Tree | string, packageName: string, version: string): void;
16
+ updateCatalogVersions(treeOrRoot: Tree | string, updates: Array<{
17
+ packageName: string;
18
+ version: string;
19
+ catalogName?: string;
20
+ }>): void;
21
+ }
22
+ //# sourceMappingURL=pnpm-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pnpm-manager.d.ts","sourceRoot":"","sources":["../../../../../../packages/devkit/src/utils/catalog/pnpm-manager.ts"],"names":[],"mappings":"AAGA,OAAO,EAAU,KAAK,IAAI,EAAE,MAAM,uBAAuB,CAAC;AAE1D,OAAO,KAAK,EAEV,iBAAiB,EAClB,MAAM,6BAA6B,CAAC;AACrC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAChD,OAAO,EAAE,KAAK,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAEhD;;GAEG;AACH,qBAAa,kBAAmB,YAAW,cAAc;IACvD,QAAQ,CAAC,IAAI,UAAU;IACvB,QAAQ,CAAC,eAAe,cAAc;IAEtC,kBAAkB,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO;IAI5C,qBAAqB,CAAC,OAAO,EAAE,MAAM,GAAG,gBAAgB,GAAG,IAAI;IAe/D,qBAAqB,CAAC,UAAU,EAAE,IAAI,GAAG,MAAM,GAAG,iBAAiB,GAAG,IAAI;IAe1E,uBAAuB,CACrB,UAAU,EAAE,IAAI,GAAG,MAAM,EACzB,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,MAAM,GAAG,IAAI;IAuBhB,wBAAwB,CACtB,UAAU,EAAE,IAAI,GAAG,MAAM,EACzB,WAAW,EAAE,MAAM,EACnB,OAAO,EAAE,MAAM,GACd,IAAI;IA0HP,qBAAqB,CACnB,UAAU,EAAE,IAAI,GAAG,MAAM,EACzB,OAAO,EAAE,KAAK,CAAC;QACb,WAAW,EAAE,MAAM,CAAC;QACpB,OAAO,EAAE,MAAM,CAAC;QAChB,WAAW,CAAC,EAAE,MAAM,CAAC;KACtB,CAAC,GACD,IAAI;CAgFR"}
@@ -0,0 +1,257 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.PnpmCatalogManager = void 0;
4
+ const js_yaml_1 = require("@zkochan/js-yaml");
5
+ const node_fs_1 = require("node:fs");
6
+ const node_path_1 = require("node:path");
7
+ const devkit_exports_1 = require("nx/src/devkit-exports");
8
+ const devkit_internals_1 = require("nx/src/devkit-internals");
9
+ /**
10
+ * PNPM-specific catalog manager implementation
11
+ */
12
+ class PnpmCatalogManager {
13
+ constructor() {
14
+ this.name = 'pnpm';
15
+ this.catalogProtocol = 'catalog:';
16
+ }
17
+ isCatalogReference(version) {
18
+ return version.startsWith(this.catalogProtocol);
19
+ }
20
+ parseCatalogReference(version) {
21
+ if (!this.isCatalogReference(version)) {
22
+ return null;
23
+ }
24
+ const catalogName = version.substring(this.catalogProtocol.length);
25
+ // Normalize both "catalog:" and "catalog:default" to the same representation
26
+ const isDefault = !catalogName || catalogName === 'default';
27
+ return {
28
+ catalogName: isDefault ? undefined : catalogName,
29
+ isDefaultCatalog: isDefault,
30
+ };
31
+ }
32
+ getCatalogDefinitions(treeOrRoot) {
33
+ if (typeof treeOrRoot === 'string') {
34
+ const pnpmWorkspacePath = (0, node_path_1.join)(treeOrRoot, 'pnpm-workspace.yaml');
35
+ if (!(0, node_fs_1.existsSync)(pnpmWorkspacePath)) {
36
+ return null;
37
+ }
38
+ return readYamlFileFromFs(pnpmWorkspacePath);
39
+ }
40
+ else {
41
+ if (!treeOrRoot.exists('pnpm-workspace.yaml')) {
42
+ return null;
43
+ }
44
+ return readYamlFileFromTree(treeOrRoot, 'pnpm-workspace.yaml');
45
+ }
46
+ }
47
+ resolveCatalogReference(treeOrRoot, packageName, version) {
48
+ const catalogRef = this.parseCatalogReference(version);
49
+ if (!catalogRef) {
50
+ return null;
51
+ }
52
+ const workspaceConfig = this.getCatalogDefinitions(treeOrRoot);
53
+ if (!workspaceConfig) {
54
+ return null;
55
+ }
56
+ let catalogToUse;
57
+ if (catalogRef.isDefaultCatalog) {
58
+ // Check both locations for default catalog
59
+ catalogToUse =
60
+ workspaceConfig.catalog ?? workspaceConfig.catalogs?.default;
61
+ }
62
+ else if (catalogRef.catalogName) {
63
+ catalogToUse = workspaceConfig.catalogs?.[catalogRef.catalogName];
64
+ }
65
+ return catalogToUse?.[packageName] || null;
66
+ }
67
+ validateCatalogReference(treeOrRoot, packageName, version) {
68
+ const catalogRef = this.parseCatalogReference(version);
69
+ if (!catalogRef) {
70
+ throw new Error(`Invalid catalog reference syntax: "${version}". Expected format: "catalog:" or "catalog:name"`);
71
+ }
72
+ const workspaceConfig = this.getCatalogDefinitions(treeOrRoot);
73
+ if (!workspaceConfig) {
74
+ throw new Error(formatCatalogError('Cannot get Pnpm Catalog definitions. No pnpm-workspace.yaml found in workspace root.', ['Create a pnpm-workspace.yaml file in your workspace root']));
75
+ }
76
+ let catalogToUse;
77
+ if (catalogRef.isDefaultCatalog) {
78
+ const hasCatalog = !!workspaceConfig.catalog;
79
+ const hasCatalogsDefault = !!workspaceConfig.catalogs?.default;
80
+ // Error if both defined (matches pnpm behavior)
81
+ if (hasCatalog && hasCatalogsDefault) {
82
+ throw new Error("The 'default' catalog was defined multiple times. Use the 'catalog' field or 'catalogs.default', but not both.");
83
+ }
84
+ catalogToUse =
85
+ workspaceConfig.catalog ?? workspaceConfig.catalogs?.default;
86
+ if (!catalogToUse) {
87
+ const availableCatalogs = Object.keys(workspaceConfig.catalogs || {});
88
+ const suggestions = [
89
+ 'Define a default catalog in pnpm-workspace.yaml under the "catalog" key',
90
+ ];
91
+ if (availableCatalogs.length > 0) {
92
+ suggestions.push(`Or select from the available named catalogs: ${availableCatalogs
93
+ .map((c) => `"catalog:${c}"`)
94
+ .join(', ')}`);
95
+ }
96
+ throw new Error(formatCatalogError('No default catalog defined in pnpm-workspace.yaml', suggestions));
97
+ }
98
+ }
99
+ else if (catalogRef.catalogName) {
100
+ catalogToUse = workspaceConfig.catalogs?.[catalogRef.catalogName];
101
+ if (!catalogToUse) {
102
+ const availableCatalogs = Object.keys(workspaceConfig.catalogs || {}).filter((c) => c !== 'default');
103
+ const defaultCatalog = !!workspaceConfig.catalog
104
+ ? 'catalog'
105
+ : !workspaceConfig.catalogs?.default
106
+ ? 'catalogs.default'
107
+ : null;
108
+ const suggestions = [
109
+ 'Define the catalog in pnpm-workspace.yaml under the "catalogs" key',
110
+ ];
111
+ if (availableCatalogs.length > 0) {
112
+ suggestions.push(`Or select from the available named catalogs: ${availableCatalogs
113
+ .map((c) => `"catalog:${c}"`)
114
+ .join(', ')}`);
115
+ }
116
+ if (defaultCatalog) {
117
+ suggestions.push(`Or use the default catalog ("${defaultCatalog}")`);
118
+ }
119
+ throw new Error(formatCatalogError(`Catalog "${catalogRef.catalogName}" not found in pnpm-workspace.yaml`, suggestions));
120
+ }
121
+ }
122
+ if (!catalogToUse[packageName]) {
123
+ let catalogName;
124
+ if (catalogRef.isDefaultCatalog) {
125
+ // Context-aware messaging based on which location exists
126
+ const hasCatalog = !!workspaceConfig.catalog;
127
+ catalogName = hasCatalog
128
+ ? 'default catalog ("catalog")'
129
+ : 'default catalog ("catalogs.default")';
130
+ }
131
+ else {
132
+ catalogName = `catalog '${catalogRef.catalogName}'`;
133
+ }
134
+ const availablePackages = Object.keys(catalogToUse);
135
+ const suggestions = [
136
+ `Add "${packageName}" to ${catalogName} in pnpm-workspace.yaml`,
137
+ ];
138
+ if (availablePackages.length > 0) {
139
+ suggestions.push(`Or select from the available packages in ${catalogName}: ${availablePackages
140
+ .map((p) => `"${p}"`)
141
+ .join(', ')}`);
142
+ }
143
+ throw new Error(formatCatalogError(`Package "${packageName}" not found in ${catalogName}`, suggestions));
144
+ }
145
+ }
146
+ updateCatalogVersions(treeOrRoot, updates) {
147
+ let checkExists;
148
+ let readYaml;
149
+ let writeYaml;
150
+ if (typeof treeOrRoot === 'string') {
151
+ const workspaceYamlPath = (0, node_path_1.join)(treeOrRoot, 'pnpm-workspace.yaml');
152
+ checkExists = () => (0, node_fs_1.existsSync)(workspaceYamlPath);
153
+ readYaml = () => (0, node_fs_1.readFileSync)(workspaceYamlPath, 'utf-8');
154
+ writeYaml = (content) => (0, node_fs_1.writeFileSync)(workspaceYamlPath, content, 'utf-8');
155
+ }
156
+ else {
157
+ checkExists = () => treeOrRoot.exists('pnpm-workspace.yaml');
158
+ readYaml = () => treeOrRoot.read('pnpm-workspace.yaml', 'utf-8');
159
+ writeYaml = (content) => treeOrRoot.write('pnpm-workspace.yaml', content);
160
+ }
161
+ if (!checkExists()) {
162
+ devkit_exports_1.output.warn({
163
+ title: 'No pnpm-workspace.yaml found',
164
+ bodyLines: [
165
+ 'Cannot update catalog versions without a pnpm-workspace.yaml file.',
166
+ 'Create a pnpm-workspace.yaml file to use catalogs.',
167
+ ],
168
+ });
169
+ return;
170
+ }
171
+ try {
172
+ const workspaceContent = readYaml();
173
+ const workspaceData = (0, js_yaml_1.load)(workspaceContent) || {};
174
+ let hasChanges = false;
175
+ for (const update of updates) {
176
+ const { packageName, version, catalogName } = update;
177
+ const normalizedCatalogName = catalogName === 'default' ? undefined : catalogName;
178
+ let targetCatalog;
179
+ if (!normalizedCatalogName) {
180
+ // Default catalog - update whichever exists, prefer catalog over catalogs.default
181
+ if (workspaceData.catalog) {
182
+ targetCatalog = workspaceData.catalog;
183
+ }
184
+ else if (workspaceData.catalogs?.default) {
185
+ targetCatalog = workspaceData.catalogs.default;
186
+ }
187
+ else {
188
+ // Neither exists, create catalog (shorthand syntax)
189
+ workspaceData.catalog ??= {};
190
+ targetCatalog = workspaceData.catalog;
191
+ }
192
+ }
193
+ else {
194
+ // Named catalog
195
+ workspaceData.catalogs ??= {};
196
+ workspaceData.catalogs[normalizedCatalogName] ??= {};
197
+ targetCatalog = workspaceData.catalogs[normalizedCatalogName];
198
+ }
199
+ if (targetCatalog[packageName] !== version) {
200
+ targetCatalog[packageName] = version;
201
+ hasChanges = true;
202
+ }
203
+ }
204
+ if (hasChanges) {
205
+ writeYaml((0, js_yaml_1.dump)(workspaceData, {
206
+ indent: 2,
207
+ quotingType: '"',
208
+ forceQuotes: true,
209
+ }));
210
+ }
211
+ }
212
+ catch (error) {
213
+ devkit_exports_1.output.error({
214
+ title: 'Failed to update catalog versions',
215
+ bodyLines: [error instanceof Error ? error.message : String(error)],
216
+ });
217
+ throw error;
218
+ }
219
+ }
220
+ }
221
+ exports.PnpmCatalogManager = PnpmCatalogManager;
222
+ function readYamlFileFromFs(path) {
223
+ try {
224
+ return (0, devkit_internals_1.readYamlFile)(path);
225
+ }
226
+ catch (error) {
227
+ devkit_exports_1.output.warn({
228
+ title: 'Unable to parse pnpm-workspace.yaml',
229
+ bodyLines: [error.toString()],
230
+ });
231
+ return null;
232
+ }
233
+ }
234
+ function readYamlFileFromTree(tree, path) {
235
+ const content = tree.read(path, 'utf-8');
236
+ const { load } = require('@zkochan/js-yaml');
237
+ try {
238
+ return load(content, { filename: path });
239
+ }
240
+ catch (error) {
241
+ devkit_exports_1.output.warn({
242
+ title: 'Unable to parse pnpm-workspace.yaml',
243
+ bodyLines: [error.toString()],
244
+ });
245
+ return null;
246
+ }
247
+ }
248
+ function formatCatalogError(error, suggestions) {
249
+ let message = error;
250
+ if (suggestions && suggestions.length > 0) {
251
+ message += '\n\nSuggestions:';
252
+ suggestions.forEach((suggestion) => {
253
+ message += `\n • ${suggestion}`;
254
+ });
255
+ }
256
+ return message;
257
+ }
@@ -0,0 +1,5 @@
1
+ export interface CatalogReference {
2
+ catalogName?: string;
3
+ isDefaultCatalog: boolean;
4
+ }
5
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../../../packages/devkit/src/utils/catalog/types.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,gBAAgB;IAC/B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,gBAAgB,EAAE,OAAO,CAAC;CAC3B"}
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -1,4 +1,82 @@
1
- import { GeneratorCallback, Tree } from 'nx/src/devkit-exports';
1
+ import { type GeneratorCallback, type Tree } from 'nx/src/devkit-exports';
2
+ import type { PackageJson, PackageJsonDependencySection } from 'nx/src/utils/package-json';
3
+ /**
4
+ * Get the resolved version of a dependency from package.json.
5
+ *
6
+ * Retrieves a package version and automatically resolves PNPM catalog references
7
+ * (e.g., "catalog:default") to their actual version strings. By default, searches
8
+ * `dependencies` first, then falls back to `devDependencies`.
9
+ *
10
+ * **Tree-based usage** (generators and migrations):
11
+ * Use when you have a `Tree` object, which is typical in Nx generators and migrations.
12
+ *
13
+ * **Filesystem-based usage** (CLI commands and scripts):
14
+ * Use when reading directly from the filesystem without a `Tree` object.
15
+ *
16
+ * @example
17
+ * ```typescript
18
+ * // Tree-based - from root package.json (checks dependencies then devDependencies)
19
+ * const reactVersion = getDependencyVersionFromPackageJson(tree, 'react');
20
+ * // Returns: "^18.0.0" (resolves "catalog:default" if present)
21
+ *
22
+ * // Tree-based - check only dependencies section
23
+ * const version = getDependencyVersionFromPackageJson(
24
+ * tree,
25
+ * 'react',
26
+ * 'package.json',
27
+ * ['dependencies']
28
+ * );
29
+ *
30
+ * // Tree-based - check only devDependencies section
31
+ * const version = getDependencyVersionFromPackageJson(
32
+ * tree,
33
+ * 'jest',
34
+ * 'package.json',
35
+ * ['devDependencies']
36
+ * );
37
+ *
38
+ * // Tree-based - custom lookup order
39
+ * const version = getDependencyVersionFromPackageJson(
40
+ * tree,
41
+ * 'pkg',
42
+ * 'package.json',
43
+ * ['devDependencies', 'dependencies', 'peerDependencies']
44
+ * );
45
+ *
46
+ * // Tree-based - with pre-loaded package.json
47
+ * const packageJson = readJson(tree, 'package.json');
48
+ * const version = getDependencyVersionFromPackageJson(
49
+ * tree,
50
+ * 'react',
51
+ * packageJson,
52
+ * ['dependencies']
53
+ * );
54
+ * ```
55
+ *
56
+ * @example
57
+ * ```typescript
58
+ * // Filesystem-based - from current directory
59
+ * const reactVersion = getDependencyVersionFromPackageJson('react');
60
+ *
61
+ * // Filesystem-based - with workspace root
62
+ * const version = getDependencyVersionFromPackageJson('react', '/path/to/workspace');
63
+ *
64
+ * // Filesystem-based - with specific package.json and section
65
+ * const version = getDependencyVersionFromPackageJson(
66
+ * 'react',
67
+ * '/path/to/workspace',
68
+ * 'apps/my-app/package.json',
69
+ * ['dependencies']
70
+ * );
71
+ * ```
72
+ *
73
+ * @param dependencyLookup Array of dependency sections to check in order. Defaults to ['dependencies', 'devDependencies']
74
+ * @returns The resolved version string, or `null` if the package is not found in any of the specified sections
75
+ */
76
+ export declare function getDependencyVersionFromPackageJson(tree: Tree, packageName: string, packageJsonPath?: string, dependencyLookup?: PackageJsonDependencySection[]): string | null;
77
+ export declare function getDependencyVersionFromPackageJson(tree: Tree, packageName: string, packageJson?: PackageJson, dependencyLookup?: PackageJsonDependencySection[]): string | null;
78
+ export declare function getDependencyVersionFromPackageJson(packageName: string, workspaceRootPath?: string, packageJsonPath?: string, dependencyLookup?: PackageJsonDependencySection[]): string | null;
79
+ export declare function getDependencyVersionFromPackageJson(packageName: string, workspaceRootPath?: string, packageJson?: PackageJson, dependencyLookup?: PackageJsonDependencySection[]): string | null;
2
80
  /**
3
81
  * Add Dependencies and Dev Dependencies to package.json
4
82
  *
@@ -1 +1 @@
1
- {"version":3,"file":"package-json.d.ts","sourceRoot":"","sources":["../../../../../packages/devkit/src/utils/package-json.ts"],"names":[],"mappings":"AACA,OAAO,EACL,iBAAiB,EAEjB,IAAI,EAGL,MAAM,uBAAuB,CAAC;AAsG/B;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,4BAA4B,CAC1C,IAAI,EAAE,IAAI,EACV,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EACpC,eAAe,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EACvC,eAAe,GAAE,MAAuB,EACxC,oBAAoB,CAAC,EAAE,OAAO,GAC7B,iBAAiB,CAyFnB;AAgCD;;;;;;;;;;;;GAYG;AACH,wBAAgB,iCAAiC,CAC/C,IAAI,EAAE,IAAI,EACV,YAAY,EAAE,MAAM,EAAE,EACtB,eAAe,EAAE,MAAM,EAAE,EACzB,eAAe,GAAE,MAAuB,GACvC,iBAAiB,CA6BnB;AA8FD;;;;;GAKG;AAEH;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,IAAI,EACV,GAAG,EAAE,MAAM,EACX,eAAe,EAAE,MAAM,EACvB,OAAO,CAAC,EAAE;IAAE,GAAG,CAAC,EAAE,OAAO,CAAC;IAAC,cAAc,CAAC,EAAE,OAAO,CAAA;CAAE,GACpD,IAAI,CAAC;AAER;;;;;;;;;;;GAWG;AACH,wBAAgB,aAAa,CAAC,CAAC,SAAS,GAAG,GAAG,GAAG,EAC/C,GAAG,EAAE,MAAM,EACX,OAAO,EAAE,MAAM,GACd,CAAC,CAAC;AA4FL;;GAEG;AACH,eAAO,MAAM,UAAU,QAA0B,CAAC"}
1
+ {"version":3,"file":"package-json.d.ts","sourceRoot":"","sources":["../../../../../packages/devkit/src/utils/package-json.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,KAAK,iBAAiB,EAItB,KAAK,IAAI,EAGV,MAAM,uBAAuB,CAAC;AAE/B,OAAO,KAAK,EACV,WAAW,EACX,4BAA4B,EAC7B,MAAM,2BAA2B,CAAC;AAmBnC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwEG;AACH,wBAAgB,mCAAmC,CACjD,IAAI,EAAE,IAAI,EACV,WAAW,EAAE,MAAM,EACnB,eAAe,CAAC,EAAE,MAAM,EACxB,gBAAgB,CAAC,EAAE,4BAA4B,EAAE,GAChD,MAAM,GAAG,IAAI,CAAC;AACjB,wBAAgB,mCAAmC,CACjD,IAAI,EAAE,IAAI,EACV,WAAW,EAAE,MAAM,EACnB,WAAW,CAAC,EAAE,WAAW,EACzB,gBAAgB,CAAC,EAAE,4BAA4B,EAAE,GAChD,MAAM,GAAG,IAAI,CAAC;AACjB,wBAAgB,mCAAmC,CACjD,WAAW,EAAE,MAAM,EACnB,iBAAiB,CAAC,EAAE,MAAM,EAC1B,eAAe,CAAC,EAAE,MAAM,EACxB,gBAAgB,CAAC,EAAE,4BAA4B,EAAE,GAChD,MAAM,GAAG,IAAI,CAAC;AACjB,wBAAgB,mCAAmC,CACjD,WAAW,EAAE,MAAM,EACnB,iBAAiB,CAAC,EAAE,MAAM,EAC1B,WAAW,CAAC,EAAE,WAAW,EACzB,gBAAgB,CAAC,EAAE,4BAA4B,EAAE,GAChD,MAAM,GAAG,IAAI,CAAC;AAqPjB;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,4BAA4B,CAC1C,IAAI,EAAE,IAAI,EACV,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EACpC,eAAe,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EACvC,eAAe,GAAE,MAAuB,EACxC,oBAAoB,CAAC,EAAE,OAAO,GAC7B,iBAAiB,CAqGnB;AA8JD;;;;;;;;;;;;GAYG;AACH,wBAAgB,iCAAiC,CAC/C,IAAI,EAAE,IAAI,EACV,YAAY,EAAE,MAAM,EAAE,EACtB,eAAe,EAAE,MAAM,EAAE,EACzB,eAAe,GAAE,MAAuB,GACvC,iBAAiB,CA6BnB;AAwHD;;;;;GAKG;AAEH;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,IAAI,EACV,GAAG,EAAE,MAAM,EACX,eAAe,EAAE,MAAM,EACvB,OAAO,CAAC,EAAE;IAAE,GAAG,CAAC,EAAE,OAAO,CAAC;IAAC,cAAc,CAAC,EAAE,OAAO,CAAA;CAAE,GACpD,IAAI,CAAC;AAER;;;;;;;;;;;GAWG;AACH,wBAAgB,aAAa,CAAC,CAAC,SAAS,GAAG,GAAG,GAAG,EAC/C,GAAG,EAAE,MAAM,EACX,OAAO,EAAE,MAAM,GACd,CAAC,CAAC;AA4FL;;GAEG;AACH,eAAO,MAAM,UAAU,QAAyC,CAAC"}
@@ -1,15 +1,18 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.NX_VERSION = void 0;
4
+ exports.getDependencyVersionFromPackageJson = getDependencyVersionFromPackageJson;
4
5
  exports.addDependenciesToPackageJson = addDependenciesToPackageJson;
5
6
  exports.removeDependenciesFromPackageJson = removeDependenciesFromPackageJson;
6
7
  exports.ensurePackage = ensurePackage;
7
- const semver_1 = require("semver");
8
+ const fs_1 = require("fs");
9
+ const module_1 = require("module");
8
10
  const devkit_exports_1 = require("nx/src/devkit-exports");
9
11
  const devkit_internals_1 = require("nx/src/devkit-internals");
10
12
  const path_1 = require("path");
13
+ const semver_1 = require("semver");
11
14
  const install_packages_task_1 = require("../tasks/install-packages-task");
12
- const module_1 = require("module");
15
+ const catalog_1 = require("./catalog");
13
16
  const UNIDENTIFIED_VERSION = 'UNIDENTIFIED_VERSION';
14
17
  const NON_SEMVER_TAGS = {
15
18
  '*': 2,
@@ -19,6 +22,81 @@ const NON_SEMVER_TAGS = {
19
22
  previous: -1,
20
23
  legacy: -2,
21
24
  };
25
+ function getDependencyVersionFromPackageJson(treeOrPackageName, packageNameOrRoot, packageJsonPathOrObjectOrRoot, dependencyLookup) {
26
+ if (typeof treeOrPackageName !== 'string') {
27
+ return getDependencyVersionFromPackageJsonFromTree(treeOrPackageName, packageNameOrRoot, packageJsonPathOrObjectOrRoot, dependencyLookup);
28
+ }
29
+ else {
30
+ return getDependencyVersionFromPackageJsonFromFileSystem(treeOrPackageName, packageNameOrRoot, packageJsonPathOrObjectOrRoot, dependencyLookup);
31
+ }
32
+ }
33
+ /**
34
+ * Tree-based implementation for getDependencyVersionFromPackageJson
35
+ */
36
+ function getDependencyVersionFromPackageJsonFromTree(tree, packageName, packageJsonPathOrObject = 'package.json', dependencyLookup = [
37
+ 'dependencies',
38
+ 'devDependencies',
39
+ ]) {
40
+ let packageJson;
41
+ if (typeof packageJsonPathOrObject === 'object') {
42
+ packageJson = packageJsonPathOrObject;
43
+ }
44
+ else if (tree.exists(packageJsonPathOrObject)) {
45
+ packageJson = (0, devkit_exports_1.readJson)(tree, packageJsonPathOrObject);
46
+ }
47
+ else {
48
+ return null;
49
+ }
50
+ let version = null;
51
+ for (const section of dependencyLookup) {
52
+ const foundVersion = packageJson[section]?.[packageName];
53
+ if (foundVersion) {
54
+ version = foundVersion;
55
+ break;
56
+ }
57
+ }
58
+ // Resolve catalog reference if needed
59
+ const manager = (0, catalog_1.getCatalogManager)(tree.root);
60
+ if (version && manager?.isCatalogReference(version)) {
61
+ version = manager.resolveCatalogReference(tree, packageName, version);
62
+ }
63
+ return version;
64
+ }
65
+ /**
66
+ * Filesystem-based implementation for getDependencyVersionFromPackageJson
67
+ */
68
+ function getDependencyVersionFromPackageJsonFromFileSystem(packageName, root = devkit_exports_1.workspaceRoot, packageJsonPathOrObject = 'package.json', dependencyLookup = [
69
+ 'dependencies',
70
+ 'devDependencies',
71
+ ]) {
72
+ let packageJson;
73
+ if (typeof packageJsonPathOrObject === 'object') {
74
+ packageJson = packageJsonPathOrObject;
75
+ }
76
+ else {
77
+ const packageJsonPath = (0, path_1.resolve)(root, packageJsonPathOrObject);
78
+ if ((0, fs_1.existsSync)(packageJsonPath)) {
79
+ packageJson = (0, devkit_exports_1.readJsonFile)(packageJsonPath);
80
+ }
81
+ else {
82
+ return null;
83
+ }
84
+ }
85
+ let version = null;
86
+ for (const section of dependencyLookup) {
87
+ const foundVersion = packageJson[section]?.[packageName];
88
+ if (foundVersion) {
89
+ version = foundVersion;
90
+ break;
91
+ }
92
+ }
93
+ // Resolve catalog reference if needed
94
+ const manager = (0, catalog_1.getCatalogManager)(root);
95
+ if (version && manager?.isCatalogReference(version)) {
96
+ version = manager.resolveCatalogReference(packageName, version, root);
97
+ }
98
+ return version;
99
+ }
22
100
  function filterExistingDependencies(dependencies, existingAltDependencies) {
23
101
  if (!existingAltDependencies) {
24
102
  return dependencies;
@@ -27,17 +105,39 @@ function filterExistingDependencies(dependencies, existingAltDependencies) {
27
105
  .filter((d) => !existingAltDependencies[d])
28
106
  .reduce((acc, d) => ({ ...acc, [d]: dependencies[d] }), {});
29
107
  }
30
- function cleanSemver(version) {
108
+ function cleanSemver(tree, version, packageName) {
109
+ const manager = (0, catalog_1.getCatalogManager)(tree.root);
110
+ if (manager?.isCatalogReference(version)) {
111
+ const resolvedVersion = manager.resolveCatalogReference(tree, packageName, version);
112
+ if (!resolvedVersion) {
113
+ throw new Error(`Failed to resolve catalog reference '${version}' for package '${packageName}'`);
114
+ }
115
+ return (0, semver_1.clean)(resolvedVersion) ?? (0, semver_1.coerce)(resolvedVersion);
116
+ }
31
117
  return (0, semver_1.clean)(version) ?? (0, semver_1.coerce)(version);
32
118
  }
33
- function isIncomingVersionGreater(incomingVersion, existingVersion) {
119
+ function isIncomingVersionGreater(tree, incomingVersion, existingVersion, packageName) {
120
+ // the existing version might be a catalog reference, so we need to resolve
121
+ // it if that's the case
122
+ let resolvedExistingVersion = existingVersion;
123
+ const manager = (0, catalog_1.getCatalogManager)(tree.root);
124
+ if (manager?.isCatalogReference(existingVersion)) {
125
+ const resolved = manager.resolveCatalogReference(tree, packageName, existingVersion);
126
+ if (!resolved) {
127
+ // catalog is supported, but failed to resolve, we throw an error
128
+ throw new Error(`Failed to resolve catalog reference '${existingVersion}' for package '${packageName}'`);
129
+ }
130
+ resolvedExistingVersion = resolved;
131
+ }
34
132
  // if version is in the format of "latest", "next" or similar - keep it, otherwise try to parse it
35
133
  const incomingVersionCompareBy = incomingVersion in NON_SEMVER_TAGS
36
134
  ? incomingVersion
37
- : cleanSemver(incomingVersion)?.toString() ?? UNIDENTIFIED_VERSION;
38
- const existingVersionCompareBy = existingVersion in NON_SEMVER_TAGS
39
- ? existingVersion
40
- : cleanSemver(existingVersion)?.toString() ?? UNIDENTIFIED_VERSION;
135
+ : cleanSemver(tree, incomingVersion, packageName)?.toString() ??
136
+ UNIDENTIFIED_VERSION;
137
+ const existingVersionCompareBy = resolvedExistingVersion in NON_SEMVER_TAGS
138
+ ? resolvedExistingVersion
139
+ : cleanSemver(tree, resolvedExistingVersion, packageName)?.toString() ??
140
+ UNIDENTIFIED_VERSION;
41
141
  if (incomingVersionCompareBy in NON_SEMVER_TAGS &&
42
142
  existingVersionCompareBy in NON_SEMVER_TAGS) {
43
143
  return (NON_SEMVER_TAGS[incomingVersionCompareBy] >
@@ -47,9 +147,9 @@ function isIncomingVersionGreater(incomingVersion, existingVersion) {
47
147
  existingVersionCompareBy in NON_SEMVER_TAGS) {
48
148
  return true;
49
149
  }
50
- return (0, semver_1.gt)(cleanSemver(incomingVersion), cleanSemver(existingVersion));
150
+ return (0, semver_1.gt)(cleanSemver(tree, incomingVersion, packageName), cleanSemver(tree, resolvedExistingVersion, packageName));
51
151
  }
52
- function updateExistingAltDependenciesVersion(dependencies, existingAltDependencies) {
152
+ function updateExistingAltDependenciesVersion(tree, dependencies, existingAltDependencies, workspaceRootPath) {
53
153
  return Object.keys(existingAltDependencies || {})
54
154
  .filter((d) => {
55
155
  if (!dependencies[d]) {
@@ -57,11 +157,11 @@ function updateExistingAltDependenciesVersion(dependencies, existingAltDependenc
57
157
  }
58
158
  const incomingVersion = dependencies[d];
59
159
  const existingVersion = existingAltDependencies[d];
60
- return isIncomingVersionGreater(incomingVersion, existingVersion);
160
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, d);
61
161
  })
62
162
  .reduce((acc, d) => ({ ...acc, [d]: dependencies[d] }), {});
63
163
  }
64
- function updateExistingDependenciesVersion(dependencies, existingDependencies = {}) {
164
+ function updateExistingDependenciesVersion(tree, dependencies, existingDependencies = {}, workspaceRootPath) {
65
165
  return Object.keys(dependencies)
66
166
  .filter((d) => {
67
167
  if (!existingDependencies[d]) {
@@ -69,7 +169,7 @@ function updateExistingDependenciesVersion(dependencies, existingDependencies =
69
169
  }
70
170
  const incomingVersion = dependencies[d];
71
171
  const existingVersion = existingDependencies[d];
72
- return isIncomingVersionGreater(incomingVersion, existingVersion);
172
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, d);
73
173
  })
74
174
  .reduce((acc, d) => ({ ...acc, [d]: dependencies[d] }), {});
75
175
  }
@@ -101,48 +201,111 @@ function addDependenciesToPackageJson(tree, dependencies, devDependencies, packa
101
201
  // - dependencies of the same type that have greater version
102
202
  // - specified dependencies of the other type that have greater version and are already installed as current type
103
203
  filteredDependencies = {
104
- ...updateExistingDependenciesVersion(filteredDependencies, currentPackageJson.dependencies),
105
- ...updateExistingAltDependenciesVersion(devDependencies, currentPackageJson.dependencies),
204
+ ...updateExistingDependenciesVersion(tree, filteredDependencies, currentPackageJson.dependencies, tree.root),
205
+ ...updateExistingAltDependenciesVersion(tree, devDependencies, currentPackageJson.dependencies, tree.root),
106
206
  };
107
207
  filteredDevDependencies = {
108
- ...updateExistingDependenciesVersion(filteredDevDependencies, currentPackageJson.devDependencies),
109
- ...updateExistingAltDependenciesVersion(dependencies, currentPackageJson.devDependencies),
208
+ ...updateExistingDependenciesVersion(tree, filteredDevDependencies, currentPackageJson.devDependencies, tree.root),
209
+ ...updateExistingAltDependenciesVersion(tree, dependencies, currentPackageJson.devDependencies, tree.root),
110
210
  };
111
211
  if (keepExistingVersions) {
112
212
  filteredDependencies = removeExistingDependencies(filteredDependencies, currentPackageJson.dependencies);
113
213
  filteredDevDependencies = removeExistingDependencies(filteredDevDependencies, currentPackageJson.devDependencies);
114
214
  }
115
215
  else {
116
- filteredDependencies = removeLowerVersions(filteredDependencies, currentPackageJson.dependencies);
117
- filteredDevDependencies = removeLowerVersions(filteredDevDependencies, currentPackageJson.devDependencies);
216
+ filteredDependencies = removeLowerVersions(tree, filteredDependencies, currentPackageJson.dependencies, tree.root);
217
+ filteredDevDependencies = removeLowerVersions(tree, filteredDevDependencies, currentPackageJson.devDependencies, tree.root);
118
218
  }
119
- if (requiresAddingOfPackages(currentPackageJson, filteredDependencies, filteredDevDependencies)) {
120
- (0, devkit_exports_1.updateJson)(tree, packageJsonPath, (json) => {
121
- json.dependencies = {
122
- ...(json.dependencies || {}),
123
- ...filteredDependencies,
124
- };
125
- json.devDependencies = {
126
- ...(json.devDependencies || {}),
127
- ...filteredDevDependencies,
128
- };
129
- json.dependencies = sortObjectByKeys(json.dependencies);
130
- json.devDependencies = sortObjectByKeys(json.devDependencies);
131
- return json;
132
- });
219
+ if (requiresAddingOfPackages(tree, currentPackageJson, filteredDependencies, filteredDevDependencies, tree.root)) {
220
+ const { catalogUpdates, directDependencies, directDevDependencies } = splitDependenciesByCatalogType(tree, filteredDependencies, filteredDevDependencies, packageJsonPath);
221
+ writeCatalogDependencies(tree, catalogUpdates);
222
+ writeDirectDependencies(tree, packageJsonPath, directDependencies, directDevDependencies);
133
223
  return () => {
134
224
  (0, install_packages_task_1.installPackagesTask)(tree);
135
225
  };
136
226
  }
137
227
  return () => { };
138
228
  }
229
+ function splitDependenciesByCatalogType(tree, filteredDependencies, filteredDevDependencies, packageJsonPath) {
230
+ const allFilteredUpdates = {
231
+ ...filteredDependencies,
232
+ ...filteredDevDependencies,
233
+ };
234
+ const catalogUpdates = [];
235
+ let directDependencies = { ...filteredDependencies };
236
+ let directDevDependencies = { ...filteredDevDependencies };
237
+ const manager = (0, catalog_1.getCatalogManager)(tree.root);
238
+ if (!manager) {
239
+ return {
240
+ catalogUpdates: [],
241
+ directDependencies: filteredDependencies,
242
+ directDevDependencies: filteredDevDependencies,
243
+ };
244
+ }
245
+ const existingCatalogDeps = (0, catalog_1.getCatalogDependenciesFromPackageJson)(tree, packageJsonPath, manager);
246
+ if (!existingCatalogDeps.size) {
247
+ return {
248
+ catalogUpdates: [],
249
+ directDependencies: filteredDependencies,
250
+ directDevDependencies: filteredDevDependencies,
251
+ };
252
+ }
253
+ // Check filtered results for catalog references or existing catalog dependencies
254
+ for (const [packageName, version] of Object.entries(allFilteredUpdates)) {
255
+ if (!existingCatalogDeps.has(packageName)) {
256
+ continue;
257
+ }
258
+ let catalogName = existingCatalogDeps.get(packageName);
259
+ const catalogRef = catalogName ? `catalog:${catalogName}` : 'catalog:';
260
+ try {
261
+ manager.validateCatalogReference(tree, packageName, catalogRef);
262
+ catalogUpdates.push({ packageName, version, catalogName });
263
+ // Remove from direct updates since this will be handled via catalog
264
+ delete directDependencies[packageName];
265
+ delete directDevDependencies[packageName];
266
+ }
267
+ catch (error) {
268
+ devkit_exports_1.output.error({
269
+ title: 'Invalid catalog reference',
270
+ bodyLines: [
271
+ `Invalid catalog reference "${catalogRef}" for package "${packageName}".`,
272
+ error.message,
273
+ ],
274
+ });
275
+ throw new Error(`Could not update "${packageName}" to version "${version}". See above for more details.`);
276
+ }
277
+ }
278
+ return { catalogUpdates, directDependencies, directDevDependencies };
279
+ }
280
+ function writeCatalogDependencies(tree, catalogUpdates) {
281
+ if (!catalogUpdates.length) {
282
+ return;
283
+ }
284
+ const manager = (0, catalog_1.getCatalogManager)(tree.root);
285
+ manager.updateCatalogVersions(tree, catalogUpdates);
286
+ }
287
+ function writeDirectDependencies(tree, packageJsonPath, dependencies, devDependencies) {
288
+ (0, devkit_exports_1.updateJson)(tree, packageJsonPath, (json) => {
289
+ json.dependencies = {
290
+ ...(json.dependencies || {}),
291
+ ...dependencies,
292
+ };
293
+ json.devDependencies = {
294
+ ...(json.devDependencies || {}),
295
+ ...devDependencies,
296
+ };
297
+ json.dependencies = sortObjectByKeys(json.dependencies);
298
+ json.devDependencies = sortObjectByKeys(json.devDependencies);
299
+ return json;
300
+ });
301
+ }
139
302
  /**
140
303
  * @returns The the incoming dependencies that are higher than the existing verions
141
304
  **/
142
- function removeLowerVersions(incomingDeps, existingDeps) {
305
+ function removeLowerVersions(tree, incomingDeps, existingDeps, workspaceRootPath) {
143
306
  return Object.keys(incomingDeps).reduce((acc, d) => {
144
307
  if (!existingDeps?.[d] ||
145
- isIncomingVersionGreater(incomingDeps[d], existingDeps[d])) {
308
+ isIncomingVersionGreater(tree, incomingDeps[d], existingDeps[d], d)) {
146
309
  acc[d] = incomingDeps[d];
147
310
  }
148
311
  return acc;
@@ -209,7 +372,7 @@ function sortObjectByKeys(obj) {
209
372
  * Verifies whether the given packageJson dependencies require an update
210
373
  * given the deps & devDeps passed in
211
374
  */
212
- function requiresAddingOfPackages(packageJsonFile, deps, devDeps) {
375
+ function requiresAddingOfPackages(tree, packageJsonFile, deps, devDeps, workspaceRootPath) {
213
376
  let needsDepsUpdate = false;
214
377
  let needsDevDepsUpdate = false;
215
378
  packageJsonFile.dependencies = packageJsonFile.dependencies || {};
@@ -219,11 +382,11 @@ function requiresAddingOfPackages(packageJsonFile, deps, devDeps) {
219
382
  const incomingVersion = deps[entry];
220
383
  if (packageJsonFile.dependencies[entry]) {
221
384
  const existingVersion = packageJsonFile.dependencies[entry];
222
- return isIncomingVersionGreater(incomingVersion, existingVersion);
385
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, entry);
223
386
  }
224
387
  if (packageJsonFile.devDependencies[entry]) {
225
388
  const existingVersion = packageJsonFile.devDependencies[entry];
226
- return isIncomingVersionGreater(incomingVersion, existingVersion);
389
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, entry);
227
390
  }
228
391
  return true;
229
392
  });
@@ -233,11 +396,11 @@ function requiresAddingOfPackages(packageJsonFile, deps, devDeps) {
233
396
  const incomingVersion = devDeps[entry];
234
397
  if (packageJsonFile.devDependencies[entry]) {
235
398
  const existingVersion = packageJsonFile.devDependencies[entry];
236
- return isIncomingVersionGreater(incomingVersion, existingVersion);
399
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, entry);
237
400
  }
238
401
  if (packageJsonFile.dependencies[entry]) {
239
402
  const existingVersion = packageJsonFile.dependencies[entry];
240
- return isIncomingVersionGreater(incomingVersion, existingVersion);
403
+ return isIncomingVersionGreater(tree, incomingVersion, existingVersion, entry);
241
404
  }
242
405
  return true;
243
406
  });
@@ -331,10 +494,10 @@ function addToNodePath(dir) {
331
494
  // Update the env variable.
332
495
  process.env.NODE_PATH = paths.join(delimiter);
333
496
  }
334
- function getPackageVersion(pkg) {
497
+ function getInstalledPackageModuleVersion(pkg) {
335
498
  return require((0, path_1.join)(pkg, 'package.json')).version;
336
499
  }
337
500
  /**
338
501
  * @description The version of Nx used by the workspace. Returns null if no version is found.
339
502
  */
340
- exports.NX_VERSION = getPackageVersion('nx');
503
+ exports.NX_VERSION = getInstalledPackageModuleVersion('nx');
@@ -1,2 +1,4 @@
1
+ import { type Tree } from 'nx/src/devkit-exports';
1
2
  export declare function checkAndCleanWithSemver(pkgName: string, version: string): string;
3
+ export declare function checkAndCleanWithSemver(tree: Tree, pkgName: string, version: string): string;
2
4
  //# sourceMappingURL=semver.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"semver.d.ts","sourceRoot":"","sources":["../../../../../packages/devkit/src/utils/semver.ts"],"names":[],"mappings":"AAEA,wBAAgB,uBAAuB,CACrC,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,GACd,MAAM,CAkBR"}
1
+ {"version":3,"file":"semver.d.ts","sourceRoot":"","sources":["../../../../../packages/devkit/src/utils/semver.ts"],"names":[],"mappings":"AAAA,OAAO,EAAiB,KAAK,IAAI,EAAE,MAAM,uBAAuB,CAAC;AAIjE,wBAAgB,uBAAuB,CACrC,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,GACd,MAAM,CAAC;AACV,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,IAAI,EACV,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,GACd,MAAM,CAAC"}
@@ -1,17 +1,43 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.checkAndCleanWithSemver = checkAndCleanWithSemver;
4
+ const devkit_exports_1 = require("nx/src/devkit-exports");
4
5
  const semver_1 = require("semver");
5
- function checkAndCleanWithSemver(pkgName, version) {
6
- let newVersion = version;
6
+ const catalog_1 = require("./catalog");
7
+ function checkAndCleanWithSemver(treeOrPkgName, pkgNameOrVersion, version) {
8
+ const tree = typeof treeOrPkgName === 'string' ? undefined : treeOrPkgName;
9
+ const root = tree?.root ?? devkit_exports_1.workspaceRoot;
10
+ const pkgName = typeof treeOrPkgName === 'string' ? treeOrPkgName : pkgNameOrVersion;
11
+ let newVersion = typeof treeOrPkgName === 'string' ? pkgNameOrVersion : version;
12
+ const manager = (0, catalog_1.getCatalogManager)(root);
13
+ if (manager?.isCatalogReference(newVersion)) {
14
+ try {
15
+ if (tree) {
16
+ manager.validateCatalogReference(tree, pkgName, newVersion);
17
+ }
18
+ else {
19
+ manager.validateCatalogReference(root, pkgName, newVersion);
20
+ }
21
+ }
22
+ catch (error) {
23
+ throw new Error(`The catalog reference for ${pkgName} is invalid - (${newVersion})\n${error.message}`);
24
+ }
25
+ const resolvedVersion = tree
26
+ ? manager.resolveCatalogReference(tree, pkgName, newVersion)
27
+ : manager.resolveCatalogReference(root, pkgName, newVersion);
28
+ if (!resolvedVersion) {
29
+ throw new Error(`Could not resolve catalog reference for package ${pkgName}@${newVersion}.`);
30
+ }
31
+ newVersion = resolvedVersion;
32
+ }
7
33
  if ((0, semver_1.valid)(newVersion)) {
8
34
  return newVersion;
9
35
  }
10
- if (version.startsWith('~') || version.startsWith('^')) {
11
- newVersion = version.substring(1);
36
+ if (newVersion.startsWith('~') || newVersion.startsWith('^')) {
37
+ newVersion = newVersion.substring(1);
12
38
  }
13
39
  if (!(0, semver_1.valid)(newVersion)) {
14
- throw new Error(`The package.json lists a version of ${pkgName} that Nx is unable to validate - (${version})`);
40
+ throw new Error(`The package.json lists a version of ${pkgName} that Nx is unable to validate - (${newVersion})`);
15
41
  }
16
42
  return newVersion;
17
43
  }