1 | "use strict";
|
2 | Object.defineProperty(exports, "__esModule", { value: true });
|
3 | exports.isSafeToUnpackElectronOnRemoteBuildServer = exports.chooseNotNull = exports.resolveFunction = exports.normalizeExt = exports.computeSafeArtifactNameIfNeeded = exports.isSafeGithubName = exports.PlatformPackager = void 0;
|
4 | const bluebird_lst_1 = require("bluebird-lst");
|
5 | const builder_util_1 = require("builder-util");
|
6 | const arch_1 = require("builder-util/out/arch");
|
7 | const fs_1 = require("builder-util/out/fs");
|
8 | const promise_1 = require("builder-util/out/promise");
|
9 | const promises_1 = require("fs/promises");
|
10 | const lazy_val_1 = require("lazy-val");
|
11 | const path = require("path");
|
12 | const appInfo_1 = require("./appInfo");
|
13 | const asarFileChecker_1 = require("./asar/asarFileChecker");
|
14 | const asarUtil_1 = require("./asar/asarUtil");
|
15 | const integrity_1 = require("./asar/integrity");
|
16 | const fileMatcher_1 = require("./fileMatcher");
|
17 | const fileTransformer_1 = require("./fileTransformer");
|
18 | const Framework_1 = require("./Framework");
|
19 | const index_1 = require("./index");
|
20 | const appBuilder_1 = require("./util/appBuilder");
|
21 | const appFileCopier_1 = require("./util/appFileCopier");
|
22 | const macroExpander_1 = require("./util/macroExpander");
|
23 | class PlatformPackager {
|
24 | constructor(info, platform) {
|
25 | this.info = info;
|
26 | this.platform = platform;
|
27 | this._resourceList = new lazy_val_1.Lazy(() => promise_1.orIfFileNotExist(promises_1.readdir(this.info.buildResourcesDir), []));
|
28 | this.platformSpecificBuildOptions = PlatformPackager.normalizePlatformSpecificBuildOptions(this.config[platform.buildConfigurationKey]);
|
29 | this.appInfo = this.prepareAppInfo(info.appInfo);
|
30 | }
|
31 | get packagerOptions() {
|
32 | return this.info.options;
|
33 | }
|
34 | get buildResourcesDir() {
|
35 | return this.info.buildResourcesDir;
|
36 | }
|
37 | get projectDir() {
|
38 | return this.info.projectDir;
|
39 | }
|
40 | get config() {
|
41 | return this.info.config;
|
42 | }
|
43 | get resourceList() {
|
44 | return this._resourceList.value;
|
45 | }
|
46 | get compression() {
|
47 | const compression = this.platformSpecificBuildOptions.compression;
|
48 |
|
49 | if (compression === null) {
|
50 | return "normal";
|
51 | }
|
52 | return compression || this.config.compression || "normal";
|
53 | }
|
54 | get debugLogger() {
|
55 | return this.info.debugLogger;
|
56 | }
|
57 |
|
58 | prepareAppInfo(appInfo) {
|
59 | return new appInfo_1.AppInfo(this.info, null, this.platformSpecificBuildOptions);
|
60 | }
|
61 | static normalizePlatformSpecificBuildOptions(options) {
|
62 | return options == null ? Object.create(null) : options;
|
63 | }
|
64 | getCscPassword() {
|
65 | const password = this.doGetCscPassword();
|
66 | if (builder_util_1.isEmptyOrSpaces(password)) {
|
67 | builder_util_1.log.info({ reason: "CSC_KEY_PASSWORD is not defined" }, "empty password will be used for code signing");
|
68 | return "";
|
69 | }
|
70 | else {
|
71 | return password.trim();
|
72 | }
|
73 | }
|
74 | getCscLink(extraEnvName) {
|
75 |
|
76 | const envValue = chooseNotNull(extraEnvName == null ? null : process.env[extraEnvName], process.env.CSC_LINK);
|
77 | return chooseNotNull(chooseNotNull(this.info.config.cscLink, this.platformSpecificBuildOptions.cscLink), envValue);
|
78 | }
|
79 | doGetCscPassword() {
|
80 |
|
81 | return chooseNotNull(chooseNotNull(this.info.config.cscKeyPassword, this.platformSpecificBuildOptions.cscKeyPassword), process.env.CSC_KEY_PASSWORD);
|
82 | }
|
83 | computeAppOutDir(outDir, arch) {
|
84 | return (this.packagerOptions.prepackaged ||
|
85 | path.join(outDir, `${this.platform.buildConfigurationKey}${builder_util_1.getArchSuffix(arch, this.platformSpecificBuildOptions.defaultArch)}${this.platform === index_1.Platform.MAC ? "" : "-unpacked"}`));
|
86 | }
|
87 | dispatchArtifactCreated(file, target, arch, safeArtifactName) {
|
88 | return this.info.callArtifactBuildCompleted({
|
89 | file,
|
90 | safeArtifactName,
|
91 | target,
|
92 | arch,
|
93 | packager: this,
|
94 | });
|
95 | }
|
96 | async pack(outDir, arch, targets, taskManager) {
|
97 | const appOutDir = this.computeAppOutDir(outDir, arch);
|
98 | await this.doPack(outDir, appOutDir, this.platform.nodeName, arch, this.platformSpecificBuildOptions, targets);
|
99 | this.packageInDistributableFormat(appOutDir, arch, targets, taskManager);
|
100 | }
|
101 | packageInDistributableFormat(appOutDir, arch, targets, taskManager) {
|
102 | if (targets.find(it => !it.isAsyncSupported) == null) {
|
103 | PlatformPackager.buildAsyncTargets(targets, taskManager, appOutDir, arch);
|
104 | return;
|
105 | }
|
106 | taskManager.add(async () => {
|
107 |
|
108 | const subTaskManager = new builder_util_1.AsyncTaskManager(this.info.cancellationToken);
|
109 | PlatformPackager.buildAsyncTargets(targets, subTaskManager, appOutDir, arch);
|
110 | await subTaskManager.awaitTasks();
|
111 | for (const target of targets) {
|
112 | if (!target.isAsyncSupported) {
|
113 | await target.build(appOutDir, arch);
|
114 | }
|
115 | }
|
116 | });
|
117 | }
|
118 | static buildAsyncTargets(targets, taskManager, appOutDir, arch) {
|
119 | for (const target of targets) {
|
120 | if (target.isAsyncSupported) {
|
121 | taskManager.addTask(target.build(appOutDir, arch));
|
122 | }
|
123 | }
|
124 | }
|
125 | getExtraFileMatchers(isResources, appOutDir, options) {
|
126 | const base = isResources
|
127 | ? this.getResourcesDir(appOutDir)
|
128 | : this.platform === index_1.Platform.MAC
|
129 | ? path.join(appOutDir, `${this.appInfo.productFilename}.app`, "Contents")
|
130 | : appOutDir;
|
131 | return fileMatcher_1.getFileMatchers(this.config, isResources ? "extraResources" : "extraFiles", base, options);
|
132 | }
|
133 | createGetFileMatchersOptions(outDir, arch, customBuildOptions) {
|
134 | return {
|
135 | macroExpander: it => this.expandMacro(it, arch == null ? null : builder_util_1.Arch[arch], { "/*": "{,/**/*}" }),
|
136 | customBuildOptions,
|
137 | globalOutDir: outDir,
|
138 | defaultSrc: this.projectDir,
|
139 | };
|
140 | }
|
141 | async doPack(outDir, appOutDir, platformName, arch, platformSpecificBuildOptions, targets, sign = true, disableAsarIntegrity = false) {
|
142 | if (this.packagerOptions.prepackaged != null) {
|
143 | return;
|
144 | }
|
145 | if (this.info.cancellationToken.cancelled) {
|
146 | return;
|
147 | }
|
148 | const beforePack = resolveFunction(this.config.beforePack, "beforePack");
|
149 | if (beforePack != null) {
|
150 | await beforePack({
|
151 | appOutDir,
|
152 | outDir,
|
153 | arch,
|
154 | targets,
|
155 | packager: this,
|
156 | electronPlatformName: platformName,
|
157 | });
|
158 | }
|
159 | await this.info.installAppDependencies(this.platform, arch);
|
160 | if (this.info.cancellationToken.cancelled) {
|
161 | return;
|
162 | }
|
163 | const framework = this.info.framework;
|
164 | builder_util_1.log.info({
|
165 | platform: platformName,
|
166 | arch: builder_util_1.Arch[arch],
|
167 | [`${framework.name}`]: framework.version,
|
168 | appOutDir: builder_util_1.log.filePath(appOutDir),
|
169 | }, `packaging`);
|
170 | await framework.prepareApplicationStageDirectory({
|
171 | packager: this,
|
172 | appOutDir,
|
173 | platformName,
|
174 | arch: builder_util_1.Arch[arch],
|
175 | version: framework.version,
|
176 | });
|
177 | const excludePatterns = [];
|
178 | const computeParsedPatterns = (patterns) => {
|
179 | if (patterns != null) {
|
180 | for (const pattern of patterns) {
|
181 | pattern.computeParsedPatterns(excludePatterns, this.info.projectDir);
|
182 | }
|
183 | }
|
184 | };
|
185 | const getFileMatchersOptions = this.createGetFileMatchersOptions(outDir, arch, platformSpecificBuildOptions);
|
186 | const macroExpander = getFileMatchersOptions.macroExpander;
|
187 | const extraResourceMatchers = this.getExtraFileMatchers(true, appOutDir, getFileMatchersOptions);
|
188 | computeParsedPatterns(extraResourceMatchers);
|
189 | const extraFileMatchers = this.getExtraFileMatchers(false, appOutDir, getFileMatchersOptions);
|
190 | computeParsedPatterns(extraFileMatchers);
|
191 | const packContext = {
|
192 | appOutDir,
|
193 | outDir,
|
194 | arch,
|
195 | targets,
|
196 | packager: this,
|
197 | electronPlatformName: platformName,
|
198 | };
|
199 | const asarOptions = await this.computeAsarOptions(platformSpecificBuildOptions);
|
200 | const resourcesPath = this.platform === index_1.Platform.MAC
|
201 | ? path.join(appOutDir, framework.distMacOsAppName, "Contents", "Resources")
|
202 | : Framework_1.isElectronBased(framework)
|
203 | ? path.join(appOutDir, "resources")
|
204 | : appOutDir;
|
205 | const taskManager = new builder_util_1.AsyncTaskManager(this.info.cancellationToken);
|
206 | this.copyAppFiles(taskManager, asarOptions, resourcesPath, path.join(resourcesPath, "app"), packContext, platformSpecificBuildOptions, excludePatterns, macroExpander);
|
207 | await taskManager.awaitTasks();
|
208 | if (this.info.cancellationToken.cancelled) {
|
209 | return;
|
210 | }
|
211 | if (framework.beforeCopyExtraFiles != null) {
|
212 | await framework.beforeCopyExtraFiles({
|
213 | packager: this,
|
214 | appOutDir,
|
215 | asarIntegrity: asarOptions == null || disableAsarIntegrity ? null : await integrity_1.computeData(resourcesPath, asarOptions.externalAllowed ? { externalAllowed: true } : null),
|
216 | platformName,
|
217 | });
|
218 | }
|
219 | if (this.info.cancellationToken.cancelled) {
|
220 | return;
|
221 | }
|
222 | const transformerForExtraFiles = this.createTransformerForExtraFiles(packContext);
|
223 | await fileMatcher_1.copyFiles(extraResourceMatchers, transformerForExtraFiles);
|
224 | await fileMatcher_1.copyFiles(extraFileMatchers, transformerForExtraFiles);
|
225 | if (this.info.cancellationToken.cancelled) {
|
226 | return;
|
227 | }
|
228 | await this.info.afterPack(packContext);
|
229 | if (framework.afterPack != null) {
|
230 | await framework.afterPack(packContext);
|
231 | }
|
232 | const isAsar = asarOptions != null;
|
233 | await this.sanityCheckPackage(appOutDir, isAsar, framework);
|
234 | if (sign) {
|
235 | await this.doSignAfterPack(outDir, appOutDir, platformName, arch, platformSpecificBuildOptions, targets);
|
236 | }
|
237 | }
|
238 | async doSignAfterPack(outDir, appOutDir, platformName, arch, platformSpecificBuildOptions, targets) {
|
239 | const asarOptions = await this.computeAsarOptions(platformSpecificBuildOptions);
|
240 | const isAsar = asarOptions != null;
|
241 | const packContext = {
|
242 | appOutDir,
|
243 | outDir,
|
244 | arch,
|
245 | targets,
|
246 | packager: this,
|
247 | electronPlatformName: platformName,
|
248 | };
|
249 | await this.signApp(packContext, isAsar);
|
250 | const afterSign = resolveFunction(this.config.afterSign, "afterSign");
|
251 | if (afterSign != null) {
|
252 | await Promise.resolve(afterSign(packContext));
|
253 | }
|
254 | }
|
255 |
|
256 | createTransformerForExtraFiles(packContext) {
|
257 | return null;
|
258 | }
|
259 | copyAppFiles(taskManager, asarOptions, resourcePath, defaultDestination, packContext, platformSpecificBuildOptions, excludePatterns, macroExpander) {
|
260 | const appDir = this.info.appDir;
|
261 | const config = this.config;
|
262 | const isElectronCompile = asarOptions != null && fileTransformer_1.isElectronCompileUsed(this.info);
|
263 | const mainMatchers = fileMatcher_1.getMainFileMatchers(appDir, defaultDestination, macroExpander, platformSpecificBuildOptions, this, packContext.outDir, isElectronCompile);
|
264 | if (excludePatterns.length > 0) {
|
265 | for (const matcher of mainMatchers) {
|
266 | matcher.excludePatterns = excludePatterns;
|
267 | }
|
268 | }
|
269 | const framework = this.info.framework;
|
270 | const transformer = fileTransformer_1.createTransformer(appDir, config, isElectronCompile
|
271 | ? {
|
272 | originalMain: this.info.metadata.main,
|
273 | main: appFileCopier_1.ELECTRON_COMPILE_SHIM_FILENAME,
|
274 | ...config.extraMetadata,
|
275 | }
|
276 | : config.extraMetadata, framework.createTransformer == null ? null : framework.createTransformer());
|
277 | const _computeFileSets = (matchers) => {
|
278 | return appFileCopier_1.computeFileSets(matchers, this.info.isPrepackedAppAsar ? null : transformer, this, isElectronCompile).then(async (result) => {
|
279 | if (!this.info.isPrepackedAppAsar && !this.info.areNodeModulesHandledExternally) {
|
280 | const moduleFileMatcher = fileMatcher_1.getNodeModuleFileMatcher(appDir, defaultDestination, macroExpander, platformSpecificBuildOptions, this.info);
|
281 | result = result.concat(await appFileCopier_1.computeNodeModuleFileSets(this, moduleFileMatcher));
|
282 | }
|
283 | return result.filter(it => it.files.length > 0);
|
284 | });
|
285 | };
|
286 | if (this.info.isPrepackedAppAsar) {
|
287 | taskManager.addTask(bluebird_lst_1.default.each(_computeFileSets([new fileMatcher_1.FileMatcher(appDir, resourcePath, macroExpander)]), it => appFileCopier_1.copyAppFiles(it, this.info, transformer)));
|
288 | }
|
289 | else if (asarOptions == null) {
|
290 |
|
291 |
|
292 |
|
293 | const transformerForExtraFiles = this.createTransformerForExtraFiles(packContext);
|
294 | const combinedTransformer = file => {
|
295 | if (transformerForExtraFiles != null) {
|
296 | const result = transformerForExtraFiles(file);
|
297 | if (result != null) {
|
298 | return result;
|
299 | }
|
300 | }
|
301 | return transformer(file);
|
302 | };
|
303 | taskManager.addTask(bluebird_lst_1.default.each(_computeFileSets(mainMatchers), it => appFileCopier_1.copyAppFiles(it, this.info, combinedTransformer)));
|
304 | }
|
305 | else {
|
306 | const unpackPattern = fileMatcher_1.getFileMatchers(config, "asarUnpack", defaultDestination, {
|
307 | macroExpander,
|
308 | customBuildOptions: platformSpecificBuildOptions,
|
309 | globalOutDir: packContext.outDir,
|
310 | defaultSrc: appDir,
|
311 | });
|
312 | const fileMatcher = unpackPattern == null ? null : unpackPattern[0];
|
313 | taskManager.addTask(_computeFileSets(mainMatchers).then(async (fileSets) => {
|
314 | for (const fileSet of fileSets) {
|
315 | await appFileCopier_1.transformFiles(transformer, fileSet);
|
316 | }
|
317 | await new asarUtil_1.AsarPackager(appDir, resourcePath, asarOptions, fileMatcher == null ? null : fileMatcher.createFilter()).pack(fileSets, this);
|
318 | }));
|
319 | }
|
320 | }
|
321 |
|
322 | signApp(packContext, isAsar) {
|
323 | return Promise.resolve();
|
324 | }
|
325 | getIconPath() {
|
326 | return Promise.resolve(null);
|
327 | }
|
328 | async computeAsarOptions(customBuildOptions) {
|
329 | if (!Framework_1.isElectronBased(this.info.framework)) {
|
330 | return null;
|
331 | }
|
332 | function errorMessage(name) {
|
333 | return `${name} is deprecated is deprecated and not supported — please use asarUnpack`;
|
334 | }
|
335 | const buildMetadata = this.config;
|
336 | if (buildMetadata["asar-unpack"] != null) {
|
337 | throw new Error(errorMessage("asar-unpack"));
|
338 | }
|
339 | if (buildMetadata["asar-unpack-dir"] != null) {
|
340 | throw new Error(errorMessage("asar-unpack-dir"));
|
341 | }
|
342 | const platformSpecific = customBuildOptions.asar;
|
343 | const result = platformSpecific == null ? this.config.asar : platformSpecific;
|
344 | if (result === false) {
|
345 | const appAsarStat = await fs_1.statOrNull(path.join(this.info.appDir, "app.asar"));
|
346 |
|
347 | if (appAsarStat == null || !appAsarStat.isFile()) {
|
348 | builder_util_1.log.warn({
|
349 | solution: "enable asar and use asarUnpack to unpack files that must be externally available",
|
350 | }, "asar usage is disabled — this is strongly not recommended");
|
351 | }
|
352 | return null;
|
353 | }
|
354 | if (result == null || result === true) {
|
355 | return {};
|
356 | }
|
357 | for (const name of ["unpackDir", "unpack"]) {
|
358 | if (result[name] != null) {
|
359 | throw new Error(errorMessage(`asar.${name}`));
|
360 | }
|
361 | }
|
362 | return builder_util_1.deepAssign({}, result);
|
363 | }
|
364 | getElectronSrcDir(dist) {
|
365 | return path.resolve(this.projectDir, dist);
|
366 | }
|
367 | getElectronDestinationDir(appOutDir) {
|
368 | return appOutDir;
|
369 | }
|
370 | getResourcesDir(appOutDir) {
|
371 | if (this.platform === index_1.Platform.MAC) {
|
372 | return this.getMacOsResourcesDir(appOutDir);
|
373 | }
|
374 | else if (Framework_1.isElectronBased(this.info.framework)) {
|
375 | return path.join(appOutDir, "resources");
|
376 | }
|
377 | else {
|
378 | return appOutDir;
|
379 | }
|
380 | }
|
381 | getMacOsResourcesDir(appOutDir) {
|
382 | return path.join(appOutDir, `${this.appInfo.productFilename}.app`, "Contents", "Resources");
|
383 | }
|
384 | async checkFileInPackage(resourcesDir, file, messagePrefix, isAsar) {
|
385 | const relativeFile = path.relative(this.info.appDir, path.resolve(this.info.appDir, file));
|
386 | if (isAsar) {
|
387 | await asarFileChecker_1.checkFileInArchive(path.join(resourcesDir, "app.asar"), relativeFile, messagePrefix);
|
388 | return;
|
389 | }
|
390 | const pathParsed = path.parse(file);
|
391 |
|
392 |
|
393 | if (pathParsed.dir.includes(".asar")) {
|
394 |
|
395 |
|
396 |
|
397 | const pathSplit = pathParsed.dir.split(path.sep);
|
398 | let partWithAsarIndex = 0;
|
399 | pathSplit.some((pathPart, index) => {
|
400 | partWithAsarIndex = index;
|
401 | return pathPart.endsWith(".asar");
|
402 | });
|
403 | const asarPath = path.join(...pathSplit.slice(0, partWithAsarIndex + 1));
|
404 | let mainPath = pathSplit.length > partWithAsarIndex + 1 ? path.join.apply(pathSplit.slice(partWithAsarIndex + 1)) : "";
|
405 | mainPath += path.join(mainPath, pathParsed.base);
|
406 | await asarFileChecker_1.checkFileInArchive(path.join(resourcesDir, "app", asarPath), mainPath, messagePrefix);
|
407 | }
|
408 | else {
|
409 | const fullPath = path.join(resourcesDir, "app", relativeFile);
|
410 | const outStat = await fs_1.statOrNull(fullPath);
|
411 | if (outStat == null) {
|
412 | throw new Error(`${messagePrefix} "${fullPath}" does not exist. Seems like a wrong configuration.`);
|
413 | }
|
414 | else {
|
415 |
|
416 | if (!outStat.isFile()) {
|
417 | throw new Error(`${messagePrefix} "${fullPath}" is not a file. Seems like a wrong configuration.`);
|
418 | }
|
419 | }
|
420 | }
|
421 | }
|
422 | async sanityCheckPackage(appOutDir, isAsar, framework) {
|
423 | const outStat = await fs_1.statOrNull(appOutDir);
|
424 | if (outStat == null) {
|
425 | throw new Error(`Output directory "${appOutDir}" does not exist. Seems like a wrong configuration.`);
|
426 | }
|
427 | else {
|
428 |
|
429 | if (!outStat.isDirectory()) {
|
430 | throw new Error(`Output directory "${appOutDir}" is not a directory. Seems like a wrong configuration.`);
|
431 | }
|
432 | }
|
433 | const resourcesDir = this.getResourcesDir(appOutDir);
|
434 | const mainFile = (framework.getMainFile == null ? null : framework.getMainFile(this.platform)) || this.info.metadata.main || "index.js";
|
435 | await this.checkFileInPackage(resourcesDir, mainFile, "Application entry file", isAsar);
|
436 | await this.checkFileInPackage(resourcesDir, "package.json", "Application", isAsar);
|
437 | }
|
438 |
|
439 | computeSafeArtifactName(suggestedName, ext, arch, skipDefaultArch = true, defaultArch, safePattern = "${name}-${version}-${arch}.${ext}") {
|
440 | return computeSafeArtifactNameIfNeeded(suggestedName, () => this.computeArtifactName(safePattern, ext, skipDefaultArch && arch === arch_1.defaultArchFromString(defaultArch) ? null : arch));
|
441 | }
|
442 | expandArtifactNamePattern(targetSpecificOptions, ext, arch, defaultPattern, skipDefaultArch = true, defaultArch) {
|
443 | const { pattern, isUserForced } = this.artifactPatternConfig(targetSpecificOptions, defaultPattern);
|
444 | return this.computeArtifactName(pattern, ext, !isUserForced && skipDefaultArch && arch === arch_1.defaultArchFromString(defaultArch) ? null : arch);
|
445 | }
|
446 | artifactPatternConfig(targetSpecificOptions, defaultPattern) {
|
447 | const userSpecifiedPattern = (targetSpecificOptions === null || targetSpecificOptions === void 0 ? void 0 : targetSpecificOptions.artifactName) || this.platformSpecificBuildOptions.artifactName || this.config.artifactName;
|
448 | return {
|
449 | isUserForced: !!userSpecifiedPattern,
|
450 | pattern: userSpecifiedPattern || defaultPattern || "${productName}-${version}-${arch}.${ext}",
|
451 | };
|
452 | }
|
453 | expandArtifactBeautyNamePattern(targetSpecificOptions, ext, arch) {
|
454 |
|
455 | return this.expandArtifactNamePattern(targetSpecificOptions, ext, arch, "${productName} ${version} ${arch}.${ext}", true);
|
456 | }
|
457 | computeArtifactName(pattern, ext, arch) {
|
458 | const archName = arch == null ? null : arch_1.getArtifactArchName(arch, ext);
|
459 | return this.expandMacro(pattern, archName, {
|
460 | ext,
|
461 | });
|
462 | }
|
463 | expandMacro(pattern, arch, extra = {}, isProductNameSanitized = true) {
|
464 | return macroExpander_1.expandMacro(pattern, arch, this.appInfo, { os: this.platform.buildConfigurationKey, ...extra }, isProductNameSanitized);
|
465 | }
|
466 | generateName2(ext, classifier, deployment) {
|
467 | const dotExt = ext == null ? "" : `.${ext}`;
|
468 | const separator = ext === "deb" ? "_" : "-";
|
469 | return `${deployment ? this.appInfo.name : this.appInfo.productFilename}${separator}${this.appInfo.version}${classifier == null ? "" : `${separator}${classifier}`}${dotExt}`;
|
470 | }
|
471 | getTempFile(suffix) {
|
472 | return this.info.tempDirManager.getTempFile({ suffix });
|
473 | }
|
474 | get fileAssociations() {
|
475 | return builder_util_1.asArray(this.config.fileAssociations).concat(builder_util_1.asArray(this.platformSpecificBuildOptions.fileAssociations));
|
476 | }
|
477 | async getResource(custom, ...names) {
|
478 | const resourcesDir = this.info.buildResourcesDir;
|
479 | if (custom === undefined) {
|
480 | const resourceList = await this.resourceList;
|
481 | for (const name of names) {
|
482 | if (resourceList.includes(name)) {
|
483 | return path.join(resourcesDir, name);
|
484 | }
|
485 | }
|
486 | }
|
487 | else if (custom != null && !builder_util_1.isEmptyOrSpaces(custom)) {
|
488 | const resourceList = await this.resourceList;
|
489 | if (resourceList.includes(custom)) {
|
490 | return path.join(resourcesDir, custom);
|
491 | }
|
492 | let p = path.resolve(resourcesDir, custom);
|
493 | if ((await fs_1.statOrNull(p)) == null) {
|
494 | p = path.resolve(this.projectDir, custom);
|
495 | if ((await fs_1.statOrNull(p)) == null) {
|
496 | throw new builder_util_1.InvalidConfigurationError(`cannot find specified resource "${custom}", nor relative to "${resourcesDir}", neither relative to project dir ("${this.projectDir}")`);
|
497 | }
|
498 | }
|
499 | return p;
|
500 | }
|
501 | return null;
|
502 | }
|
503 | get forceCodeSigning() {
|
504 | const forceCodeSigningPlatform = this.platformSpecificBuildOptions.forceCodeSigning;
|
505 | return (forceCodeSigningPlatform == null ? this.config.forceCodeSigning : forceCodeSigningPlatform) || false;
|
506 | }
|
507 | async getOrConvertIcon(format) {
|
508 | const result = await this.resolveIcon(builder_util_1.asArray(this.platformSpecificBuildOptions.icon || this.config.icon), [], format);
|
509 | if (result.length === 0) {
|
510 | const framework = this.info.framework;
|
511 | if (framework.getDefaultIcon != null) {
|
512 | return framework.getDefaultIcon(this.platform);
|
513 | }
|
514 | builder_util_1.log.warn({ reason: "application icon is not set" }, `default ${capitalizeFirstLetter(framework.name)} icon is used`);
|
515 | return this.getDefaultFrameworkIcon();
|
516 | }
|
517 | else {
|
518 | return result[0].file;
|
519 | }
|
520 | }
|
521 | getDefaultFrameworkIcon() {
|
522 | const framework = this.info.framework;
|
523 | return framework.getDefaultIcon == null ? null : framework.getDefaultIcon(this.platform);
|
524 | }
|
525 |
|
526 | async resolveIcon(sources, fallbackSources, outputFormat) {
|
527 | const args = [
|
528 | "icon",
|
529 | "--format",
|
530 | outputFormat,
|
531 | "--root",
|
532 | this.buildResourcesDir,
|
533 | "--root",
|
534 | this.projectDir,
|
535 | "--out",
|
536 | path.resolve(this.projectDir, this.config.directories.output, `.icon-${outputFormat}`),
|
537 | ];
|
538 | for (const source of sources) {
|
539 | args.push("--input", source);
|
540 | }
|
541 | for (const source of fallbackSources) {
|
542 | args.push("--fallback-input", source);
|
543 | }
|
544 | const result = await appBuilder_1.executeAppBuilderAsJson(args);
|
545 | const errorMessage = result.error;
|
546 | if (errorMessage != null) {
|
547 | throw new builder_util_1.InvalidConfigurationError(errorMessage, result.errorCode);
|
548 | }
|
549 | if (result.isFallback) {
|
550 | builder_util_1.log.warn({ reason: "application icon is not set" }, `default ${capitalizeFirstLetter(this.info.framework.name)} icon is used`);
|
551 | }
|
552 | return result.icons || [];
|
553 | }
|
554 | }
|
555 | exports.PlatformPackager = PlatformPackager;
|
556 | function isSafeGithubName(name) {
|
557 | return /^[0-9A-Za-z._-]+$/.test(name);
|
558 | }
|
559 | exports.isSafeGithubName = isSafeGithubName;
|
560 | function computeSafeArtifactNameIfNeeded(suggestedName, safeNameProducer) {
|
561 |
|
562 | if (suggestedName != null) {
|
563 | if (isSafeGithubName(suggestedName)) {
|
564 | return null;
|
565 | }
|
566 |
|
567 | suggestedName = suggestedName.replace(/ /g, "-");
|
568 | if (isSafeGithubName(suggestedName)) {
|
569 | return suggestedName;
|
570 | }
|
571 | }
|
572 | return safeNameProducer();
|
573 | }
|
574 | exports.computeSafeArtifactNameIfNeeded = computeSafeArtifactNameIfNeeded;
|
575 |
|
576 | function normalizeExt(ext) {
|
577 | return ext.startsWith(".") ? ext.substring(1) : ext;
|
578 | }
|
579 | exports.normalizeExt = normalizeExt;
|
580 | function resolveFunction(executor, name) {
|
581 | if (executor == null || typeof executor !== "string") {
|
582 | return executor;
|
583 | }
|
584 | let p = executor;
|
585 | if (p.startsWith(".")) {
|
586 | p = path.resolve(p);
|
587 | }
|
588 | try {
|
589 | p = require.resolve(p);
|
590 | }
|
591 | catch (e) {
|
592 | builder_util_1.debug(e);
|
593 | p = path.resolve(p);
|
594 | }
|
595 |
|
596 | const m = require(p);
|
597 | const namedExport = m[name];
|
598 | if (namedExport == null) {
|
599 | return m.default || m;
|
600 | }
|
601 | else {
|
602 | return namedExport;
|
603 | }
|
604 | }
|
605 | exports.resolveFunction = resolveFunction;
|
606 | function chooseNotNull(v1, v2) {
|
607 | return v1 == null ? v2 : v1;
|
608 | }
|
609 | exports.chooseNotNull = chooseNotNull;
|
610 | function capitalizeFirstLetter(text) {
|
611 | return text.charAt(0).toUpperCase() + text.slice(1);
|
612 | }
|
613 | function isSafeToUnpackElectronOnRemoteBuildServer(packager) {
|
614 | if (packager.platform !== index_1.Platform.LINUX || packager.config.remoteBuild === false) {
|
615 | return false;
|
616 | }
|
617 | if (process.platform === "win32" || builder_util_1.isEnvTrue(process.env._REMOTE_BUILD)) {
|
618 | return packager.config.electronDist == null && packager.config.electronDownload == null;
|
619 | }
|
620 | return false;
|
621 | }
|
622 | exports.isSafeToUnpackElectronOnRemoteBuildServer = isSafeToUnpackElectronOnRemoteBuildServer;
|
623 |
|
\ | No newline at end of file |