cli
react-native-community/cli v6.4.0
入口函数是index.ts的run函数,调用路径如下, run->setupAndRun -> attachCommand 解析命令,同时支持metroCommands
命令
- start,启动开发服务器
- bundle 打包命令
- ram-bundle ram bundle 打包命令
- init 初始化一个工程,详见init.ts的createProject
- run-android,运行android
- build-android,build android项目
- run-ios,运行iOS
- build-ios,build iOS项目
- upgrade
- profile-hermes
- info,见envinfo.ts的getEnvironmentInfo函数,调用的是第三方库tabrindle/envinfo,获取设备的信息
- log-android
- log-ios
- clean,通过yarn add @react-native-community/cli-clean 添加该命令,清理缓存,包括android, cocoapods, metro, npm, watchman, yarn
- config,通过yarn add @react-native-community/cli-config添加该命令
- doctor,yarn add @react-native-community/cli-doctor
react-native.config.js
module.exports = {
project: {
ios: {
sourceDir: './custom-ios-location',
},
},
};
project.ios.sourceDir,表示iOS代码所在的文件夹
command 插件
react-native.config.js 可以实现command插件
module.exports = {
commands: [
{
name: 'foo-command',
func: () => console.log('It worked'),
},
],
};
终端输入npx react-native foo-command,会打印出It worked
系统还有需要多插件,以config举例
具体写法和实现如
export default {
name: 'config',
description: 'Print CLI configuration',
func: async (_argv: string[], ctx: Config) => {
console.log(JSON.stringify(filterConfig(ctx), null, 2));
},
};
command的接口定义
type Command = {
name: string;
description?: string;
func: (argv: Array<string>, config: ConfigT, args: Object) => ?Promise<void>;
options?: Array<{
name: string;
description?: string;
parse?: (val: string) => any;
default?:
| string
| boolean
| number
| ((config: ConfigT) => string | boolean | number);
}>;
examples?: Array<{
desc: string;
cmd: string;
}>;
};
cli-plugin-metro bundle
metroCommands 见cli-plugin-metro
命令定义
export default {
name: 'bundle',
description: 'builds the javascript bundle for offline use',
func: bundleWithOutput,
options: bundleCommandLineArgs,
// Used by `ramBundle.js`
withOutput: bundleWithOutput,
};
const withOutput = bundleWithOutput;
export {withOutput};
bundleWithOutput->buildBundle->buildBundleWithConfig
接下来的调用metro的打包操作
const bundle = await output.build(server, requestOpts);
await output.save(bundle, args, logger.info);
// Save the assets of the bundle
const outputAssets: AssetData[] = await server.getAssets({
...Server.DEFAULT_BUNDLE_OPTIONS,
...requestOpts,
bundleType: 'todo',
});
// When we're done saving bundle output and the assets, we're done.
return await saveAssets(outputAssets, args.platform, args.assetsDest);
cli-plugin-metro ram-bundle
export default {
name: 'ram-bundle',
description:
'builds javascript as a "Random Access Module" bundle for offline use',
func: ramBundle,
options: bundleCommandLineArgs.concat({
name: '--indexed-ram-bundle',
description:
'Force the "Indexed RAM" bundle file format, even when building for android',
default: false,
}),
};
主要添加了--indexed-ram-bundle参数
cli-plugin-metro start
export default {
name: 'start',
func: runServer,
description: 'starts the webserver',
};
该命令实现在cli-plugin-metro 的commands/start文件夹的runServer函数
- loadMetroConfig,调用metro-config的loadConfig
- metroConfig.transformer.assetPlugins 赋值
- createDevServerMiddleware,实现在cli-server-api
- metroConfig.server.enhanceMiddleware赋值
- Metro.runServer
- attachToServer
cli-server-api
createDevServerMiddleware
- connect函数调用
- 返回attachToServer函数
auto-linking
对应依赖Native的代码,rn 提供auto-linking功能,在执行pod install会自动的链接到对应的native代码
源码见packages/platform-ios/native_modules.rb use_native_modules函数的found_pods部分