@uipath/maestro-builder-sdk 6.21.1 → 6.21.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/dist/case/compile-cli.js +82 -26
- package/package.json +2 -2
package/dist/case/compile-cli.js
CHANGED
|
@@ -7,11 +7,14 @@
|
|
|
7
7
|
*
|
|
8
8
|
* Runs the fast static check first; if it passes, serializes to a V30
|
|
9
9
|
* caseplan.json. The authoritative deploy gate is `uip maestro case validate`.
|
|
10
|
-
* Output defaults to
|
|
10
|
+
* Output defaults to the plan file the project in the working directory ships
|
|
11
|
+
* (`caseplan.case` for a project `uip maestro case init` scaffolded), else
|
|
12
|
+
* `caseplan.json`. An `-o` that names a different plan file than the project
|
|
13
|
+
* ships is refused (CASE_OUTPUT_NOT_SHIPPED).
|
|
11
14
|
*/
|
|
12
15
|
import { reportDiagnostics, reportResult, thrownDiagnostic } from '../cli-result.js';
|
|
13
16
|
import { writeJsonFile } from '../core/json-file.js';
|
|
14
|
-
import { readFileSync, existsSync } from 'node:fs';
|
|
17
|
+
import { readFileSync, existsSync, readdirSync } from 'node:fs';
|
|
15
18
|
import { join, dirname, basename, resolve } from 'node:path';
|
|
16
19
|
import { resolveCaseFile, loadBuiltCase } from './load.js';
|
|
17
20
|
import { serialize } from './serialize.js';
|
|
@@ -28,7 +31,7 @@ import { sha256Uuid } from '../core/stable-id.js';
|
|
|
28
31
|
import { isRecord } from '../core/node-envelope.js';
|
|
29
32
|
export async function run(argv) {
|
|
30
33
|
if (argv.length === 0 || argv[0] === '-h' || argv[0] === '--help') {
|
|
31
|
-
console.error('usage: compile <case.ts | BaseName> [-o caseplan.
|
|
34
|
+
console.error('usage: compile <case.ts | BaseName> [-o <project>/caseplan.case]');
|
|
32
35
|
return 2;
|
|
33
36
|
}
|
|
34
37
|
const flags = new Set(['-o', '--library', '--bindings', '--connectors-local']);
|
|
@@ -61,6 +64,14 @@ export async function run(argv) {
|
|
|
61
64
|
console.error(`compile: ${errors.length} error(s); not emitting.`);
|
|
62
65
|
return 1;
|
|
63
66
|
}
|
|
67
|
+
const out = flagValue(argv, '-o') ?? shippedCasePlanName('.') ?? 'caseplan.json';
|
|
68
|
+
const shadow = shadowedOutputDiagnostic(out);
|
|
69
|
+
if (shadow) {
|
|
70
|
+
console.error(` ✗ [${shadow.code}] ${shadow.message}`);
|
|
71
|
+
reportDiagnostics([...diags, shadow]);
|
|
72
|
+
console.error('compile: 1 error(s); not emitting.');
|
|
73
|
+
return 1;
|
|
74
|
+
}
|
|
64
75
|
let caseplan;
|
|
65
76
|
try {
|
|
66
77
|
caseplan = serialize(built, { library, bindings });
|
|
@@ -69,7 +80,6 @@ export async function run(argv) {
|
|
|
69
80
|
reportDiagnostics([...diags, thrownDiagnostic(error)]);
|
|
70
81
|
throw error;
|
|
71
82
|
}
|
|
72
|
-
const out = flagValue(argv, '-o') ?? 'caseplan.json';
|
|
73
83
|
writeJsonFile(out, caseplan);
|
|
74
84
|
const stages = caseplan.nodes.filter((n) => String(n.type).endsWith('Stage')).length;
|
|
75
85
|
const triggers = syncEntryPoints(caseplan, out);
|
|
@@ -80,6 +90,70 @@ export async function run(argv) {
|
|
|
80
90
|
reportResult({ path: resolve(out), stages, ...(triggers >= 0 ? { triggers } : {}), ...(resources >= 0 ? { resources } : {}) });
|
|
81
91
|
return 0;
|
|
82
92
|
}
|
|
93
|
+
/**
|
|
94
|
+
* The file names a Case project's plan can have, in the order the packager
|
|
95
|
+
* (`@uipath/packager-tool-case` `CasePlanFileNames`) picks the first one present.
|
|
96
|
+
* `uip maestro case init` scaffolds `caseplan.case` since uipath-cli#5004.
|
|
97
|
+
*/
|
|
98
|
+
const CASE_PLAN_FILE_NAMES = ['caseplan.case', 'caseplan.json', 'case.stage.json', 'default.stage.json'];
|
|
99
|
+
/**
|
|
100
|
+
* The plan file the project in `dir` ships, or undefined when `dir` is not a
|
|
101
|
+
* Case project. Decided as the packager decides: the first plan file present in
|
|
102
|
+
* packager order. The packager regenerates `package-descriptor.json` from that
|
|
103
|
+
* file (Studio Web renames the plan without updating the descriptor), so the
|
|
104
|
+
* descriptor is only a fallback when no plan file exists yet.
|
|
105
|
+
*/
|
|
106
|
+
function shippedCasePlanName(dir) {
|
|
107
|
+
// Exact directory entries, as the packager matches them: `existsSync` ignores
|
|
108
|
+
// case on macOS and Windows, so `CasePlan.case` would pass for `caseplan.case`.
|
|
109
|
+
let entries;
|
|
110
|
+
try {
|
|
111
|
+
entries = new Set(readdirSync(dir));
|
|
112
|
+
}
|
|
113
|
+
catch {
|
|
114
|
+
entries = new Set();
|
|
115
|
+
}
|
|
116
|
+
return CASE_PLAN_FILE_NAMES.find((name) => entries.has(name)) ?? describedCaseFileName(dir);
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Refuse to write a plan file the package will not ship: pack, debug and deploy
|
|
120
|
+
* would read the other plan. Non-plan names (`<Name>.caseplan.json`) are not
|
|
121
|
+
* checked.
|
|
122
|
+
*/
|
|
123
|
+
function shadowedOutputDiagnostic(outPath) {
|
|
124
|
+
const name = basename(outPath);
|
|
125
|
+
// Case-insensitive: on macOS and Windows `-o CasePlan.json` writes over caseplan.json.
|
|
126
|
+
if (!CASE_PLAN_FILE_NAMES.includes(name.toLowerCase()))
|
|
127
|
+
return undefined;
|
|
128
|
+
const dir = dirname(outPath);
|
|
129
|
+
const shipped = shippedCasePlanName(dir);
|
|
130
|
+
if (!shipped || shipped === name)
|
|
131
|
+
return undefined;
|
|
132
|
+
const target = join(dir, shipped);
|
|
133
|
+
return {
|
|
134
|
+
level: 'error',
|
|
135
|
+
code: 'CASE_OUTPUT_NOT_SHIPPED',
|
|
136
|
+
message: `the project ships ${target}, not ${outPath}; writing ${name} beside it leaves the shipped plan unchanged, ` +
|
|
137
|
+
`so pack, debug and deploy would use the old ${shipped}.`,
|
|
138
|
+
suggestion: `compile with -o ${target}`,
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
/** The case file `package-descriptor.json` in `dir` ships, if it names one. */
|
|
142
|
+
function describedCaseFileName(dir) {
|
|
143
|
+
const descriptorPath = join(dir, 'package-descriptor.json');
|
|
144
|
+
if (!existsSync(descriptorPath))
|
|
145
|
+
return undefined;
|
|
146
|
+
try {
|
|
147
|
+
const files = JSON.parse(readFileSync(descriptorPath, 'utf8'))?.files;
|
|
148
|
+
if (files && typeof files === 'object') {
|
|
149
|
+
// The descriptor keys the pair by logical name; the case file is the one
|
|
150
|
+
// whose BPMN sibling it also ships.
|
|
151
|
+
return Object.keys(files).find((k) => `${k}.bpmn` in files);
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
catch { /* a malformed descriptor is not worth failing a compile over */ }
|
|
155
|
+
return undefined;
|
|
156
|
+
}
|
|
83
157
|
/**
|
|
84
158
|
* The name of the case file THE PACKAGE SHIPS, which is what an entry point's
|
|
85
159
|
* `filePath` has to name — not the name this compile happened to write.
|
|
@@ -92,30 +166,12 @@ export async function run(argv) {
|
|
|
92
166
|
* task that took that path never left `Pending (0/0 elements completed)`: the
|
|
93
167
|
* debug instance was created and no element ever started.
|
|
94
168
|
*
|
|
95
|
-
*
|
|
96
|
-
*
|
|
97
|
-
*
|
|
169
|
+
* The packaged pair is decided by `shippedCasePlanName` (the plan file on disk,
|
|
170
|
+
* in packager order, else the descriptor); only when neither exists does the
|
|
171
|
+
* output's own name stand.
|
|
98
172
|
*/
|
|
99
173
|
function packagedCaseFileName(dir, outPath) {
|
|
100
|
-
|
|
101
|
-
if (existsSync(descriptorPath)) {
|
|
102
|
-
try {
|
|
103
|
-
const files = JSON.parse(readFileSync(descriptorPath, 'utf8'))?.files;
|
|
104
|
-
if (files && typeof files === 'object') {
|
|
105
|
-
// The descriptor keys the pair by logical name; the case file is the one
|
|
106
|
-
// whose BPMN sibling it also ships.
|
|
107
|
-
const named = Object.keys(files).find((k) => `${k}.bpmn` in files);
|
|
108
|
-
if (named)
|
|
109
|
-
return named;
|
|
110
|
-
}
|
|
111
|
-
}
|
|
112
|
-
catch { /* a malformed descriptor is not worth failing a compile over */ }
|
|
113
|
-
}
|
|
114
|
-
// No descriptor (a project scaffolded some other way): a sibling `caseplan.json`
|
|
115
|
-
// still says what the project ships, and only the output name is in doubt.
|
|
116
|
-
if (existsSync(join(dir, 'caseplan.json')))
|
|
117
|
-
return 'caseplan.json';
|
|
118
|
-
return basename(outPath);
|
|
174
|
+
return shippedCasePlanName(dir) ?? basename(outPath);
|
|
119
175
|
}
|
|
120
176
|
/**
|
|
121
177
|
* Keep the sibling `entry-points.json` in step with the caseplan's trigger nodes:
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@uipath/maestro-builder-sdk",
|
|
3
|
-
"version": "6.21.
|
|
3
|
+
"version": "6.21.2",
|
|
4
4
|
"description": "Build UiPath Flow, Case, and BPMN artifacts by writing TypeScript.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"homepage": "https://docs.uipath.com/maestro",
|
|
@@ -92,5 +92,5 @@
|
|
|
92
92
|
"@types/node": "^22.7.0",
|
|
93
93
|
"esbuild": "^0.28.1"
|
|
94
94
|
},
|
|
95
|
-
"gitref": "
|
|
95
|
+
"gitref": "1e310a7eebe0932dacee8f36729f54ce6ccc73f4"
|
|
96
96
|
}
|