UNPKG

18.1 kBJavaScriptView Raw
1"use strict";
2
3Object.defineProperty(exports, "__esModule", {
4 value: true
5});
6exports.default = void 0;
7
8function _bluebirdLst() {
9 const data = _interopRequireDefault(require("bluebird-lst"));
10
11 _bluebirdLst = function () {
12 return data;
13 };
14
15 return data;
16}
17
18function _builderUtil() {
19 const data = require("builder-util");
20
21 _builderUtil = function () {
22 return data;
23 };
24
25 return data;
26}
27
28function _electronOsxSign() {
29 const data = require("../electron-osx-sign");
30
31 _electronOsxSign = function () {
32 return data;
33 };
34
35 return data;
36}
37
38function _fsExtra() {
39 const data = require("fs-extra");
40
41 _fsExtra = function () {
42 return data;
43 };
44
45 return data;
46}
47
48function _lazyVal() {
49 const data = require("lazy-val");
50
51 _lazyVal = function () {
52 return data;
53 };
54
55 return data;
56}
57
58var path = _interopRequireWildcard(require("path"));
59
60function _fs() {
61 const data = require("builder-util/out/fs");
62
63 _fs = function () {
64 return data;
65 };
66
67 return data;
68}
69
70function _promise() {
71 const data = require("builder-util/out/promise");
72
73 _promise = function () {
74 return data;
75 };
76
77 return data;
78}
79
80function _appInfo() {
81 const data = require("./appInfo");
82
83 _appInfo = function () {
84 return data;
85 };
86
87 return data;
88}
89
90function _macCodeSign() {
91 const data = require("./codeSign/macCodeSign");
92
93 _macCodeSign = function () {
94 return data;
95 };
96
97 return data;
98}
99
100function _core() {
101 const data = require("./core");
102
103 _core = function () {
104 return data;
105 };
106
107 return data;
108}
109
110function _platformPackager() {
111 const data = require("./platformPackager");
112
113 _platformPackager = function () {
114 return data;
115 };
116
117 return data;
118}
119
120function _ArchiveTarget() {
121 const data = require("./targets/ArchiveTarget");
122
123 _ArchiveTarget = function () {
124 return data;
125 };
126
127 return data;
128}
129
130function _pkg() {
131 const data = require("./targets/pkg");
132
133 _pkg = function () {
134 return data;
135 };
136
137 return data;
138}
139
140function _targetFactory() {
141 const data = require("./targets/targetFactory");
142
143 _targetFactory = function () {
144 return data;
145 };
146
147 return data;
148}
149
150function _macosVersion() {
151 const data = require("./util/macosVersion");
152
153 _macosVersion = function () {
154 return data;
155 };
156
157 return data;
158}
159
160function _pathManager() {
161 const data = require("./util/pathManager");
162
163 _pathManager = function () {
164 return data;
165 };
166
167 return data;
168}
169
170function _getRequireWildcardCache() { if (typeof WeakMap !== "function") return null; var cache = new WeakMap(); _getRequireWildcardCache = function () { return cache; }; return cache; }
171
172function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
173
174function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
175
176class MacPackager extends _platformPackager().PlatformPackager {
177 constructor(info) {
178 super(info, _core().Platform.MAC);
179 this.codeSigningInfo = new (_lazyVal().Lazy)(() => {
180 const cscLink = this.getCscLink();
181
182 if (cscLink == null || process.platform !== "darwin") {
183 return Promise.resolve({
184 keychainFile: process.env.CSC_KEYCHAIN || null
185 });
186 }
187
188 return (0, _macCodeSign().createKeychain)({
189 tmpDir: this.info.tempDirManager,
190 cscLink,
191 cscKeyPassword: this.getCscPassword(),
192 cscILink: (0, _platformPackager().chooseNotNull)(this.platformSpecificBuildOptions.cscInstallerLink, process.env.CSC_INSTALLER_LINK),
193 cscIKeyPassword: (0, _platformPackager().chooseNotNull)(this.platformSpecificBuildOptions.cscInstallerKeyPassword, process.env.CSC_INSTALLER_KEY_PASSWORD),
194 currentDir: this.projectDir
195 }).then(result => {
196 const keychainFile = result.keychainFile;
197
198 if (keychainFile != null) {
199 this.info.disposeOnBuildFinish(() => (0, _macCodeSign().removeKeychain)(keychainFile));
200 }
201
202 return result;
203 });
204 });
205 this._iconPath = new (_lazyVal().Lazy)(() => this.getOrConvertIcon("icns"));
206 }
207
208 get defaultTarget() {
209 return this.info.framework.macOsDefaultTargets;
210 } // eslint-disable-next-line @typescript-eslint/no-unused-vars
211
212
213 prepareAppInfo(appInfo) {
214 return new (_appInfo().AppInfo)(this.info, this.platformSpecificBuildOptions.bundleVersion, this.platformSpecificBuildOptions);
215 }
216
217 async getIconPath() {
218 return this._iconPath.value;
219 }
220
221 createTargets(targets, mapper) {
222 for (const name of targets) {
223 switch (name) {
224 case _core().DIR_TARGET:
225 break;
226
227 case "dmg":
228 {
229 // eslint-disable-next-line @typescript-eslint/no-var-requires
230 const {
231 DmgTarget
232 } = require("dmg-builder");
233
234 mapper(name, outDir => new DmgTarget(this, outDir));
235 break;
236 }
237
238 case "zip":
239 // https://github.com/electron-userland/electron-builder/issues/2313
240 mapper(name, outDir => new (_ArchiveTarget().ArchiveTarget)(name, outDir, this, true));
241 break;
242
243 case "pkg":
244 mapper(name, outDir => new (_pkg().PkgTarget)(this, outDir));
245 break;
246
247 default:
248 mapper(name, outDir => name === "mas" || name === "mas-dev" ? new (_targetFactory().NoOpTarget)(name) : (0, _targetFactory().createCommonTarget)(name, outDir, this));
249 break;
250 }
251 }
252 }
253
254 async pack(outDir, arch, targets, taskManager) {
255 let nonMasPromise = null;
256 const hasMas = targets.length !== 0 && targets.some(it => it.name === "mas" || it.name === "mas-dev");
257 const prepackaged = this.packagerOptions.prepackaged;
258
259 if (!hasMas || targets.length > 1) {
260 const appPath = prepackaged == null ? path.join(this.computeAppOutDir(outDir, arch), `${this.appInfo.productFilename}.app`) : prepackaged;
261 nonMasPromise = (prepackaged ? Promise.resolve() : this.doPack(outDir, path.dirname(appPath), this.platform.nodeName, arch, this.platformSpecificBuildOptions, targets)).then(() => this.packageInDistributableFormat(appPath, arch, targets, taskManager));
262 }
263
264 for (const target of targets) {
265 const targetName = target.name;
266
267 if (!(targetName === "mas" || targetName === "mas-dev")) {
268 continue;
269 }
270
271 const masBuildOptions = (0, _builderUtil().deepAssign)({}, this.platformSpecificBuildOptions, this.config.mas);
272
273 if (targetName === "mas-dev") {
274 (0, _builderUtil().deepAssign)(masBuildOptions, this.config.masDev, {
275 type: "development"
276 });
277 }
278
279 const targetOutDir = path.join(outDir, targetName);
280
281 if (prepackaged == null) {
282 await this.doPack(outDir, targetOutDir, "mas", arch, masBuildOptions, [target]);
283 await this.sign(path.join(targetOutDir, `${this.appInfo.productFilename}.app`), targetOutDir, masBuildOptions);
284 } else {
285 await this.sign(prepackaged, targetOutDir, masBuildOptions);
286 }
287 }
288
289 if (nonMasPromise != null) {
290 await nonMasPromise;
291 }
292 }
293
294 async sign(appPath, outDir, masOptions) {
295 if (!(0, _macCodeSign().isSignAllowed)()) {
296 return;
297 }
298
299 const isMas = masOptions != null;
300 const options = masOptions == null ? this.platformSpecificBuildOptions : masOptions;
301 const qualifier = options.identity;
302
303 if (!isMas && qualifier === null) {
304 if (this.forceCodeSigning) {
305 throw new (_builderUtil().InvalidConfigurationError)("identity explicitly is set to null, but forceCodeSigning is set to true");
306 }
307
308 _builderUtil().log.info({
309 reason: "identity explicitly is set to null"
310 }, "skipped macOS code signing");
311
312 return;
313 }
314
315 const keychainFile = (await this.codeSigningInfo.value).keychainFile;
316 const explicitType = options.type;
317 const type = explicitType || "distribution";
318 const isDevelopment = type === "development";
319 const certificateType = getCertificateType(isMas, isDevelopment);
320 let identity = await (0, _macCodeSign().findIdentity)(certificateType, qualifier, keychainFile);
321
322 if (identity == null) {
323 if (!isMas && !isDevelopment && explicitType !== "distribution") {
324 identity = await (0, _macCodeSign().findIdentity)("Mac Developer", qualifier, keychainFile);
325
326 if (identity != null) {
327 _builderUtil().log.warn("Mac Developer is used to sign app — it is only for development and testing, not for production");
328 }
329 }
330
331 if (identity == null) {
332 await (0, _macCodeSign().reportError)(isMas, certificateType, qualifier, keychainFile, this.forceCodeSigning);
333 return;
334 }
335 }
336
337 if (!(0, _macosVersion().isMacOsHighSierra)()) {
338 throw new (_builderUtil().InvalidConfigurationError)("macOS High Sierra 10.13.6 is required to sign");
339 }
340
341 let filter = options.signIgnore;
342
343 if (Array.isArray(filter)) {
344 if (filter.length == 0) {
345 filter = null;
346 }
347 } else if (filter != null) {
348 filter = filter.length === 0 ? null : [filter];
349 }
350
351 const filterRe = filter == null ? null : filter.map(it => new RegExp(it));
352 const signOptions = {
353 "identity-validation": false,
354 // https://github.com/electron-userland/electron-builder/issues/1699
355 // kext are signed by the chipset manufacturers. You need a special certificate (only available on request) from Apple to be able to sign kext.
356 ignore: file => {
357 if (filterRe != null) {
358 for (const regExp of filterRe) {
359 if (regExp.test(file)) {
360 return true;
361 }
362 }
363 }
364
365 return file.endsWith(".kext") || file.startsWith("/Contents/PlugIns", appPath.length) || file.includes("/node_modules/puppeteer/.local-chromium") || file.includes("/node_modules/playwright-firefox/.local-browsers") || file.includes("/node_modules/playwright/.local-browsers");
366 /* Those are browser automating modules, browser (chromium, nightly) cannot be signed
367 https://github.com/electron-userland/electron-builder/issues/2010
368 https://github.com/electron-userland/electron-builder/issues/5383
369 */
370 },
371 identity: identity,
372 type,
373 platform: isMas ? "mas" : "darwin",
374 version: this.config.electronVersion,
375 app: appPath,
376 keychain: keychainFile || undefined,
377 binaries: options.binaries || undefined,
378 requirements: isMas || this.platformSpecificBuildOptions.requirements == null ? undefined : await this.getResource(this.platformSpecificBuildOptions.requirements),
379 // https://github.com/electron-userland/electron-osx-sign/issues/196
380 // will fail on 10.14.5+ because a signed but unnotarized app is also rejected.
381 "gatekeeper-assess": options.gatekeeperAssess === true,
382 // https://github.com/electron-userland/electron-builder/issues/1480
383 "strict-verify": options.strictVerify,
384 hardenedRuntime: isMas ? masOptions && masOptions.hardenedRuntime === true : options.hardenedRuntime !== false
385 };
386 await this.adjustSignOptions(signOptions, masOptions);
387
388 _builderUtil().log.info({
389 file: _builderUtil().log.filePath(appPath),
390 identityName: identity.name,
391 identityHash: identity.hash,
392 provisioningProfile: signOptions["provisioning-profile"] || "none"
393 }, "signing");
394
395 await this.doSign(signOptions); // https://github.com/electron-userland/electron-builder/issues/1196#issuecomment-312310209
396
397 if (masOptions != null && !isDevelopment) {
398 const certType = isDevelopment ? "Mac Developer" : "3rd Party Mac Developer Installer";
399 const masInstallerIdentity = await (0, _macCodeSign().findIdentity)(certType, masOptions.identity, keychainFile);
400
401 if (masInstallerIdentity == null) {
402 throw new (_builderUtil().InvalidConfigurationError)(`Cannot find valid "${certType}" identity to sign MAS installer, please see https://electron.build/code-signing`);
403 } // mas uploaded to AppStore, so, use "-" instead of space for name
404
405
406 const artifactName = this.expandArtifactNamePattern(masOptions, "pkg");
407 const artifactPath = path.join(outDir, artifactName);
408 await this.doFlat(appPath, artifactPath, masInstallerIdentity, keychainFile);
409 await this.dispatchArtifactCreated(artifactPath, null, _builderUtil().Arch.x64, this.computeSafeArtifactName(artifactName, "pkg"));
410 }
411 }
412
413 async adjustSignOptions(signOptions, masOptions) {
414 const resourceList = await this.resourceList;
415 const customSignOptions = masOptions || this.platformSpecificBuildOptions;
416 const entitlementsSuffix = masOptions == null ? "mac" : "mas";
417 let entitlements = customSignOptions.entitlements;
418
419 if (entitlements == null) {
420 const p = `entitlements.${entitlementsSuffix}.plist`;
421
422 if (resourceList.includes(p)) {
423 entitlements = path.join(this.info.buildResourcesDir, p);
424 } else {
425 entitlements = (0, _pathManager().getTemplatePath)("entitlements.mac.plist");
426 }
427 }
428
429 signOptions.entitlements = entitlements;
430 let entitlementsInherit = customSignOptions.entitlementsInherit;
431
432 if (entitlementsInherit == null) {
433 const p = `entitlements.${entitlementsSuffix}.inherit.plist`;
434
435 if (resourceList.includes(p)) {
436 entitlementsInherit = path.join(this.info.buildResourcesDir, p);
437 } else {
438 entitlementsInherit = (0, _pathManager().getTemplatePath)("entitlements.mac.plist");
439 }
440 }
441
442 signOptions["entitlements-inherit"] = entitlementsInherit;
443
444 if (customSignOptions.provisioningProfile != null) {
445 signOptions["provisioning-profile"] = customSignOptions.provisioningProfile;
446 }
447
448 signOptions['entitlements-loginhelper'] = customSignOptions.entitlementsLoginHelper;
449 } //noinspection JSMethodCanBeStatic
450
451
452 async doSign(opts) {
453 return (0, _electronOsxSign().signAsync)(opts);
454 } //noinspection JSMethodCanBeStatic
455
456
457 async doFlat(appPath, outFile, identity, keychain) {
458 // productbuild doesn't created directory for out file
459 await (0, _fsExtra().mkdirs)(path.dirname(outFile));
460 const args = (0, _pkg().prepareProductBuildArgs)(identity, keychain);
461 args.push("--component", appPath, "/Applications");
462 args.push(outFile);
463 return await (0, _builderUtil().exec)("productbuild", args);
464 }
465
466 getElectronSrcDir(dist) {
467 return path.resolve(this.projectDir, dist, this.info.framework.distMacOsAppName);
468 }
469
470 getElectronDestinationDir(appOutDir) {
471 return path.join(appOutDir, this.info.framework.distMacOsAppName);
472 } // todo fileAssociations
473
474
475 async applyCommonInfo(appPlist, contentsPath) {
476 const appInfo = this.appInfo;
477 const appFilename = appInfo.productFilename; // https://github.com/electron-userland/electron-builder/issues/1278
478
479 appPlist.CFBundleExecutable = appFilename.endsWith(" Helper") ? appFilename.substring(0, appFilename.length - " Helper".length) : appFilename;
480 const icon = await this.getIconPath();
481
482 if (icon != null) {
483 const oldIcon = appPlist.CFBundleIconFile;
484 const resourcesPath = path.join(contentsPath, "Resources");
485
486 if (oldIcon != null) {
487 await (0, _fs().unlinkIfExists)(path.join(resourcesPath, oldIcon));
488 }
489
490 const iconFileName = `${appFilename}.icns`;
491 appPlist.CFBundleIconFile = iconFileName;
492 await (0, _fs().copyFile)(icon, path.join(resourcesPath, iconFileName));
493 }
494
495 appPlist.CFBundleName = appInfo.productName;
496 appPlist.CFBundleDisplayName = appInfo.productName;
497 const minimumSystemVersion = this.platformSpecificBuildOptions.minimumSystemVersion;
498
499 if (minimumSystemVersion != null) {
500 appPlist.LSMinimumSystemVersion = minimumSystemVersion;
501 }
502
503 appPlist.CFBundleIdentifier = appInfo.macBundleIdentifier;
504 appPlist.CFBundleShortVersionString = this.platformSpecificBuildOptions.bundleShortVersion || appInfo.version;
505 appPlist.CFBundleVersion = appInfo.buildVersion;
506 (0, _builderUtil().use)(this.platformSpecificBuildOptions.category || this.config.category, it => appPlist.LSApplicationCategoryType = it);
507 appPlist.NSHumanReadableCopyright = appInfo.copyright;
508
509 if (this.platformSpecificBuildOptions.darkModeSupport) {
510 appPlist.NSRequiresAquaSystemAppearance = false;
511 }
512
513 const extendInfo = this.platformSpecificBuildOptions.extendInfo;
514
515 if (extendInfo != null) {
516 Object.assign(appPlist, extendInfo);
517 }
518 }
519
520 async signApp(packContext, isAsar) {
521 const appFileName = `${this.appInfo.productFilename}.app`;
522 await _bluebirdLst().default.map((0, _fsExtra().readdir)(packContext.appOutDir), file => {
523 if (file === appFileName) {
524 return this.sign(path.join(packContext.appOutDir, file), null, null);
525 }
526
527 return null;
528 });
529
530 if (!isAsar) {
531 return;
532 }
533
534 const outResourcesDir = path.join(packContext.appOutDir, "resources", "app.asar.unpacked");
535 await _bluebirdLst().default.map((0, _promise().orIfFileNotExist)((0, _fsExtra().readdir)(outResourcesDir), []), file => {
536 if (file.endsWith(".app")) {
537 return this.sign(path.join(outResourcesDir, file), null, null);
538 } else {
539 return null;
540 }
541 });
542 }
543
544}
545
546exports.default = MacPackager;
547
548function getCertificateType(isMas, isDevelopment) {
549 if (isDevelopment) {
550 return "Mac Developer";
551 }
552
553 return isMas ? "3rd Party Mac Developer Application" : "Developer ID Application";
554}
555// __ts-babel@6.0.4
556//# sourceMappingURL=macPackager.js.map
\No newline at end of file