expo-release-it 0.1.1 → 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (65) hide show
  1. package/build/command/build.js +119 -95
  2. package/build/command/build.js.map +1 -1
  3. package/build/command/bump.js +33 -27
  4. package/build/command/bump.js.map +1 -1
  5. package/build/command/init.js +75 -63
  6. package/build/command/init.js.map +1 -1
  7. package/build/command/pull.d.ts +5 -0
  8. package/build/command/pull.js +525 -0
  9. package/build/command/pull.js.map +1 -0
  10. package/build/command/submit.js +102 -85
  11. package/build/command/submit.js.map +1 -1
  12. package/build/command/upload.js +117 -105
  13. package/build/command/upload.js.map +1 -1
  14. package/build/index.js +328 -240
  15. package/build/index.js.map +1 -1
  16. package/build/util/FastlaneOption.js +9 -14
  17. package/build/util/FastlaneOption.js.map +1 -1
  18. package/build/util/FileUtil.d.ts +2 -1
  19. package/build/util/FileUtil.js +4 -0
  20. package/build/util/FileUtil.js.map +1 -1
  21. package/build/util/OptionHolder.d.ts +1 -2
  22. package/build/util/OptionHolder.js +7 -8
  23. package/build/util/OptionHolder.js.map +1 -1
  24. package/build/util/generateAppStoreConnectApiKeyFile.d.ts +3 -0
  25. package/build/util/{setup/promptCommonInputs.js → generateAppStoreConnectApiKeyFile.js} +36 -20
  26. package/build/util/generateAppStoreConnectApiKeyFile.js.map +1 -0
  27. package/build/util/injectTemplatePlaceHolders.js +8 -11
  28. package/build/util/injectTemplatePlaceHolders.js.map +1 -1
  29. package/build/util/input/InqueryInputs.js +7 -8
  30. package/build/util/input/InqueryInputs.js.map +1 -1
  31. package/build/util/iterateAllFiles.js.map +1 -1
  32. package/build/util/logger.d.ts +1 -0
  33. package/build/util/logger.js +1 -0
  34. package/build/util/logger.js.map +1 -1
  35. package/build/util/{VersionUtil.js → setup/VersionUtil.js} +9 -9
  36. package/build/util/setup/VersionUtil.js.map +1 -0
  37. package/build/util/setup/execShellScript.d.ts +19 -0
  38. package/build/util/setup/execShellScript.js +19 -0
  39. package/build/util/setup/execShellScript.js.map +1 -0
  40. package/build/util/{hydrateKeyholderFileValues.js → setup/hydrateKeyholderFileValues.js} +14 -10
  41. package/build/util/setup/hydrateKeyholderFileValues.js.map +1 -0
  42. package/build/util/setup/prepareAndroid.js +64 -37
  43. package/build/util/setup/prepareAndroid.js.map +1 -1
  44. package/build/util/setup/prepareIos.js +63 -35
  45. package/build/util/setup/prepareIos.js.map +1 -1
  46. package/build/util/setup/setup.d.ts +2 -1
  47. package/build/util/setup/setup.js +30 -25
  48. package/build/util/setup/setup.js.map +1 -1
  49. package/build/util/spinner.d.ts +3 -0
  50. package/build/util/spinner.js +14 -0
  51. package/build/util/spinner.js.map +1 -0
  52. package/build/util/throwError.js +1 -0
  53. package/build/util/throwError.js.map +1 -1
  54. package/package.json +5 -5
  55. package/template/android/Gemfile +1 -1
  56. package/template/android/fastlane/Fastfile +2 -2
  57. package/template/ios/Gemfile +2 -1
  58. package/template/ios/fastlane/Fastfile +20 -3
  59. package/build/util/VersionUtil.js.map +0 -1
  60. package/build/util/hydrateKeyholderFileValues.js.map +0 -1
  61. package/build/util/setup/promptCommonInputs.d.ts +0 -3
  62. package/build/util/setup/promptCommonInputs.js.map +0 -1
  63. package/template/ios/fastlane/Matchfile +0 -5
  64. /package/build/util/{VersionUtil.d.ts → setup/VersionUtil.d.ts} +0 -0
  65. /package/build/util/{hydrateKeyholderFileValues.d.ts → setup/hydrateKeyholderFileValues.d.ts} +0 -0
@@ -1,6 +1,3 @@
1
- // src/util/setup/prepareAndroid.ts
2
- import { spinner, $ } from "zx";
3
-
4
1
  // src/util/FileUtil.ts
5
2
  import fs from "fs-extra";
6
3
  import * as path from "path";
@@ -61,11 +58,11 @@ var package_default = {
61
58
  name: "expo-release-it",
62
59
  module: "src/index.ts",
63
60
  type: "module",
64
- version: "0.1.0",
61
+ version: "0.1.1",
65
62
  license: "MIT",
66
63
  scripts: {
67
64
  build: "tsup",
68
- dev: "bun run build && NODE_ENV=development node bin/expo-release-it.mjs",
65
+ dev: "yarn run build && NODE_ENV=development node bin/expo-release-it.mjs",
69
66
  release: "yarn build && release-it",
70
67
  android: "expo run:android",
71
68
  ios: "expo run:ios",
@@ -76,15 +73,15 @@ var package_default = {
76
73
  "@mj-studio/js-util": "^1.1.20",
77
74
  chalk: "^5.4.1",
78
75
  commander: "^13.1.0",
76
+ execa: "^9.5.2",
79
77
  "fs-extra": "^11.3.0",
78
+ ora: "^8.2.0",
80
79
  react: "18.3.1",
81
80
  "react-native": "0.76.9",
82
81
  semver: "^7.7.1",
83
- url: "^0.11.4",
84
- zx: "^8.5.3"
82
+ url: "^0.11.4"
85
83
  },
86
84
  devDependencies: {
87
- "@types/bun": "latest",
88
85
  "@types/fs-extra": "^11.0.4",
89
86
  "@types/semver": "^7.7.0",
90
87
  prettier: "3.5.3",
@@ -117,26 +114,13 @@ var OptionHolder = {
117
114
  input: {},
118
115
  keyholderMap: {},
119
116
  templateDirNames: ["key"],
120
- iosBundleIdentifier: "",
121
- androidPackageName: "",
122
117
  projectDir: "",
123
118
  outputOfInitDir: "",
124
119
  keyDir: "",
125
120
  keyholderFilePath: "",
126
121
  versionName: "",
127
- versionCode: ""
128
- };
129
-
130
- // src/util/logger.ts
131
- import chalk from "chalk";
132
- var logger = {
133
- success: (...msg) => console.log(chalk.green(`\u2714 ${msg.join(", ")}`)),
134
- error: (...msg) => console.log(chalk.red(`\u2716 ${msg.join(", ")}`)),
135
- warn: (...msg) => console.log(chalk.yellow(`\u26A0 ${msg.join(", ")}`)),
136
- info: (...msg) => console.log(chalk.cyan(`\u2139 ${msg.join(", ")}`)),
137
- title: (...msg) => console.log(chalk.bold.blue(`
138
- ${msg.join(", ")}`)),
139
- dim: (...msg) => console.log(chalk.dim(msg.join(", ")))
122
+ versionCode: "",
123
+ tempDir: ""
140
124
  };
141
125
 
142
126
  // src/util/iterateAllFiles.ts
@@ -155,7 +139,7 @@ async function iterateAllFiles(root, callback) {
155
139
  }
156
140
 
157
141
  // src/util/injectTemplatePlaceHolders.ts
158
- import { path as path2 } from "zx";
142
+ import * as path2 from "node:path";
159
143
  async function injectTemplatePlaceHolders(root) {
160
144
  await iterateAllFiles(root, async (filePath) => {
161
145
  const dirPath = path2.dirname(filePath);
@@ -171,25 +155,68 @@ async function injectTemplatePlaceHolders(root) {
171
155
  });
172
156
  }
173
157
 
158
+ // src/util/spinner.ts
159
+ import { oraPromise } from "ora";
160
+ import chalk from "chalk";
161
+ async function spinner(text, promise) {
162
+ return oraPromise(promise, {
163
+ text,
164
+ successText: chalk.green(`${text} - Done`),
165
+ failText: chalk.red(`${text} - Failed`)
166
+ });
167
+ }
168
+
169
+ // src/util/setup/execShellScript.ts
170
+ import { execa } from "execa";
171
+ var exe = execa({
172
+ stdin: "pipe",
173
+ stdout: "inherit",
174
+ stderr: "inherit",
175
+ shell: false
176
+ });
177
+ var yesShell = (command, args = [], options) => {
178
+ const subProcess = exe(command, args, { ...options, stdin: "pipe" });
179
+ subProcess.stdin?.write("y\n");
180
+ subProcess.stdin?.end();
181
+ return subProcess;
182
+ };
183
+
184
+ // src/util/logger.ts
185
+ import chalk2 from "chalk";
186
+ var logger = {
187
+ success: (...msg) => console.log(chalk2.green(`\u2714 ${msg.join(", ")}`)),
188
+ done: (...msg) => console.log(chalk2.green(`\u2714 ${msg.join(", ")} - Done`)),
189
+ error: (...msg) => console.log(chalk2.red(`\u2716 ${msg.join(", ")}`)),
190
+ warn: (...msg) => console.log(chalk2.yellow(`\u26A0 ${msg.join(", ")}`)),
191
+ info: (...msg) => console.log(chalk2.cyan(`\u2139 ${msg.join(", ")}`)),
192
+ title: (...msg) => console.log(chalk2.bold.blue(`
193
+ ${msg.join(", ")}`)),
194
+ dim: (...msg) => console.log(chalk2.dim(msg.join(", ")))
195
+ };
196
+
174
197
  // src/util/setup/prepareAndroid.ts
175
198
  async function prepareAndroid() {
176
199
  const srcDir = resolve2(OptionHolder.cli.templateDir, "android");
177
200
  const destDir = resolve2(OptionHolder.projectDir, "android");
201
+ await yesShell("expo", ["prebuild", "-p", "android", "--no-install"], {
202
+ cwd: OptionHolder.projectDir
203
+ });
204
+ logger.success("Expo Prebuild - Done");
178
205
  await spinner(
179
- "Prebuild Android",
180
- () => $`cd ${OptionHolder.projectDir} && expo prebuild -p android --no-install`
206
+ "Inject Templates",
207
+ iterateDir(srcDir, async (file) => {
208
+ const filePath = resolve2(srcDir, file);
209
+ remove(resolve2(destDir, file));
210
+ copy(filePath, resolve2(destDir, file));
211
+ })
181
212
  );
182
- logger.success("expo prebuild");
183
- await iterateDir(srcDir, async (file) => {
184
- const filePath = resolve2(srcDir, file);
185
- remove(resolve2(destDir, file));
186
- copy(filePath, resolve2(destDir, file));
187
- });
188
- logger.success("Inject Android templates");
189
- await replaceAndroidSigningConfig(destDir);
190
- logger.success("Overwrite Android Release Signing Config");
191
- await injectTemplatePlaceHolders(resolve2(destDir, "fastlane"));
192
- logger.success("Hydrate template placeholders");
213
+ await spinner("Overwrite Android Release Signing Config", replaceAndroidSigningConfig(destDir));
214
+ await spinner(
215
+ "Hydrate template placeholders",
216
+ injectTemplatePlaceHolders(resolve2(destDir, "fastlane"))
217
+ );
218
+ await exe({ cwd: destDir })`bundle install`;
219
+ logger.success("Bunder Install - Done");
193
220
  }
194
221
  async function replaceAndroidSigningConfig(destDir) {
195
222
  const buildGradleDirPath = resolve2(destDir, "app");
@@ -215,21 +242,11 @@ async function replaceAndroidSigningConfig(destDir) {
215
242
  write(buildGradlePath, content);
216
243
  }
217
244
 
218
- // src/util/EnvUtil.ts
219
- var isDev = process.env.NODE_ENV === "development";
220
- var isWin = process.platform.startsWith("win");
221
-
222
- // src/util/setup/promptCommonInputs.ts
223
- async function promptCommonInputs() {
224
- OptionHolder.projectDir = isDev ? resolve2("example") : resolve2(".");
225
- OptionHolder.outputOfInitDir = resolve2(OptionHolder.projectDir, "expo-release-it");
226
- OptionHolder.keyDir = resolve2(OptionHolder.outputOfInitDir, "key");
227
- OptionHolder.keyholderFilePath = resolve2(OptionHolder.outputOfInitDir, "keyholder.json");
228
- }
229
-
230
- // src/util/hydrateKeyholderFileValues.ts
245
+ // src/util/setup/hydrateKeyholderFileValues.ts
231
246
  async function hydrateKeyholderFileValues() {
232
- Object.assign(OptionHolder.keyholderMap, readJsonSlow(OptionHolder.keyholderFilePath));
247
+ if (exist(OptionHolder.keyholderFilePath)) {
248
+ Object.assign(OptionHolder.keyholderMap, readJsonSlow(OptionHolder.keyholderFilePath));
249
+ }
233
250
  }
234
251
 
235
252
  // src/util/throwError.ts
@@ -242,7 +259,7 @@ function throwError(message, e) {
242
259
  process.exit(1);
243
260
  }
244
261
 
245
- // src/util/VersionUtil.ts
262
+ // src/util/setup/VersionUtil.ts
246
263
  import semver from "semver";
247
264
  async function parseBinaryVersions() {
248
265
  const files = readdir(OptionHolder.projectDir);
@@ -299,36 +316,50 @@ async function parseBinaryVersions() {
299
316
  }
300
317
  }
301
318
 
319
+ // src/util/EnvUtil.ts
320
+ var isDev = process.env.NODE_ENV === "development";
321
+ var isWin = process.platform.startsWith("win");
322
+
302
323
  // src/util/setup/setup.ts
303
324
  async function setup() {
304
- await promptCommonInputs();
325
+ await setupBasicOptions();
305
326
  await hydrateKeyholderFileValues();
306
327
  await parseBinaryVersions();
307
328
  }
329
+ async function setupBasicOptions() {
330
+ OptionHolder.projectDir = isDev ? resolve2("example") : resolve2(".");
331
+ OptionHolder.outputOfInitDir = resolve2(OptionHolder.projectDir, "expo-release-it");
332
+ OptionHolder.keyDir = resolve2(OptionHolder.outputOfInitDir, "key");
333
+ OptionHolder.keyholderFilePath = resolve2(OptionHolder.outputOfInitDir, "keyholder.json");
334
+ OptionHolder.tempDir = resolve2(OptionHolder.outputOfInitDir, ".temp");
335
+ }
308
336
 
309
337
  // src/util/setup/prepareIos.ts
310
- import { $ as $2, spinner as spinner2 } from "zx";
311
338
  async function prepareIos() {
312
339
  const srcDir = resolve2(OptionHolder.cli.templateDir, "ios");
313
340
  const destDir = resolve2(OptionHolder.projectDir, "ios");
314
- await spinner2(
315
- "Prebuild iOS",
316
- () => $2`cd ${OptionHolder.projectDir} && expo prebuild -p ios --no-install`
317
- );
318
- logger.success("expo prebuild");
319
- await iterateDir(srcDir, async (file) => {
320
- const filePath = resolve2(srcDir, file);
321
- remove(resolve2(destDir, file));
322
- copy(filePath, resolve2(destDir, file));
341
+ await yesShell("expo", ["prebuild", "-p", "ios", "--no-install"], {
342
+ cwd: OptionHolder.projectDir
323
343
  });
324
- logger.success("Inject iOS templates");
325
- await injectTemplatePlaceHolders(resolve2(destDir, "fastlane"));
326
- logger.success("Hydrate template placeholders");
344
+ logger.success("Expo Prebuild - Done");
345
+ await spinner(
346
+ "Inject templates",
347
+ iterateDir(srcDir, async (file) => {
348
+ const filePath = resolve2(srcDir, file);
349
+ remove(resolve2(destDir, file));
350
+ copy(filePath, resolve2(destDir, file));
351
+ })
352
+ );
353
+ await spinner(
354
+ "Hydrate template placeholders",
355
+ injectTemplatePlaceHolders(resolve2(destDir, "fastlane"))
356
+ );
357
+ await exe({ cwd: destDir })`bundle install`;
358
+ logger.success("Bunder Install - Done");
327
359
  }
328
360
 
329
361
  // src/command/build.ts
330
- import { spinner as spinner3, $ as $3 } from "zx";
331
- import chalk3 from "chalk";
362
+ import chalk4 from "chalk";
332
363
 
333
364
  // src/util/calculateElapsed.ts
334
365
  import { padZero } from "@mj-studio/js-util";
@@ -342,7 +373,7 @@ function calculateElapsed(t) {
342
373
  // src/util/input/InqueryInputs.ts
343
374
  import { select } from "@inquirer/prompts";
344
375
  import { is } from "@mj-studio/js-util";
345
- import chalk2 from "chalk";
376
+ import chalk3 from "chalk";
346
377
  var InqueryInputs = {
347
378
  platform: async () => {
348
379
  if (!OptionHolder.input.platform) {
@@ -406,19 +437,19 @@ function constructInquirerFormattedMessage({
406
437
  referUrl,
407
438
  name
408
439
  }) {
409
- let ret = `${chalk2.bold(name)}`;
440
+ let ret = `${chalk3.bold(name)}`;
410
441
  if (explanation) {
411
442
  ret += `
412
443
 
413
- ${chalk2.italic.blue(explanation)}`;
444
+ ${chalk3.italic.blue(explanation)}`;
414
445
  }
415
446
  if (example) {
416
447
  ret += `
417
- ${chalk2.italic(`${chalk2.greenBright("example :")} ${example}`)}`;
448
+ ${chalk3.italic(`${chalk3.greenBright("example :")} ${example}`)}`;
418
449
  }
419
450
  if (referUrl) {
420
451
  ret += `
421
- ${chalk2.italic(`${chalk2.greenBright("references :")} ${chalk2.underline.blue(referUrl)}`)}`;
452
+ ${chalk3.italic(`${chalk3.greenBright("references :")} ${chalk3.underline.blue(referUrl)}`)}`;
422
453
  }
423
454
  if (explanation) {
424
455
  ret += "\n";
@@ -432,13 +463,9 @@ ${chalk2.italic(`${chalk2.greenBright("references :")} ${chalk2.underline.blue(r
432
463
  // src/util/FastlaneOption.ts
433
464
  function getIosFastlaneOptions() {
434
465
  return [
466
+ ...Object.entries(OptionHolder.keyholderMap).map(([k, v]) => `${k}:${v}`),
435
467
  `version_name:${OptionHolder.versionName}`,
436
468
  `version_code:${OptionHolder.versionCode}`,
437
- `ios_app_identifier:${OptionHolder.iosBundleIdentifier}`,
438
- `ios_xcode_project_target:${OptionHolder.keyholderMap.ios_xcode_project_target}`,
439
- `ios_developer_team_id:${OptionHolder.keyholderMap.ios_developer_team_id}`,
440
- `ios_app_store_connect_api_key_id:${OptionHolder.keyholderMap.ios_app_store_connect_api_key_id}`,
441
- `ios_app_store_connect_api_key_issuer_id:${OptionHolder.keyholderMap.ios_app_store_connect_api_key_issuer_id}`,
442
469
  `api_key_filepath:${resolve2(OptionHolder.keyDir, "ios_testflight_upload_api_key.p8")}`,
443
470
  `upload_metadata:${OptionHolder.input.uploadMetadata}`,
444
471
  `ipa_path:${resolve2(OptionHolder.outputOfInitDir, "output", "ios", "app.ipa")}`,
@@ -457,10 +484,10 @@ async function build({ options }) {
457
484
  logger.info(`Version: ${OptionHolder.versionName}(${OptionHolder.versionCode})`);
458
485
  if (OptionHolder.input.platform === "ios") {
459
486
  await buildIos();
460
- logger.success(`iOS Build ${chalk3.bold.inverse(calculateElapsed(startTime))}`);
487
+ logger.success(`iOS Build ${chalk4.bold.inverse(calculateElapsed(startTime))}`);
461
488
  } else {
462
489
  await buildAndroid();
463
- logger.success(`Android Build ${chalk3.bold.inverse(calculateElapsed(startTime))}`);
490
+ logger.success(`Android Build ${chalk4.bold.inverse(calculateElapsed(startTime))}`);
464
491
  }
465
492
  }
466
493
  async function promptInputs() {
@@ -470,8 +497,7 @@ async function promptInputs() {
470
497
  }
471
498
  async function buildIos() {
472
499
  const iosDir = resolve2(OptionHolder.projectDir, "ios");
473
- const $$ = $3({
474
- verbose: false,
500
+ const exeEnv = exe({
475
501
  cwd: iosDir,
476
502
  env: {
477
503
  MATCH_PASSWORD: OptionHolder.keyholderMap.ios_match_password
@@ -480,40 +506,38 @@ async function buildIos() {
480
506
  await prepareIos();
481
507
  await fastlane();
482
508
  async function fastlane() {
483
- await spinner3("Bundler Install", () => $$`bundle install`);
484
- logger.success("Bundler Install");
485
509
  if (OptionHolder.input.pod) {
486
- await spinner3("Pod Install", () => $$`bundle exec pod install`);
487
- logger.success("Pod Install");
510
+ await exeEnv("bundle", ["exec", "pod", "install"]);
511
+ logger.done("Pod Install");
488
512
  }
489
513
  remove(resolve2(iosDir, ".xcode.env.local"));
490
- await spinner3("Fastlane", () => $$`bundle exec fastlane build ${getIosFastlaneOptions()}`);
514
+ await exeEnv("bundle", ["exec", "fastlane", "build", ...getIosFastlaneOptions()]);
515
+ logger.success(
516
+ `artifact generated: ${relativePath(OptionHolder.projectDir, resolve2(OptionHolder.outputOfInitDir, "output", "ios", "app.ipa"))}`
517
+ );
491
518
  }
492
519
  }
493
520
  async function buildAndroid() {
494
521
  const androidDir = resolve2(OptionHolder.projectDir, "android");
495
- const $$ = $3({
496
- verbose: false,
522
+ const exeEnv = exe({
497
523
  cwd: androidDir
498
524
  });
499
525
  await prepareAndroid();
500
526
  await fastlane();
501
527
  async function fastlane() {
502
- await spinner3("Bundler Install", () => $$`bundle install`);
503
- logger.success("Bundler Install");
504
528
  let buildOutputDir;
505
529
  let outputDir;
506
530
  if (OptionHolder.input.androidOutput === "aab") {
507
- await spinner3(
531
+ await spinner(
508
532
  "Bundle AAB",
509
- () => $$`${isWin ? "gradle.bat" : "./gradlew"} app:bundleRelease`
533
+ exeEnv(isWin ? "gradle.bat" : "./gradlew", ["app:bundleRelease"])
510
534
  );
511
535
  buildOutputDir = resolve2(androidDir, "app", "build", "outputs", "bundle", "release");
512
536
  outputDir = resolve2(OptionHolder.outputOfInitDir, "output", "android", "aab");
513
537
  } else {
514
- await spinner3(
538
+ await spinner(
515
539
  "Bundle APK",
516
- () => $$`${isWin ? "gradle.bat" : "./gradlew"} app:assembleRelease`
540
+ exeEnv(isWin ? "gradle.bat" : "./gradlew", ["app:assembleRelease"])
517
541
  );
518
542
  buildOutputDir = resolve2(androidDir, "app", "build", "outputs", "apk", "release");
519
543
  outputDir = resolve2(OptionHolder.outputOfInitDir, "output", "android", "apk");
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/util/setup/prepareAndroid.ts","../../src/util/FileUtil.ts","../../package.json","../../src/util/OptionHolder.ts","../../src/util/logger.ts","../../src/util/iterateAllFiles.ts","../../src/util/injectTemplatePlaceHolders.ts","../../src/util/EnvUtil.ts","../../src/util/setup/promptCommonInputs.ts","../../src/util/hydrateKeyholderFileValues.ts","../../src/util/throwError.ts","../../src/util/VersionUtil.ts","../../src/util/setup/setup.ts","../../src/util/setup/prepareIos.ts","../../src/command/build.ts","../../src/util/calculateElapsed.ts","../../src/util/input/InqueryInputs.ts","../../src/util/FastlaneOption.ts"],"sourcesContent":["import { spinner, $ } from 'zx';\nimport { resolve, remove, iterateDir, copy, read, write, relativePath } from '../FileUtil';\nimport { OptionHolder } from '../OptionHolder';\nimport { logger } from '../logger';\nimport { injectTemplatePlaceHolders } from '../injectTemplatePlaceHolders';\n\nexport async function prepareAndroid() {\n const srcDir = resolve(OptionHolder.cli.templateDir, 'android');\n const destDir = resolve(OptionHolder.projectDir, 'android');\n\n await spinner(\n 'Prebuild Android',\n () => $`cd ${OptionHolder.projectDir} && expo prebuild -p android --no-install`,\n );\n logger.success('expo prebuild');\n\n await iterateDir(srcDir, async (file) => {\n const filePath = resolve(srcDir, file);\n remove(resolve(destDir, file));\n copy(filePath, resolve(destDir, file));\n });\n logger.success('Inject Android templates');\n\n await replaceAndroidSigningConfig(destDir);\n logger.success('Overwrite Android Release Signing Config');\n\n await injectTemplatePlaceHolders(resolve(destDir, 'fastlane'));\n logger.success('Hydrate template placeholders');\n}\n\nasync function replaceAndroidSigningConfig(destDir: string) {\n const buildGradleDirPath = resolve(destDir, 'app');\n const buildGradlePath = resolve(destDir, 'app', 'build.gradle');\n const {\n android_keystore_store_password,\n android_keystore_key_alias,\n android_keystore_key_password,\n } = OptionHolder.keyholderMap;\n\n const content = read(buildGradlePath).replace(\n /signingConfigs.*?{.*?debug.*?{.*?}.*?}/s,\n `\n signingConfigs {\n debug {\n storeFile file('${relativePath(buildGradleDirPath, resolve(OptionHolder.outputOfInitDir, 'key', 'android_release_keystore.jks'))}')\n storePassword '${android_keystore_store_password}'\n keyAlias '${android_keystore_key_alias}'\n keyPassword '${android_keystore_key_password}'\n }\n }\n `,\n );\n write(buildGradlePath, content);\n}\n","import fs from 'fs-extra';\nimport * as path from 'path';\n\nexport const join = path.join;\nexport const resolve = path.resolve;\n\nexport function exist(path: string) {\n return fs.existsSync(path);\n}\n\nexport function isDir(path: string) {\n return exist(path) && fs.lstatSync(path).isDirectory();\n}\n\nexport function relativePath(from: string, to: string) {\n return path.relative(from, to);\n}\n\nexport function isFile(path: string) {\n return exist(path) && fs.lstatSync(path).isFile();\n}\n\nexport function read(path: string) {\n return fs.readFileSync(path, { encoding: 'utf8' });\n}\n\nexport function readdir(path: string) {\n return fs.readdirSync(path);\n}\n\n// you should require when possible(optimized in js)\nexport function readJsonSlow(path: string) {\n return fs.readJSONSync(path);\n}\n\nexport function write(p: string, content: string) {\n const dir = path.dirname(p);\n if (!exist(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n\n return fs.writeFileSync(p, content);\n}\nexport function copy(src: string, dest: string, options?: fs.CopyOptionsSync) {\n fs.copySync(src, dest, options);\n}\n\nexport function writeJson(path: string, json: any) {\n return write(path, JSON.stringify(json, null, 2));\n}\n\nexport function remove(path: string) {\n if (!exist(path)) {\n return;\n }\n\n if (fs.lstatSync(path).isDirectory()) {\n return fs.rmSync(path, { force: true, recursive: true });\n } else {\n return fs.rmSync(path, { force: true });\n }\n}\n\nexport async function iterateDir(path: string, fn: (file: string) => Promise<void> | void) {\n if (!isDir(path)) {\n return;\n }\n\n for (const file of fs.readdirSync(path)) {\n await fn(file);\n }\n}\n","{\n \"name\": \"expo-release-it\",\n \"module\": \"src/index.ts\",\n \"type\": \"module\",\n \"version\": \"0.1.0\",\n \"license\": \"MIT\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"bun run build && NODE_ENV=development node bin/expo-release-it.mjs\",\n \"release\": \"yarn build && release-it\",\n \"android\": \"expo run:android\",\n \"ios\": \"expo run:ios\",\n \"t\": \"tsc --noEmit -p .\"\n },\n \"dependencies\": {\n \"@inquirer/prompts\": \"^7.4.1\",\n \"@mj-studio/js-util\": \"^1.1.20\",\n \"chalk\": \"^5.4.1\",\n \"commander\": \"^13.1.0\",\n \"fs-extra\": \"^11.3.0\",\n \"react\": \"18.3.1\",\n \"react-native\": \"0.76.9\",\n \"semver\": \"^7.7.1\",\n \"url\": \"^0.11.4\",\n \"zx\": \"^8.5.3\"\n },\n \"devDependencies\": {\n \"@types/bun\": \"latest\",\n \"@types/fs-extra\": \"^11.0.4\",\n \"@types/semver\": \"^7.7.0\",\n \"prettier\": \"3.5.3\",\n \"release-it\": \"^19.0.1\",\n \"tiny-glob\": \"^0.2.9\",\n \"tsup\": \"^8.4.0\",\n \"typescript\": \"^5.8.3\"\n },\n \"workspaces\": [\n \"example\"\n ],\n \"bin\": \"./bin/expo-release-it.mjs\",\n \"files\": [\n \"build\",\n \"package.json\",\n \"bin\",\n \"template\"\n ],\n \"packageManager\": \"yarn@4.9.1\"\n}\n","import pkgJson from '../../package.json';\nimport { resolve } from './FileUtil';\nimport { fileURLToPath } from 'url';\n\n/**\n * CLI Comprehensive options\n * Each values can be empty by command and timing.\n */\nexport const OptionHolder: {\n // cli specific options\n cli: {\n // cli version\n version: string;\n // cli project root directory\n rootDir: string;\n // cli template source directory\n templateDir: string;\n };\n input: {\n platform: 'android' | 'ios';\n uploadMetadata: boolean;\n androidOutput: 'apk' | 'aab';\n pod: boolean;\n };\n keyholderMap: {\n ios_app_identifier: string;\n ios_developer_team_id: string;\n ios_match_git_url: string;\n ios_app_store_connect_api_key_id: string;\n ios_app_store_connect_api_key_issuer_id: string;\n ios_xcode_project_target: string;\n ios_match_password: string;\n\n android_keystore_store_password: string;\n android_keystore_key_alias: string;\n android_keystore_key_password: string;\n android_package_name: string;\n };\n iosBundleIdentifier: string;\n androidPackageName: string;\n templateDirNames: string[];\n // dest project root directory\n projectDir: string;\n // dest project output of init command direcotry\n outputOfInitDir: string;\n keyDir: string;\n keyholderFilePath: string;\n versionName: string;\n versionCode: string;\n} = {\n cli: {\n version: pkgJson.version,\n rootDir: resolve(fileURLToPath(import.meta.url), '../..'),\n templateDir: resolve(fileURLToPath(import.meta.url), '../../template'),\n },\n input: {} as any,\n keyholderMap: {} as any,\n templateDirNames: ['key'],\n iosBundleIdentifier: '',\n androidPackageName: '',\n projectDir: '',\n outputOfInitDir: '',\n keyDir: '',\n keyholderFilePath: '',\n versionName: '',\n versionCode: '',\n};\n","import chalk from 'chalk';\n\nexport const logger = {\n success: (...msg: any[]) => console.log(chalk.green(`✔ ${msg.join(', ')}`)),\n error: (...msg: any[]) => console.log(chalk.red(`✖ ${msg.join(', ')}`)),\n warn: (...msg: any[]) => console.log(chalk.yellow(`⚠ ${msg.join(', ')}`)),\n info: (...msg: any[]) => console.log(chalk.cyan(`ℹ ${msg.join(', ')}`)),\n title: (...msg: any[]) => console.log(chalk.bold.blue(`\\n${msg.join(', ')}`)),\n dim: (...msg: any[]) => console.log(chalk.dim(msg.join(', '))),\n};\n","import { readdir, isFile, isDir, join } from './FileUtil';\n\nexport async function iterateAllFiles(root: string, callback: (filePath: string) => Promise<void>) {\n await go(root);\n\n async function go(dirPath: string) {\n const paths = readdir(dirPath).map((f) => join(dirPath, f));\n\n for (const p of paths) {\n if (isFile(p)) {\n await callback(p);\n } else if (isDir(p)) {\n await go(p);\n }\n }\n }\n}\n","import { iterateAllFiles } from './iterateAllFiles';\nimport { path } from 'zx';\nimport { read, relativePath, write } from './FileUtil';\nimport { OptionHolder } from './OptionHolder';\n\nexport async function injectTemplatePlaceHolders(root: string) {\n await iterateAllFiles(root, async (filePath: string) => {\n const dirPath = path.dirname(filePath);\n let content = read(filePath);\n for (const [key, value] of Object.entries(OptionHolder.keyholderMap)) {\n content = content.replaceAll(`{{${key}}}`, value);\n }\n // dynamic replacements\n content = content.replaceAll(\n '{{key_dir_relative_path}}',\n relativePath(dirPath, OptionHolder.keyDir),\n );\n write(filePath, content);\n });\n}\n","export const isDev = process.env.NODE_ENV === 'development';\nexport const isWin = process.platform.startsWith('win');\n","import { OptionHolder } from '../OptionHolder';\nimport { isDev } from '../EnvUtil';\nimport { resolve } from '../FileUtil';\n\nexport async function promptCommonInputs() {\n OptionHolder.projectDir = isDev ? resolve('example') : resolve('.');\n\n OptionHolder.outputOfInitDir = resolve(OptionHolder.projectDir, 'expo-release-it');\n OptionHolder.keyDir = resolve(OptionHolder.outputOfInitDir, 'key');\n OptionHolder.keyholderFilePath = resolve(OptionHolder.outputOfInitDir, 'keyholder.json');\n}\n","import { OptionHolder } from './OptionHolder';\nimport { readJsonSlow } from './FileUtil';\n\nexport async function hydrateKeyholderFileValues() {\n Object.assign(OptionHolder.keyholderMap, readJsonSlow(OptionHolder.keyholderFilePath));\n}\n","import { logger } from './logger';\n\nexport function throwError(message: string, e?: any): never {\n if (e) {\n logger.error(message, e);\n } else {\n logger.error(message);\n }\n process.exit(1);\n}\n","import { OptionHolder } from './OptionHolder';\nimport { throwError } from './throwError';\nimport semver from 'semver';\nimport { readdir, read, readJsonSlow, write, writeJson, resolve } from './FileUtil';\n\nexport async function parseBinaryVersions() {\n const files = readdir(OptionHolder.projectDir);\n\n const jsConfigFiles = ['app.config.ts', 'app.config.js', 'app.config.cjs', 'app.config.mjs'];\n const jsonConfigFile = 'app.json';\n\n for (const jsConfigFile of jsConfigFiles) {\n if (files.includes(jsConfigFile)) {\n await parseFromJsConfigFile(jsConfigFile);\n return;\n }\n }\n\n if (files.includes(jsonConfigFile)) {\n await parseFromJsonConfigFile(jsonConfigFile);\n return;\n }\n\n throwError('expo config file not found');\n\n async function parseFromJsConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const content = read(filePath);\n\n const VERSION_NAME = /const VERSION_NAME = '(.*?)';/.exec(content)?.[1];\n const VERSION_CODE = /const VERSION_CODE = (.*?);/.exec(content)?.[1];\n\n if (!VERSION_NAME) {\n throwError('cannot parse version name');\n }\n if (!VERSION_CODE) {\n throwError('cannot parse version code');\n }\n\n if (!semver.valid(VERSION_NAME)) {\n throwError('VERSION_NAME is not a valid semver format');\n }\n\n OptionHolder.versionName = VERSION_NAME;\n OptionHolder.versionCode = VERSION_CODE;\n }\n\n async function parseFromJsonConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const json = readJsonSlow(filePath);\n\n const versionName = json.expo?.version + '';\n const iosVersionCode = json.expo?.ios?.buildNumber + '';\n const androidVersionCode = json.expo?.android?.versionCode + '';\n\n if (!/\\d+/.test(iosVersionCode)) {\n throwError('app.json expo.ios.buildNumber is not an integer');\n }\n\n if (!/\\d+/.test(androidVersionCode)) {\n throwError('app.json expo.android.versionCode is not an integer');\n }\n\n if (iosVersionCode !== androidVersionCode) {\n throwError('app.json expo.ios.buildNumber is not equal with expo.android.versionCode');\n }\n\n if (!semver.valid(versionName)) {\n throwError('VERSION_NAME is not a valid semver format');\n }\n\n OptionHolder.versionName = versionName;\n OptionHolder.versionCode = iosVersionCode;\n }\n}\n\nexport async function injectBinaryVersions({\n versionCode,\n versionName,\n}: {\n versionName: string;\n versionCode: string;\n}) {\n const files = readdir(OptionHolder.projectDir);\n\n const jsConfigFiles = ['app.config.ts', 'app.config.js', 'app.config.cjs', 'app.config.mjs'];\n const jsonConfigFile = 'app.json';\n\n for (const jsConfigFile of jsConfigFiles) {\n if (files.includes(jsConfigFile)) {\n await injectToJsConfigFile(jsConfigFile);\n return;\n }\n }\n\n if (files.includes(jsonConfigFile)) {\n await injectToJsonConfigFile(jsonConfigFile);\n return;\n }\n\n throwError('expo config file not found');\n\n async function injectToJsConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n let content = read(filePath);\n\n content = content.replace(\n /const VERSION_NAME = '(.*?)';/,\n `const VERSION_NAME = '${versionName}';`,\n );\n content = content.replace(\n /const VERSION_CODE = (.*?);/,\n `const VERSION_CODE = ${versionCode};`,\n );\n\n write(filePath, content);\n }\n\n async function injectToJsonConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const json = readJsonSlow(filePath);\n\n json.expo.version = versionName;\n json.expo.ios.buildNumber = versionCode;\n json.expo.android.versionCode = +versionCode;\n\n writeJson(filePath, json);\n }\n}\n","import { promptCommonInputs } from './promptCommonInputs';\nimport { hydrateKeyholderFileValues } from '../hydrateKeyholderFileValues';\nimport { parseBinaryVersions } from '../VersionUtil';\n\nexport async function setup() {\n await promptCommonInputs();\n await hydrateKeyholderFileValues();\n await parseBinaryVersions();\n}\n","import { $, spinner } from 'zx';\nimport { remove, resolve, iterateDir, copy } from '../FileUtil';\nimport { OptionHolder } from '../OptionHolder';\nimport { logger } from '../logger';\nimport { injectTemplatePlaceHolders } from '../injectTemplatePlaceHolders';\n\nexport async function prepareIos() {\n const srcDir = resolve(OptionHolder.cli.templateDir, 'ios');\n const destDir = resolve(OptionHolder.projectDir, 'ios');\n\n await spinner(\n 'Prebuild iOS',\n () => $`cd ${OptionHolder.projectDir} && expo prebuild -p ios --no-install`,\n );\n logger.success('expo prebuild');\n\n await iterateDir(srcDir, async (file) => {\n const filePath = resolve(srcDir, file);\n remove(resolve(destDir, file));\n copy(filePath, resolve(destDir, file));\n });\n logger.success('Inject iOS templates');\n\n await injectTemplatePlaceHolders(resolve(destDir, 'fastlane'));\n logger.success('Hydrate template placeholders');\n}\n","import { prepareAndroid } from '../util/setup/prepareAndroid';\nimport { setup } from '../util/setup/setup';\nimport { prepareIos } from '../util/setup/prepareIos';\nimport { logger } from '../util/logger';\nimport { OptionHolder } from '../util/OptionHolder';\nimport { spinner, $ } from 'zx';\nimport { resolve, remove, copy, relativePath } from '../util/FileUtil';\nimport chalk from 'chalk';\nimport { calculateElapsed } from '../util/calculateElapsed';\nimport { isWin } from '../util/EnvUtil';\nimport { InqueryInputs } from '../util/input/InqueryInputs';\nimport { getIosFastlaneOptions } from '../util/FastlaneOption';\n\nexport async function build({ options }: { options: any }) {\n Object.assign(OptionHolder.input, options);\n const startTime = Date.now();\n await setup();\n await promptInputs();\n\n logger.info('Build Started');\n logger.info(`Version: ${OptionHolder.versionName}(${OptionHolder.versionCode})`);\n\n if (OptionHolder.input.platform === 'ios') {\n await buildIos();\n logger.success(`iOS Build ${chalk.bold.inverse(calculateElapsed(startTime))}`);\n } else {\n await buildAndroid();\n logger.success(`Android Build ${chalk.bold.inverse(calculateElapsed(startTime))}`);\n }\n}\n\nasync function promptInputs() {\n await InqueryInputs.platform();\n await InqueryInputs.podinstall();\n await InqueryInputs.androidBuildOutput();\n}\n\nasync function buildIos() {\n const iosDir = resolve(OptionHolder.projectDir, 'ios');\n const $$ = $({\n verbose: false,\n cwd: iosDir,\n env: {\n MATCH_PASSWORD: OptionHolder.keyholderMap.ios_match_password,\n },\n });\n await prepareIos();\n await fastlane();\n\n async function fastlane() {\n await spinner('Bundler Install', () => $$`bundle install`);\n logger.success('Bundler Install');\n\n if (OptionHolder.input.pod) {\n await spinner('Pod Install', () => $$`bundle exec pod install`);\n logger.success('Pod Install');\n }\n remove(resolve(iosDir, '.xcode.env.local'));\n\n await spinner('Fastlane', () => $$`bundle exec fastlane build ${getIosFastlaneOptions()}`);\n }\n}\nasync function buildAndroid() {\n const androidDir = resolve(OptionHolder.projectDir, 'android');\n const $$ = $({\n verbose: false,\n cwd: androidDir,\n });\n await prepareAndroid();\n await fastlane();\n\n async function fastlane() {\n await spinner('Bundler Install', () => $$`bundle install`);\n logger.success('Bundler Install');\n\n let buildOutputDir: string;\n let outputDir: string;\n\n if (OptionHolder.input.androidOutput === 'aab') {\n // aab: app/build/outputs/bundle/release/app-release.aab\n await spinner(\n 'Bundle AAB',\n () => $$`${isWin ? 'gradle.bat' : './gradlew'} app:bundleRelease`,\n );\n buildOutputDir = resolve(androidDir, 'app', 'build', 'outputs', 'bundle', 'release');\n outputDir = resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'aab');\n } else {\n // apk: app/build/outputs/apk/release/app-release.apk\n await spinner(\n 'Bundle APK',\n () => $$`${isWin ? 'gradle.bat' : './gradlew'} app:assembleRelease`,\n );\n buildOutputDir = resolve(androidDir, 'app', 'build', 'outputs', 'apk', 'release');\n outputDir = resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'apk');\n }\n\n remove(outputDir);\n copy(buildOutputDir, outputDir);\n\n logger.success(`artifact generated: ${relativePath(OptionHolder.projectDir, outputDir)}`);\n }\n}\n","import { padZero } from '@mj-studio/js-util';\n\nexport function calculateElapsed(t: number) {\n let seconds = Math.floor((Date.now() - t) / 1000);\n const minutes = Math.floor(seconds / 60);\n seconds = seconds % 60;\n return `${minutes}:${padZero(seconds)}`;\n}\n","import { OptionHolder } from '../OptionHolder';\nimport { select } from '@inquirer/prompts';\nimport { is } from '@mj-studio/js-util';\nimport chalk from 'chalk';\n\nexport const InqueryInputs = {\n platform: async () => {\n if (!OptionHolder.input.platform) {\n OptionHolder.input.platform = await select({\n message: constructInquirerFormattedMessage({\n name: 'Platform',\n explanation: `Platform to run action`,\n }),\n choices: [\n { name: 'ios', value: 'ios', description: 'Release ios' },\n { name: 'android', value: 'android', description: 'Release android' },\n ],\n });\n }\n },\n podinstall: async () => {\n if (OptionHolder.input.platform === 'ios') {\n OptionHolder.input.pod = await select({\n message: constructInquirerFormattedMessage({\n name: 'Install CocoaPods?',\n }),\n choices: [\n { name: 'yes', value: true, description: 'Install pods before release' },\n { name: 'no', value: false, description: 'Skip pods install' },\n ],\n });\n }\n },\n androidBuildOutput: async () => {\n if (OptionHolder.input.platform === 'android') {\n if (!OptionHolder.input.androidOutput) {\n OptionHolder.input.androidOutput = await select({\n message: constructInquirerFormattedMessage({\n name: 'Android output artifact type',\n }),\n choices: [\n { name: 'aab', value: 'aab', description: 'Build as App bundle' },\n { name: 'apk', value: 'apk', description: 'Build as APK' },\n ],\n });\n }\n }\n },\n uploadMetadata: async () => {\n if (!is.boolean(OptionHolder.input.uploadMetadata)) {\n OptionHolder.input.uploadMetadata = await select({\n message: constructInquirerFormattedMessage({\n name: 'Upload Metadata(screenshot, title, description, ...)',\n }),\n choices: [\n { name: 'yes', value: true, description: 'Upload' },\n { name: 'no', value: false, description: \"Don't Upload\" },\n ],\n });\n }\n },\n};\n\nexport function constructInquirerFormattedMessage({\n example,\n explanation,\n referUrl,\n name,\n}: {\n name: string;\n explanation?: string;\n example?: string;\n referUrl?: string;\n}) {\n let ret = `${chalk.bold(name)}`;\n if (explanation) {\n ret += `\\n\\n${chalk.italic.blue(explanation)}`;\n }\n if (example) {\n ret += `\\n${chalk.italic(`${chalk.greenBright('example :')} ${example}`)}`;\n }\n if (referUrl) {\n ret += `\\n${chalk.italic(`${chalk.greenBright('references :')} ${chalk.underline.blue(referUrl)}`)}`;\n }\n\n if (explanation) {\n ret += '\\n';\n if (example || referUrl) {\n ret += '\\n';\n }\n }\n\n return ret;\n}\n","import { OptionHolder } from './OptionHolder';\nimport { resolve } from './FileUtil';\n\nexport function getAndroidFastlaneOptions() {\n return [\n `version_name:${OptionHolder.versionName}`,\n `version_code:${OptionHolder.versionCode}`,\n `package_name:${OptionHolder.androidPackageName}`,\n `upload_metadata:${OptionHolder.input.uploadMetadata}`,\n `aab_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'aab', 'app-release.aab')}`,\n `apk_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'apk', 'app-release.apk')}`,\n `skip_upload_apk:${OptionHolder.input.androidOutput !== 'apk'}`,\n `skip_upload_aab:${OptionHolder.input.androidOutput !== 'aab'}`,\n ];\n}\n\nexport function getIosFastlaneOptions() {\n return [\n `version_name:${OptionHolder.versionName}`,\n `version_code:${OptionHolder.versionCode}`,\n `ios_app_identifier:${OptionHolder.iosBundleIdentifier}`,\n `ios_xcode_project_target:${OptionHolder.keyholderMap.ios_xcode_project_target}`,\n `ios_developer_team_id:${OptionHolder.keyholderMap.ios_developer_team_id}`,\n `ios_app_store_connect_api_key_id:${OptionHolder.keyholderMap.ios_app_store_connect_api_key_id}`,\n `ios_app_store_connect_api_key_issuer_id:${OptionHolder.keyholderMap.ios_app_store_connect_api_key_issuer_id}`,\n `api_key_filepath:${resolve(OptionHolder.keyDir, 'ios_testflight_upload_api_key.p8')}`,\n `upload_metadata:${OptionHolder.input.uploadMetadata}`,\n `ipa_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'ios', 'app.ipa')}`,\n `ipa_dir:${resolve(OptionHolder.outputOfInitDir, 'output', 'ios')}`,\n `ipa_name:app.ipa`,\n ];\n}\n"],"mappings":"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","names":["join","resolve","path","path","resolve","join","path","path","resolve","resolve","resolve","$","spinner","resolve","spinner","$","spinner","$","chalk","chalk","resolve","chalk","resolve","$","spinner"]}
1
+ {"version":3,"sources":["../../src/util/FileUtil.ts","../../package.json","../../src/util/OptionHolder.ts","../../src/util/iterateAllFiles.ts","../../src/util/injectTemplatePlaceHolders.ts","../../src/util/spinner.ts","../../src/util/setup/execShellScript.ts","../../src/util/logger.ts","../../src/util/setup/prepareAndroid.ts","../../src/util/setup/hydrateKeyholderFileValues.ts","../../src/util/throwError.ts","../../src/util/setup/VersionUtil.ts","../../src/util/EnvUtil.ts","../../src/util/setup/setup.ts","../../src/util/setup/prepareIos.ts","../../src/command/build.ts","../../src/util/calculateElapsed.ts","../../src/util/input/InqueryInputs.ts","../../src/util/FastlaneOption.ts"],"sourcesContent":["import fs from 'fs-extra';\nimport * as path from 'path';\n\nexport const join = path.join;\nexport const resolve = path.resolve;\n\nexport function exist(path: string) {\n return fs.existsSync(path);\n}\n\nexport function isDir(path: string) {\n return exist(path) && fs.lstatSync(path).isDirectory();\n}\n\nexport function relativePath(from: string, to: string) {\n return path.relative(from, to);\n}\n\nexport function isFile(path: string) {\n return exist(path) && fs.lstatSync(path).isFile();\n}\n\nexport function read(path: string) {\n return fs.readFileSync(path, { encoding: 'utf8' });\n}\n\nexport function readdir(path: string) {\n return fs.readdirSync(path);\n}\n\n// you should require when possible(optimized in js)\nexport function readJsonSlow(path: string) {\n return fs.readJSONSync(path);\n}\n\nexport function write(p: string, content: string) {\n const dir = path.dirname(p);\n if (!exist(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n\n return fs.writeFileSync(p, content);\n}\nexport function copy(src: string, dest: string, options?: fs.CopyOptionsSync) {\n fs.copySync(src, dest, options);\n}\nexport function move(src: string, dest: string, options?: fs.MoveOptions) {\n fs.moveSync(src, dest, options);\n}\n\nexport function writeJson(path: string, json: any) {\n return write(path, JSON.stringify(json, null, 2));\n}\n\nexport function remove(path: string) {\n if (!exist(path)) {\n return;\n }\n\n if (fs.lstatSync(path).isDirectory()) {\n return fs.rmSync(path, { force: true, recursive: true });\n } else {\n return fs.rmSync(path, { force: true });\n }\n}\n\nexport async function iterateDir(path: string, fn: (file: string) => Promise<void> | void) {\n if (!isDir(path)) {\n return;\n }\n\n for (const file of fs.readdirSync(path)) {\n await fn(file);\n }\n}\n","{\n \"name\": \"expo-release-it\",\n \"module\": \"src/index.ts\",\n \"type\": \"module\",\n \"version\": \"0.1.1\",\n \"license\": \"MIT\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"yarn run build && NODE_ENV=development node bin/expo-release-it.mjs\",\n \"release\": \"yarn build && release-it\",\n \"android\": \"expo run:android\",\n \"ios\": \"expo run:ios\",\n \"t\": \"tsc --noEmit -p .\"\n },\n \"dependencies\": {\n \"@inquirer/prompts\": \"^7.4.1\",\n \"@mj-studio/js-util\": \"^1.1.20\",\n \"chalk\": \"^5.4.1\",\n \"commander\": \"^13.1.0\",\n \"execa\": \"^9.5.2\",\n \"fs-extra\": \"^11.3.0\",\n \"ora\": \"^8.2.0\",\n \"react\": \"18.3.1\",\n \"react-native\": \"0.76.9\",\n \"semver\": \"^7.7.1\",\n \"url\": \"^0.11.4\"\n },\n \"devDependencies\": {\n \"@types/fs-extra\": \"^11.0.4\",\n \"@types/semver\": \"^7.7.0\",\n \"prettier\": \"3.5.3\",\n \"release-it\": \"^19.0.1\",\n \"tiny-glob\": \"^0.2.9\",\n \"tsup\": \"^8.4.0\",\n \"typescript\": \"^5.8.3\"\n },\n \"workspaces\": [\n \"example\"\n ],\n \"bin\": \"./bin/expo-release-it.mjs\",\n \"files\": [\n \"build\",\n \"package.json\",\n \"bin\",\n \"template\"\n ],\n \"packageManager\": \"yarn@4.9.1\"\n}\n","import pkgJson from '../../package.json';\nimport { resolve } from './FileUtil';\nimport { fileURLToPath } from 'url';\n\n/**\n * CLI Comprehensive options\n * Each values can be empty by command and timing.\n */\nexport const OptionHolder: {\n // cli specific options\n cli: {\n // cli version\n version: string;\n // cli project root directory\n rootDir: string;\n // cli template source directory\n templateDir: string;\n };\n input: {\n platform: 'android' | 'ios';\n uploadMetadata: boolean;\n androidOutput: 'apk' | 'aab';\n pod: boolean;\n };\n keyholderMap: {\n ios_app_identifier: string;\n ios_developer_team_id: string;\n ios_match_git_url: string;\n ios_app_store_connect_api_key_id: string;\n ios_app_store_connect_api_key_issuer_id: string;\n ios_xcode_project_target: string;\n ios_match_password: string;\n\n android_keystore_store_password: string;\n android_keystore_key_alias: string;\n android_keystore_key_password: string;\n android_package_name: string;\n };\n templateDirNames: string[];\n // dest project root directory\n projectDir: string;\n // dest project output of init command direcotry\n outputOfInitDir: string;\n keyDir: string;\n keyholderFilePath: string;\n tempDir: string;\n versionName: string;\n versionCode: string;\n} = {\n cli: {\n version: pkgJson.version,\n rootDir: resolve(fileURLToPath(import.meta.url), '../..'),\n templateDir: resolve(fileURLToPath(import.meta.url), '../../template'),\n },\n input: {} as any,\n keyholderMap: {} as any,\n templateDirNames: ['key'],\n projectDir: '',\n outputOfInitDir: '',\n keyDir: '',\n keyholderFilePath: '',\n versionName: '',\n versionCode: '',\n tempDir: '',\n};\n","import { readdir, isFile, isDir, join } from './FileUtil';\n\nexport async function iterateAllFiles(root: string, callback: (filePath: string) => Promise<void>) {\n await go(root);\n\n async function go(dirPath: string) {\n const paths = readdir(dirPath).map((f) => join(dirPath, f));\n\n for (const p of paths) {\n if (isFile(p)) {\n await callback(p);\n } else if (isDir(p)) {\n await go(p);\n }\n }\n }\n}\n","import { iterateAllFiles } from './iterateAllFiles';\nimport { read, relativePath, write } from './FileUtil';\nimport { OptionHolder } from './OptionHolder';\nimport * as path from 'node:path';\n\nexport async function injectTemplatePlaceHolders(root: string) {\n await iterateAllFiles(root, async (filePath: string) => {\n const dirPath = path.dirname(filePath);\n let content = read(filePath);\n for (const [key, value] of Object.entries(OptionHolder.keyholderMap)) {\n content = content.replaceAll(`{{${key}}}`, value);\n }\n // dynamic replacements\n content = content.replaceAll(\n '{{key_dir_relative_path}}',\n relativePath(dirPath, OptionHolder.keyDir),\n );\n write(filePath, content);\n });\n}\n","import { oraPromise } from 'ora';\nimport chalk from 'chalk';\n\nexport async function spinner<T>(text: string, promise: Promise<T>): Promise<T> {\n return oraPromise(promise, {\n text,\n successText: chalk.green(`${text} - Done`),\n failText: chalk.red(`${text} - Failed`),\n });\n}\n","import { execa, type Options } from 'execa';\n\nexport const exe = execa({\n stdin: 'pipe',\n stdout: 'inherit',\n stderr: 'inherit',\n shell: false,\n});\n\nexport const yesShell = <OptionsType extends Options>(\n command: string,\n args: string[] = [],\n options: OptionsType,\n) => {\n const subProcess = exe(command, args, { ...options, stdin: 'pipe' });\n subProcess.stdin?.write('y\\n');\n subProcess.stdin?.end();\n return subProcess;\n};\n","import chalk from 'chalk';\n\nexport const logger = {\n success: (...msg: any[]) => console.log(chalk.green(`✔ ${msg.join(', ')}`)),\n done: (...msg: any[]) => console.log(chalk.green(`✔ ${msg.join(', ')} - Done`)),\n error: (...msg: any[]) => console.log(chalk.red(`✖ ${msg.join(', ')}`)),\n warn: (...msg: any[]) => console.log(chalk.yellow(`⚠ ${msg.join(', ')}`)),\n info: (...msg: any[]) => console.log(chalk.cyan(`ℹ ${msg.join(', ')}`)),\n title: (...msg: any[]) => console.log(chalk.bold.blue(`\\n${msg.join(', ')}`)),\n dim: (...msg: any[]) => console.log(chalk.dim(msg.join(', '))),\n};\n","import { resolve, remove, iterateDir, copy, read, write, relativePath } from '../FileUtil';\nimport { OptionHolder } from '../OptionHolder';\nimport { injectTemplatePlaceHolders } from '../injectTemplatePlaceHolders';\nimport { spinner } from '../spinner';\nimport { exe, yesShell } from './execShellScript';\nimport { logger } from '../logger';\n\nexport async function prepareAndroid() {\n const srcDir = resolve(OptionHolder.cli.templateDir, 'android');\n const destDir = resolve(OptionHolder.projectDir, 'android');\n\n await yesShell('expo', ['prebuild', '-p', 'android', '--no-install'], {\n cwd: OptionHolder.projectDir,\n });\n logger.success('Expo Prebuild - Done');\n\n await spinner(\n 'Inject Templates',\n iterateDir(srcDir, async (file) => {\n const filePath = resolve(srcDir, file);\n remove(resolve(destDir, file));\n copy(filePath, resolve(destDir, file));\n }),\n );\n\n await spinner('Overwrite Android Release Signing Config', replaceAndroidSigningConfig(destDir));\n\n await spinner(\n 'Hydrate template placeholders',\n injectTemplatePlaceHolders(resolve(destDir, 'fastlane')),\n );\n\n await exe({ cwd: destDir })`bundle install`;\n logger.success('Bunder Install - Done');\n}\n\nasync function replaceAndroidSigningConfig(destDir: string) {\n const buildGradleDirPath = resolve(destDir, 'app');\n const buildGradlePath = resolve(destDir, 'app', 'build.gradle');\n const {\n android_keystore_store_password,\n android_keystore_key_alias,\n android_keystore_key_password,\n } = OptionHolder.keyholderMap;\n\n const content = read(buildGradlePath).replace(\n /signingConfigs.*?{.*?debug.*?{.*?}.*?}/s,\n `\n signingConfigs {\n debug {\n storeFile file('${relativePath(buildGradleDirPath, resolve(OptionHolder.outputOfInitDir, 'key', 'android_release_keystore.jks'))}')\n storePassword '${android_keystore_store_password}'\n keyAlias '${android_keystore_key_alias}'\n keyPassword '${android_keystore_key_password}'\n }\n }\n `,\n );\n write(buildGradlePath, content);\n}\n","import { OptionHolder } from '../OptionHolder';\nimport { readJsonSlow, exist } from '../FileUtil';\n\nexport async function hydrateKeyholderFileValues() {\n if (exist(OptionHolder.keyholderFilePath)) {\n Object.assign(OptionHolder.keyholderMap, readJsonSlow(OptionHolder.keyholderFilePath));\n }\n}\n","import { logger } from './logger';\n\nexport function throwError(message: string, e?: any): never {\n if (e) {\n logger.error(message, e);\n } else {\n logger.error(message);\n }\n process.exit(1);\n}\n","import { OptionHolder } from '../OptionHolder';\nimport { throwError } from '../throwError';\nimport semver from 'semver';\nimport { readdir, read, readJsonSlow, write, writeJson, resolve } from '../FileUtil';\n\nexport async function parseBinaryVersions() {\n const files = readdir(OptionHolder.projectDir);\n\n const jsConfigFiles = ['app.config.ts', 'app.config.js', 'app.config.cjs', 'app.config.mjs'];\n const jsonConfigFile = 'app.json';\n\n for (const jsConfigFile of jsConfigFiles) {\n if (files.includes(jsConfigFile)) {\n await parseFromJsConfigFile(jsConfigFile);\n return;\n }\n }\n\n if (files.includes(jsonConfigFile)) {\n await parseFromJsonConfigFile(jsonConfigFile);\n return;\n }\n\n throwError('expo config file not found');\n\n async function parseFromJsConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const content = read(filePath);\n\n const VERSION_NAME = /const VERSION_NAME = '(.*?)';/.exec(content)?.[1];\n const VERSION_CODE = /const VERSION_CODE = (.*?);/.exec(content)?.[1];\n\n if (!VERSION_NAME) {\n throwError('cannot parse version name');\n }\n if (!VERSION_CODE) {\n throwError('cannot parse version code');\n }\n\n if (!semver.valid(VERSION_NAME)) {\n throwError('VERSION_NAME is not a valid semver format');\n }\n\n OptionHolder.versionName = VERSION_NAME;\n OptionHolder.versionCode = VERSION_CODE;\n }\n\n async function parseFromJsonConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const json = readJsonSlow(filePath);\n\n const versionName = json.expo?.version + '';\n const iosVersionCode = json.expo?.ios?.buildNumber + '';\n const androidVersionCode = json.expo?.android?.versionCode + '';\n\n if (!/\\d+/.test(iosVersionCode)) {\n throwError('app.json expo.ios.buildNumber is not an integer');\n }\n\n if (!/\\d+/.test(androidVersionCode)) {\n throwError('app.json expo.android.versionCode is not an integer');\n }\n\n if (iosVersionCode !== androidVersionCode) {\n throwError('app.json expo.ios.buildNumber is not equal with expo.android.versionCode');\n }\n\n if (!semver.valid(versionName)) {\n throwError('VERSION_NAME is not a valid semver format');\n }\n\n OptionHolder.versionName = versionName;\n OptionHolder.versionCode = iosVersionCode;\n }\n}\n\nexport async function injectBinaryVersions({\n versionCode,\n versionName,\n}: {\n versionName: string;\n versionCode: string;\n}) {\n const files = readdir(OptionHolder.projectDir);\n\n const jsConfigFiles = ['app.config.ts', 'app.config.js', 'app.config.cjs', 'app.config.mjs'];\n const jsonConfigFile = 'app.json';\n\n for (const jsConfigFile of jsConfigFiles) {\n if (files.includes(jsConfigFile)) {\n await injectToJsConfigFile(jsConfigFile);\n return;\n }\n }\n\n if (files.includes(jsonConfigFile)) {\n await injectToJsonConfigFile(jsonConfigFile);\n return;\n }\n\n throwError('expo config file not found');\n\n async function injectToJsConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n let content = read(filePath);\n\n content = content.replace(\n /const VERSION_NAME = '(.*?)';/,\n `const VERSION_NAME = '${versionName}';`,\n );\n content = content.replace(\n /const VERSION_CODE = (.*?);/,\n `const VERSION_CODE = ${versionCode};`,\n );\n\n write(filePath, content);\n }\n\n async function injectToJsonConfigFile(filename: string) {\n const filePath = resolve(OptionHolder.projectDir, filename);\n const json = readJsonSlow(filePath);\n\n json.expo.version = versionName;\n json.expo.ios.buildNumber = versionCode;\n json.expo.android.versionCode = +versionCode;\n\n writeJson(filePath, json);\n }\n}\n","export const isDev = process.env.NODE_ENV === 'development';\nexport const isWin = process.platform.startsWith('win');\n","import { hydrateKeyholderFileValues } from './hydrateKeyholderFileValues';\nimport { parseBinaryVersions } from './VersionUtil';\nimport { OptionHolder } from '../OptionHolder';\nimport { isDev } from '../EnvUtil';\nimport { resolve } from '../FileUtil';\n\nexport async function setup() {\n await setupBasicOptions();\n await hydrateKeyholderFileValues();\n await parseBinaryVersions();\n}\n\nexport async function setupBasicOptions() {\n OptionHolder.projectDir = isDev ? resolve('example') : resolve('.');\n OptionHolder.outputOfInitDir = resolve(OptionHolder.projectDir, 'expo-release-it');\n OptionHolder.keyDir = resolve(OptionHolder.outputOfInitDir, 'key');\n OptionHolder.keyholderFilePath = resolve(OptionHolder.outputOfInitDir, 'keyholder.json');\n OptionHolder.tempDir = resolve(OptionHolder.outputOfInitDir, '.temp');\n}\n","import { remove, resolve, iterateDir, copy } from '../FileUtil';\nimport { OptionHolder } from '../OptionHolder';\nimport { injectTemplatePlaceHolders } from '../injectTemplatePlaceHolders';\nimport { spinner } from '../spinner';\nimport { exe, yesShell } from './execShellScript';\nimport { logger } from '../logger';\n\nexport async function prepareIos() {\n const srcDir = resolve(OptionHolder.cli.templateDir, 'ios');\n const destDir = resolve(OptionHolder.projectDir, 'ios');\n\n await yesShell('expo', ['prebuild', '-p', 'ios', '--no-install'], {\n cwd: OptionHolder.projectDir,\n });\n logger.success('Expo Prebuild - Done');\n\n await spinner(\n 'Inject templates',\n iterateDir(srcDir, async (file) => {\n const filePath = resolve(srcDir, file);\n remove(resolve(destDir, file));\n copy(filePath, resolve(destDir, file));\n }),\n );\n\n await spinner(\n 'Hydrate template placeholders',\n injectTemplatePlaceHolders(resolve(destDir, 'fastlane')),\n );\n\n await exe({ cwd: destDir })`bundle install`;\n logger.success('Bunder Install - Done');\n}\n","import { prepareAndroid } from '../util/setup/prepareAndroid';\nimport { setup } from '../util/setup/setup';\nimport { prepareIos } from '../util/setup/prepareIos';\nimport { logger } from '../util/logger';\nimport { OptionHolder } from '../util/OptionHolder';\nimport { resolve, remove, copy, relativePath } from '../util/FileUtil';\nimport chalk from 'chalk';\nimport { calculateElapsed } from '../util/calculateElapsed';\nimport { isWin } from '../util/EnvUtil';\nimport { InqueryInputs } from '../util/input/InqueryInputs';\nimport { getIosFastlaneOptions } from '../util/FastlaneOption';\nimport { spinner } from '../util/spinner';\nimport { exe } from '../util/setup/execShellScript';\n\nexport async function build({ options }: { options: any }) {\n Object.assign(OptionHolder.input, options);\n const startTime = Date.now();\n await setup();\n await promptInputs();\n\n logger.info('Build Started');\n logger.info(`Version: ${OptionHolder.versionName}(${OptionHolder.versionCode})`);\n\n if (OptionHolder.input.platform === 'ios') {\n await buildIos();\n logger.success(`iOS Build ${chalk.bold.inverse(calculateElapsed(startTime))}`);\n } else {\n await buildAndroid();\n logger.success(`Android Build ${chalk.bold.inverse(calculateElapsed(startTime))}`);\n }\n}\n\nasync function promptInputs() {\n await InqueryInputs.platform();\n await InqueryInputs.podinstall();\n await InqueryInputs.androidBuildOutput();\n}\n\nasync function buildIos() {\n const iosDir = resolve(OptionHolder.projectDir, 'ios');\n const exeEnv = exe({\n cwd: iosDir,\n env: {\n MATCH_PASSWORD: OptionHolder.keyholderMap.ios_match_password,\n },\n });\n await prepareIos();\n await fastlane();\n\n async function fastlane() {\n if (OptionHolder.input.pod) {\n await exeEnv('bundle', ['exec', 'pod', 'install']);\n logger.done('Pod Install');\n }\n remove(resolve(iosDir, '.xcode.env.local'));\n\n await exeEnv('bundle', ['exec', 'fastlane', 'build', ...getIosFastlaneOptions()]);\n\n logger.success(\n `artifact generated: ${relativePath(OptionHolder.projectDir, resolve(OptionHolder.outputOfInitDir, 'output', 'ios', 'app.ipa'))}`,\n );\n }\n}\nasync function buildAndroid() {\n const androidDir = resolve(OptionHolder.projectDir, 'android');\n const exeEnv = exe({\n cwd: androidDir,\n });\n await prepareAndroid();\n await fastlane();\n\n async function fastlane() {\n let buildOutputDir: string;\n let outputDir: string;\n\n if (OptionHolder.input.androidOutput === 'aab') {\n // aab: app/build/outputs/bundle/release/app-release.aab\n await spinner(\n 'Bundle AAB',\n exeEnv(isWin ? 'gradle.bat' : './gradlew', ['app:bundleRelease']),\n );\n buildOutputDir = resolve(androidDir, 'app', 'build', 'outputs', 'bundle', 'release');\n outputDir = resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'aab');\n } else {\n // apk: app/build/outputs/apk/release/app-release.apk\n await spinner(\n 'Bundle APK',\n exeEnv(isWin ? 'gradle.bat' : './gradlew', ['app:assembleRelease']),\n );\n buildOutputDir = resolve(androidDir, 'app', 'build', 'outputs', 'apk', 'release');\n outputDir = resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'apk');\n }\n\n remove(outputDir);\n copy(buildOutputDir, outputDir);\n\n logger.success(`artifact generated: ${relativePath(OptionHolder.projectDir, outputDir)}`);\n }\n}\n","import { padZero } from '@mj-studio/js-util';\n\nexport function calculateElapsed(t: number) {\n let seconds = Math.floor((Date.now() - t) / 1000);\n const minutes = Math.floor(seconds / 60);\n seconds = seconds % 60;\n return `${minutes}:${padZero(seconds)}`;\n}\n","import { OptionHolder } from '../OptionHolder';\nimport { select } from '@inquirer/prompts';\nimport { is } from '@mj-studio/js-util';\nimport chalk from 'chalk';\n\nexport const InqueryInputs = {\n platform: async () => {\n if (!OptionHolder.input.platform) {\n OptionHolder.input.platform = await select({\n message: constructInquirerFormattedMessage({\n name: 'Platform',\n explanation: `Platform to run action`,\n }),\n choices: [\n { name: 'ios', value: 'ios', description: 'Release ios' },\n { name: 'android', value: 'android', description: 'Release android' },\n ],\n });\n }\n },\n podinstall: async () => {\n if (OptionHolder.input.platform === 'ios') {\n OptionHolder.input.pod = await select({\n message: constructInquirerFormattedMessage({\n name: 'Install CocoaPods?',\n }),\n choices: [\n { name: 'yes', value: true, description: 'Install pods before release' },\n { name: 'no', value: false, description: 'Skip pods install' },\n ],\n });\n }\n },\n androidBuildOutput: async () => {\n if (OptionHolder.input.platform === 'android') {\n if (!OptionHolder.input.androidOutput) {\n OptionHolder.input.androidOutput = await select({\n message: constructInquirerFormattedMessage({\n name: 'Android output artifact type',\n }),\n choices: [\n { name: 'aab', value: 'aab', description: 'Build as App bundle' },\n { name: 'apk', value: 'apk', description: 'Build as APK' },\n ],\n });\n }\n }\n },\n uploadMetadata: async () => {\n if (!is.boolean(OptionHolder.input.uploadMetadata)) {\n OptionHolder.input.uploadMetadata = await select({\n message: constructInquirerFormattedMessage({\n name: 'Upload Metadata(screenshot, title, description, ...)',\n }),\n choices: [\n { name: 'yes', value: true, description: 'Upload' },\n { name: 'no', value: false, description: \"Don't Upload\" },\n ],\n });\n }\n },\n};\n\nexport function constructInquirerFormattedMessage({\n example,\n explanation,\n referUrl,\n name,\n}: {\n name: string;\n explanation?: string;\n example?: string;\n referUrl?: string;\n}) {\n let ret = `${chalk.bold(name)}`;\n if (explanation) {\n ret += `\\n\\n${chalk.italic.blue(explanation)}`;\n }\n if (example) {\n ret += `\\n${chalk.italic(`${chalk.greenBright('example :')} ${example}`)}`;\n }\n if (referUrl) {\n ret += `\\n${chalk.italic(`${chalk.greenBright('references :')} ${chalk.underline.blue(referUrl)}`)}`;\n }\n\n if (explanation) {\n ret += '\\n';\n if (example || referUrl) {\n ret += '\\n';\n }\n }\n\n return ret;\n}\n","import { OptionHolder } from './OptionHolder';\nimport { resolve } from './FileUtil';\n\nexport function getAndroidFastlaneOptions() {\n return [\n ...Object.entries(OptionHolder.keyholderMap).map(([k, v]) => `${k}:${v}`),\n `version_name:${OptionHolder.versionName}`,\n `version_code:${OptionHolder.versionCode}`,\n `upload_metadata:${OptionHolder.input.uploadMetadata}`,\n `aab_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'aab', 'app-release.aab')}`,\n `apk_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'android', 'apk', 'app-release.apk')}`,\n `skip_upload_apk:${OptionHolder.input.androidOutput !== 'apk'}`,\n `skip_upload_aab:${OptionHolder.input.androidOutput !== 'aab'}`,\n ];\n}\n\nexport function getIosFastlaneOptions() {\n return [\n ...Object.entries(OptionHolder.keyholderMap).map(([k, v]) => `${k}:${v}`),\n `version_name:${OptionHolder.versionName}`,\n `version_code:${OptionHolder.versionCode}`,\n `api_key_filepath:${resolve(OptionHolder.keyDir, 'ios_testflight_upload_api_key.p8')}`,\n `upload_metadata:${OptionHolder.input.uploadMetadata}`,\n `ipa_path:${resolve(OptionHolder.outputOfInitDir, 'output', 'ios', 'app.ipa')}`,\n `ipa_dir:${resolve(OptionHolder.outputOfInitDir, 'output', 'ios')}`,\n `ipa_name:app.ipa`,\n ];\n}\n"],"mappings":"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","names":["join","resolve","path","path","resolve","join","path","chalk","resolve","resolve","resolve","resolve","chalk","chalk","resolve","chalk","resolve"]}