/
resolveOptions.ts
97 lines (83 loc) · 3.26 KB
/
resolveOptions.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
import { ExpoConfig, getConfig, Platform } from '@expo/config';
import { getPlatformBundlers, PlatformBundlers } from '../start/server/platformBundlers';
import { CommandError } from '../utils/errors';
import { learnMore } from '../utils/link';
export type Options = {
outputDir: string;
platforms: Platform[];
maxWorkers?: number;
dev: boolean;
clear: boolean;
minify: boolean;
bytecode: boolean;
dumpAssetmap: boolean;
sourceMaps: boolean;
};
/** Returns an array of platforms based on the input platform identifier and runtime constraints. */
export function resolvePlatformOption(
exp: ExpoConfig,
platformBundlers: PlatformBundlers,
platform: string[] = ['all']
): Platform[] {
const platformsAvailable: Partial<PlatformBundlers> = Object.fromEntries(
Object.entries(platformBundlers).filter(
([platform, bundler]) => bundler === 'metro' && exp.platforms?.includes(platform as Platform)
)
);
if (!Object.keys(platformsAvailable).length) {
throw new CommandError(
`No platforms are configured to use the Metro bundler in the project Expo config.`
);
}
const assertPlatformBundler = (platform: Platform): Platform => {
if (!platformsAvailable[platform]) {
if (!exp.platforms?.includes(platform) && platform === 'web') {
// Pass through so the more robust error message is shown.
return platform;
}
let error = `Platform "${platform}" is not configured to use the Metro bundler in the project Expo config, or is missing from the supported platforms in the platforms array: [${exp.platforms?.join(
', '
)}].`;
if (platform === 'web') {
error = `${error} ${learnMore('https://docs.expo.dev/guides/customizing-metro/#web-support')}`;
}
throw new CommandError('BAD_ARGS', error);
}
return platform;
};
const knownPlatforms = ['android', 'ios', 'web'] as Platform[];
const assertPlatformIsKnown = (platform: string): Platform => {
if (!knownPlatforms.includes(platform as Platform)) {
throw new CommandError(
`Unsupported platform "${platform}". Options are: ${knownPlatforms.join(',')},all`
);
}
return platform as Platform;
};
return (
platform
// Expand `all` to all available platforms.
.map((platform) => (platform === 'all' ? Object.keys(platformsAvailable) : platform))
.flat()
// Remove duplicated platforms
.filter((platform, index, list) => list.indexOf(platform) === index)
// Assert platforms are valid
.map((platform) => assertPlatformIsKnown(platform))
.map((platform) => assertPlatformBundler(platform))
);
}
export async function resolveOptionsAsync(projectRoot: string, args: any): Promise<Options> {
const { exp } = getConfig(projectRoot, { skipPlugins: true, skipSDKVersionRequirement: true });
const platformBundlers = getPlatformBundlers(projectRoot, exp);
return {
platforms: resolvePlatformOption(exp, platformBundlers, args['--platform']),
outputDir: args['--output-dir'] ?? 'dist',
minify: !args['--no-minify'],
bytecode: !args['--no-bytecode'],
clear: !!args['--clear'],
dev: !!args['--dev'],
maxWorkers: args['--max-workers'],
dumpAssetmap: !!args['--dump-assetmap'],
sourceMaps: !!args['--source-maps'],
};
}