@intelligentgraphics/ig.gfx.packager 3.0.10 → 3.0.11
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/build/bin.mjs +6 -0
- package/build/bin.mjs.map +1 -0
- package/build/{cli-cb85e4b5.js → cli-381989cc.mjs} +8 -12
- package/build/cli-381989cc.mjs.map +1 -0
- package/build/{dependencies-2565d80c.js → dependencies-1f665204.mjs} +3 -7
- package/build/dependencies-1f665204.mjs.map +1 -0
- package/build/{generateIndex-f386d332.js → generateIndex-074f4aa1.mjs} +2 -2
- package/build/generateIndex-074f4aa1.mjs.map +1 -0
- package/build/{generateParameterType-151ab313.js → generateParameterType-4c9e95a5.mjs} +2 -2
- package/build/generateParameterType-4c9e95a5.mjs.map +1 -0
- package/build/{index-7a955335.js → index-06ac2c4c.mjs} +44 -28
- package/build/index-06ac2c4c.mjs.map +1 -0
- package/build/{index-67a112b8.js → index-cc42a478.mjs} +6 -6
- package/build/index-cc42a478.mjs.map +1 -0
- package/build/{postinstall-962af586.js → postinstall-c38d9b55.mjs} +3 -3
- package/build/postinstall-c38d9b55.mjs.map +1 -0
- package/build/{publishNpm-1838e45c.js → publishNpm-8ec1b871.mjs} +4 -4
- package/build/publishNpm-8ec1b871.mjs.map +1 -0
- package/build/{versionFile-cf6657c8.js → versionFile-aa8b6b7a.mjs} +2 -2
- package/build/versionFile-aa8b6b7a.mjs.map +1 -0
- package/lib/lib.mjs +1476 -0
- package/package.json +11 -5
- package/readme.md +5 -0
- package/build/cli-cb85e4b5.js.map +0 -1
- package/build/dependencies-2565d80c.js.map +0 -1
- package/build/generateIndex-f386d332.js.map +0 -1
- package/build/generateParameterType-151ab313.js.map +0 -1
- package/build/index-67a112b8.js.map +0 -1
- package/build/index-7a955335.js.map +0 -1
- package/build/index.mjs +0 -6
- package/build/index.mjs.map +0 -1
- package/build/postinstall-962af586.js.map +0 -1
- package/build/publishNpm-1838e45c.js.map +0 -1
- package/build/versionFile-cf6657c8.js.map +0 -1
package/lib/lib.mjs
ADDED
|
@@ -0,0 +1,1476 @@
|
|
|
1
|
+
import * as path from 'path';
|
|
2
|
+
import * as fs from 'fs';
|
|
3
|
+
import * as terser from 'terser';
|
|
4
|
+
import resolve from 'resolve';
|
|
5
|
+
import 'write-pkg';
|
|
6
|
+
import glob from 'glob';
|
|
7
|
+
import 'write-json-file';
|
|
8
|
+
import axios from 'axios';
|
|
9
|
+
import ts from 'typescript';
|
|
10
|
+
import typedoc from 'typedoc';
|
|
11
|
+
import { pipeline } from 'stream/promises';
|
|
12
|
+
import { execSync } from 'child_process';
|
|
13
|
+
import simpleGit from 'simple-git';
|
|
14
|
+
import Ajv from 'ajv';
|
|
15
|
+
import JSZip from 'jszip';
|
|
16
|
+
|
|
17
|
+
const stripUtf8Bom = (text)=>{
|
|
18
|
+
// Catches EFBBBF (UTF-8 BOM) because the buffer-to-string
|
|
19
|
+
// conversion translates it to FEFF (UTF-16 BOM).
|
|
20
|
+
if (text.charCodeAt(0) === 0xfeff) {
|
|
21
|
+
return text.slice(1);
|
|
22
|
+
}
|
|
23
|
+
return text;
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
const readNpmManifest = (directory)=>{
|
|
27
|
+
const packageJsonPath = path.join(directory, "package.json");
|
|
28
|
+
const packageJson = stripUtf8Bom(fs.readFileSync(packageJsonPath, {
|
|
29
|
+
encoding: "utf8"
|
|
30
|
+
}));
|
|
31
|
+
return JSON.parse(packageJson);
|
|
32
|
+
};
|
|
33
|
+
|
|
34
|
+
const getNodeErrorCode = (error)=>{
|
|
35
|
+
if (error !== null && typeof error === "object" && error.code !== undefined) {
|
|
36
|
+
return error.code;
|
|
37
|
+
}
|
|
38
|
+
};
|
|
39
|
+
/**
|
|
40
|
+
* No such file or directory: Commonly raised by fs operations to indicate that a component of the specified pathname does not exist. No entity (file or directory) could be found by the given path.
|
|
41
|
+
*
|
|
42
|
+
* @param {unknown} error
|
|
43
|
+
*/ const isErrorENOENT = (error)=>getNodeErrorCode(error) === "ENOENT";
|
|
44
|
+
|
|
45
|
+
// Functionality related to working with a single package.
|
|
46
|
+
const PACKAGE_FILE = "_Package.json";
|
|
47
|
+
const INDEX_FILE = "_Index.json";
|
|
48
|
+
const ANIMATION_FILE_SUFFIX = ".animation.json";
|
|
49
|
+
const parseCreatorPackageName = (manifest)=>{
|
|
50
|
+
const [domain, ...subdomainParts] = manifest.Package.split(".");
|
|
51
|
+
return {
|
|
52
|
+
domain,
|
|
53
|
+
subdomain: subdomainParts.join(".")
|
|
54
|
+
};
|
|
55
|
+
};
|
|
56
|
+
const readPackageCreatorManifest = (location)=>{
|
|
57
|
+
const packageJsonPath = path.join(location.manifestDir, PACKAGE_FILE);
|
|
58
|
+
const packageJson = stripUtf8Bom(fs.readFileSync(packageJsonPath, {
|
|
59
|
+
encoding: "utf8"
|
|
60
|
+
}));
|
|
61
|
+
return JSON.parse(packageJson);
|
|
62
|
+
};
|
|
63
|
+
const writePackageCreatorManifest = (location, creatorPackage)=>{
|
|
64
|
+
const packageJsonPath = path.join(location.manifestDir, PACKAGE_FILE);
|
|
65
|
+
fs.writeFileSync(packageJsonPath, JSON.stringify(creatorPackage, null, "\t") + "\n");
|
|
66
|
+
};
|
|
67
|
+
const getPackageCreatorIndexPath = (location)=>path.join(location.manifestDir, INDEX_FILE);
|
|
68
|
+
const readPackageCreatorIndex = (location)=>{
|
|
69
|
+
try {
|
|
70
|
+
const indexPath = getPackageCreatorIndexPath(location);
|
|
71
|
+
const index = stripUtf8Bom(fs.readFileSync(indexPath, {
|
|
72
|
+
encoding: "utf8"
|
|
73
|
+
}));
|
|
74
|
+
return JSON.parse(index);
|
|
75
|
+
} catch (err) {
|
|
76
|
+
if (isErrorENOENT(err)) {
|
|
77
|
+
return undefined;
|
|
78
|
+
}
|
|
79
|
+
throw err;
|
|
80
|
+
}
|
|
81
|
+
};
|
|
82
|
+
const readPackageNpmManifest = (location)=>{
|
|
83
|
+
try {
|
|
84
|
+
return readNpmManifest(location.manifestDir);
|
|
85
|
+
} catch (err) {
|
|
86
|
+
if (isErrorENOENT(err)) {
|
|
87
|
+
return undefined;
|
|
88
|
+
}
|
|
89
|
+
throw err;
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
const readPackageAnimationList = (location)=>{
|
|
93
|
+
const directoryContent = fs.readdirSync(location.manifestDir);
|
|
94
|
+
const animationPathList = [];
|
|
95
|
+
for (const entry of directoryContent){
|
|
96
|
+
if (entry.endsWith(ANIMATION_FILE_SUFFIX)) {
|
|
97
|
+
const animationPath = path.join(location.manifestDir, entry);
|
|
98
|
+
animationPathList.push(animationPath);
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
return animationPathList;
|
|
102
|
+
};
|
|
103
|
+
const getPackageReleasesDirectory = (location)=>path.join(location.path, "Releases");
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* Detects a published package from a path.
|
|
107
|
+
*
|
|
108
|
+
* Can return undefined if the package is not installed.
|
|
109
|
+
*
|
|
110
|
+
* @param {string} resolveBasePath
|
|
111
|
+
* @param {string} name
|
|
112
|
+
* @return {*} {(PublishedPackageLocation | undefined)}
|
|
113
|
+
*/ const detectPublishedPackageFromPath = (resolveBasePath, name)=>{
|
|
114
|
+
try {
|
|
115
|
+
const manifestPath = resolve.sync(name + "/package.json", {
|
|
116
|
+
basedir: resolveBasePath
|
|
117
|
+
});
|
|
118
|
+
const dir = path.dirname(manifestPath);
|
|
119
|
+
return {
|
|
120
|
+
_kind: "PublishedPackageLocation",
|
|
121
|
+
path: dir
|
|
122
|
+
};
|
|
123
|
+
} catch (err) {
|
|
124
|
+
return undefined;
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
const readPublishedPackageNpmManifest = (location)=>{
|
|
128
|
+
return readNpmManifest(location.path);
|
|
129
|
+
};
|
|
130
|
+
const readPublishedPackageCreatorManifest = (location)=>{
|
|
131
|
+
try {
|
|
132
|
+
const packageJsonPath = path.join(location.path, PACKAGE_FILE);
|
|
133
|
+
const packageJson = stripUtf8Bom(fs.readFileSync(packageJsonPath, {
|
|
134
|
+
encoding: "utf8"
|
|
135
|
+
}));
|
|
136
|
+
return JSON.parse(packageJson);
|
|
137
|
+
} catch (err) {
|
|
138
|
+
if (isErrorENOENT(err)) {
|
|
139
|
+
return undefined;
|
|
140
|
+
}
|
|
141
|
+
throw err;
|
|
142
|
+
}
|
|
143
|
+
};
|
|
144
|
+
const readPublishedPackageCreatorIndex = (location)=>{
|
|
145
|
+
try {
|
|
146
|
+
const packageJsonPath = path.join(location.path, INDEX_FILE);
|
|
147
|
+
const packageJson = stripUtf8Bom(fs.readFileSync(packageJsonPath, {
|
|
148
|
+
encoding: "utf8"
|
|
149
|
+
}));
|
|
150
|
+
const result = JSON.parse(packageJson);
|
|
151
|
+
return result;
|
|
152
|
+
} catch (err) {
|
|
153
|
+
if (isErrorENOENT(err)) {
|
|
154
|
+
return undefined;
|
|
155
|
+
}
|
|
156
|
+
throw err;
|
|
157
|
+
}
|
|
158
|
+
};
|
|
159
|
+
|
|
160
|
+
const readWorkspaceNpmManifest = (workspace)=>{
|
|
161
|
+
try {
|
|
162
|
+
return readNpmManifest(workspace.path);
|
|
163
|
+
} catch (err) {
|
|
164
|
+
if (isErrorENOENT(err)) {
|
|
165
|
+
throw new Error(`Expected a package.json file to exist in ${workspace.path}. See packager readme for instructions on how to create the package.json.`);
|
|
166
|
+
}
|
|
167
|
+
throw err;
|
|
168
|
+
}
|
|
169
|
+
};
|
|
170
|
+
const getWorkspaceOutputPath = (workspace)=>path.join(workspace.path, "bin");
|
|
171
|
+
|
|
172
|
+
// /**
|
|
173
|
+
// * Determines the implicit dependencies of a an actual data workspace package.
|
|
174
|
+
// *
|
|
175
|
+
// * An implicit dependency is a dependency that is installed for the workspace and has the same runtime environment (evaluator, interactor) as the package.
|
|
176
|
+
// *
|
|
177
|
+
// * @param {WorkspaceLocation} workspace
|
|
178
|
+
// * @param {CreatorPackage} creatorPackage
|
|
179
|
+
// * @returns {PublishedPackageLocation[]}
|
|
180
|
+
// */
|
|
181
|
+
// export const determinePackageImplicitDependencies = (
|
|
182
|
+
// workspace: WorkspaceLocation,
|
|
183
|
+
// creatorPackage: CreatorPackage,
|
|
184
|
+
// ): PublishedPackageLocation[] => {
|
|
185
|
+
// const libraries = determineWorkspaceIGLibraries(workspace);
|
|
186
|
+
// const results: PublishedPackageLocation[] = [];
|
|
187
|
+
// for (const librarylocation of libraries) {
|
|
188
|
+
// const libraryManifest =
|
|
189
|
+
// readPublishedPackageCreatorManifest(librarylocation);
|
|
190
|
+
// if (
|
|
191
|
+
// libraryManifest !== undefined &&
|
|
192
|
+
// (libraryManifest.Type === "Mixed" ||
|
|
193
|
+
// libraryManifest.RunTime === creatorPackage.RunTime)
|
|
194
|
+
// ) {
|
|
195
|
+
// results.push(librarylocation);
|
|
196
|
+
// }
|
|
197
|
+
// }
|
|
198
|
+
// return results;
|
|
199
|
+
// };
|
|
200
|
+
/**
|
|
201
|
+
* Recursively determines all installed ig libraries for a workspace.
|
|
202
|
+
*
|
|
203
|
+
* @param {WorkspaceLocation} workspace
|
|
204
|
+
* @returns {PublishedPackageLocation[]}
|
|
205
|
+
*/ const determineWorkspaceIGLibraries = (workspace)=>{
|
|
206
|
+
const manifest = readWorkspaceNpmManifest(workspace);
|
|
207
|
+
const libraries = collectIGLibraries(workspace, manifest);
|
|
208
|
+
const results = new Map();
|
|
209
|
+
for (const location of libraries){
|
|
210
|
+
const manifest = readPublishedPackageNpmManifest(location);
|
|
211
|
+
if (!results.has(manifest.name)) {
|
|
212
|
+
results.set(manifest.name, location);
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
return Array.from(results.values());
|
|
216
|
+
};
|
|
217
|
+
const collectIGLibraries = (workspace, manifest)=>{
|
|
218
|
+
if (!manifest.dependencies) {
|
|
219
|
+
return [];
|
|
220
|
+
}
|
|
221
|
+
const runtimeDependencies = Object.getOwnPropertyNames(manifest.dependencies);
|
|
222
|
+
const result = [];
|
|
223
|
+
for (const runtimeDependency of runtimeDependencies){
|
|
224
|
+
var _runtimeManifest_ig;
|
|
225
|
+
const location = detectPublishedPackageFromPath(workspace.path, runtimeDependency);
|
|
226
|
+
if (location === undefined) {
|
|
227
|
+
continue;
|
|
228
|
+
}
|
|
229
|
+
const runtimeManifest = readPublishedPackageNpmManifest(location);
|
|
230
|
+
// packages need to explicitly be marked as ig scriptingLibraries
|
|
231
|
+
if ((_runtimeManifest_ig = runtimeManifest.ig) == null ? void 0 : _runtimeManifest_ig.scriptingLibrary) {
|
|
232
|
+
result.push(location);
|
|
233
|
+
result.push(...collectIGLibraries(workspace, runtimeManifest));
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
return result;
|
|
237
|
+
};
|
|
238
|
+
|
|
239
|
+
const readStringFromFile = (filePath)=>fs.readFileSync(filePath, {
|
|
240
|
+
encoding: "utf8"
|
|
241
|
+
});
|
|
242
|
+
const readStringFromFileOrUndefined = (filePath)=>{
|
|
243
|
+
try {
|
|
244
|
+
return readStringFromFile(filePath);
|
|
245
|
+
} catch (err) {
|
|
246
|
+
if (!isErrorENOENT(err)) {
|
|
247
|
+
throw err;
|
|
248
|
+
}
|
|
249
|
+
return undefined;
|
|
250
|
+
}
|
|
251
|
+
};
|
|
252
|
+
|
|
253
|
+
const logPackageMessage = (name, step, index, total)=>{
|
|
254
|
+
const numLength = total === undefined ? undefined : total.toString().length;
|
|
255
|
+
const indexString = total === undefined || total < 2 ? "" : `${index.toString().padStart(numLength, "0")}/${total} `;
|
|
256
|
+
const identifierString = `${indexString}${name.padEnd(15)}`;
|
|
257
|
+
console.log(`${identifierString} >> ${step}`);
|
|
258
|
+
};
|
|
259
|
+
|
|
260
|
+
const getPackageTypescriptFiles = (location)=>glob.sync("**/*.ts", {
|
|
261
|
+
absolute: true,
|
|
262
|
+
cwd: location.scriptsDir,
|
|
263
|
+
ignore: "node_modules/**/*"
|
|
264
|
+
});
|
|
265
|
+
|
|
266
|
+
var CreatorWorkspaceGeometryFileType;
|
|
267
|
+
(function(CreatorWorkspaceGeometryFileType) {
|
|
268
|
+
CreatorWorkspaceGeometryFileType["StandardObj"] = "standard.obj";
|
|
269
|
+
CreatorWorkspaceGeometryFileType["StandardCtm"] = "standard.ctm";
|
|
270
|
+
CreatorWorkspaceGeometryFileType["StandardNormals"] = "normals_std.png";
|
|
271
|
+
CreatorWorkspaceGeometryFileType["DeformationGlb"] = "deformation.glb";
|
|
272
|
+
})(CreatorWorkspaceGeometryFileType || (CreatorWorkspaceGeometryFileType = {}));
|
|
273
|
+
|
|
274
|
+
const PLUGIN_ID = "0feba3a0-b6d1-11e6-9598-0800200c9a66";
|
|
275
|
+
/**
|
|
276
|
+
* Starts an IG.Asset.Server session and returns the sessionId
|
|
277
|
+
*
|
|
278
|
+
* @param {SessionStartParams} params
|
|
279
|
+
* @returns
|
|
280
|
+
*/ const startSession = async ({ url , authentication , ...params })=>{
|
|
281
|
+
const payload = {
|
|
282
|
+
...params,
|
|
283
|
+
user: undefined,
|
|
284
|
+
password: undefined,
|
|
285
|
+
license: undefined,
|
|
286
|
+
plugin: PLUGIN_ID
|
|
287
|
+
};
|
|
288
|
+
if (authentication.type === "credentials") {
|
|
289
|
+
payload.user = authentication.username;
|
|
290
|
+
payload.password = authentication.password;
|
|
291
|
+
} else if (authentication.type === "license") {
|
|
292
|
+
payload.license = authentication.license;
|
|
293
|
+
}
|
|
294
|
+
const { data: { session: sessionId , state , response } } = await axios.post(`Session/Start2`, JSON.stringify(payload), {
|
|
295
|
+
baseURL: url
|
|
296
|
+
});
|
|
297
|
+
if (state !== "SUCCESS") {
|
|
298
|
+
let message = `Could not start session. IG.Asset.Server responded with ${state}`;
|
|
299
|
+
if (response) {
|
|
300
|
+
message += `: ${response}`;
|
|
301
|
+
}
|
|
302
|
+
throw new Error(message);
|
|
303
|
+
}
|
|
304
|
+
return {
|
|
305
|
+
_kind: "AssetService",
|
|
306
|
+
url,
|
|
307
|
+
sessionId,
|
|
308
|
+
domain: params.domain,
|
|
309
|
+
subDomain: params.subDomain
|
|
310
|
+
};
|
|
311
|
+
};
|
|
312
|
+
const closeSession = async (session)=>{
|
|
313
|
+
await axios.get(`Session/Close/${session.sessionId}`, {
|
|
314
|
+
baseURL: session.url
|
|
315
|
+
});
|
|
316
|
+
};
|
|
317
|
+
const uploadPackage = async (session, { name , version }, zipFilePath)=>{
|
|
318
|
+
try {
|
|
319
|
+
await uploadPackageToUrl(session.url, `UploadPackage/${session.sessionId}/${name}_${version}`, zipFilePath);
|
|
320
|
+
} catch (err) {
|
|
321
|
+
await uploadPackageToUrl(session.url, `UploadPackage/${session.sessionId}/${name}_${version}/`, zipFilePath);
|
|
322
|
+
}
|
|
323
|
+
};
|
|
324
|
+
const uploadPackageToUrl = async (url, path, zipFilePath)=>{
|
|
325
|
+
const { data , status } = await axios.post(path, fs.createReadStream(zipFilePath), {
|
|
326
|
+
baseURL: url
|
|
327
|
+
});
|
|
328
|
+
let objectBody;
|
|
329
|
+
if (typeof data === "string") {
|
|
330
|
+
try {
|
|
331
|
+
objectBody = JSON.parse(data);
|
|
332
|
+
} catch (err) {}
|
|
333
|
+
} else if (typeof data === "object") {
|
|
334
|
+
objectBody = data;
|
|
335
|
+
}
|
|
336
|
+
if (objectBody !== undefined) {
|
|
337
|
+
if ("state" in objectBody && objectBody.state !== "SUCCESS") {
|
|
338
|
+
throw new Error(objectBody.response ?? objectBody.state);
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
if (status >= 400) {
|
|
342
|
+
if (objectBody !== undefined) {
|
|
343
|
+
let text_1 = "";
|
|
344
|
+
for(const key in objectBody){
|
|
345
|
+
text_1 += key + ": \n";
|
|
346
|
+
if (typeof objectBody[key] === "object") {
|
|
347
|
+
text_1 += JSON.stringify(objectBody[key], undefined, 2);
|
|
348
|
+
} else {
|
|
349
|
+
text_1 += objectBody[key];
|
|
350
|
+
}
|
|
351
|
+
text_1 += "\n\n";
|
|
352
|
+
}
|
|
353
|
+
throw new Error(text_1);
|
|
354
|
+
}
|
|
355
|
+
throw new Error(data);
|
|
356
|
+
}
|
|
357
|
+
return data;
|
|
358
|
+
};
|
|
359
|
+
const getExistingPackages = async (session)=>{
|
|
360
|
+
const { data } = await axios.get(`Script/GetInformation/${session.sessionId}`, {
|
|
361
|
+
baseURL: session.url,
|
|
362
|
+
validateStatus: (status)=>status === 404 || status === 200
|
|
363
|
+
}).catch((err)=>{
|
|
364
|
+
throw new Error(`Failed to get existing packages: ${err.message}`);
|
|
365
|
+
});
|
|
366
|
+
return data;
|
|
367
|
+
};
|
|
368
|
+
|
|
369
|
+
const tryReadTsConfig = (location)=>{
|
|
370
|
+
const { config } = ts.readConfigFile(path.join(location.scriptsDir, "tsconfig.json"), (path)=>{
|
|
371
|
+
try {
|
|
372
|
+
return fs.readFileSync(path, "utf8");
|
|
373
|
+
} catch {
|
|
374
|
+
return undefined;
|
|
375
|
+
}
|
|
376
|
+
});
|
|
377
|
+
return config;
|
|
378
|
+
};
|
|
379
|
+
const build = async (location, outputDir)=>{
|
|
380
|
+
const config = tryReadTsConfig(location);
|
|
381
|
+
config.compilerOptions.lib = [
|
|
382
|
+
"es5",
|
|
383
|
+
"dom"
|
|
384
|
+
];
|
|
385
|
+
const result = ts.convertCompilerOptionsFromJson(config.compilerOptions, location.scriptsDir);
|
|
386
|
+
const compilerOptions = {
|
|
387
|
+
...result.options,
|
|
388
|
+
removeComments: false,
|
|
389
|
+
declaration: true,
|
|
390
|
+
sourceMap: false,
|
|
391
|
+
// We don't use tsc to actually emit the files, but we still need to set the correct
|
|
392
|
+
// output directory so the compiler can rewrite the `reference path` directives.
|
|
393
|
+
outFile: path.join(outputDir, "out.js"),
|
|
394
|
+
target: ts.ScriptTarget.ES5,
|
|
395
|
+
noEmitOnError: true
|
|
396
|
+
};
|
|
397
|
+
const host = ts.createCompilerHost(compilerOptions);
|
|
398
|
+
host.getCurrentDirectory = ()=>location.scriptsDir;
|
|
399
|
+
let js;
|
|
400
|
+
let definitions;
|
|
401
|
+
host.writeFile = (fileName, data, writeByteOrderMark)=>{
|
|
402
|
+
if (fileName.endsWith(".js")) {
|
|
403
|
+
js = data;
|
|
404
|
+
} else if (fileName.endsWith(".d.ts")) {
|
|
405
|
+
definitions = data;
|
|
406
|
+
}
|
|
407
|
+
};
|
|
408
|
+
const files = getPackageTypescriptFiles(location);
|
|
409
|
+
if (files.length === 0) {
|
|
410
|
+
throw new Error(`Expected typescript files to exist when building a package. Packages only consisting of animation jsons do not need to be built.`);
|
|
411
|
+
}
|
|
412
|
+
const programOptions = {
|
|
413
|
+
rootNames: files,
|
|
414
|
+
options: compilerOptions,
|
|
415
|
+
host
|
|
416
|
+
};
|
|
417
|
+
const program = ts.createProgram(programOptions);
|
|
418
|
+
const emitResult = program.emit();
|
|
419
|
+
const allDiagnostics = ts.getPreEmitDiagnostics(program);
|
|
420
|
+
if (!emitResult.emitSkipped) {
|
|
421
|
+
if (allDiagnostics.length > 0) {
|
|
422
|
+
console.log(allDiagnostics.map(createErrorMessage).join("\n"));
|
|
423
|
+
}
|
|
424
|
+
if (js === undefined || definitions === undefined) {
|
|
425
|
+
throw new Error(`Unexpected: no js or definitions were created`);
|
|
426
|
+
}
|
|
427
|
+
return {
|
|
428
|
+
js,
|
|
429
|
+
definitions
|
|
430
|
+
};
|
|
431
|
+
}
|
|
432
|
+
const error = allDiagnostics.map(createErrorMessage).join("\n");
|
|
433
|
+
throw new Error(error);
|
|
434
|
+
};
|
|
435
|
+
const createErrorMessage = (diagnostic)=>{
|
|
436
|
+
if (!diagnostic.file) {
|
|
437
|
+
return `${ts.flattenDiagnosticMessageText(diagnostic.messageText, "\n")}`;
|
|
438
|
+
}
|
|
439
|
+
const { line , character } = diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start);
|
|
440
|
+
const message = ts.flattenDiagnosticMessageText(diagnostic.messageText, "\n");
|
|
441
|
+
return `${diagnostic.file.fileName} (${line + 1},${character + 1}): ${message}`;
|
|
442
|
+
};
|
|
443
|
+
|
|
444
|
+
const generateDocs = async (location, declarationFile, outFolder, name)=>{
|
|
445
|
+
const app = new typedoc.Application();
|
|
446
|
+
const mediaDir = path.join(location.manifestDir, "Media");
|
|
447
|
+
app.bootstrap({
|
|
448
|
+
entryPoints: [
|
|
449
|
+
declarationFile
|
|
450
|
+
],
|
|
451
|
+
media: mediaDir,
|
|
452
|
+
out: outFolder,
|
|
453
|
+
tsconfig: path.join(location.scriptsDir, "tsconfig.json"),
|
|
454
|
+
skipErrorChecking: true
|
|
455
|
+
});
|
|
456
|
+
app.options.setCompilerOptions([
|
|
457
|
+
declarationFile
|
|
458
|
+
], {
|
|
459
|
+
target: ts.ScriptTarget.ES5
|
|
460
|
+
}, undefined);
|
|
461
|
+
app.options.setValue("name", name);
|
|
462
|
+
const [readmePath] = glob.sync("**/readme.md", {
|
|
463
|
+
absolute: true,
|
|
464
|
+
cwd: location.manifestDir
|
|
465
|
+
});
|
|
466
|
+
if (readmePath) {
|
|
467
|
+
app.options.setValue("readme", readmePath);
|
|
468
|
+
}
|
|
469
|
+
const project = app.convert();
|
|
470
|
+
if (project) {
|
|
471
|
+
await app.generateDocs(project, outFolder);
|
|
472
|
+
}
|
|
473
|
+
};
|
|
474
|
+
|
|
475
|
+
// Stolen from ig.tools.core
|
|
476
|
+
const toposort = (packages)=>{
|
|
477
|
+
const queue = Object.getOwnPropertyNames(packages);
|
|
478
|
+
const result = [];
|
|
479
|
+
let index = 0;
|
|
480
|
+
while(queue.length > 0){
|
|
481
|
+
if (index >= queue.length) {
|
|
482
|
+
throw new Error("Packages can not have cyclic dependencies");
|
|
483
|
+
}
|
|
484
|
+
const queueEntry = queue[index];
|
|
485
|
+
const dependencies = packages[queueEntry];
|
|
486
|
+
const dependencyQueued = dependencies.some((dependency)=>queue.includes(dependency));
|
|
487
|
+
if (dependencyQueued) {
|
|
488
|
+
index++;
|
|
489
|
+
continue;
|
|
490
|
+
}
|
|
491
|
+
queue.splice(index, 1);
|
|
492
|
+
index = 0;
|
|
493
|
+
result.push(queueEntry);
|
|
494
|
+
}
|
|
495
|
+
return result;
|
|
496
|
+
};
|
|
497
|
+
|
|
498
|
+
const buildFolders = async (options)=>{
|
|
499
|
+
if (options.outDir !== undefined && options.clean) {
|
|
500
|
+
fs.rmSync(options.outDir, {
|
|
501
|
+
recursive: true
|
|
502
|
+
});
|
|
503
|
+
}
|
|
504
|
+
const workspace = options.workspace;
|
|
505
|
+
const folders = options.packages;
|
|
506
|
+
let sortedPackages = sortPackagesByBuildOrder(folders);
|
|
507
|
+
if (options.skipPackagesWithoutTsFiles) {
|
|
508
|
+
sortedPackages = sortedPackages.filter((location)=>getPackageTypescriptFiles(location).length > 0);
|
|
509
|
+
}
|
|
510
|
+
let index = 1;
|
|
511
|
+
for (const location of sortedPackages){
|
|
512
|
+
ensureTsConfig(location);
|
|
513
|
+
const data = readPackageCreatorManifest(location);
|
|
514
|
+
const logStep = (step)=>logPackageMessage(data.Package, step, index, folders.length);
|
|
515
|
+
logStep("Compiling typescript to javascript");
|
|
516
|
+
const outputDirectory = options.outDir || location.scriptsDir;
|
|
517
|
+
fs.mkdirSync(outputDirectory, {
|
|
518
|
+
recursive: true
|
|
519
|
+
});
|
|
520
|
+
const buildResult = await build(location, outputDirectory);
|
|
521
|
+
const banner = options.banner ? createBannerComment(options.banner) : undefined;
|
|
522
|
+
if (banner) {
|
|
523
|
+
buildResult.js = banner + "\n" + buildResult.js;
|
|
524
|
+
buildResult.definitions = banner + "\n" + buildResult.definitions;
|
|
525
|
+
}
|
|
526
|
+
fs.writeFileSync(path.join(outputDirectory, `${data.Package}.js`), buildResult.js, {
|
|
527
|
+
encoding: "utf8"
|
|
528
|
+
});
|
|
529
|
+
fs.writeFileSync(path.join(outputDirectory, `${data.Package}.d.ts`), buildResult.definitions, {
|
|
530
|
+
encoding: "utf8"
|
|
531
|
+
});
|
|
532
|
+
if (options.minimize) {
|
|
533
|
+
const minifyResult = await terser.minify(buildResult.js, {
|
|
534
|
+
ecma: 5
|
|
535
|
+
});
|
|
536
|
+
const minifiedPath = path.join(outputDirectory, `${data.Package}.min.js`);
|
|
537
|
+
fs.writeFileSync(minifiedPath, minifyResult.code, {
|
|
538
|
+
encoding: "utf8"
|
|
539
|
+
});
|
|
540
|
+
}
|
|
541
|
+
if (location.path.includes("Basics")) {
|
|
542
|
+
fs.mkdirSync(path.join(workspace.path, "lib"), {
|
|
543
|
+
recursive: true
|
|
544
|
+
});
|
|
545
|
+
logStep("Copying basics definition file to the lib folder");
|
|
546
|
+
fs.writeFileSync(path.join(workspace.path, "lib", `${data.Package}.d.ts`), buildResult.definitions, {
|
|
547
|
+
encoding: "utf8"
|
|
548
|
+
});
|
|
549
|
+
}
|
|
550
|
+
if (options.docs) {
|
|
551
|
+
logStep("Generating typedoc documentation");
|
|
552
|
+
await generateDocs(location, path.join(outputDirectory, `${data.Package}.d.ts`), path.join(workspace.path, "docs", data.Package), data.Package);
|
|
553
|
+
}
|
|
554
|
+
index++;
|
|
555
|
+
}
|
|
556
|
+
};
|
|
557
|
+
const ensureTsConfig = (location)=>{
|
|
558
|
+
const tsconfigPath = path.join(location.scriptsDir, "tsconfig.json");
|
|
559
|
+
if (!fs.existsSync(tsconfigPath)) {
|
|
560
|
+
const content = {};
|
|
561
|
+
applyTsConfigOption(content);
|
|
562
|
+
fs.writeFileSync(tsconfigPath, JSON.stringify(content, undefined, "\t"), "utf8");
|
|
563
|
+
} else {
|
|
564
|
+
const content = JSON.parse(fs.readFileSync(tsconfigPath, "utf8"));
|
|
565
|
+
applyTsConfigOption(content);
|
|
566
|
+
fs.writeFileSync(tsconfigPath, JSON.stringify(content, undefined, "\t"), "utf8");
|
|
567
|
+
}
|
|
568
|
+
};
|
|
569
|
+
const applyTsConfigOption = (data)=>{
|
|
570
|
+
data.compilerOptions = data.compilerOptions ?? {};
|
|
571
|
+
data.compilerOptions.target = "es5";
|
|
572
|
+
data.compilerOptions.lib = [
|
|
573
|
+
"es5",
|
|
574
|
+
"dom"
|
|
575
|
+
];
|
|
576
|
+
};
|
|
577
|
+
const sortPackagesByBuildOrder = (folders)=>{
|
|
578
|
+
const packages = Array.from(folders).reduce((acc, location)=>{
|
|
579
|
+
const data = readPackageNpmManifest(location);
|
|
580
|
+
if (data !== undefined) {
|
|
581
|
+
acc[data.name] = {
|
|
582
|
+
data,
|
|
583
|
+
location
|
|
584
|
+
};
|
|
585
|
+
} else {
|
|
586
|
+
acc[location.path] = {
|
|
587
|
+
data: undefined,
|
|
588
|
+
location
|
|
589
|
+
};
|
|
590
|
+
}
|
|
591
|
+
return acc;
|
|
592
|
+
}, {});
|
|
593
|
+
const packageDependencies = Object.getOwnPropertyNames(packages).reduce((acc, packageName)=>{
|
|
594
|
+
const packageData = packages[packageName];
|
|
595
|
+
if (packageData.data === undefined) {
|
|
596
|
+
acc[packageName] = [];
|
|
597
|
+
} else {
|
|
598
|
+
acc[packageName] = Object.getOwnPropertyNames({
|
|
599
|
+
...packageData.data.devDependencies,
|
|
600
|
+
...packageData.data.dependencies,
|
|
601
|
+
...packageData.data.peerDependencies
|
|
602
|
+
}).filter((packageName)=>packages[packageName] !== undefined);
|
|
603
|
+
}
|
|
604
|
+
return acc;
|
|
605
|
+
}, {});
|
|
606
|
+
const sortedPackages = toposort(packageDependencies);
|
|
607
|
+
const result = [];
|
|
608
|
+
for (const packageName of sortedPackages){
|
|
609
|
+
const location = packages[packageName].location;
|
|
610
|
+
if (readPackageCreatorManifest(location).Package.endsWith(".Basics")) {
|
|
611
|
+
result.unshift(location);
|
|
612
|
+
} else {
|
|
613
|
+
result.push(location);
|
|
614
|
+
}
|
|
615
|
+
}
|
|
616
|
+
return result;
|
|
617
|
+
};
|
|
618
|
+
const createBannerComment = (banner)=>{
|
|
619
|
+
const bannerParts = [];
|
|
620
|
+
if (banner.text) {
|
|
621
|
+
bannerParts.push(" * " + banner.text);
|
|
622
|
+
}
|
|
623
|
+
{
|
|
624
|
+
const details = [];
|
|
625
|
+
if (banner.version) {
|
|
626
|
+
details.push(`Version: ${banner.version}`);
|
|
627
|
+
}
|
|
628
|
+
if (banner.commit) {
|
|
629
|
+
if (banner.commitDirty) {
|
|
630
|
+
details.push(`Commit: ${banner.commit} (dirty)`);
|
|
631
|
+
} else {
|
|
632
|
+
details.push(`Commit: ${banner.commit}`);
|
|
633
|
+
}
|
|
634
|
+
}
|
|
635
|
+
if (banner.date) {
|
|
636
|
+
details.push(`Date: ${banner.date.toISOString()}`);
|
|
637
|
+
}
|
|
638
|
+
const detailsText = details.map((line)=>` * ${line}`).join("\n");
|
|
639
|
+
if (detailsText) {
|
|
640
|
+
bannerParts.push(detailsText);
|
|
641
|
+
}
|
|
642
|
+
}
|
|
643
|
+
const bannerText = bannerParts.join("\n\n");
|
|
644
|
+
if (bannerText) {
|
|
645
|
+
return `/*
|
|
646
|
+
${bannerText}
|
|
647
|
+
*
|
|
648
|
+
* @preserve
|
|
649
|
+
*/`;
|
|
650
|
+
}
|
|
651
|
+
return undefined;
|
|
652
|
+
};
|
|
653
|
+
|
|
654
|
+
const getVersionInformationFromGit = async (workspaceLocation, packageLocation)=>{
|
|
655
|
+
try {
|
|
656
|
+
var _log_latest, _log_latest1;
|
|
657
|
+
const git = simpleGit({
|
|
658
|
+
baseDir: workspaceLocation.path
|
|
659
|
+
});
|
|
660
|
+
// check wether the files for a folder are changed
|
|
661
|
+
// if so, mark as dirty
|
|
662
|
+
const diff = await git.diffSummary();
|
|
663
|
+
const dirty = diff.files.some((file)=>{
|
|
664
|
+
if (file.file.toLowerCase().includes("releases") || file.file.toLowerCase().endsWith("version.ts") || file.file.toLowerCase().endsWith("package.json")) {
|
|
665
|
+
return false;
|
|
666
|
+
}
|
|
667
|
+
const fullPath = path.resolve(workspaceLocation.path, file.file);
|
|
668
|
+
const relativePath = path.relative(packageLocation.path, fullPath);
|
|
669
|
+
return !relativePath.startsWith("..");
|
|
670
|
+
});
|
|
671
|
+
const log = await git.log({
|
|
672
|
+
maxCount: 1
|
|
673
|
+
});
|
|
674
|
+
const commit = !((_log_latest = log.latest) == null ? void 0 : _log_latest.hash) ? undefined : log.latest.hash.substring(0, 7);
|
|
675
|
+
return {
|
|
676
|
+
commit,
|
|
677
|
+
dirty,
|
|
678
|
+
commitDate: (_log_latest1 = log.latest) == null ? void 0 : _log_latest1.date
|
|
679
|
+
};
|
|
680
|
+
} catch (err) {
|
|
681
|
+
return {};
|
|
682
|
+
}
|
|
683
|
+
};
|
|
684
|
+
|
|
685
|
+
const getWorkspaceBannerText = (manifest)=>{
|
|
686
|
+
var _manifest_packager;
|
|
687
|
+
let bannerText = manifest == null ? void 0 : (_manifest_packager = manifest.packager) == null ? void 0 : _manifest_packager.banner;
|
|
688
|
+
if (bannerText) {
|
|
689
|
+
const match = bannerText.match(/Copyright \(C\) (\d+)( ?- ?(\d+))?/);
|
|
690
|
+
if (match !== null) {
|
|
691
|
+
const startYear = parseInt(match[1]);
|
|
692
|
+
const endYear = new Date().getFullYear();
|
|
693
|
+
if (startYear !== endYear) {
|
|
694
|
+
bannerText = bannerText.replace(match[0], `Copyright (C) ${startYear} - ${endYear}`);
|
|
695
|
+
} else {
|
|
696
|
+
bannerText = bannerText.replace(match[0], `Copyright (C) ${startYear}`);
|
|
697
|
+
}
|
|
698
|
+
}
|
|
699
|
+
}
|
|
700
|
+
return bannerText;
|
|
701
|
+
};
|
|
702
|
+
|
|
703
|
+
// Stolen from ig.tools.core
|
|
704
|
+
class PackageVersion {
|
|
705
|
+
static #_ = (()=>{
|
|
706
|
+
// https://regex101.com/r/90PEY9/1
|
|
707
|
+
this.fullTextMatcher = /(\d+)(\.(\d+)(\.(\d+)(\.(\d+))?(-([^\.]+)\.(\d+))?)?)?/;
|
|
708
|
+
})();
|
|
709
|
+
static #_1 = (()=>{
|
|
710
|
+
this.lineMatcher = /^(\d+)(\.(\d+)(\.(\d+)(\.(\d+))?(-([^\.]+)\.(\d+))?)?)?$/;
|
|
711
|
+
})();
|
|
712
|
+
static extractFromText(input, description) {
|
|
713
|
+
if (input === undefined) {
|
|
714
|
+
throw new Error(`Can not parse version from undefined`);
|
|
715
|
+
}
|
|
716
|
+
const match = input.match(PackageVersion.fullTextMatcher);
|
|
717
|
+
if (!match) {
|
|
718
|
+
throw new Error(`Could not extract a version from input: ${input}`);
|
|
719
|
+
}
|
|
720
|
+
return PackageVersion.fromMatch(match, description);
|
|
721
|
+
}
|
|
722
|
+
static extractFromLine(input, description) {
|
|
723
|
+
if (input === undefined) {
|
|
724
|
+
throw new Error(`Can not parse version from undefined`);
|
|
725
|
+
}
|
|
726
|
+
const match = input.match(PackageVersion.lineMatcher);
|
|
727
|
+
if (!match) {
|
|
728
|
+
throw new Error(`Could not parse version from input: ${input}`);
|
|
729
|
+
}
|
|
730
|
+
return PackageVersion.fromMatch(match, description);
|
|
731
|
+
}
|
|
732
|
+
static equals(a, b, checkPrerelease = false) {
|
|
733
|
+
if (a.major !== b.major || a.minor !== b.minor || a.patch !== b.patch) {
|
|
734
|
+
return false;
|
|
735
|
+
}
|
|
736
|
+
if (checkPrerelease === false) {
|
|
737
|
+
return true;
|
|
738
|
+
}
|
|
739
|
+
if (a.preRelease === b.preRelease) {
|
|
740
|
+
return true;
|
|
741
|
+
}
|
|
742
|
+
if (a.preRelease === undefined || b.preRelease === undefined) {
|
|
743
|
+
return false;
|
|
744
|
+
}
|
|
745
|
+
return a.preRelease.type === b.preRelease.type && a.preRelease.version === b.preRelease.version;
|
|
746
|
+
}
|
|
747
|
+
static fromMatch([, major, , minor = "0", , patch = "0", , build, , preReleaseType, preReleaseNumber], description) {
|
|
748
|
+
let preRelease = undefined;
|
|
749
|
+
let buildNumber = 100;
|
|
750
|
+
if (preReleaseType && preReleaseNumber) {
|
|
751
|
+
preRelease = {
|
|
752
|
+
type: preReleaseType,
|
|
753
|
+
version: parseInt(preReleaseNumber)
|
|
754
|
+
};
|
|
755
|
+
}
|
|
756
|
+
if (build) {
|
|
757
|
+
buildNumber = Number(build);
|
|
758
|
+
} else if (description) {
|
|
759
|
+
const descriptionMatch = description.match(/(\d+)\)$/);
|
|
760
|
+
if (descriptionMatch) {
|
|
761
|
+
buildNumber = parseInt(descriptionMatch[1]);
|
|
762
|
+
}
|
|
763
|
+
}
|
|
764
|
+
return new PackageVersion(parseInt(major), parseInt(minor), parseInt(patch), preRelease, buildNumber);
|
|
765
|
+
}
|
|
766
|
+
static sort(a, b, ascending = true) {
|
|
767
|
+
const createSortResult = (a, b)=>ascending ? a - b : b - a;
|
|
768
|
+
if (a.major !== b.major) {
|
|
769
|
+
return createSortResult(a.major, b.major);
|
|
770
|
+
}
|
|
771
|
+
if (a.minor !== b.minor) {
|
|
772
|
+
return createSortResult(a.minor, b.minor);
|
|
773
|
+
}
|
|
774
|
+
if (a.patch !== b.patch) {
|
|
775
|
+
return createSortResult(a.patch, b.patch);
|
|
776
|
+
}
|
|
777
|
+
return createSortResult(a.preRelease ? a.preRelease.version : 0, b.preRelease ? b.preRelease.version : 0);
|
|
778
|
+
}
|
|
779
|
+
static toNumber(version) {
|
|
780
|
+
return ((version.major * 1000 + version.minor) * 1000 + version.patch) * 1000 + version.buildNumber;
|
|
781
|
+
}
|
|
782
|
+
constructor(major, minor, patch, preRelease, buildNumber){
|
|
783
|
+
this.major = major;
|
|
784
|
+
this.minor = minor;
|
|
785
|
+
this.patch = patch;
|
|
786
|
+
this.preRelease = preRelease;
|
|
787
|
+
this.buildNumber = buildNumber;
|
|
788
|
+
}
|
|
789
|
+
isPreRelease() {
|
|
790
|
+
return this.preRelease !== undefined;
|
|
791
|
+
}
|
|
792
|
+
clone() {
|
|
793
|
+
return new PackageVersion(this.major, this.minor, this.patch, this.preRelease ? {
|
|
794
|
+
...this.preRelease
|
|
795
|
+
} : undefined, this.buildNumber);
|
|
796
|
+
}
|
|
797
|
+
incrementMajor() {
|
|
798
|
+
this.preRelease = undefined;
|
|
799
|
+
this.patch = 0;
|
|
800
|
+
this.minor = 0;
|
|
801
|
+
this.major++;
|
|
802
|
+
}
|
|
803
|
+
incrementMinor() {
|
|
804
|
+
this.preRelease = undefined;
|
|
805
|
+
this.patch = 0;
|
|
806
|
+
this.minor++;
|
|
807
|
+
}
|
|
808
|
+
incrementPatch() {
|
|
809
|
+
this.preRelease = undefined;
|
|
810
|
+
this.patch++;
|
|
811
|
+
}
|
|
812
|
+
createPreRelease(type) {
|
|
813
|
+
if (!this.preRelease) {
|
|
814
|
+
this.buildNumber = 1;
|
|
815
|
+
} else {
|
|
816
|
+
this.buildNumber++;
|
|
817
|
+
}
|
|
818
|
+
if (this.preRelease && type === this.preRelease.type) {
|
|
819
|
+
this.preRelease.version++;
|
|
820
|
+
return;
|
|
821
|
+
}
|
|
822
|
+
this.preRelease = {
|
|
823
|
+
version: 0,
|
|
824
|
+
type
|
|
825
|
+
};
|
|
826
|
+
}
|
|
827
|
+
createRelease() {
|
|
828
|
+
this.preRelease = undefined;
|
|
829
|
+
this.buildNumber = 100;
|
|
830
|
+
}
|
|
831
|
+
toVersionString({ buildNumber } = {}) {
|
|
832
|
+
let version = [
|
|
833
|
+
this.major,
|
|
834
|
+
this.minor,
|
|
835
|
+
this.patch
|
|
836
|
+
].join(".");
|
|
837
|
+
if (buildNumber) {
|
|
838
|
+
version += "." + this.buildNumber;
|
|
839
|
+
}
|
|
840
|
+
if (this.preRelease) {
|
|
841
|
+
version += `-${this.preRelease.type}.${this.preRelease.version}`;
|
|
842
|
+
}
|
|
843
|
+
return version;
|
|
844
|
+
}
|
|
845
|
+
toDescriptionString(packageName) {
|
|
846
|
+
const base = [
|
|
847
|
+
this.major,
|
|
848
|
+
this.minor,
|
|
849
|
+
this.patch
|
|
850
|
+
].join(".");
|
|
851
|
+
const parts = [
|
|
852
|
+
packageName,
|
|
853
|
+
base
|
|
854
|
+
];
|
|
855
|
+
if (this.preRelease) {
|
|
856
|
+
parts.push(upperCaseFirst(this.preRelease.type));
|
|
857
|
+
parts.push(this.preRelease.version);
|
|
858
|
+
}
|
|
859
|
+
parts.push(`(${base}.${this.buildNumber})`);
|
|
860
|
+
return parts.join(" ");
|
|
861
|
+
}
|
|
862
|
+
/**
|
|
863
|
+
* Determines wether the version is lesser than the input version
|
|
864
|
+
*
|
|
865
|
+
* @param {PackageVersion} version
|
|
866
|
+
* @returns
|
|
867
|
+
*/ isLesserThan(version) {
|
|
868
|
+
return PackageVersion.toNumber(this) < PackageVersion.toNumber(version);
|
|
869
|
+
}
|
|
870
|
+
/**
|
|
871
|
+
* Determines wether the version is greater than the input version
|
|
872
|
+
*
|
|
873
|
+
* @param {PackageVersion} version
|
|
874
|
+
* @returns
|
|
875
|
+
*/ isGreaterThan(version) {
|
|
876
|
+
return PackageVersion.toNumber(this) > PackageVersion.toNumber(version);
|
|
877
|
+
}
|
|
878
|
+
}
|
|
879
|
+
const upperCaseFirst = (input)=>{
|
|
880
|
+
return input.slice(0, 1).toUpperCase() + input.slice(1);
|
|
881
|
+
};
|
|
882
|
+
|
|
883
|
+
const parseVersionFromString = (input)=>{
|
|
884
|
+
if (input === undefined) {
|
|
885
|
+
throw new Error(`Can not parse version from undefined`);
|
|
886
|
+
}
|
|
887
|
+
let match;
|
|
888
|
+
let major;
|
|
889
|
+
let minor;
|
|
890
|
+
let patch;
|
|
891
|
+
let build;
|
|
892
|
+
let preReleaseType;
|
|
893
|
+
let preReleaseNumber;
|
|
894
|
+
if (// first try to find a full match with build number
|
|
895
|
+
(match = input.match(/(\d+)\.(\d+)\.(\d+)\.(\d+)(-([^\.]+)\.(\d+))?/)) !== null) {
|
|
896
|
+
[, major, minor, patch, build, preReleaseType, preReleaseNumber] = match;
|
|
897
|
+
} else if ((match = input.match(/(\d+)\.(\d+)\.(\d+)(-([^\.]+)\.(\d+))?/)) !== null) {
|
|
898
|
+
[, major, minor, patch, , preReleaseType, preReleaseNumber] = match;
|
|
899
|
+
}
|
|
900
|
+
if (match === null) {
|
|
901
|
+
throw new Error(`Could not parse version from input: ${input}`);
|
|
902
|
+
}
|
|
903
|
+
let preRelease = undefined;
|
|
904
|
+
let buildNumber = 100;
|
|
905
|
+
if (preReleaseType && preReleaseNumber) {
|
|
906
|
+
preRelease = {
|
|
907
|
+
type: preReleaseType,
|
|
908
|
+
version: parseInt(preReleaseNumber)
|
|
909
|
+
};
|
|
910
|
+
}
|
|
911
|
+
if (build) {
|
|
912
|
+
buildNumber = Number(build);
|
|
913
|
+
} else if (input) {
|
|
914
|
+
const descriptionMatch = input.match(/(\d+)\)$/);
|
|
915
|
+
if (descriptionMatch) {
|
|
916
|
+
buildNumber = parseInt(descriptionMatch[1]);
|
|
917
|
+
}
|
|
918
|
+
}
|
|
919
|
+
return new PackageVersion(parseInt(major), parseInt(minor), parseInt(patch), preRelease, buildNumber);
|
|
920
|
+
};
|
|
921
|
+
// 1000001001 -> 1.0.1.1
|
|
922
|
+
// 1002017001 -> 1.2.17.1
|
|
923
|
+
const parseVersionFromNumericVersion = (version)=>{
|
|
924
|
+
const major = Math.floor(version / 1000000000);
|
|
925
|
+
const minor = Math.floor(version % 1000000000 / 1000000);
|
|
926
|
+
const patch = Math.floor(version % 1000000 / 1000);
|
|
927
|
+
const buildNumber = version % 1000;
|
|
928
|
+
return new PackageVersion(major, minor, patch, undefined, buildNumber);
|
|
929
|
+
};
|
|
930
|
+
|
|
931
|
+
// https://regex101.com/r/LtGAu5/1
|
|
932
|
+
const logRegex = /console\.log\(\s*"([\w\s\.\(\)]+)\ *Copyright[\w\s\(\)\.]+(\d{4}|\d{4} - \d{4})([\w\s\(\)\.]+)?",?\s*\)/i;
|
|
933
|
+
const currentYear = new Date(Date.now()).getFullYear();
|
|
934
|
+
const getVersionFileHandler = (location)=>{
|
|
935
|
+
const filePath = path.join(location.scriptsDir, "Version.ts");
|
|
936
|
+
const invalidVersionFile = (versionFile)=>({
|
|
937
|
+
version: undefined,
|
|
938
|
+
write: (name, newVersion)=>{
|
|
939
|
+
const scriptsContent = fs.readdirSync(location.scriptsDir);
|
|
940
|
+
const tsFiles = scriptsContent.filter((file)=>file.endsWith(".ts"));
|
|
941
|
+
if (tsFiles.length > 0) {
|
|
942
|
+
return createVersionFileWriter([
|
|
943
|
+
currentYear
|
|
944
|
+
], "")(name, newVersion);
|
|
945
|
+
}
|
|
946
|
+
},
|
|
947
|
+
reset: ()=>{
|
|
948
|
+
if (versionFile !== undefined) {
|
|
949
|
+
fs.writeFileSync(filePath, versionFile, {
|
|
950
|
+
encoding: "utf8"
|
|
951
|
+
});
|
|
952
|
+
} else {
|
|
953
|
+
try {
|
|
954
|
+
fs.rmSync(filePath);
|
|
955
|
+
} catch (err) {
|
|
956
|
+
if (!isErrorENOENT(err)) {
|
|
957
|
+
throw err;
|
|
958
|
+
}
|
|
959
|
+
}
|
|
960
|
+
}
|
|
961
|
+
}
|
|
962
|
+
});
|
|
963
|
+
const createVersionFileWriter = (copyright = [
|
|
964
|
+
currentYear
|
|
965
|
+
], copyrightStuff = "")=>(name, newVersion)=>{
|
|
966
|
+
const descriptionText = newVersion.toDescriptionString(name);
|
|
967
|
+
const copyrightText = createYearString(copyright);
|
|
968
|
+
const result = `console.log("${descriptionText}. Copyright (C) ${copyrightText}${copyrightStuff}");`;
|
|
969
|
+
fs.writeFileSync(filePath, result, {
|
|
970
|
+
encoding: "utf-8"
|
|
971
|
+
});
|
|
972
|
+
};
|
|
973
|
+
let rawVersionFile = readStringFromFileOrUndefined(filePath);
|
|
974
|
+
if (rawVersionFile === undefined) {
|
|
975
|
+
return invalidVersionFile(rawVersionFile);
|
|
976
|
+
}
|
|
977
|
+
const versionFile = rawVersionFile.replace(/\n/g, "");
|
|
978
|
+
const match = versionFile.match(logRegex);
|
|
979
|
+
if (!match) {
|
|
980
|
+
return invalidVersionFile(versionFile);
|
|
981
|
+
}
|
|
982
|
+
const [_full, _description, copyright, copyrightStuff] = match;
|
|
983
|
+
const copyrightYears = copyright.match(/^(\d+)( ?- ?(\d+))?$/);
|
|
984
|
+
let years;
|
|
985
|
+
if (copyrightYears === null) {
|
|
986
|
+
years = [
|
|
987
|
+
currentYear
|
|
988
|
+
];
|
|
989
|
+
} else {
|
|
990
|
+
years = [
|
|
991
|
+
Number(copyrightYears[1]),
|
|
992
|
+
currentYear
|
|
993
|
+
];
|
|
994
|
+
}
|
|
995
|
+
return {
|
|
996
|
+
write: createVersionFileWriter(years, copyrightStuff),
|
|
997
|
+
reset: ()=>{
|
|
998
|
+
fs.writeFileSync(filePath, versionFile, {
|
|
999
|
+
encoding: "utf8"
|
|
1000
|
+
});
|
|
1001
|
+
}
|
|
1002
|
+
};
|
|
1003
|
+
};
|
|
1004
|
+
const createYearString = (years)=>{
|
|
1005
|
+
if (years[1] === undefined || years[0] === years[1]) {
|
|
1006
|
+
return years[0].toString();
|
|
1007
|
+
}
|
|
1008
|
+
return `${years[0]} - ${years[1]}`;
|
|
1009
|
+
};
|
|
1010
|
+
|
|
1011
|
+
const buildArchiveFromPublishedPackage = (location, manifest, creatorPackage)=>{
|
|
1012
|
+
const archive = new JSZip();
|
|
1013
|
+
archive.file(PACKAGE_FILE, JSON.stringify(creatorPackage, null, 2));
|
|
1014
|
+
const index = readPublishedPackageCreatorIndex(location);
|
|
1015
|
+
if (index !== undefined) {
|
|
1016
|
+
archive.file(INDEX_FILE, JSON.stringify(index, null, 2));
|
|
1017
|
+
}
|
|
1018
|
+
archive.file(manifest.main, fs.createReadStream(path.join(location.path, manifest.main)));
|
|
1019
|
+
return archive;
|
|
1020
|
+
};
|
|
1021
|
+
let validateSchema;
|
|
1022
|
+
const runtimeScripts = [
|
|
1023
|
+
"Interactor",
|
|
1024
|
+
"Core",
|
|
1025
|
+
"Mixed"
|
|
1026
|
+
];
|
|
1027
|
+
const notRuntimeScripts = [
|
|
1028
|
+
"Context",
|
|
1029
|
+
"Evaluator"
|
|
1030
|
+
];
|
|
1031
|
+
const buildArchiveFromPackage = async (workspaceLocation, packageLocation, data)=>{
|
|
1032
|
+
const { domain , subdomain } = parseCreatorPackageName(data);
|
|
1033
|
+
const logStep = (step)=>logPackageMessage(data.Package, step);
|
|
1034
|
+
if (validateSchema === undefined) {
|
|
1035
|
+
validateSchema = await axios.get("https://archive.intelligentgraphics.biz/schemas/gfx/animation.json").then(({ data })=>new Ajv({
|
|
1036
|
+
coerceTypes: true,
|
|
1037
|
+
allErrors: true,
|
|
1038
|
+
removeAdditional: true,
|
|
1039
|
+
useDefaults: "empty",
|
|
1040
|
+
validateSchema: "log"
|
|
1041
|
+
}).compile(data));
|
|
1042
|
+
}
|
|
1043
|
+
const libFilePath = path.join(getWorkspaceOutputPath(workspaceLocation), `${data.Package}.min.js`);
|
|
1044
|
+
const scriptDirectories = [
|
|
1045
|
+
packageLocation.path,
|
|
1046
|
+
packageLocation.scriptsDir
|
|
1047
|
+
];
|
|
1048
|
+
if (subdomain === "GFX.Standard") {
|
|
1049
|
+
logStep(`Including Images folder`);
|
|
1050
|
+
scriptDirectories.push(path.join(packageLocation.path, "Images"));
|
|
1051
|
+
}
|
|
1052
|
+
const manifest = readPackageCreatorManifest(packageLocation);
|
|
1053
|
+
if (manifest !== undefined) {
|
|
1054
|
+
if (manifest.RunTime && notRuntimeScripts.includes(manifest.Type)) {
|
|
1055
|
+
logStep("Setting script RunTime to false because of script type");
|
|
1056
|
+
writePackageCreatorManifest(packageLocation, {
|
|
1057
|
+
...manifest,
|
|
1058
|
+
RunTime: false
|
|
1059
|
+
});
|
|
1060
|
+
} else if (!manifest.RunTime && runtimeScripts.includes(manifest.Type)) {
|
|
1061
|
+
logStep("Setting script RunTime to true because of script type");
|
|
1062
|
+
writePackageCreatorManifest(packageLocation, {
|
|
1063
|
+
...manifest,
|
|
1064
|
+
RunTime: true
|
|
1065
|
+
});
|
|
1066
|
+
}
|
|
1067
|
+
}
|
|
1068
|
+
// if (index === undefined) {
|
|
1069
|
+
// throw new Error(
|
|
1070
|
+
// `Could not find an "${INDEX_FILE}" file in "${primaryScriptDir}"`,
|
|
1071
|
+
// );
|
|
1072
|
+
// }
|
|
1073
|
+
const animations = new Map();
|
|
1074
|
+
for (const scriptFilePath of readPackageAnimationList(packageLocation)){
|
|
1075
|
+
const content = fs.readFileSync(scriptFilePath, {
|
|
1076
|
+
encoding: "utf8"
|
|
1077
|
+
});
|
|
1078
|
+
let data;
|
|
1079
|
+
try {
|
|
1080
|
+
data = JSON.parse(content);
|
|
1081
|
+
} catch (err) {
|
|
1082
|
+
const relativePath = path.relative(workspaceLocation.path, scriptFilePath);
|
|
1083
|
+
if (err instanceof SyntaxError) {
|
|
1084
|
+
throw new Error(`Encountered invalid syntax in file "${relativePath}": ${String(err)}`);
|
|
1085
|
+
}
|
|
1086
|
+
throw new Error(`Encountered an unexpected error while parsing animation json file at path "${relativePath}"`, {
|
|
1087
|
+
cause: err
|
|
1088
|
+
});
|
|
1089
|
+
}
|
|
1090
|
+
validateSchema(data);
|
|
1091
|
+
animations.set(data.Id, JSON.stringify(data));
|
|
1092
|
+
}
|
|
1093
|
+
let libFile;
|
|
1094
|
+
try {
|
|
1095
|
+
libFile = fs.readFileSync(libFilePath, {
|
|
1096
|
+
encoding: "utf8"
|
|
1097
|
+
});
|
|
1098
|
+
} catch (err) {
|
|
1099
|
+
if (!isErrorENOENT(err)) {
|
|
1100
|
+
throw err;
|
|
1101
|
+
}
|
|
1102
|
+
}
|
|
1103
|
+
if (libFile === undefined) {
|
|
1104
|
+
if (animations.size === 0) {
|
|
1105
|
+
throw new Error(`Could not find a javascript file at "${libFilePath}".
|
|
1106
|
+
Packaging without a javascript file is only allowed when animation json files are available`);
|
|
1107
|
+
}
|
|
1108
|
+
}
|
|
1109
|
+
const archive = new JSZip();
|
|
1110
|
+
let library = "";
|
|
1111
|
+
if (libFile) {
|
|
1112
|
+
library = libFile;
|
|
1113
|
+
}
|
|
1114
|
+
if (!library) {
|
|
1115
|
+
const date = new Date(Date.now());
|
|
1116
|
+
library = `/* This file is part of the ${domain} Data Packages.
|
|
1117
|
+
* Copyright (C) ${date.getFullYear()} intelligentgraphics. All Rights Reserved. */`;
|
|
1118
|
+
}
|
|
1119
|
+
if (animations.size > 0) {
|
|
1120
|
+
const scope = data.Scope ?? data.Package;
|
|
1121
|
+
const scopeParts = scope.split(".");
|
|
1122
|
+
library += createNamespace(scopeParts);
|
|
1123
|
+
for (const [name, data] of animations){
|
|
1124
|
+
library += `${scope}.${name} = ` + data + ";";
|
|
1125
|
+
logPackageMessage(manifest.Package, `Added animation ${scope}.${name}`);
|
|
1126
|
+
}
|
|
1127
|
+
}
|
|
1128
|
+
const minifyResult = await terser.minify(library, {
|
|
1129
|
+
ecma: 5
|
|
1130
|
+
});
|
|
1131
|
+
archive.file(`${data.Package}.js`, minifyResult.code);
|
|
1132
|
+
archive.file(PACKAGE_FILE, JSON.stringify(data, null, 2));
|
|
1133
|
+
const creatorIndex = readPackageCreatorIndex(packageLocation);
|
|
1134
|
+
if (creatorIndex !== undefined) {
|
|
1135
|
+
archive.file(INDEX_FILE, JSON.stringify(creatorIndex, null, 2));
|
|
1136
|
+
}
|
|
1137
|
+
for (const directory of scriptDirectories){
|
|
1138
|
+
try {
|
|
1139
|
+
for (const file of fs.readdirSync(directory)){
|
|
1140
|
+
const { ext } = path.parse(file);
|
|
1141
|
+
switch(ext){
|
|
1142
|
+
case ".png":
|
|
1143
|
+
case ".jpeg":
|
|
1144
|
+
case ".jpg":
|
|
1145
|
+
break;
|
|
1146
|
+
default:
|
|
1147
|
+
continue;
|
|
1148
|
+
}
|
|
1149
|
+
archive.file(file, fs.createReadStream(path.join(directory, file)));
|
|
1150
|
+
}
|
|
1151
|
+
} catch (err) {
|
|
1152
|
+
console.error(`Script directory "${directory}" does not exist`);
|
|
1153
|
+
}
|
|
1154
|
+
}
|
|
1155
|
+
return archive;
|
|
1156
|
+
};
|
|
1157
|
+
const createNamespace = (parts)=>{
|
|
1158
|
+
let code = `var ${parts[0]};`;
|
|
1159
|
+
for(let index = 0; index < parts.length; index++){
|
|
1160
|
+
const path = parts.slice(0, index + 1).join(".");
|
|
1161
|
+
code += `\n(${path} = ${path} || {});`;
|
|
1162
|
+
}
|
|
1163
|
+
return code;
|
|
1164
|
+
};
|
|
1165
|
+
|
|
1166
|
+
const releaseFolder = async (options)=>{
|
|
1167
|
+
const workspace = options.workspace;
|
|
1168
|
+
const location = options.directory;
|
|
1169
|
+
const { write: writeVersionFile , reset: resetVersionFile } = getVersionFileHandler(location);
|
|
1170
|
+
const packageDescription = readPackageCreatorManifest(location);
|
|
1171
|
+
const fullPackageName = packageDescription.Package;
|
|
1172
|
+
const { domain , subdomain } = parseCreatorPackageName(packageDescription);
|
|
1173
|
+
const publishDomain = options.domain ?? domain;
|
|
1174
|
+
const publishSubdomain = options.subdomain ?? subdomain;
|
|
1175
|
+
const sharedPackageJson = readWorkspaceNpmManifest(workspace);
|
|
1176
|
+
let newVersion;
|
|
1177
|
+
try {
|
|
1178
|
+
newVersion = parseVersionFromString(options.newVersion);
|
|
1179
|
+
} catch (err) {
|
|
1180
|
+
throw new Error(`Please enter a version in this format 1.0.0.100`);
|
|
1181
|
+
}
|
|
1182
|
+
packageDescription.Version = newVersion.toVersionString({
|
|
1183
|
+
buildNumber: true
|
|
1184
|
+
});
|
|
1185
|
+
writePackageCreatorManifest(location, packageDescription);
|
|
1186
|
+
if (newVersion.buildNumber < 100) {
|
|
1187
|
+
newVersion.preRelease = {
|
|
1188
|
+
type: "beta",
|
|
1189
|
+
version: newVersion.buildNumber
|
|
1190
|
+
};
|
|
1191
|
+
} else if (newVersion.buildNumber > 100) {
|
|
1192
|
+
newVersion.preRelease = {
|
|
1193
|
+
type: "patch",
|
|
1194
|
+
version: newVersion.buildNumber - 100
|
|
1195
|
+
};
|
|
1196
|
+
}
|
|
1197
|
+
if (sharedPackageJson !== undefined) {
|
|
1198
|
+
logPackageMessage(packageDescription.Package, `Running npm install to make sure all dependencies are up to date`);
|
|
1199
|
+
execSync(`npm install`, {
|
|
1200
|
+
encoding: "utf-8",
|
|
1201
|
+
cwd: workspace.path
|
|
1202
|
+
});
|
|
1203
|
+
}
|
|
1204
|
+
const binDir = getWorkspaceOutputPath(workspace);
|
|
1205
|
+
fs.mkdirSync(binDir, {
|
|
1206
|
+
recursive: true
|
|
1207
|
+
});
|
|
1208
|
+
let assetServerPackageDetails;
|
|
1209
|
+
let packageNameWithVersion;
|
|
1210
|
+
{
|
|
1211
|
+
const versionWithoutPrelease = newVersion.clone();
|
|
1212
|
+
versionWithoutPrelease.preRelease = undefined;
|
|
1213
|
+
const newVersionString = versionWithoutPrelease.toVersionString({
|
|
1214
|
+
buildNumber: true
|
|
1215
|
+
});
|
|
1216
|
+
packageNameWithVersion = `${packageDescription.Package}_${newVersionString}`;
|
|
1217
|
+
assetServerPackageDetails = {
|
|
1218
|
+
name: packageDescription.Package,
|
|
1219
|
+
version: newVersionString
|
|
1220
|
+
};
|
|
1221
|
+
}
|
|
1222
|
+
const zipFilePath = path.join(binDir, packageNameWithVersion + ".zip");
|
|
1223
|
+
try {
|
|
1224
|
+
if (options.pushOnly) {
|
|
1225
|
+
if (!fs.existsSync(zipFilePath)) {
|
|
1226
|
+
throw new Error(`Expected a zip file to exist at path ${zipFilePath} since pushOnly is specified`);
|
|
1227
|
+
}
|
|
1228
|
+
} else {
|
|
1229
|
+
const gitVersionInformation = await getVersionInformationFromGit(workspace, location);
|
|
1230
|
+
writeVersionFile(fullPackageName, newVersion);
|
|
1231
|
+
const bannerText = sharedPackageJson !== undefined ? getWorkspaceBannerText(sharedPackageJson) : undefined;
|
|
1232
|
+
await buildFolders({
|
|
1233
|
+
...options,
|
|
1234
|
+
packages: [
|
|
1235
|
+
location
|
|
1236
|
+
],
|
|
1237
|
+
skipPackagesWithoutTsFiles: true,
|
|
1238
|
+
banner: options.banner ? {
|
|
1239
|
+
text: bannerText,
|
|
1240
|
+
commit: gitVersionInformation.commit,
|
|
1241
|
+
commitDirty: gitVersionInformation.dirty,
|
|
1242
|
+
version: newVersion.toVersionString({
|
|
1243
|
+
buildNumber: true
|
|
1244
|
+
}),
|
|
1245
|
+
date: new Date(Date.now())
|
|
1246
|
+
} : undefined
|
|
1247
|
+
});
|
|
1248
|
+
newVersion.preRelease = undefined;
|
|
1249
|
+
try {
|
|
1250
|
+
fs.rmSync(zipFilePath);
|
|
1251
|
+
} catch (err) {
|
|
1252
|
+
if (!isErrorENOENT(err)) {
|
|
1253
|
+
throw err;
|
|
1254
|
+
}
|
|
1255
|
+
}
|
|
1256
|
+
if (readPackageAnimationList(location).length > 0) {
|
|
1257
|
+
var _workspaceManifest_dependencies;
|
|
1258
|
+
const workspaceManifest = readWorkspaceNpmManifest(workspace);
|
|
1259
|
+
if (!((_workspaceManifest_dependencies = workspaceManifest.dependencies) == null ? void 0 : _workspaceManifest_dependencies["@intelligentgraphics/3d.ig.gfx.standard"])) {
|
|
1260
|
+
const install = await options.prompter.confirm(`Animation.json files require the library 'IG.GFX.Standard' to be available, but it is not registered as a dependency. Do you want to install it now?`);
|
|
1261
|
+
if (install) {
|
|
1262
|
+
execSync(`npm install @intelligentgraphics/3d.ig.gfx.standard`, {
|
|
1263
|
+
encoding: "utf-8",
|
|
1264
|
+
cwd: workspace.path,
|
|
1265
|
+
stdio: "inherit"
|
|
1266
|
+
});
|
|
1267
|
+
execSync(`npm run postinstall`, {
|
|
1268
|
+
cwd: workspace.path
|
|
1269
|
+
});
|
|
1270
|
+
}
|
|
1271
|
+
}
|
|
1272
|
+
}
|
|
1273
|
+
const archive = await buildArchiveFromPackage(workspace, location, packageDescription);
|
|
1274
|
+
const zipOutputStream = fs.createWriteStream(zipFilePath);
|
|
1275
|
+
await pipeline(archive.generateNodeStream(), zipOutputStream);
|
|
1276
|
+
}
|
|
1277
|
+
if (!options.noUpload) {
|
|
1278
|
+
if (!options.authentication) {
|
|
1279
|
+
throw new Error(`Expected authentication to be available`);
|
|
1280
|
+
}
|
|
1281
|
+
logPackageMessage(packageDescription.Package, `Opening connection to IG.Asset.Server`);
|
|
1282
|
+
const sessionManager = await createSessionManager({
|
|
1283
|
+
url: options.service,
|
|
1284
|
+
address: options.address,
|
|
1285
|
+
domain: publishDomain,
|
|
1286
|
+
subDomain: publishSubdomain,
|
|
1287
|
+
authentication: options.authentication
|
|
1288
|
+
});
|
|
1289
|
+
try {
|
|
1290
|
+
if (!options.skipDependencies) {
|
|
1291
|
+
await ensureRequiredVersions(workspace, packageDescription, sessionManager, options.prompter);
|
|
1292
|
+
}
|
|
1293
|
+
logPackageMessage(packageDescription.Package, `Uploading package to ${publishDomain}.${publishSubdomain}`);
|
|
1294
|
+
await uploadPackage(sessionManager.getTargetSession(), assetServerPackageDetails, zipFilePath);
|
|
1295
|
+
} finally{
|
|
1296
|
+
await sessionManager.destroy().catch((err)=>{
|
|
1297
|
+
logPackageMessage(packageDescription.Package, `Failed to close IG.Asset.Server session(s): ${err}`);
|
|
1298
|
+
});
|
|
1299
|
+
}
|
|
1300
|
+
}
|
|
1301
|
+
} catch (err) {
|
|
1302
|
+
resetVersionFile();
|
|
1303
|
+
throw err;
|
|
1304
|
+
}
|
|
1305
|
+
if (newVersion.buildNumber >= 100 && !options.pushOnly) {
|
|
1306
|
+
logPackageMessage(fullPackageName, "Copying zip to releases folder");
|
|
1307
|
+
const zipFileName = `${packageNameWithVersion}.zip`;
|
|
1308
|
+
const releasesPath = getPackageReleasesDirectory(location);
|
|
1309
|
+
fs.mkdirSync(releasesPath, {
|
|
1310
|
+
recursive: true
|
|
1311
|
+
});
|
|
1312
|
+
fs.copyFileSync(zipFilePath, path.join(releasesPath, zipFileName));
|
|
1313
|
+
}
|
|
1314
|
+
};
|
|
1315
|
+
const ensureRequiredVersions = async (workspaceLocation, creatorPackage, sessionManager, prompter)=>{
|
|
1316
|
+
const libraries = determineWorkspaceIGLibraries(workspaceLocation);
|
|
1317
|
+
// If there are no libraries, we don't need to check for required versions
|
|
1318
|
+
if (libraries.length === 0) {
|
|
1319
|
+
return true;
|
|
1320
|
+
}
|
|
1321
|
+
const targetSession = sessionManager.getTargetSession();
|
|
1322
|
+
const rawUploadedPackages = await getExistingPackages(targetSession);
|
|
1323
|
+
const uploadedPackages = rawUploadedPackages.map((entry)=>{
|
|
1324
|
+
let version;
|
|
1325
|
+
try {
|
|
1326
|
+
version = parseVersionFromNumericVersion(entry.numericVersion);
|
|
1327
|
+
} catch (err) {
|
|
1328
|
+
throw new Error(`Encountered invalid format for version ${entry.numericVersion}`);
|
|
1329
|
+
}
|
|
1330
|
+
if (version.buildNumber < 100) {
|
|
1331
|
+
version.preRelease = {
|
|
1332
|
+
type: "beta",
|
|
1333
|
+
version: version.buildNumber
|
|
1334
|
+
};
|
|
1335
|
+
} else if (version.buildNumber > 100) {
|
|
1336
|
+
version.preRelease = {
|
|
1337
|
+
type: "patch",
|
|
1338
|
+
version: version.buildNumber - 100
|
|
1339
|
+
};
|
|
1340
|
+
}
|
|
1341
|
+
return {
|
|
1342
|
+
...entry,
|
|
1343
|
+
version
|
|
1344
|
+
};
|
|
1345
|
+
});
|
|
1346
|
+
for (const libraryLocation of libraries){
|
|
1347
|
+
const libraryManifest = readPublishedPackageNpmManifest(libraryLocation);
|
|
1348
|
+
const libraryCreatorPackage = readPublishedPackageCreatorManifest(libraryLocation);
|
|
1349
|
+
if (libraryCreatorPackage === undefined || libraryManifest.main === undefined || libraryCreatorPackage.Package === creatorPackage.Package) {
|
|
1350
|
+
continue;
|
|
1351
|
+
}
|
|
1352
|
+
const libraryVersion = PackageVersion.extractFromLine(libraryManifest.version);
|
|
1353
|
+
if (libraryVersion.preRelease) {
|
|
1354
|
+
libraryVersion.buildNumber = libraryVersion.preRelease.version;
|
|
1355
|
+
libraryVersion.preRelease = undefined;
|
|
1356
|
+
} else {
|
|
1357
|
+
libraryVersion.buildNumber = 100;
|
|
1358
|
+
}
|
|
1359
|
+
let uploadedPackageInBasics;
|
|
1360
|
+
let uploadedPackageInTarget;
|
|
1361
|
+
for (const uploadedPackage of uploadedPackages){
|
|
1362
|
+
if (uploadedPackage.scope === libraryCreatorPackage.Package) {
|
|
1363
|
+
if (uploadedPackage.support) {
|
|
1364
|
+
uploadedPackageInBasics = uploadedPackage;
|
|
1365
|
+
} else {
|
|
1366
|
+
uploadedPackageInTarget = uploadedPackage;
|
|
1367
|
+
}
|
|
1368
|
+
}
|
|
1369
|
+
}
|
|
1370
|
+
const validInBasics = uploadedPackageInBasics !== undefined && !uploadedPackageInBasics.version.isLesserThan(libraryVersion);
|
|
1371
|
+
const validInTarget = uploadedPackageInTarget !== undefined && !uploadedPackageInTarget.version.isLesserThan(libraryVersion);
|
|
1372
|
+
if (validInBasics || validInTarget) {
|
|
1373
|
+
if (targetSession.subDomain !== "Basics" && uploadedPackageInBasics !== undefined && uploadedPackageInTarget !== undefined) {
|
|
1374
|
+
logPackageMessage(creatorPackage.Package, `Package ${libraryCreatorPackage.Package} is uploaded both for Basics and ${targetSession.subDomain}. The package within ${targetSession.subDomain} will be used.`);
|
|
1375
|
+
}
|
|
1376
|
+
continue;
|
|
1377
|
+
}
|
|
1378
|
+
const possibleTargets = [];
|
|
1379
|
+
if (uploadedPackageInBasics) {
|
|
1380
|
+
const version = uploadedPackageInBasics.version.toVersionString({
|
|
1381
|
+
buildNumber: true
|
|
1382
|
+
});
|
|
1383
|
+
possibleTargets.push({
|
|
1384
|
+
value: "Basics",
|
|
1385
|
+
name: `Basics (Current: ${version})`
|
|
1386
|
+
});
|
|
1387
|
+
} else {
|
|
1388
|
+
possibleTargets.push({
|
|
1389
|
+
value: "Basics",
|
|
1390
|
+
name: "Basics (Current: None)"
|
|
1391
|
+
});
|
|
1392
|
+
}
|
|
1393
|
+
if (targetSession.subDomain !== "Basics") {
|
|
1394
|
+
if (uploadedPackageInTarget) {
|
|
1395
|
+
const version = uploadedPackageInTarget.version.toVersionString({
|
|
1396
|
+
buildNumber: true
|
|
1397
|
+
});
|
|
1398
|
+
possibleTargets.push({
|
|
1399
|
+
value: targetSession.subDomain,
|
|
1400
|
+
name: `${targetSession.subDomain} (Current: ${version})`
|
|
1401
|
+
});
|
|
1402
|
+
} else {
|
|
1403
|
+
possibleTargets.push({
|
|
1404
|
+
value: targetSession.subDomain,
|
|
1405
|
+
name: `${targetSession.subDomain} (Current: None)`
|
|
1406
|
+
});
|
|
1407
|
+
}
|
|
1408
|
+
}
|
|
1409
|
+
const libraryVersionString = libraryVersion.toVersionString({
|
|
1410
|
+
buildNumber: true
|
|
1411
|
+
});
|
|
1412
|
+
const uploadTargetScope = await prompter.ask({
|
|
1413
|
+
message: `Version ${libraryVersionString} of dependency ${libraryCreatorPackage.Package} is required but not available. Please select a subdomain to upload the correct dependency version to`,
|
|
1414
|
+
options: [
|
|
1415
|
+
...possibleTargets,
|
|
1416
|
+
{
|
|
1417
|
+
name: "Skip upload",
|
|
1418
|
+
value: "Skip"
|
|
1419
|
+
}
|
|
1420
|
+
],
|
|
1421
|
+
default: possibleTargets[0].value
|
|
1422
|
+
});
|
|
1423
|
+
if (uploadTargetScope === "Skip") {
|
|
1424
|
+
continue;
|
|
1425
|
+
}
|
|
1426
|
+
const archive = buildArchiveFromPublishedPackage(libraryLocation, libraryManifest, libraryCreatorPackage);
|
|
1427
|
+
const newVersionString = libraryVersion.toVersionString({
|
|
1428
|
+
buildNumber: true
|
|
1429
|
+
});
|
|
1430
|
+
const packageNameWithVersion = `${libraryCreatorPackage.Package}_${newVersionString}`;
|
|
1431
|
+
const zipFilePath = path.join(getWorkspaceOutputPath(workspaceLocation), `${packageNameWithVersion}.zip`);
|
|
1432
|
+
try {
|
|
1433
|
+
fs.rmSync(zipFilePath);
|
|
1434
|
+
} catch (err) {
|
|
1435
|
+
if (!isErrorENOENT(err)) {
|
|
1436
|
+
throw err;
|
|
1437
|
+
}
|
|
1438
|
+
}
|
|
1439
|
+
const zipOutputStream = fs.createWriteStream(zipFilePath);
|
|
1440
|
+
await pipeline(archive.generateNodeStream(), zipOutputStream);
|
|
1441
|
+
const session = uploadTargetScope === "Basics" ? await sessionManager.getBasicsSession() : targetSession;
|
|
1442
|
+
logPackageMessage(creatorPackage.Package, `Uploading package ${libraryCreatorPackage.Package} with version ${newVersionString} to ${session.domain}.${session.subDomain}`);
|
|
1443
|
+
await uploadPackage(session, {
|
|
1444
|
+
name: libraryCreatorPackage.Package,
|
|
1445
|
+
version: newVersionString
|
|
1446
|
+
}, zipFilePath);
|
|
1447
|
+
}
|
|
1448
|
+
};
|
|
1449
|
+
const createSessionManager = async (params)=>{
|
|
1450
|
+
const targetSession = await startSession(params);
|
|
1451
|
+
let basicsSession;
|
|
1452
|
+
return {
|
|
1453
|
+
getBasicsSession: async ()=>{
|
|
1454
|
+
if (targetSession.subDomain === "Basics") {
|
|
1455
|
+
return targetSession;
|
|
1456
|
+
}
|
|
1457
|
+
if (basicsSession === undefined) {
|
|
1458
|
+
basicsSession = await startSession({
|
|
1459
|
+
...params,
|
|
1460
|
+
subDomain: "Basics"
|
|
1461
|
+
});
|
|
1462
|
+
}
|
|
1463
|
+
return basicsSession;
|
|
1464
|
+
},
|
|
1465
|
+
getTargetSession: ()=>targetSession,
|
|
1466
|
+
destroy: async ()=>{
|
|
1467
|
+
await closeSession(targetSession);
|
|
1468
|
+
if (basicsSession !== undefined) {
|
|
1469
|
+
await closeSession(basicsSession);
|
|
1470
|
+
}
|
|
1471
|
+
}
|
|
1472
|
+
};
|
|
1473
|
+
};
|
|
1474
|
+
|
|
1475
|
+
export { buildFolders, releaseFolder };
|
|
1476
|
+
//# sourceMappingURL=lib.mjs.map
|