@salesforce/ui-bundle-features 1.117.2
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/LICENSE.txt +82 -0
- package/README.md +153 -0
- package/dist/aggregate-features.d.ts +16 -0
- package/dist/aggregate-features.d.ts.map +1 -0
- package/dist/aggregate-features.js +43 -0
- package/dist/aggregate-features.js.map +1 -0
- package/dist/cli.d.ts +8 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +71 -0
- package/dist/cli.js.map +1 -0
- package/dist/conflict-detector.d.ts +31 -0
- package/dist/conflict-detector.d.ts.map +1 -0
- package/dist/conflict-detector.js +153 -0
- package/dist/conflict-detector.js.map +1 -0
- package/dist/dependency-resolver.d.ts +18 -0
- package/dist/dependency-resolver.d.ts.map +1 -0
- package/dist/dependency-resolver.js +96 -0
- package/dist/dependency-resolver.js.map +1 -0
- package/dist/describe-command.d.ts +10 -0
- package/dist/describe-command.d.ts.map +1 -0
- package/dist/describe-command.js +119 -0
- package/dist/describe-command.js.map +1 -0
- package/dist/feature-metadata.d.ts +30 -0
- package/dist/feature-metadata.d.ts.map +1 -0
- package/dist/feature-metadata.js +136 -0
- package/dist/feature-metadata.js.map +1 -0
- package/dist/feature-search.d.ts +16 -0
- package/dist/feature-search.d.ts.map +1 -0
- package/dist/feature-search.js +140 -0
- package/dist/feature-search.js.map +1 -0
- package/dist/features.json +137 -0
- package/dist/file-copier.d.ts +15 -0
- package/dist/file-copier.d.ts.map +1 -0
- package/dist/file-copier.js +105 -0
- package/dist/file-copier.js.map +1 -0
- package/dist/install-command.d.ts +15 -0
- package/dist/install-command.d.ts.map +1 -0
- package/dist/install-command.js +314 -0
- package/dist/install-command.js.map +1 -0
- package/dist/list-command.d.ts +13 -0
- package/dist/list-command.d.ts.map +1 -0
- package/dist/list-command.js +71 -0
- package/dist/list-command.js.map +1 -0
- package/dist/logger.d.ts +48 -0
- package/dist/logger.d.ts.map +1 -0
- package/dist/logger.js +82 -0
- package/dist/logger.js.map +1 -0
- package/dist/package-manager.d.ts +22 -0
- package/dist/package-manager.d.ts.map +1 -0
- package/dist/package-manager.js +172 -0
- package/dist/package-manager.js.map +1 -0
- package/dist/placeholder-resolver.d.ts +25 -0
- package/dist/placeholder-resolver.d.ts.map +1 -0
- package/dist/placeholder-resolver.js +78 -0
- package/dist/placeholder-resolver.js.map +1 -0
- package/dist/schema-loader.d.ts +17 -0
- package/dist/schema-loader.d.ts.map +1 -0
- package/dist/schema-loader.js +82 -0
- package/dist/schema-loader.js.map +1 -0
- package/dist/types.d.ts +174 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +7 -0
- package/dist/types.js.map +1 -0
- package/dist/utils.d.ts +30 -0
- package/dist/utils.d.ts.map +1 -0
- package/dist/utils.js +58 -0
- package/dist/utils.js.map +1 -0
- package/package.json +53 -0
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import { getAllFeatures, getFeatureNameFromPackage } from "./feature-metadata.js";
|
|
7
|
+
import { searchFeatures } from "./feature-search.js";
|
|
8
|
+
/**
|
|
9
|
+
* List all available features
|
|
10
|
+
*/
|
|
11
|
+
export function listFeatures(options) {
|
|
12
|
+
const allFeatures = getAllFeatures();
|
|
13
|
+
let features = Object.entries(allFeatures);
|
|
14
|
+
// Filter by search query if provided
|
|
15
|
+
if (options.search) {
|
|
16
|
+
const searchResults = searchFeatures(options.search);
|
|
17
|
+
const searchNames = new Set(searchResults.map((f) => getFeatureNameFromPackage(f.package)).filter(Boolean));
|
|
18
|
+
features = features.filter(([name]) => searchNames.has(name));
|
|
19
|
+
console.log(`\nSearch results for "${options.search}":\n`);
|
|
20
|
+
if (features.length === 0) {
|
|
21
|
+
console.log("No features found.");
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
// For search results, maintain the order from searchFeatures (sorted by relevance)
|
|
25
|
+
// Create a map of feature name to rank
|
|
26
|
+
const rankMap = new Map();
|
|
27
|
+
searchResults.forEach((f, index) => {
|
|
28
|
+
const name = getFeatureNameFromPackage(f.package);
|
|
29
|
+
if (name) {
|
|
30
|
+
rankMap.set(name, index);
|
|
31
|
+
}
|
|
32
|
+
});
|
|
33
|
+
// Sort by search relevance rank
|
|
34
|
+
features.sort((a, b) => {
|
|
35
|
+
const rankA = rankMap.get(a[0]) ?? 999;
|
|
36
|
+
const rankB = rankMap.get(b[0]) ?? 999;
|
|
37
|
+
return rankA - rankB;
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
else {
|
|
41
|
+
console.log("\nAvailable Features:\n");
|
|
42
|
+
if (features.length === 0) {
|
|
43
|
+
console.log("No features found.");
|
|
44
|
+
return;
|
|
45
|
+
}
|
|
46
|
+
// Sort by name alphabetically when not searching
|
|
47
|
+
features.sort((a, b) => a[1].name.localeCompare(b[1].name));
|
|
48
|
+
}
|
|
49
|
+
for (const [featureName, feature] of features) {
|
|
50
|
+
// Only show feature ID in parens if it differs from the name (ignoring case)
|
|
51
|
+
const displayName = feature.name.toLowerCase() === featureName.toLowerCase()
|
|
52
|
+
? feature.name
|
|
53
|
+
: `${feature.name} (${featureName})`;
|
|
54
|
+
console.log(`${displayName}`);
|
|
55
|
+
if (options.verbose) {
|
|
56
|
+
console.log(` ${feature.longDescription}`);
|
|
57
|
+
console.log(` Package: ${feature.package}`);
|
|
58
|
+
if (feature.featureDependencies && feature.featureDependencies.length > 0) {
|
|
59
|
+
console.log(` Dependencies: ${feature.featureDependencies.join(", ")}`);
|
|
60
|
+
}
|
|
61
|
+
console.log();
|
|
62
|
+
}
|
|
63
|
+
else {
|
|
64
|
+
console.log(` ${feature.shortDescription}`);
|
|
65
|
+
console.log();
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
console.log('Use "npx @salesforce/ui-bundle-features describe <feature>" for detailed information');
|
|
69
|
+
console.log('Use "npx @salesforce/ui-bundle-features install <feature>" to install a feature\n');
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=list-command.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"list-command.js","sourceRoot":"","sources":["../src/list-command.ts"],"names":[],"mappings":"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"}
|
package/dist/logger.d.ts
ADDED
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
export declare class Logger {
|
|
7
|
+
private verbose;
|
|
8
|
+
constructor(verbose?: boolean);
|
|
9
|
+
/**
|
|
10
|
+
* Log info message
|
|
11
|
+
*/
|
|
12
|
+
info(message: string, ...args: unknown[]): void;
|
|
13
|
+
/**
|
|
14
|
+
* Log warning message
|
|
15
|
+
*/
|
|
16
|
+
warn(message: string, ...args: unknown[]): void;
|
|
17
|
+
/**
|
|
18
|
+
* Log error message with optional stack trace in verbose mode
|
|
19
|
+
*/
|
|
20
|
+
error(message: string, error?: Error): void;
|
|
21
|
+
/**
|
|
22
|
+
* Log debug message (only in verbose mode)
|
|
23
|
+
*/
|
|
24
|
+
debug(message: string, ...args: unknown[]): void;
|
|
25
|
+
/**
|
|
26
|
+
* Log success message
|
|
27
|
+
*/
|
|
28
|
+
success(message: string, ...args: unknown[]): void;
|
|
29
|
+
/**
|
|
30
|
+
* Log a section header (e.g. ── Installing dependency: shadcn ──────)
|
|
31
|
+
* Prints two blank lines before the header for visual separation.
|
|
32
|
+
*/
|
|
33
|
+
section(title: string): void;
|
|
34
|
+
/**
|
|
35
|
+
* Log a section footer (e.g. ── Dependency installed: shadcn ──────)
|
|
36
|
+
* Prints one blank line before the footer.
|
|
37
|
+
*/
|
|
38
|
+
sectionEnd(title: string): void;
|
|
39
|
+
/**
|
|
40
|
+
* Log a plain indented message (no prefix) for use inside sections.
|
|
41
|
+
*/
|
|
42
|
+
plain(message: string): void;
|
|
43
|
+
/**
|
|
44
|
+
* Print a blank line.
|
|
45
|
+
*/
|
|
46
|
+
blank(): void;
|
|
47
|
+
}
|
|
48
|
+
//# sourceMappingURL=logger.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,qBAAa,MAAM;IAClB,OAAO,CAAC,OAAO,CAAU;gBAEb,OAAO,UAAQ;IAI3B;;OAEG;IACH,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAI/C;;OAEG;IACH,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAI/C;;OAEG;IACH,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,KAAK,GAAG,IAAI;IAO3C;;OAEG;IACH,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAMhD;;OAEG;IACH,OAAO,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,IAAI;IAIlD;;;OAGG;IACH,OAAO,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAS5B;;;OAGG;IACH,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAQ/B;;OAEG;IACH,KAAK,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI;IAI5B;;OAEG;IACH,KAAK,IAAI,IAAI;CAGb"}
|
package/dist/logger.js
ADDED
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
export class Logger {
|
|
7
|
+
verbose;
|
|
8
|
+
constructor(verbose = false) {
|
|
9
|
+
this.verbose = verbose;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Log info message
|
|
13
|
+
*/
|
|
14
|
+
info(message, ...args) {
|
|
15
|
+
console.log(`[INFO] ${message}`, ...args);
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Log warning message
|
|
19
|
+
*/
|
|
20
|
+
warn(message, ...args) {
|
|
21
|
+
console.warn(`[WARN] ${message}`, ...args);
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Log error message with optional stack trace in verbose mode
|
|
25
|
+
*/
|
|
26
|
+
error(message, error) {
|
|
27
|
+
console.error(`[ERROR] ${message}`);
|
|
28
|
+
if (error && this.verbose && error.stack) {
|
|
29
|
+
console.error(error.stack);
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Log debug message (only in verbose mode)
|
|
34
|
+
*/
|
|
35
|
+
debug(message, ...args) {
|
|
36
|
+
if (this.verbose) {
|
|
37
|
+
console.log(`[DEBUG] ${message}`, ...args);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Log success message
|
|
42
|
+
*/
|
|
43
|
+
success(message, ...args) {
|
|
44
|
+
console.log(`[SUCCESS] ${message}`, ...args);
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Log a section header (e.g. ── Installing dependency: shadcn ──────)
|
|
48
|
+
* Prints two blank lines before the header for visual separation.
|
|
49
|
+
*/
|
|
50
|
+
section(title) {
|
|
51
|
+
const prefix = `── ${title} `;
|
|
52
|
+
const remaining = Math.max(3, 56 - prefix.length);
|
|
53
|
+
const line = "─".repeat(remaining);
|
|
54
|
+
console.log();
|
|
55
|
+
console.log();
|
|
56
|
+
console.log(`${prefix}${line}`);
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Log a section footer (e.g. ── Dependency installed: shadcn ──────)
|
|
60
|
+
* Prints one blank line before the footer.
|
|
61
|
+
*/
|
|
62
|
+
sectionEnd(title) {
|
|
63
|
+
const prefix = `── ${title} `;
|
|
64
|
+
const remaining = Math.max(3, 56 - prefix.length);
|
|
65
|
+
const line = "─".repeat(remaining);
|
|
66
|
+
console.log();
|
|
67
|
+
console.log(`${prefix}${line}`);
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Log a plain indented message (no prefix) for use inside sections.
|
|
71
|
+
*/
|
|
72
|
+
plain(message) {
|
|
73
|
+
console.log(` ${message}`);
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Print a blank line.
|
|
77
|
+
*/
|
|
78
|
+
blank() {
|
|
79
|
+
console.log();
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=logger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"logger.js","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,MAAM,OAAO,MAAM;IACV,OAAO,CAAU;IAEzB,YAAY,OAAO,GAAG,KAAK;QAC1B,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;IACxB,CAAC;IAED;;OAEG;IACH,IAAI,CAAC,OAAe,EAAE,GAAG,IAAe;QACvC,OAAO,CAAC,GAAG,CAAC,UAAU,OAAO,EAAE,EAAE,GAAG,IAAI,CAAC,CAAC;IAC3C,CAAC;IAED;;OAEG;IACH,IAAI,CAAC,OAAe,EAAE,GAAG,IAAe;QACvC,OAAO,CAAC,IAAI,CAAC,UAAU,OAAO,EAAE,EAAE,GAAG,IAAI,CAAC,CAAC;IAC5C,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,OAAe,EAAE,KAAa;QACnC,OAAO,CAAC,KAAK,CAAC,WAAW,OAAO,EAAE,CAAC,CAAC;QACpC,IAAI,KAAK,IAAI,IAAI,CAAC,OAAO,IAAI,KAAK,CAAC,KAAK,EAAE,CAAC;YAC1C,OAAO,CAAC,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;QAC5B,CAAC;IACF,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,OAAe,EAAE,GAAG,IAAe;QACxC,IAAI,IAAI,CAAC,OAAO,EAAE,CAAC;YAClB,OAAO,CAAC,GAAG,CAAC,WAAW,OAAO,EAAE,EAAE,GAAG,IAAI,CAAC,CAAC;QAC5C,CAAC;IACF,CAAC;IAED;;OAEG;IACH,OAAO,CAAC,OAAe,EAAE,GAAG,IAAe;QAC1C,OAAO,CAAC,GAAG,CAAC,aAAa,OAAO,EAAE,EAAE,GAAG,IAAI,CAAC,CAAC;IAC9C,CAAC;IAED;;;OAGG;IACH,OAAO,CAAC,KAAa;QACpB,MAAM,MAAM,GAAG,MAAM,KAAK,GAAG,CAAC;QAC9B,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;QAClD,MAAM,IAAI,GAAG,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QACnC,OAAO,CAAC,GAAG,EAAE,CAAC;QACd,OAAO,CAAC,GAAG,EAAE,CAAC;QACd,OAAO,CAAC,GAAG,CAAC,GAAG,MAAM,GAAG,IAAI,EAAE,CAAC,CAAC;IACjC,CAAC;IAED;;;OAGG;IACH,UAAU,CAAC,KAAa;QACvB,MAAM,MAAM,GAAG,MAAM,KAAK,GAAG,CAAC;QAC9B,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;QAClD,MAAM,IAAI,GAAG,GAAG,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QACnC,OAAO,CAAC,GAAG,EAAE,CAAC;QACd,OAAO,CAAC,GAAG,CAAC,GAAG,MAAM,GAAG,IAAI,EAAE,CAAC,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,OAAe;QACpB,OAAO,CAAC,GAAG,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC;IAC7B,CAAC;IAED;;OAEG;IACH,KAAK;QACJ,OAAO,CAAC,GAAG,EAAE,CAAC;IACf,CAAC;CACD"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import type { FileCopySchema, InstallationContext } from "./types.js";
|
|
7
|
+
/**
|
|
8
|
+
* Install a single npm package and ensure it's saved to package.json.
|
|
9
|
+
* npm output is suppressed by default; shown on verbose or error.
|
|
10
|
+
*/
|
|
11
|
+
export declare function installPackage(packageName: string, isDev: boolean, uiBundleDir: string, dryRun?: boolean, verbose?: boolean): Promise<void>;
|
|
12
|
+
/**
|
|
13
|
+
* Install package dependencies from schema.
|
|
14
|
+
* Merges dependencies into package.json and runs npm install with a spinner.
|
|
15
|
+
*/
|
|
16
|
+
export declare function installPackageDependencies(schema: FileCopySchema, context: InstallationContext): Promise<void>;
|
|
17
|
+
/**
|
|
18
|
+
* Check if a package is already installed and listed in package.json
|
|
19
|
+
* This ensures the package won't be removed by subsequent npm install commands
|
|
20
|
+
*/
|
|
21
|
+
export declare function isPackageInstalled(packageName: string, uiBundleDir: string): boolean;
|
|
22
|
+
//# sourceMappingURL=package-manager.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"package-manager.d.ts","sourceRoot":"","sources":["../src/package-manager.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAMH,OAAO,KAAK,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAkCtE;;;GAGG;AACH,wBAAsB,cAAc,CACnC,WAAW,EAAE,MAAM,EACnB,KAAK,EAAE,OAAO,EACd,WAAW,EAAE,MAAM,EACnB,MAAM,UAAQ,EACd,OAAO,UAAQ,GACb,OAAO,CAAC,IAAI,CAAC,CAkBf;AAED;;;GAGG;AACH,wBAAsB,0BAA0B,CAC/C,MAAM,EAAE,cAAc,EACtB,OAAO,EAAE,mBAAmB,GAC1B,OAAO,CAAC,IAAI,CAAC,CAoGf;AAED;;;GAGG;AACH,wBAAgB,kBAAkB,CAAC,WAAW,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,OAAO,CAoBpF"}
|
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import { spawn } from "child_process";
|
|
7
|
+
import { existsSync, readFileSync, writeFileSync } from "fs";
|
|
8
|
+
import { join } from "path";
|
|
9
|
+
import { Logger } from "./logger.js";
|
|
10
|
+
const fallbackLogger = new Logger();
|
|
11
|
+
/**
|
|
12
|
+
* Run an npm command asynchronously, capturing output.
|
|
13
|
+
* Returns stdout on success; throws with captured output on failure.
|
|
14
|
+
*/
|
|
15
|
+
function runNpm(args, cwd) {
|
|
16
|
+
return new Promise((resolve, reject) => {
|
|
17
|
+
const child = spawn("npm", args, {
|
|
18
|
+
cwd,
|
|
19
|
+
stdio: "pipe",
|
|
20
|
+
});
|
|
21
|
+
let stdout = "";
|
|
22
|
+
let stderr = "";
|
|
23
|
+
child.stdout.on("data", (data) => {
|
|
24
|
+
stdout += data.toString();
|
|
25
|
+
});
|
|
26
|
+
child.stderr.on("data", (data) => {
|
|
27
|
+
stderr += data.toString();
|
|
28
|
+
});
|
|
29
|
+
child.on("close", (code) => {
|
|
30
|
+
if (code !== 0) {
|
|
31
|
+
reject(new Error(`npm ${args.join(" ")} failed (exit code ${code}):\n${stderr}\n${stdout}`));
|
|
32
|
+
}
|
|
33
|
+
else {
|
|
34
|
+
resolve(stdout);
|
|
35
|
+
}
|
|
36
|
+
});
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Install a single npm package and ensure it's saved to package.json.
|
|
41
|
+
* npm output is suppressed by default; shown on verbose or error.
|
|
42
|
+
*/
|
|
43
|
+
export async function installPackage(packageName, isDev, uiBundleDir, dryRun = false, verbose = false) {
|
|
44
|
+
if (dryRun) {
|
|
45
|
+
return;
|
|
46
|
+
}
|
|
47
|
+
const saveFlag = isDev ? "--save-dev" : "--save";
|
|
48
|
+
try {
|
|
49
|
+
const output = await runNpm(["install", saveFlag, packageName], uiBundleDir);
|
|
50
|
+
if (verbose && output.trim()) {
|
|
51
|
+
console.log(output);
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
catch (error) {
|
|
55
|
+
if (error instanceof Error) {
|
|
56
|
+
console.error(error.message);
|
|
57
|
+
}
|
|
58
|
+
throw new Error(`Failed to install package: ${packageName}`);
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Install package dependencies from schema.
|
|
63
|
+
* Merges dependencies into package.json and runs npm install with a spinner.
|
|
64
|
+
*/
|
|
65
|
+
export async function installPackageDependencies(schema, context) {
|
|
66
|
+
const logger = context.logger;
|
|
67
|
+
const packageJsonPath = join(context.uiBundleDir, "package.json");
|
|
68
|
+
if (!existsSync(packageJsonPath)) {
|
|
69
|
+
throw new Error(`package.json not found in: ${context.uiBundleDir}`);
|
|
70
|
+
}
|
|
71
|
+
// Read current package.json
|
|
72
|
+
const packageJsonContent = readFileSync(packageJsonPath, "utf-8");
|
|
73
|
+
const packageJson = JSON.parse(packageJsonContent);
|
|
74
|
+
let hasChanges = false;
|
|
75
|
+
// Merge regular dependencies
|
|
76
|
+
if (schema.packageDependencies) {
|
|
77
|
+
packageJson.dependencies = packageJson.dependencies || {};
|
|
78
|
+
for (const [pkg, version] of Object.entries(schema.packageDependencies)) {
|
|
79
|
+
const currentVersion = packageJson.dependencies[pkg];
|
|
80
|
+
if (!currentVersion) {
|
|
81
|
+
logger.plain(`${context.dryRun ? "[DRY RUN] Would add" : "Adding"} dependency: ${pkg}@${version}`);
|
|
82
|
+
if (!context.dryRun) {
|
|
83
|
+
packageJson.dependencies[pkg] = version;
|
|
84
|
+
hasChanges = true;
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
else if (currentVersion === "*") {
|
|
88
|
+
logger.plain(`${context.dryRun ? "[DRY RUN] Would update" : "Updating"} dependency: ${pkg} from * to ${version}`);
|
|
89
|
+
if (!context.dryRun) {
|
|
90
|
+
packageJson.dependencies[pkg] = version;
|
|
91
|
+
hasChanges = true;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
else {
|
|
95
|
+
logger.debug(`Dependency already exists: ${pkg}@${currentVersion}`);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
// Merge dev dependencies
|
|
100
|
+
if (schema.packageDevDependencies) {
|
|
101
|
+
packageJson.devDependencies = packageJson.devDependencies || {};
|
|
102
|
+
for (const [pkg, version] of Object.entries(schema.packageDevDependencies)) {
|
|
103
|
+
const currentVersion = packageJson.devDependencies[pkg];
|
|
104
|
+
if (!currentVersion) {
|
|
105
|
+
logger.plain(`${context.dryRun ? "[DRY RUN] Would add" : "Adding"} dev dependency: ${pkg}@${version}`);
|
|
106
|
+
if (!context.dryRun) {
|
|
107
|
+
packageJson.devDependencies[pkg] = version;
|
|
108
|
+
hasChanges = true;
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
else if (currentVersion === "*") {
|
|
112
|
+
logger.plain(`${context.dryRun ? "[DRY RUN] Would update" : "Updating"} dev dependency: ${pkg} from * to ${version}`);
|
|
113
|
+
if (!context.dryRun) {
|
|
114
|
+
packageJson.devDependencies[pkg] = version;
|
|
115
|
+
hasChanges = true;
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
else {
|
|
119
|
+
logger.debug(`Dev dependency already exists: ${pkg}@${currentVersion}`);
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
if (!hasChanges) {
|
|
124
|
+
logger.debug("No new dependencies to install");
|
|
125
|
+
return;
|
|
126
|
+
}
|
|
127
|
+
if (context.dryRun) {
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
// Write updated package.json
|
|
131
|
+
writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2) + "\n", "utf-8");
|
|
132
|
+
// Run npm install with spinner
|
|
133
|
+
const { default: ora } = await import("ora");
|
|
134
|
+
const spinner = ora({ text: "Running npm install...", indent: 2 }).start();
|
|
135
|
+
try {
|
|
136
|
+
const output = await runNpm(["install"], context.uiBundleDir);
|
|
137
|
+
spinner.succeed("npm install complete");
|
|
138
|
+
if (context.verbose && output.trim()) {
|
|
139
|
+
console.log(output);
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
catch (error) {
|
|
143
|
+
spinner.fail("npm install failed");
|
|
144
|
+
if (error instanceof Error) {
|
|
145
|
+
console.error(error.message);
|
|
146
|
+
}
|
|
147
|
+
throw error;
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
/**
|
|
151
|
+
* Check if a package is already installed and listed in package.json
|
|
152
|
+
* This ensures the package won't be removed by subsequent npm install commands
|
|
153
|
+
*/
|
|
154
|
+
export function isPackageInstalled(packageName, uiBundleDir) {
|
|
155
|
+
const packageJsonPath = join(uiBundleDir, "package.json");
|
|
156
|
+
if (!existsSync(packageJsonPath)) {
|
|
157
|
+
return false;
|
|
158
|
+
}
|
|
159
|
+
try {
|
|
160
|
+
const packageJsonContent = readFileSync(packageJsonPath, "utf-8");
|
|
161
|
+
const packageJson = JSON.parse(packageJsonContent);
|
|
162
|
+
// Check both dependencies and devDependencies
|
|
163
|
+
const inDependencies = packageJson.dependencies?.[packageName] !== undefined;
|
|
164
|
+
const inDevDependencies = packageJson.devDependencies?.[packageName] !== undefined;
|
|
165
|
+
return inDependencies || inDevDependencies;
|
|
166
|
+
}
|
|
167
|
+
catch (error) {
|
|
168
|
+
fallbackLogger.error("Failed to read package.json", error);
|
|
169
|
+
return false;
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
//# sourceMappingURL=package-manager.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"package-manager.js","sourceRoot":"","sources":["../src/package-manager.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import type { InstallationContext } from "./types.js";
|
|
7
|
+
/**
|
|
8
|
+
* Resolve a schema path to an actual file system path
|
|
9
|
+
*
|
|
10
|
+
* Supports three placeholder formats:
|
|
11
|
+
* 1. <sfdxSource>/path → resolves to context.sfdxSource/path
|
|
12
|
+
* 2. <uiBundleDir>/path → resolves to context.uiBundleDir/path
|
|
13
|
+
* 3. <uiBundle> → replaced with context.uiBundleName (legacy)
|
|
14
|
+
*
|
|
15
|
+
* For backward compatibility, also handles paths without placeholders:
|
|
16
|
+
* - force-app/main/default/... → treated as SFDX metadata
|
|
17
|
+
* - Other paths → treated as relative to uiBundleDir
|
|
18
|
+
*/
|
|
19
|
+
export declare function resolvePath(schemaPath: string, context: InstallationContext): string;
|
|
20
|
+
/**
|
|
21
|
+
* Resolve source path from package, trying multiple possible locations
|
|
22
|
+
* Returns the first path that exists, or throws an error with all attempted paths
|
|
23
|
+
*/
|
|
24
|
+
export declare function resolveSourcePath(packagePath: string, schemaFrom: string): string;
|
|
25
|
+
//# sourceMappingURL=placeholder-resolver.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"placeholder-resolver.d.ts","sourceRoot":"","sources":["../src/placeholder-resolver.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAIH,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAGtD;;;;;;;;;;;GAWG;AACH,wBAAgB,WAAW,CAAC,UAAU,EAAE,MAAM,EAAE,OAAO,EAAE,mBAAmB,GAAG,MAAM,CAsCpF;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,WAAW,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,MAAM,CAwBjF"}
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import { existsSync } from "fs";
|
|
7
|
+
import { join } from "path";
|
|
8
|
+
import { hasUIBundlePlaceholder, isSfdxMetadataPath } from "./utils.js";
|
|
9
|
+
/**
|
|
10
|
+
* Resolve a schema path to an actual file system path
|
|
11
|
+
*
|
|
12
|
+
* Supports three placeholder formats:
|
|
13
|
+
* 1. <sfdxSource>/path → resolves to context.sfdxSource/path
|
|
14
|
+
* 2. <uiBundleDir>/path → resolves to context.uiBundleDir/path
|
|
15
|
+
* 3. <uiBundle> → replaced with context.uiBundleName (legacy)
|
|
16
|
+
*
|
|
17
|
+
* For backward compatibility, also handles paths without placeholders:
|
|
18
|
+
* - force-app/main/default/... → treated as SFDX metadata
|
|
19
|
+
* - Other paths → treated as relative to uiBundleDir
|
|
20
|
+
*/
|
|
21
|
+
export function resolvePath(schemaPath, context) {
|
|
22
|
+
// Handle <sfdxSource> placeholder
|
|
23
|
+
if (schemaPath.startsWith("<sfdxSource>")) {
|
|
24
|
+
const relativePath = schemaPath.replace(/^<sfdxSource>\/?/, "");
|
|
25
|
+
return relativePath ? join(context.sfdxSource, relativePath) : context.sfdxSource;
|
|
26
|
+
}
|
|
27
|
+
// Handle <uiBundleDir> placeholder
|
|
28
|
+
if (schemaPath.startsWith("<uiBundleDir>")) {
|
|
29
|
+
const relativePath = schemaPath.replace(/^<uiBundleDir>\/?/, "");
|
|
30
|
+
return relativePath ? join(context.uiBundleDir, relativePath) : context.uiBundleDir;
|
|
31
|
+
}
|
|
32
|
+
// === Backward compatibility for legacy path formats ===
|
|
33
|
+
// Handle SFDX metadata paths (legacy format: force-app/main/default/...)
|
|
34
|
+
if (isSfdxMetadataPath(schemaPath)) {
|
|
35
|
+
const relativePath = schemaPath.replace(/^force-app\/main\/default\//, "");
|
|
36
|
+
return join(context.sfdxSource, relativePath);
|
|
37
|
+
}
|
|
38
|
+
// Handle UI bundle paths with <uiBundle> placeholder (legacy format)
|
|
39
|
+
if (hasUIBundlePlaceholder(schemaPath)) {
|
|
40
|
+
const withName = schemaPath.replace(/<uiBundle>/g, context.uiBundleName);
|
|
41
|
+
// Strip 'force-app/main/default/uiBundles/{uiBundleName}/' prefix
|
|
42
|
+
const prefix = `force-app/main/default/uiBundles/${context.uiBundleName}/`;
|
|
43
|
+
if (withName.startsWith(prefix)) {
|
|
44
|
+
const relativePath = withName.substring(prefix.length);
|
|
45
|
+
return join(context.uiBundleDir, relativePath);
|
|
46
|
+
}
|
|
47
|
+
// If no prefix, just join with uiBundleDir
|
|
48
|
+
return join(context.uiBundleDir, withName);
|
|
49
|
+
}
|
|
50
|
+
// Default: treat as relative to uiBundleDir
|
|
51
|
+
return join(context.uiBundleDir, schemaPath);
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Resolve source path from package, trying multiple possible locations
|
|
55
|
+
* Returns the first path that exists, or throws an error with all attempted paths
|
|
56
|
+
*/
|
|
57
|
+
export function resolveSourcePath(packagePath, schemaFrom) {
|
|
58
|
+
// Try multiple possible locations in order of likelihood
|
|
59
|
+
const possiblePaths = [
|
|
60
|
+
join(packagePath, "dist", schemaFrom), // Built packages often have dist/
|
|
61
|
+
join(packagePath, schemaFrom), // Some packages don't have dist/
|
|
62
|
+
];
|
|
63
|
+
// Return the first path that exists
|
|
64
|
+
for (const path of possiblePaths) {
|
|
65
|
+
if (existsSync(path)) {
|
|
66
|
+
return path;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
// None found - throw descriptive error
|
|
70
|
+
const error = new Error(`Source path not found in package. Tried:\n${possiblePaths.map((p) => ` - ${p}`).join("\n")}\n\n` +
|
|
71
|
+
`This usually means:\n` +
|
|
72
|
+
` 1. The package hasn't been built (run npm run build in the package)\n` +
|
|
73
|
+
` 2. The "from" path in features.json is incorrect\n` +
|
|
74
|
+
` 3. The package structure doesn't match expectations`);
|
|
75
|
+
error.name = "SourcePathNotFoundError";
|
|
76
|
+
throw error;
|
|
77
|
+
}
|
|
78
|
+
//# sourceMappingURL=placeholder-resolver.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"placeholder-resolver.js","sourceRoot":"","sources":["../src/placeholder-resolver.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import { Logger } from "./logger.js";
|
|
7
|
+
import type { FileCopySchema } from "./types.js";
|
|
8
|
+
/**
|
|
9
|
+
* Load and validate a feature schema from a package directory
|
|
10
|
+
* Tries multiple locations: root and dist/ directory
|
|
11
|
+
*/
|
|
12
|
+
export declare function loadSchema(packagePath: string, logger?: Logger): FileCopySchema | null;
|
|
13
|
+
/**
|
|
14
|
+
* Load schema from node_modules OR from local features.json metadata
|
|
15
|
+
*/
|
|
16
|
+
export declare function loadSchemaFromNodeModules(packageName: string, uiBundleDir: string, logger?: Logger): FileCopySchema | null;
|
|
17
|
+
//# sourceMappingURL=schema-loader.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schema-loader.d.ts","sourceRoot":"","sources":["../src/schema-loader.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAMH,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAiBjD;;;GAGG;AACH,wBAAgB,UAAU,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,cAAc,GAAG,IAAI,CA2BtF;AAED;;GAEG;AACH,wBAAgB,yBAAyB,CACxC,WAAW,EAAE,MAAM,EACnB,WAAW,EAAE,MAAM,EACnB,MAAM,CAAC,EAAE,MAAM,GACb,cAAc,GAAG,IAAI,CA6BvB"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2026, Salesforce, Inc.,
|
|
3
|
+
* All rights reserved.
|
|
4
|
+
* For full license text, see the LICENSE.txt file
|
|
5
|
+
*/
|
|
6
|
+
import { existsSync, readFileSync } from "fs";
|
|
7
|
+
import { join } from "path";
|
|
8
|
+
import { z } from "zod";
|
|
9
|
+
import { getFeatureMetadata, getFeatureNameFromPackage } from "./feature-metadata.js";
|
|
10
|
+
import { Logger } from "./logger.js";
|
|
11
|
+
// Zod schema for validation
|
|
12
|
+
const CopyOperationSchema = z.object({
|
|
13
|
+
from: z.string(),
|
|
14
|
+
to: z.string(),
|
|
15
|
+
description: z.string().optional(),
|
|
16
|
+
integrationTarget: z.string().optional(),
|
|
17
|
+
});
|
|
18
|
+
const FileCopySchemaValidator = z.object({
|
|
19
|
+
featureDependencies: z.array(z.string()).optional(),
|
|
20
|
+
packageDependencies: z.record(z.string()).optional(),
|
|
21
|
+
packageDevDependencies: z.record(z.string()).optional(),
|
|
22
|
+
copy: z.array(CopyOperationSchema).optional(),
|
|
23
|
+
});
|
|
24
|
+
/**
|
|
25
|
+
* Load and validate a feature schema from a package directory
|
|
26
|
+
* Tries multiple locations: root and dist/ directory
|
|
27
|
+
*/
|
|
28
|
+
export function loadSchema(packagePath, logger) {
|
|
29
|
+
const log = logger ?? new Logger();
|
|
30
|
+
const possibleLocations = [
|
|
31
|
+
join(packagePath, "features.json"),
|
|
32
|
+
join(packagePath, "dist", "features.json"),
|
|
33
|
+
];
|
|
34
|
+
for (const schemaPath of possibleLocations) {
|
|
35
|
+
if (existsSync(schemaPath)) {
|
|
36
|
+
try {
|
|
37
|
+
const content = readFileSync(schemaPath, "utf-8");
|
|
38
|
+
const parsed = JSON.parse(content);
|
|
39
|
+
// Validate with Zod
|
|
40
|
+
const validated = FileCopySchemaValidator.parse(parsed);
|
|
41
|
+
log.debug(`Loaded schema from: ${schemaPath}`);
|
|
42
|
+
return validated;
|
|
43
|
+
}
|
|
44
|
+
catch (error) {
|
|
45
|
+
log.error(`Failed to parse schema at ${schemaPath}:`, error);
|
|
46
|
+
throw new Error(`Invalid schema format in ${schemaPath}`);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
log.debug(`No features.json found in: ${packagePath}`);
|
|
51
|
+
return null;
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Load schema from node_modules OR from local features.json metadata
|
|
55
|
+
*/
|
|
56
|
+
export function loadSchemaFromNodeModules(packageName, uiBundleDir, logger) {
|
|
57
|
+
const log = logger ?? new Logger();
|
|
58
|
+
// First, try to get schema from local features.json metadata
|
|
59
|
+
const featureName = getFeatureNameFromPackage(packageName);
|
|
60
|
+
if (featureName) {
|
|
61
|
+
const metadata = getFeatureMetadata(featureName);
|
|
62
|
+
if (metadata) {
|
|
63
|
+
// Check if metadata has schema information
|
|
64
|
+
if (metadata.copy ||
|
|
65
|
+
metadata.packageDependencies ||
|
|
66
|
+
metadata.packageDevDependencies ||
|
|
67
|
+
metadata.featureDependencies) {
|
|
68
|
+
log.debug(`Using schema from local features.json for: ${packageName}`);
|
|
69
|
+
return {
|
|
70
|
+
featureDependencies: metadata.featureDependencies,
|
|
71
|
+
packageDependencies: metadata.packageDependencies,
|
|
72
|
+
packageDevDependencies: metadata.packageDevDependencies,
|
|
73
|
+
copy: metadata.copy,
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
// Fallback: try to load from node_modules (for packages with their own features.json)
|
|
79
|
+
const packagePath = join(uiBundleDir, "node_modules", packageName);
|
|
80
|
+
return loadSchema(packagePath, log);
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=schema-loader.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schema-loader.js","sourceRoot":"","sources":["../src/schema-loader.ts"],"names":[],"mappings":"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"}
|