Compare commits

...
Author SHA1 Message Date
Quinlan Jung 7a669bccb0 Temporary Commit at 4/23/2024, 12:39:50 PM 2024-04-23 12:39:50 -07:00
Quinlan Jung d33cfaba67 update CHANGELOG.md 2024-04-23 19:35:45 +00:00
Quinlan Jung 7363164889 Temporary Commit at 4/23/2024, 11:21:16 AM 2024-04-23 11:21:16 -07:00
5 changed files with 116 additions and 4 deletions

No files matched your search

+2
View File
@@ -8,6 +8,8 @@ This is the log of notable changes to EAS CLI and related packages.
### 🎉 New features
- Add --no-channel flag for update and rollback to embedded. ([#2339](https://github.com/expo/eas-cli/pull/2339) by [@quinlanj](https://github.com/quinlanj))
### 🐛 Bug fixes
### 🧹 Chores
@@ -7,6 +7,7 @@ import { instance, mock } from 'ts-mockito';
import UpdatePublish from '..';
import { ensureBranchExistsAsync } from '../../../branch/queries';
import { ensureChannelExistsAsync } from '../../../channel/queries';
import {
DynamicPrivateProjectConfigContextField,
DynamicPublicProjectConfigContextField,
@@ -45,6 +46,7 @@ jest.mock('fs');
jest.mock('@expo/config');
jest.mock('@expo/config-plugins');
jest.mock('../../../branch/queries');
jest.mock('../../../channel/queries');
jest.mock('../../../commandUtils/context/contextUtils/getProjectIdAsync');
jest.mock('../../../update/configure');
jest.mock('../../../update/getBranchNameFromChannelNameAsync');
@@ -94,6 +96,16 @@ describe(UpdatePublish.name, () => {
);
});
it('errors with both --channel and --no-channel', async () => {
const flags = ['--channel=channel123', '--no-channel'];
mockTestProject();
await expect(new UpdatePublish(flags, commandOptions).run()).rejects.toThrow(
'Cannot use --channel with --no-channel'
);
});
it('creates a new update with --non-interactive, --branch, and --message', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc'];
@@ -147,6 +159,31 @@ describe(UpdatePublish.name, () => {
expect(PublishMutation.publishUpdateGroupAsync).toHaveBeenCalled();
});
it('creates a new update with --no-channel', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc', '--no-channel'];
const { platforms, runtimeVersion } = mockTestExport();
jest.mocked(getBranchNameFromChannelNameAsync).mockResolvedValue('branchFromChannel');
jest.mocked(ensureBranchExistsAsync).mockResolvedValue({
branchId: 'branch123',
createdBranch: true,
});
jest.mocked(PublishMutation.publishUpdateGroupAsync).mockResolvedValue(
platforms.map(platform => ({
...updateStub,
runtimeVersion,
platform,
}))
);
await new UpdatePublish(flags, commandOptions).run();
expect(ensureChannelExistsAsync).not.toHaveBeenCalled();
expect(PublishMutation.publishUpdateGroupAsync).toHaveBeenCalled();
});
it('creates a new update with the public expo config', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc'];
@@ -6,6 +6,7 @@ import path from 'path';
import { instance, mock } from 'ts-mockito';
import { ensureBranchExistsAsync } from '../../../branch/queries';
import { ensureChannelExistsAsync } from '../../../channel/queries';
import {
DynamicPrivateProjectConfigContextField,
DynamicPublicProjectConfigContextField,
@@ -44,6 +45,7 @@ jest.mock('fs');
jest.mock('@expo/config');
jest.mock('@expo/config-plugins');
jest.mock('../../../branch/queries');
jest.mock('../../../channel/queries');
jest.mock('../../../commandUtils/context/contextUtils/getProjectIdAsync');
jest.mock('../../../project/projectUtils', () => ({
...jest.requireActual('../../../project/projectUtils'),
@@ -80,6 +82,16 @@ describe(UpdateRollBackToEmbedded.name, () => {
);
});
it('errors with both --channel and --no-channel', async () => {
const flags = ['--channel=channel123', '--no-channel'];
mockTestProject();
await expect(new UpdateRollBackToEmbedded(flags, commandOptions).run()).rejects.toThrow(
'Cannot use --channel with --no-channel'
);
});
it('creates a roll back to embedded with --non-interactive, --branch, and --message', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc'];
@@ -137,6 +149,42 @@ describe(UpdateRollBackToEmbedded.name, () => {
expect(PublishMutation.publishUpdateGroupAsync).toHaveBeenCalled();
});
it('creates a roll back to embedded with --no-channel', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc', '--no-channel'];
const { projectId } = mockTestProject();
const platforms = ['android', 'ios'];
const runtimeVersion = 'exposdk:47.0.0';
jest.mocked(Updates.getRuntimeVersionAsync).mockResolvedValue(runtimeVersion);
jest.mocked(getBranchNameFromChannelNameAsync).mockResolvedValue('branchFromChannel');
jest.mocked(ensureBranchExistsAsync).mockResolvedValue({
branchId: 'branch123',
createdBranch: true,
});
jest.mocked(PublishMutation.publishUpdateGroupAsync).mockResolvedValue(
platforms.map(platform => ({
...updateStub,
runtimeVersion,
platform,
}))
);
await new UpdateRollBackToEmbedded(flags, commandOptions).run();
expect(ensureChannelExistsAsync).not.toHaveBeenCalled();
expect(ensureBranchExistsAsync).toHaveBeenCalledWith(
expect.any(Object), // graphql client
{
appId: projectId,
branchName: 'branchFromChannel',
}
);
expect(PublishMutation.publishUpdateGroupAsync).toHaveBeenCalled();
});
it('creates a roll back to embedded with the public expo config', async () => {
const flags = ['--non-interactive', '--branch=branch123', '--message=abc'];
+13 -1
View File
@@ -64,6 +64,7 @@ type RawUpdateFlags = {
'skip-bundler': boolean;
'clear-cache': boolean;
'private-key-path'?: string;
'no-channel': boolean;
'non-interactive': boolean;
json: boolean;
/** @deprecated see UpdateRepublish command */
@@ -81,6 +82,7 @@ type UpdateFlags = {
inputDir: string;
skipBundler: boolean;
clearCache: boolean;
noChannel: boolean;
privateKeyPath?: string;
json: boolean;
nonInteractive: boolean;
@@ -143,6 +145,10 @@ export default class UpdatePublish extends EasCommand {
description: `File containing the PEM-encoded private key corresponding to the certificate in expo-updates' configuration. Defaults to a file named "private-key.pem" in the certificate's directory.`,
required: false,
}),
'no-channel': Flags.boolean({
description: `Skip EAS channel creation.`,
default: false,
}),
...EasNonInteractiveAndJsonFlags,
};
@@ -164,6 +170,7 @@ export default class UpdatePublish extends EasCommand {
skipBundler,
clearCache,
privateKeyPath,
noChannel: noChannelFlag,
json: jsonFlag,
nonInteractive,
branchName: branchNameArg,
@@ -372,7 +379,7 @@ export default class UpdatePublish extends EasCommand {
appId: projectId,
branchName,
});
if (createdBranch) {
if (createdBranch && !noChannelFlag) {
await ensureChannelExistsAsync(graphqlClient, {
appId: projectId,
branchId,
@@ -548,6 +555,10 @@ export default class UpdatePublish extends EasCommand {
);
}
if (channelName && flags['no-channel']) {
Errors.error('Cannot use --channel with --no-channel', { exit: 1 });
}
if (flags.group || flags.republish) {
// Pick the first flag set that is defined, in this specific order
const args = [
@@ -575,6 +586,7 @@ export default class UpdatePublish extends EasCommand {
clearCache: flags['clear-cache'],
platform: flags.platform as RequestedPlatform,
privateKeyPath: flags['private-key-path'],
noChannel: flags['no-channel'],
nonInteractive,
json: flags.json ?? false,
};
@@ -54,6 +54,7 @@ type RawUpdateFlags = {
message?: string;
platform: string;
'private-key-path'?: string;
'no-channel': boolean;
'non-interactive': boolean;
json: boolean;
};
@@ -65,6 +66,7 @@ type UpdateFlags = {
channelName?: string;
updateMessage?: string;
privateKeyPath?: string;
noChannel: boolean;
json: boolean;
nonInteractive: boolean;
};
@@ -104,6 +106,10 @@ export default class UpdateRollBackToEmbedded extends EasCommand {
description: `File containing the PEM-encoded private key corresponding to the certificate in expo-updates' configuration. Defaults to a file named "private-key.pem" in the certificate's directory.`,
required: false,
}),
'no-channel': Flags.boolean({
description: `Skip EAS channel creation.`,
default: false,
}),
...EasNonInteractiveAndJsonFlags,
};
@@ -122,6 +128,7 @@ export default class UpdateRollBackToEmbedded extends EasCommand {
channelName: channelNameArg,
updateMessage: updateMessageArg,
privateKeyPath,
noChannel: noChannelFlag,
json: jsonFlag,
nonInteractive,
branchName: branchNameArg,
@@ -188,16 +195,17 @@ export default class UpdateRollBackToEmbedded extends EasCommand {
appId: projectId,
branchName,
});
if (createdBranch) {
if (createdBranch && !noChannelFlag) {
await ensureChannelExistsAsync(graphqlClient, {
appId: projectId,
branchId,
channelName: branchName,
});
Log.withTick(
`Channel: ${chalk.bold(branchName)} pointed at branch: ${chalk.bold(branchName)}`
);
}
Log.withTick(`Channel: ${chalk.bold(branchName)} pointed at branch: ${chalk.bold(branchName)}`);
const gitCommitHash = await vcsClient.getCommitHashAsync();
const isGitWorkingTreeDirty = await vcsClient.hasUncommittedChangesAsync();
@@ -387,6 +395,10 @@ export default class UpdateRollBackToEmbedded extends EasCommand {
);
}
if (channelName && flags['no-channel']) {
Errors.error('Cannot use --channel with --no-channel', { exit: 1 });
}
return {
auto,
branchName,
@@ -394,6 +406,7 @@ export default class UpdateRollBackToEmbedded extends EasCommand {
updateMessage,
platform: flags.platform as RequestedPlatform,
privateKeyPath: flags['private-key-path'],
noChannel: flags['no-channel'],
nonInteractive,
json: flags.json ?? false,
};