xref: /expo/packages/@expo/cli/bin/cli.ts (revision fdf34e39)
1#!/usr/bin/env node
2import arg from 'arg';
3import chalk from 'chalk';
4
5const defaultCmd = 'start';
6
7export type Command = (argv?: string[]) => void;
8
9const commands: { [command: string]: () => Promise<Command> } = {
10  // Add a new command here
11  'run:ios': () => import('../src/run/ios').then((i) => i.expoRunIos),
12  'run:android': () => import('../src/run/android').then((i) => i.expoRunAndroid),
13  start: () => import('../src/start').then((i) => i.expoStart),
14  prebuild: () => import('../src/prebuild').then((i) => i.expoPrebuild),
15  config: () => import('../src/config').then((i) => i.expoConfig),
16  export: () => import('../src/export').then((i) => i.expoExport),
17  'export:web': () => import('../src/export/web').then((i) => i.expoExportWeb),
18
19  // Auxiliary commands
20  install: () => import('../src/install').then((i) => i.expoInstall),
21
22  // Auth
23  login: () => import('../src/login').then((i) => i.expoLogin),
24  logout: () => import('../src/logout').then((i) => i.expoLogout),
25  register: () => import('../src/register').then((i) => i.expoRegister),
26  whoami: () => import('../src/whoami').then((i) => i.expoWhoami),
27};
28
29const args = arg(
30  {
31    // Types
32    '--version': Boolean,
33    '--help': Boolean,
34
35    // Aliases
36    '-v': '--version',
37    '-h': '--help',
38  },
39  {
40    permissive: true,
41  }
42);
43
44if (args['--version']) {
45  // Version is added in the build script.
46  console.log(process.env.__EXPO_VERSION);
47  process.exit(0);
48}
49
50// Check if we are running `npx expo <subcommand>` or `npx expo`
51const isSubcommand = Boolean(commands[args._[0]]);
52
53// Handle `--help` flag
54if (!isSubcommand && args['--help']) {
55  const {
56    login,
57    logout,
58    whoami,
59    register,
60    start,
61    install,
62    export: _export,
63    config,
64    prebuild,
65    'run:ios': runIos,
66    'run:android': runAndroid,
67    ...others
68  } = commands;
69
70  console.log(chalk`
71  {bold Usage}
72    {dim $} npx expo <command>
73
74  {bold Commands}
75    ${Object.keys({ start, install, export: _export, config, ...others }).join(', ')}
76    ${Object.keys({ 'run:ios': runIos, 'run:android': runAndroid, prebuild }).join(', ')}
77    {dim ${Object.keys({ login, logout, whoami, register }).join(', ')}}
78
79  {bold Options}
80    --version, -v   Version number
81    --help, -h      Usage info
82
83  For more info run a command with the {bold --help} flag
84    {dim $} npx expo start --help
85`);
86  process.exit(0);
87}
88
89const command = isSubcommand ? args._[0] : defaultCmd;
90const commandArgs = isSubcommand ? args._.slice(1) : args._;
91
92// Push the help flag to the subcommand args.
93if (args['--help']) {
94  commandArgs.push('--help');
95}
96
97// Install exit hooks
98process.on('SIGINT', () => process.exit(0));
99process.on('SIGTERM', () => process.exit(0));
100
101commands[command]().then((exec) => exec(commandArgs));
102