eas-cli 0.53.0 → 0.54.1

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 (71) hide show
  1. package/README.md +78 -42
  2. package/build/analytics/events.d.ts +5 -1
  3. package/build/analytics/events.js +6 -1
  4. package/build/build/build.js +3 -1
  5. package/build/build/local.js +1 -1
  6. package/build/build/runBuildAndSubmit.js +4 -2
  7. package/build/build/utils/url.d.ts +1 -0
  8. package/build/build/utils/url.js +5 -1
  9. package/build/commands/build/index.d.ts +0 -1
  10. package/build/commands/build/index.js +1 -53
  11. package/build/commands/config.js +0 -2
  12. package/build/commands/metadata/pull.d.ts +8 -0
  13. package/build/commands/metadata/pull.js +59 -0
  14. package/build/commands/metadata/push.d.ts +8 -0
  15. package/build/commands/metadata/push.js +53 -0
  16. package/build/commands/submit.js +2 -1
  17. package/build/commands/update/index.d.ts +12 -0
  18. package/build/commands/update/index.js +78 -34
  19. package/build/graphql/generated.d.ts +24 -12
  20. package/build/graphql/queries/UpdateQuery.d.ts +4 -1
  21. package/build/graphql/queries/UpdateQuery.js +8 -7
  22. package/build/metadata/apple/config/reader.d.ts +25 -0
  23. package/build/metadata/apple/config/reader.js +95 -0
  24. package/build/metadata/apple/config/writer.d.ts +23 -0
  25. package/build/metadata/apple/config/writer.js +85 -0
  26. package/build/metadata/apple/data.d.ts +20 -0
  27. package/build/metadata/apple/data.js +2 -0
  28. package/build/metadata/apple/task.d.ts +24 -0
  29. package/build/metadata/apple/task.js +6 -0
  30. package/build/metadata/apple/tasks/age-rating.d.ts +13 -0
  31. package/build/metadata/apple/tasks/age-rating.js +39 -0
  32. package/build/metadata/apple/tasks/app-info.d.ts +15 -0
  33. package/build/metadata/apple/tasks/app-info.js +73 -0
  34. package/build/metadata/apple/tasks/app-version.d.ts +27 -0
  35. package/build/metadata/apple/tasks/app-version.js +104 -0
  36. package/build/metadata/apple/tasks/index.d.ts +6 -0
  37. package/build/metadata/apple/tasks/index.js +13 -0
  38. package/build/metadata/apple/types.d.ts +50 -0
  39. package/build/metadata/apple/types.js +2 -0
  40. package/build/metadata/config.d.ts +22 -0
  41. package/build/metadata/config.js +32 -0
  42. package/build/metadata/context.d.ts +46 -0
  43. package/build/metadata/context.js +48 -0
  44. package/build/metadata/download.d.ts +6 -0
  45. package/build/metadata/download.js +65 -0
  46. package/build/metadata/errors.d.ts +37 -0
  47. package/build/metadata/errors.js +77 -0
  48. package/build/metadata/upload.d.ts +8 -0
  49. package/build/metadata/upload.js +58 -0
  50. package/build/metadata/utils/asc.d.ts +4 -0
  51. package/build/metadata/utils/asc.js +2 -0
  52. package/build/metadata/utils/date.d.ts +12 -0
  53. package/build/metadata/utils/date.js +30 -0
  54. package/build/metadata/utils/log.d.ts +16 -0
  55. package/build/metadata/utils/log.js +23 -0
  56. package/build/metadata/utils/retry.d.ts +8 -0
  57. package/build/metadata/utils/retry.js +22 -0
  58. package/build/metadata/utils/telemetry.d.ts +20 -0
  59. package/build/metadata/utils/telemetry.js +87 -0
  60. package/build/project/ensureProjectExists.js +4 -1
  61. package/build/project/publish.d.ts +6 -1
  62. package/build/project/publish.js +16 -3
  63. package/build/submit/submit.js +1 -1
  64. package/build/submit/utils/errors.js +2 -0
  65. package/build/utils/expodash/uniq.d.ts +1 -0
  66. package/build/utils/expodash/uniq.js +7 -0
  67. package/build/utils/profiles.d.ts +3 -3
  68. package/build/utils/profiles.js +5 -93
  69. package/oclif.manifest.json +1 -1
  70. package/package.json +11 -5
  71. package/schema/metadata-0.json +928 -0
@@ -0,0 +1,59 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const tslib_1 = require("tslib");
4
+ const config_1 = require("@expo/config");
5
+ const core_1 = require("@oclif/core");
6
+ const chalk_1 = tslib_1.__importDefault(require("chalk"));
7
+ const path_1 = tslib_1.__importDefault(require("path"));
8
+ const configure_1 = require("../../build/configure");
9
+ const EasCommand_1 = tslib_1.__importDefault(require("../../commandUtils/EasCommand"));
10
+ const context_1 = require("../../credentials/context");
11
+ const log_1 = tslib_1.__importStar(require("../../log"));
12
+ const context_2 = require("../../metadata/context");
13
+ const download_1 = require("../../metadata/download");
14
+ const errors_1 = require("../../metadata/errors");
15
+ const projectUtils_1 = require("../../project/projectUtils");
16
+ const actions_1 = require("../../user/actions");
17
+ class MetadataPull extends EasCommand_1.default {
18
+ async runAsync() {
19
+ log_1.default.warn('EAS Metadata is in beta and subject to breaking changes.');
20
+ const { flags } = await this.parse(MetadataPull);
21
+ const projectDir = await (0, projectUtils_1.findProjectRootAsync)();
22
+ const { exp } = (0, config_1.getConfig)(projectDir, { skipSDKVersionRequirement: true });
23
+ await (0, projectUtils_1.getProjectIdAsync)(exp);
24
+ await (0, configure_1.ensureProjectConfiguredAsync)({ projectDir, nonInteractive: false });
25
+ const credentialsCtx = new context_1.CredentialsContext({
26
+ exp,
27
+ projectDir,
28
+ user: await (0, actions_1.ensureLoggedInAsync)(),
29
+ nonInteractive: false,
30
+ });
31
+ const metadataCtx = await (0, context_2.createMetadataContextAsync)({
32
+ credentialsCtx,
33
+ projectDir,
34
+ exp,
35
+ profileName: flags.profile,
36
+ });
37
+ try {
38
+ const filePath = await (0, download_1.downloadMetadataAsync)(metadataCtx);
39
+ const relativePath = path_1.default.relative(process.cwd(), filePath);
40
+ log_1.default.addNewLineIfNone();
41
+ log_1.default.log(`🎉 Your store configuration is ready.
42
+
43
+ - Update the ${chalk_1.default.bold(relativePath)} file to prepare the app information.
44
+ - Run ${chalk_1.default.bold('eas submit')} or manually upload a new app version to the app stores.
45
+ - Once the app is uploaded, run ${chalk_1.default.bold('eas metadata:push')} to sync the store configuration.
46
+ - ${(0, log_1.learnMore)('https://docs.expo.dev/eas-metadata/introduction/')}`);
47
+ }
48
+ catch (error) {
49
+ (0, errors_1.handleMetadataError)(error);
50
+ }
51
+ }
52
+ }
53
+ exports.default = MetadataPull;
54
+ MetadataPull.description = 'generate the local store configuration from the app stores';
55
+ MetadataPull.flags = {
56
+ profile: core_1.Flags.string({
57
+ description: 'Name of the submit profile from eas.json. Defaults to "production" if defined in eas.json.',
58
+ }),
59
+ };
@@ -0,0 +1,8 @@
1
+ import EasCommand from '../../commandUtils/EasCommand';
2
+ export default class MetadataPush extends EasCommand {
3
+ static description: string;
4
+ static flags: {
5
+ profile: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined>;
6
+ };
7
+ runAsync(): Promise<void>;
8
+ }
@@ -0,0 +1,53 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const tslib_1 = require("tslib");
4
+ const config_1 = require("@expo/config");
5
+ const core_1 = require("@oclif/core");
6
+ const configure_1 = require("../../build/configure");
7
+ const EasCommand_1 = tslib_1.__importDefault(require("../../commandUtils/EasCommand"));
8
+ const context_1 = require("../../credentials/context");
9
+ const log_1 = tslib_1.__importStar(require("../../log"));
10
+ const context_2 = require("../../metadata/context");
11
+ const errors_1 = require("../../metadata/errors");
12
+ const upload_1 = require("../../metadata/upload");
13
+ const projectUtils_1 = require("../../project/projectUtils");
14
+ const actions_1 = require("../../user/actions");
15
+ class MetadataPush extends EasCommand_1.default {
16
+ async runAsync() {
17
+ log_1.default.warn('EAS Metadata is in beta and subject to breaking changes.');
18
+ const { flags } = await this.parse(MetadataPush);
19
+ const projectDir = await (0, projectUtils_1.findProjectRootAsync)();
20
+ const { exp } = (0, config_1.getConfig)(projectDir, { skipSDKVersionRequirement: true });
21
+ await (0, projectUtils_1.getProjectIdAsync)(exp);
22
+ await (0, configure_1.ensureProjectConfiguredAsync)({ projectDir, nonInteractive: false });
23
+ const credentialsCtx = new context_1.CredentialsContext({
24
+ exp,
25
+ projectDir,
26
+ user: await (0, actions_1.ensureLoggedInAsync)(),
27
+ nonInteractive: false,
28
+ });
29
+ const metadataCtx = await (0, context_2.createMetadataContextAsync)({
30
+ credentialsCtx,
31
+ projectDir,
32
+ exp,
33
+ profileName: flags.profile,
34
+ });
35
+ try {
36
+ const { appleLink } = await (0, upload_1.uploadMetadataAsync)(metadataCtx);
37
+ log_1.default.addNewLineIfNone();
38
+ log_1.default.log(`🎉 Store configuration is synced with the app stores.
39
+
40
+ ${(0, log_1.learnMore)(appleLink, { learnMoreMessage: 'See the changes in App Store Connect' })}`);
41
+ }
42
+ catch (error) {
43
+ (0, errors_1.handleMetadataError)(error);
44
+ }
45
+ }
46
+ }
47
+ exports.default = MetadataPush;
48
+ MetadataPush.description = 'sync the local store configuration to the app stores';
49
+ MetadataPush.flags = {
50
+ profile: core_1.Flags.string({
51
+ description: 'Name of the submit profile from eas.json. Defaults to "production" if defined in eas.json.',
52
+ }),
53
+ };
@@ -1,6 +1,7 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  const tslib_1 = require("tslib");
4
+ const eas_json_1 = require("@expo/eas-json");
4
5
  const core_1 = require("@oclif/core");
5
6
  const chalk_1 = tslib_1.__importDefault(require("chalk"));
6
7
  const EasCommand_1 = tslib_1.__importDefault(require("../commandUtils/EasCommand"));
@@ -23,7 +24,7 @@ class Submit extends EasCommand_1.default {
23
24
  const platforms = (0, platform_1.toPlatforms)(flags.requestedPlatform);
24
25
  const submissionProfiles = await (0, profiles_1.getProfilesAsync)({
25
26
  type: 'submit',
26
- projectDir,
27
+ easJsonReader: new eas_json_1.EasJsonReader(projectDir),
27
28
  platforms,
28
29
  profileName: flags.profile,
29
30
  });
@@ -1,6 +1,17 @@
1
1
  import EasCommand from '../../commandUtils/EasCommand';
2
+ import { ViewBranchUpdatesQuery } from '../../graphql/generated';
2
3
  import { PublishPlatform } from '../../project/publish';
3
4
  export declare const defaultPublishPlatforms: PublishPlatform[];
5
+ export declare type PublishPlatformFlag = PublishPlatform | 'all';
6
+ export declare function ensureBranchExistsAsync({ appId, name: branchName, limit, offset, }: {
7
+ appId: string;
8
+ name: string;
9
+ limit?: number;
10
+ offset?: number;
11
+ }): Promise<{
12
+ id: string;
13
+ updates: Exclude<Exclude<ViewBranchUpdatesQuery['app'], null | undefined>['byId']['updateBranchByName'], null | undefined>['updates'];
14
+ }>;
4
15
  export default class UpdatePublish extends EasCommand {
5
16
  static description: string;
6
17
  static flags: {
@@ -18,3 +29,4 @@ export default class UpdatePublish extends EasCommand {
18
29
  };
19
30
  runAsync(): Promise<void>;
20
31
  }
32
+ export declare function getUpdatesToRepublishInteractiveAsync(projectId: string, branchName: string, platformFlag: string, pageSize: number, offset?: number, cumulativeUpdates?: Exclude<Exclude<ViewBranchUpdatesQuery['app'], null | undefined>['byId']['updateBranchByName'], null | undefined>['updates']): Promise<Exclude<Exclude<ViewBranchUpdatesQuery['app'], null | undefined>['byId']['updateBranchByName'], null | undefined>['updates']>;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.defaultPublishPlatforms = void 0;
3
+ exports.getUpdatesToRepublishInteractiveAsync = exports.ensureBranchExistsAsync = exports.defaultPublishPlatforms = void 0;
4
4
  const tslib_1 = require("tslib");
5
5
  const config_plugins_1 = require("@expo/config-plugins");
6
6
  const eas_build_job_1 = require("@expo/eas-build-job");
@@ -11,12 +11,13 @@ const dateformat_1 = tslib_1.__importDefault(require("dateformat"));
11
11
  const graphql_tag_1 = tslib_1.__importDefault(require("graphql-tag"));
12
12
  const nullthrows_1 = tslib_1.__importDefault(require("nullthrows"));
13
13
  const api_1 = require("../../api");
14
+ const url_1 = require("../../build/utils/url");
14
15
  const EasCommand_1 = tslib_1.__importDefault(require("../../commandUtils/EasCommand"));
15
16
  const fetch_1 = tslib_1.__importDefault(require("../../fetch"));
16
17
  const client_1 = require("../../graphql/client");
17
18
  const PublishMutation_1 = require("../../graphql/mutations/PublishMutation");
18
19
  const UpdateQuery_1 = require("../../graphql/queries/UpdateQuery");
19
- const log_1 = tslib_1.__importDefault(require("../../log"));
20
+ const log_1 = tslib_1.__importStar(require("../../log"));
20
21
  const ora_1 = require("../../ora");
21
22
  const expoConfig_1 = require("../../project/expoConfig");
22
23
  const projectUtils_1 = require("../../project/projectUtils");
@@ -24,6 +25,7 @@ const publish_1 = require("../../project/publish");
24
25
  const workflow_1 = require("../../project/workflow");
25
26
  const prompts_1 = require("../../prompts");
26
27
  const utils_1 = require("../../update/utils");
28
+ const actions_1 = require("../../user/actions");
27
29
  const code_signing_1 = require("../../utils/code-signing");
28
30
  const uniqBy_1 = tslib_1.__importDefault(require("../../utils/expodash/uniqBy"));
29
31
  const formatFields_1 = tslib_1.__importDefault(require("../../utils/formatFields"));
@@ -70,10 +72,12 @@ async function ensureChannelExistsAsync({ appId, branchId, channelName, }) {
70
72
  }
71
73
  }
72
74
  }
73
- async function ensureBranchExistsAsync({ appId, name: branchName, }) {
75
+ async function ensureBranchExistsAsync({ appId, name: branchName, limit, offset, }) {
74
76
  const { app } = await UpdateQuery_1.UpdateQuery.viewBranchAsync({
75
77
  appId,
76
78
  name: branchName,
79
+ limit,
80
+ offset,
77
81
  });
78
82
  const updateBranch = app === null || app === void 0 ? void 0 : app.byId.updateBranchByName;
79
83
  if (updateBranch) {
@@ -86,6 +90,7 @@ async function ensureBranchExistsAsync({ appId, name: branchName, }) {
86
90
  await ensureChannelExistsAsync({ appId, branchId: newUpdateBranch.id, channelName: branchName });
87
91
  return { id: newUpdateBranch.id, updates: [] };
88
92
  }
93
+ exports.ensureBranchExistsAsync = ensureBranchExistsAsync;
89
94
  class UpdatePublish extends EasCommand_1.default {
90
95
  async runAsync() {
91
96
  var _a, _b, _c;
@@ -159,12 +164,9 @@ class UpdatePublish extends EasCommand_1.default {
159
164
  }
160
165
  (0, assert_1.default)(branchName, 'Branch name must be specified.');
161
166
  }
162
- const { id: branchId, updates } = await ensureBranchExistsAsync({
163
- appId: projectId,
164
- name: branchName,
165
- });
166
167
  let unsortedUpdateInfoGroups = {};
167
168
  let oldMessage, oldRuntimeVersion;
169
+ let uploadedAssetCount = 0;
168
170
  if (republish) {
169
171
  // If we are republishing, we don't need to worry about building the bundle or uploading the assets.
170
172
  // Instead we get the `updateInfoGroup` from the update we wish to republish.
@@ -180,26 +182,13 @@ class UpdatePublish extends EasCommand_1.default {
180
182
  if (jsonFlag) {
181
183
  throw new Error('You must specify the update group to republish.');
182
184
  }
183
- const updateGroups = (0, uniqBy_1.default)(updates, u => u.group)
184
- .filter(update => {
185
- // Only show groups that have updates on the specified platform(s).
186
- return platformFlag === 'all' || update.platform === platformFlag;
187
- })
188
- .map(update => ({
189
- title: formatUpdateTitle(update),
190
- value: update.group,
191
- }));
192
- if (updateGroups.length === 0) {
193
- throw new Error(`There are no updates on branch "${branchName}" published on the platform(s) ${platformFlag}. Did you mean to publish a new update instead?`);
194
- }
195
- const selectedUpdateGroup = await (0, prompts_1.selectAsync)('which update would you like to republish?', updateGroups);
196
- updatesToRepublish = updates.filter(update => update.group === selectedUpdateGroup);
185
+ updatesToRepublish = await getUpdatesToRepublishInteractiveAsync(projectId, branchName, platformFlag, 50);
197
186
  }
198
187
  const updatesToRepublishFilteredByPlatform = updatesToRepublish.filter(
199
188
  // Only republish to the specified platforms
200
189
  update => platformFlag === 'all' || update.platform === platformFlag);
201
190
  if (updatesToRepublishFilteredByPlatform.length === 0) {
202
- throw new Error(`There are no updates on branch "${branchName}" published on the platform(s) "${platformFlag}" with group ID "${group ? group : updatesToRepublish[0].group}". Did you mean to publish a new update instead?`);
191
+ throw new Error(`There are no updates on branch "${branchName}" published for the platform(s) "${platformFlag}" with group ID "${group ? group : updatesToRepublish[0].group}". Did you mean to publish a new update instead?`);
203
192
  }
204
193
  let publicationPlatformMessage;
205
194
  if (platformFlag === 'all') {
@@ -276,9 +265,13 @@ class UpdatePublish extends EasCommand_1.default {
276
265
  try {
277
266
  const platforms = platformFlag === 'all' ? exports.defaultPublishPlatforms : [platformFlag];
278
267
  const assets = await (0, publish_1.collectAssetsAsync)({ inputDir: inputDir, platforms });
279
- await (0, publish_1.uploadAssetsAsync)(assets);
268
+ const { uniqueUploadedAssetCount } = await (0, publish_1.uploadAssetsAsync)(assets, spinnerText => (assetSpinner.text = `Uploading assets... ${spinnerText}`));
269
+ uploadedAssetCount = uniqueUploadedAssetCount;
280
270
  unsortedUpdateInfoGroups = await (0, publish_1.buildUnsortedUpdateInfoGroupAsync)(assets, exp);
281
- assetSpinner.succeed('Uploaded assets!');
271
+ const uploadAssetSuccessMessage = uploadedAssetCount
272
+ ? `Uploaded ${uploadedAssetCount} ${uploadedAssetCount === 1 ? 'asset' : 'assets'}!`
273
+ : `Uploading assets skipped -- no new assets found!`;
274
+ assetSpinner.succeed(uploadAssetSuccessMessage);
282
275
  }
283
276
  catch (e) {
284
277
  assetSpinner.fail('Failed to upload assets');
@@ -291,6 +284,11 @@ class UpdatePublish extends EasCommand_1.default {
291
284
  .filter(pair => pair[1] === runtime)
292
285
  .map(pair => pair[0]);
293
286
  }
287
+ const { id: branchId } = await ensureBranchExistsAsync({
288
+ appId: projectId,
289
+ name: branchName,
290
+ limit: 0,
291
+ });
294
292
  // Sort the updates into different groups based on their platform specific runtime versions
295
293
  const updateGroups = Object.entries(runtimeToPlatformMapping).map(([runtime, platforms]) => {
296
294
  const localUpdateInfoGroup = Object.fromEntries(platforms.map(platform => [
@@ -355,19 +353,29 @@ class UpdatePublish extends EasCommand_1.default {
355
353
  }
356
354
  log_1.default.addNewLineIfNone();
357
355
  for (const runtime of new Set(Object.values(runtimeVersions))) {
358
- const platforms = newUpdates
359
- .filter(update => update.runtimeVersion === runtime)
360
- .map(update => update.platform);
361
- const newUpdate = newUpdates.find(update => update.runtimeVersion === runtime);
362
- if (!newUpdate) {
356
+ const newUpdatesForRuntimeVersion = newUpdates.filter(update => update.runtimeVersion === runtime);
357
+ if (!newUpdatesForRuntimeVersion.length) {
363
358
  throw new Error(`Publish response is missing updates with runtime ${runtime}.`);
364
359
  }
360
+ const platforms = newUpdatesForRuntimeVersion.map(update => update.platform);
361
+ const newAndroidUpdate = newUpdatesForRuntimeVersion.find(update => update.platform === 'android');
362
+ const newIosUpdate = newUpdatesForRuntimeVersion.find(update => update.platform === 'ios');
363
+ const updateGroupId = newUpdatesForRuntimeVersion[0].group;
364
+ const projectName = exp.slug;
365
+ const accountName = (0, projectUtils_1.getProjectAccountName)(exp, await (0, actions_1.ensureLoggedInAsync)());
366
+ const updateGroupUrl = (0, url_1.getUpdateGroupUrl)(accountName, projectName, updateGroupId);
367
+ const updateGroupLink = (0, log_1.link)(updateGroupUrl, { dim: false });
365
368
  log_1.default.log((0, formatFields_1.default)([
366
- { label: 'branch', value: branchName },
367
- { label: 'runtime version', value: runtime },
368
- { label: 'platform', value: platforms.join(', ') },
369
- { label: 'update group ID', value: newUpdate.group },
370
- { label: 'message', value: message },
369
+ { label: 'Branch', value: branchName },
370
+ { label: 'Runtime version', value: runtime },
371
+ { label: 'Platform', value: platforms.join(', ') },
372
+ { label: 'Update group ID', value: updateGroupId },
373
+ ...(newAndroidUpdate
374
+ ? [{ label: 'Android update ID', value: newAndroidUpdate.id }]
375
+ : []),
376
+ ...(newIosUpdate ? [{ label: 'iOS update ID', value: newIosUpdate.id }] : []),
377
+ { label: 'Message', value: message },
378
+ { label: 'Website link', value: updateGroupLink },
371
379
  ]));
372
380
  log_1.default.addNewLineIfNone();
373
381
  }
@@ -425,6 +433,42 @@ UpdatePublish.flags = {
425
433
  description: 'Run command in non-interactive mode',
426
434
  }),
427
435
  };
436
+ async function getUpdatesToRepublishInteractiveAsync(projectId, branchName, platformFlag, pageSize, offset = 0, cumulativeUpdates = []) {
437
+ const fetchMoreValue = '_fetchMore';
438
+ const { updates } = await ensureBranchExistsAsync({
439
+ appId: projectId,
440
+ name: branchName,
441
+ limit: pageSize + 1,
442
+ offset,
443
+ });
444
+ cumulativeUpdates = [
445
+ ...cumulativeUpdates,
446
+ // drop that extra item used for pagination from our render logic
447
+ ...updates.slice(0, updates.length - 1),
448
+ ];
449
+ const cumulativeUpdatesForTargetPlatforms = platformFlag === 'all'
450
+ ? cumulativeUpdates
451
+ : cumulativeUpdates.filter(update => {
452
+ // Only show groups that have updates on the specified platform(s).
453
+ return update.platform === platformFlag;
454
+ });
455
+ const updateGroups = (0, uniqBy_1.default)(cumulativeUpdatesForTargetPlatforms, u => u.group).map(update => ({
456
+ title: formatUpdateTitle(update),
457
+ value: update.group,
458
+ }));
459
+ if (!updateGroups.length) {
460
+ throw new Error(`There are no updates on branch "${branchName}" published for the platform(s) ${platformFlag}. Did you mean to publish a new update instead?`);
461
+ }
462
+ if (updates.length > pageSize) {
463
+ updateGroups.push({ title: 'Next page...', value: fetchMoreValue });
464
+ }
465
+ const selectedUpdateGroup = await (0, prompts_1.selectAsync)('Which update would you like to republish?', updateGroups);
466
+ if (selectedUpdateGroup === fetchMoreValue) {
467
+ return await getUpdatesToRepublishInteractiveAsync(projectId, branchName, platformFlag, pageSize, offset + pageSize, cumulativeUpdates);
468
+ }
469
+ return cumulativeUpdates.filter(update => update.group === selectedUpdateGroup);
470
+ }
471
+ exports.getUpdatesToRepublishInteractiveAsync = getUpdatesToRepublishInteractiveAsync;
428
472
  async function getRuntimeVersionObjectAsync(exp, platformFlag, projectDir) {
429
473
  var _a, _b;
430
474
  const platforms = (platformFlag === 'all' ? ['android', 'ios'] : [platformFlag]);
@@ -1301,10 +1301,13 @@ export declare type Build = ActivityTimelineProjectActivity & BuildOrBuildJob &
1301
1301
  appVersion?: Maybe<Scalars['String']>;
1302
1302
  artifacts?: Maybe<BuildArtifacts>;
1303
1303
  buildProfile?: Maybe<Scalars['String']>;
1304
+ canRetry: Scalars['Boolean'];
1304
1305
  cancelingActor?: Maybe<Actor>;
1305
1306
  channel?: Maybe<Scalars['String']>;
1306
- createdAt?: Maybe<Scalars['DateTime']>;
1307
+ completedAt?: Maybe<Scalars['DateTime']>;
1308
+ createdAt: Scalars['DateTime'];
1307
1309
  distribution?: Maybe<DistributionType>;
1310
+ enqueuedAt?: Maybe<Scalars['DateTime']>;
1308
1311
  error?: Maybe<BuildError>;
1309
1312
  estimatedWaitTimeLeftSeconds?: Maybe<Scalars['Int']>;
1310
1313
  expirationDate?: Maybe<Scalars['DateTime']>;
@@ -1319,9 +1322,11 @@ export declare type Build = ActivityTimelineProjectActivity & BuildOrBuildJob &
1319
1322
  isGitWorkingTreeDirty?: Maybe<Scalars['Boolean']>;
1320
1323
  logFiles: Array<Scalars['String']>;
1321
1324
  metrics?: Maybe<BuildMetrics>;
1325
+ parentBuild?: Maybe<Build>;
1322
1326
  platform: AppPlatform;
1323
1327
  priority: BuildPriority;
1324
1328
  project: Project;
1329
+ provisioningStartedAt?: Maybe<Scalars['DateTime']>;
1325
1330
  /** Queue position is 1-indexed */
1326
1331
  queuePosition?: Maybe<Scalars['Int']>;
1327
1332
  reactNativeVersion?: Maybe<Scalars['String']>;
@@ -1330,7 +1335,8 @@ export declare type Build = ActivityTimelineProjectActivity & BuildOrBuildJob &
1330
1335
  sdkVersion?: Maybe<Scalars['String']>;
1331
1336
  status: BuildStatus;
1332
1337
  submissions: Array<Submission>;
1333
- updatedAt?: Maybe<Scalars['DateTime']>;
1338
+ updatedAt: Scalars['DateTime'];
1339
+ workerStartedAt?: Maybe<Scalars['DateTime']>;
1334
1340
  };
1335
1341
  export declare type BuildArtifact = {
1336
1342
  __typename?: 'BuildArtifact';
@@ -1482,6 +1488,8 @@ export declare type BuildMutation = {
1482
1488
  createIosBuild: CreateBuildResult;
1483
1489
  /** Delete an EAS Build build */
1484
1490
  deleteBuild: Build;
1491
+ /** Retry an EAS Build build */
1492
+ retryBuild: Build;
1485
1493
  };
1486
1494
  export declare type BuildMutationCancelBuildArgs = {
1487
1495
  buildId: Scalars['ID'];
@@ -1499,6 +1507,9 @@ export declare type BuildMutationCreateIosBuildArgs = {
1499
1507
  export declare type BuildMutationDeleteBuildArgs = {
1500
1508
  buildId: Scalars['ID'];
1501
1509
  };
1510
+ export declare type BuildMutationRetryBuildArgs = {
1511
+ buildId: Scalars['ID'];
1512
+ };
1502
1513
  export declare type BuildOrBuildJob = {
1503
1514
  id: Scalars['ID'];
1504
1515
  };
@@ -5765,8 +5776,8 @@ export declare type CreateAndroidBuildMutation = {
5765
5776
  queuePosition?: number | null;
5766
5777
  estimatedWaitTimeLeftSeconds?: number | null;
5767
5778
  priority: BuildPriority;
5768
- createdAt?: any | null;
5769
- updatedAt?: any | null;
5779
+ createdAt: any;
5780
+ updatedAt: any;
5770
5781
  error?: {
5771
5782
  __typename?: 'BuildError';
5772
5783
  errorCode: string;
@@ -5842,8 +5853,8 @@ export declare type CreateIosBuildMutation = {
5842
5853
  queuePosition?: number | null;
5843
5854
  estimatedWaitTimeLeftSeconds?: number | null;
5844
5855
  priority: BuildPriority;
5845
- createdAt?: any | null;
5846
- updatedAt?: any | null;
5856
+ createdAt: any;
5857
+ updatedAt: any;
5847
5858
  error?: {
5848
5859
  __typename?: 'BuildError';
5849
5860
  errorCode: string;
@@ -6200,8 +6211,8 @@ export declare type BuildsByIdQuery = {
6200
6211
  queuePosition?: number | null;
6201
6212
  estimatedWaitTimeLeftSeconds?: number | null;
6202
6213
  priority: BuildPriority;
6203
- createdAt?: any | null;
6204
- updatedAt?: any | null;
6214
+ createdAt: any;
6215
+ updatedAt: any;
6205
6216
  error?: {
6206
6217
  __typename?: 'BuildError';
6207
6218
  errorCode: string;
@@ -6273,8 +6284,8 @@ export declare type GetAllBuildsForAppQuery = {
6273
6284
  queuePosition?: number | null;
6274
6285
  estimatedWaitTimeLeftSeconds?: number | null;
6275
6286
  priority: BuildPriority;
6276
- createdAt?: any | null;
6277
- updatedAt?: any | null;
6287
+ createdAt: any;
6288
+ updatedAt: any;
6278
6289
  error?: {
6279
6290
  __typename?: 'BuildError';
6280
6291
  errorCode: string;
@@ -6563,6 +6574,7 @@ export declare type ViewBranchUpdatesQueryVariables = Exact<{
6563
6574
  appId: Scalars['String'];
6564
6575
  name: Scalars['String'];
6565
6576
  limit: Scalars['Int'];
6577
+ offset: Scalars['Int'];
6566
6578
  }>;
6567
6579
  export declare type ViewBranchUpdatesQuery = {
6568
6580
  __typename?: 'RootQuery';
@@ -6689,8 +6701,8 @@ export declare type BuildFragment = {
6689
6701
  queuePosition?: number | null;
6690
6702
  estimatedWaitTimeLeftSeconds?: number | null;
6691
6703
  priority: BuildPriority;
6692
- createdAt?: any | null;
6693
- updatedAt?: any | null;
6704
+ createdAt: any;
6705
+ updatedAt: any;
6694
6706
  error?: {
6695
6707
  __typename?: 'BuildError';
6696
6708
  errorCode: string;
@@ -1,7 +1,10 @@
1
1
  import { ViewAllUpdatesQuery, ViewBranchUpdatesQuery, ViewBranchUpdatesQueryVariables } from '../generated';
2
+ export declare const viewBranchUpdatesQueryUpdateLimit = 300;
3
+ declare type ViewBranchUpdatesQueryVariablesWithOptionalLimitAndOffset = Partial<ViewBranchUpdatesQueryVariables> & Pick<ViewBranchUpdatesQueryVariables, 'appId' | 'name'>;
2
4
  export declare const UpdateQuery: {
3
5
  viewAllAsync({ appId }: {
4
6
  appId: string;
5
7
  }): Promise<ViewAllUpdatesQuery>;
6
- viewBranchAsync({ appId, name }: Pick<ViewBranchUpdatesQueryVariables, 'appId' | 'name'>): Promise<ViewBranchUpdatesQuery>;
8
+ viewBranchAsync({ appId, name, limit, offset, }: ViewBranchUpdatesQueryVariablesWithOptionalLimitAndOffset): Promise<ViewBranchUpdatesQuery>;
7
9
  };
10
+ export {};
@@ -1,10 +1,10 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.UpdateQuery = void 0;
3
+ exports.UpdateQuery = exports.viewBranchUpdatesQueryUpdateLimit = void 0;
4
4
  const tslib_1 = require("tslib");
5
5
  const graphql_tag_1 = tslib_1.__importDefault(require("graphql-tag"));
6
6
  const client_1 = require("../client");
7
- const PAGE_LIMIT = 10000;
7
+ exports.viewBranchUpdatesQueryUpdateLimit = 300;
8
8
  exports.UpdateQuery = {
9
9
  async viewAllAsync({ appId }) {
10
10
  return (0, client_1.withErrorHandlingAsync)(client_1.graphqlClient
@@ -39,21 +39,21 @@ exports.UpdateQuery = {
39
39
  }
40
40
  `, {
41
41
  appId,
42
- limit: PAGE_LIMIT,
42
+ limit: exports.viewBranchUpdatesQueryUpdateLimit,
43
43
  }, { additionalTypenames: ['UpdateBranch', 'Update'] })
44
44
  .toPromise());
45
45
  },
46
- async viewBranchAsync({ appId, name }) {
46
+ async viewBranchAsync({ appId, name, limit = exports.viewBranchUpdatesQueryUpdateLimit, offset = 0, }) {
47
47
  return (0, client_1.withErrorHandlingAsync)(client_1.graphqlClient
48
48
  .query((0, graphql_tag_1.default) `
49
- query ViewBranchUpdates($appId: String!, $name: String!, $limit: Int!) {
49
+ query ViewBranchUpdates($appId: String!, $name: String!, $limit: Int!, $offset: Int!) {
50
50
  app {
51
51
  byId(appId: $appId) {
52
52
  id
53
53
  updateBranchByName(name: $name) {
54
54
  id
55
55
  name
56
- updates(offset: 0, limit: $limit) {
56
+ updates(offset: $offset, limit: $limit) {
57
57
  id
58
58
  group
59
59
  message
@@ -78,7 +78,8 @@ exports.UpdateQuery = {
78
78
  `, {
79
79
  appId,
80
80
  name,
81
- limit: PAGE_LIMIT,
81
+ limit,
82
+ offset,
82
83
  }, { additionalTypenames: ['UpdateBranch', 'Update'] })
83
84
  .toPromise());
84
85
  },
@@ -0,0 +1,25 @@
1
+ /// <reference types="@expo/apple-utils/ts-declarations/expo__app-store" />
2
+ import { AgeRatingDeclaration, AppInfoLocalization, AppStoreVersion, AppStoreVersionLocalization, CategoryIds } from '@expo/apple-utils';
3
+ import { AttributesOf } from '../../utils/asc';
4
+ import { AppleMetadata } from '../types';
5
+ declare type PartialExcept<T, K extends keyof T> = Pick<T, K> & Partial<Omit<T, K>>;
6
+ export declare const DEFAULT_WHATSNEW = "Bug fixes and improved stability";
7
+ /**
8
+ * Deserializes the metadata config schema into attributes for different models.
9
+ * This uses version 0 of the config schema.
10
+ */
11
+ export declare class AppleConfigReader {
12
+ readonly schema: AppleMetadata;
13
+ constructor(schema: AppleMetadata);
14
+ getAgeRating(): Partial<AttributesOf<AgeRatingDeclaration>> | null;
15
+ getLocales(): string[];
16
+ getInfoLocale(locale: string): PartialExcept<AttributesOf<AppInfoLocalization>, 'locale' | 'name'> | null;
17
+ getCategories(): CategoryIds | null;
18
+ /** Get the `AppStoreVersion` object. */
19
+ getVersion(): Partial<Omit<AttributesOf<AppStoreVersion>, 'releaseType' | 'earliestReleaseDate'>> | null;
20
+ getVersionRelease(): Partial<Pick<AttributesOf<AppStoreVersion>, 'releaseType' | 'earliestReleaseDate'>> | null;
21
+ getVersionLocale(locale: string, context: {
22
+ versionIsFirst: boolean;
23
+ }): Partial<AttributesOf<AppStoreVersionLocalization>> | null;
24
+ }
25
+ export {};