React Native Android 构建优化完全指南
- 原文:The Complete Guide to React Native Build Optimization
- 作者:The Mythical Engineer
- 原文发布:2026 年 4 月 14 日
在 Linux 或 macOS 上做 React Native 时,你可能已经发现:Android 的 release 构建耗时长得不合理。构建时打开系统监视器,往往会看到同一个问题:大量构建工具只用得到一颗 CPU 核心,其余算力基本闲置。
本文按步骤讲解每项优化、为何有效,以及如何验证收益。
说明:文中的优化在 MacBook Air M1、8GB 内存 上测试过;实际效果会因机器配置而异。
为什么构建这么慢?
React Native 的构建栈包含几块:
- Gradle:构建 Android 原生代码
- Metro:打包 JavaScript
- C++ 编译器:处理 TurboModules 与 Fabric(新架构)
默认情况下,三者都偏保守:Gradle 顺序跑任务、Metro 只用很少的 worker、C++ 每次构建都整份重编——哪怕什么都没改。好消息是:这些都有简单的改法。
未做任何优化时的初始耗时
BUILD SUCCESSFUL in 21m 14s
730 actionable tasks: 554 executed, 166 from cache, 10 up-to-date
Configuration cache entry stored.
See the profiling report at: file:///.../android/build/reports/profile/profile-2026-03-13-07-45-14.html
A fine-grained performance profile is available: use the --scan option.
===========================================
RESULTS
===========================================
⏱️ Total Benchmarking Time: 22m 2s
📊 A detailed Gradle profiling report is available at:
android/build/reports/profile/
(Open the latest .html file in a browser to see where the time was spent)
===========================================
1. 让 Gradle 并行执行
Gradle 是 Android 的构建系统。开箱即用时会一个接一个跑任务,并限制内存以免拖垮系统;在多核机器上,这非常浪费。
做法
optimize-gradle.sh:脚本会根据本机规格自动改写 gradle.properties:
#!/bin/bash
# Path to the gradle.properties file
GRADLE_PROPERTIES="android/gradle.properties"
if [ ! -f "$GRADLE_PROPERTIES" ]; then
echo "Error: gradle.properties not found at $GRADLE_PROPERTIES"
exit 1
fi
# Get system specifications
TOTAL_MEM_BYTES=$(sysctl -n hw.memsize)
HALF_MEM_MB=$(( TOTAL_MEM_BYTES / 2 / 1024 / 1024 ))
EIGHTH_MEM_MB=$(( TOTAL_MEM_BYTES / 8 / 1024 / 1024 ))
CPU_CORES=$(sysctl -n hw.ncpu)
WORKERS_MAX=$(( CPU_CORES * 3 / 4 ))
if [ $WORKERS_MAX -lt 1 ]; then WORKERS_MAX=1; fi
# Desired property values
JVM_ARGS="-Xmx${HALF_MEM_MB}m -XX:MaxMetaspaceSize=${EIGHTH_MEM_MB}m"
PARALLEL="true"
echo "Optimizing Android Gradle Properties for faster builds..."
echo " - CPU Cores count: $CPU_CORES (Using $WORKERS_MAX for 75%)"
echo " - Memory (Half RAM): ${HALF_MEM_MB}MB"
echo " - Metaspace (1/8 RAM): ${EIGHTH_MEM_MB}MB"
# Remove existing properties so we don't have duplicates
sed -i '' '/^org.gradle.jvmargs/d' "$GRADLE_PROPERTIES"
sed -i '' '/^org.gradle.parallel/d' "$GRADLE_PROPERTIES"
sed -i '' '/^org.gradle.workers.max/d' "$GRADLE_PROPERTIES"
# Append optimized properties at the end of the file
echo "org.gradle.jvmargs=$JVM_ARGS" >> "$GRADLE_PROPERTIES"
echo "org.gradle.parallel=$PARALLEL" >> "$GRADLE_PROPERTIES"
echo "org.gradle.workers.max=$WORKERS_MAX" >> "$GRADLE_PROPERTIES"
echo "Success: gradle.properties optimized!"
使用方式:
chmod +x scripts/optimize-gradle.sh
./scripts/optimize-gradle.sh
也可手动把下列配置写入 android/gradle.properties:
# Enable parallel task execution
org.gradle.parallel=true
# Use 75% of your CPU cores
org.gradle.workers.max=6
# Allocate more memory: 4GB heap + 1GB metaspace
org.gradle.jvmargs=-Xmx4096m -XX:MaxMetaspaceSize=1024m
| 配置项 | 作用 |
|---|---|
org.gradle.parallel=true | 让彼此独立的构建任务并行执行 |
org.gradle.workers.max | Gradle 可用的最大并行线程数 |
org.gradle.jvmargs | JVM 堆与 Metaspace 分配 |
优化 Gradle 后的收益
BUILD SUCCESSFUL in 10m 54s
730 actionable tasks: 452 executed, 268 from cache, 10 up-to-date
Configuration cache entry stored.
See the profiling report at: file:///.../android/build/reports/profile/profile-2026-03-13-08-15-54.html
A fine-grained performance profile is available: use the --scan option.
===========================================
RESULTS
===========================================
⏱️ Total Benchmarking Time: 11m 24s
📊 A detailed Gradle profiling report is available at:
android/build/reports/profile/
(Open the latest .html file in a browser to see where the time was spent)
===========================================
约 22 分钟 → 约 11 分钟(接近快一倍)
为何有效: Gradle 可以同时推进多个阶段(编译、打包、lint 等),而不必等上一段完全结束再开始下一段。
译者注:脚本中的
sed -i ''为 BSD/macOS 写法。在 GNU/Linux 上请改为sed -i(无空字符串参数),或改用sed -i.bak等 GNUsed支持的形式,否则需安装兼容层或手工编辑gradle.properties。
2. 加速 Metro Bundler
Metro 在 release 构建里会把 JavaScript 打成 bundle。默认往往只用 1 个 worker,与 CPU 核心数无关。
做法
在 metro.config.js 里为 worker 数量做动态配置:
const { getDefaultConfig, mergeConfig } = require("@react-native/metro-config");
const os = require("os");
const config = {
// Use 50% of available CPU cores dynamically
maxWorkers: Math.max(1, Math.floor(os.cpus().length * 0.5)),
};
module.exports = mergeConfig(getDefaultConfig(__dirname), config);
优化 Metro 后的收益
BUILD SUCCESSFUL in 5m 31s
730 actionable tasks: 452 executed, 268 from cache, 10 up-to-date
Configuration cache entry stored.
See the profiling report at: file:///.../android/build/reports/profile/profile-2026-03-13-09-50-26.html
A fine-grained performance profile is available: use the --scan option.
===========================================
RESULTS
===========================================
⏱️ Total Benchmarking Time: 5m 49s
📊 A detailed Gradle profiling report is available at:
android/build/reports/profile/
(Open the latest .html file in a browser to see where the time was spent)
===========================================
约 11 分钟 → 约 5 分钟(接近快四倍)
为何有效: 不再写死 worker 数,而是随机器扩展。例如在 8 核 上 Metro 可用 4 个 worker 而非 1 个,JS 打包理论上可接近 4 倍加速。
3. 用 ccache 缓存 C++ 编译
新架构大量依赖 C++ (TurboModules、Fabric)。这些文件编译成本高,默认却每次全量重编,哪怕你只改了一行 JavaScript。
做法
安装并配置 ccache:
brew install ccache
ccache --set-config=max_size=20G
setup-ccache.sh:检查是否已安装 ccache、必要时用 Homebrew 安装,并为本机构建做好配置:
#!/bin/bash
echo "==========================================="
echo " Checking ccache (Compiler Cache) Status "
echo "==========================================="
if command -v ccache &> /dev/null; then
echo "✅ ccache is already installed."
else
echo "⚠️ ccache is not installed. Installing via Homebrew..."
if command -v brew &> /dev/null; then
brew install ccache
if [ $? -eq 0 ]; then
echo "✅ ccache successfully installed."
else
echo "❌ Failed to install ccache. Please install it manually: brew install ccache"
exit 1
fi
else
echo "❌ Homebrew is not installed. Cannot automatically install ccache."
echo "Please install Homebrew (https://brew.sh) or install ccache manually."
exit 1
fi
fi
# Configure ccache for React Native Android builds
ccache --set-config=max_size=20G
echo "✅ ccache max size configured to 20G."
# Show current stats
echo ""
echo "Current ccache stats:"
ccache -s
echo "==========================================="
echo " ccache is ready for React Native Builds "
echo "==========================================="
原理简述: ccache 插在编译器与构建系统之间,按源文件与编译选项的哈希缓存产物;后续构建中相同输入可直接命中缓存,而无需重新编译。
验证缓存是否生效
构建后查看命中率:
ccache -s
关注 cache hit rate。热缓存下,首次完整构建之后常见 70%–90% 命中率,表示对应比例的 C++ 编译被跳过。
> bash scripts/setup-ccache.sh
===========================================
Checking ccache (Compiler Cache) Status
===========================================
✅ ccache is already installed.
✅ ccache max size configured to 20G.
Current ccache stats:
Cacheable calls: 394 / 422 (93.36%)
Hits: 178 / 394 (45.18%)
Direct: 178 / 178 (100.0%)
Preprocessed: 0 / 178 ( 0.00%)
Misses: 216 / 394 (54.82%)
Uncacheable calls: 28 / 422 ( 6.64%)
Local storage:
Cache size (GB): 0.0 / 20.0 ( 0.22%)
Hits: 178 / 394 (45.18%)
Misses: 216 / 394 (54.82%)
===========================================
ccache is ready for React Native Builds
===========================================
> bash scripts/optimize-gradle.sh
Optimizing Android Gradle Properties for faster builds...
- CPU Cores count: 8 (Using 6 for 75%)
- Memory (Half RAM): 4096MB
- Metaspace (1/8 RAM): 1024MB
Success: gradle.properties optimized!
BUILD SUCCESSFUL in 40s
730 actionable tasks: 32 executed, 698 up-to-date
Configuration cache entry stored.
此时整次构建可降到秒级。
约 5 分钟 → 不足 1 分钟
为何有效: 第二次及之后的构建只重编真正变更的文件,其余从缓存加载;在不少场景下可再省 50% 以上时间。
译者注:Linux 上请用发行版包管理器安装
ccache(如apt install ccache),脚本中的 Homebrew 路径可按需改写。
4. 只构建当前活跃架构
默认会为多种 Android CPU 架构出包,例如 x86、arm64、armeabi 等,工作量成倍增加。日常开发时,通常只需要与真机或模拟器一致的那一种架构。
做法
在 package.json 里为开发脚本加上 --active-arch-only:
"scripts": {
"dev": "react-native run-android --mode debug --active-arch-only"
}
为何有效: React Native 会通过 ADB 检测已连接设备的架构,只编译该目标;debug 构建常可再快 2–3 倍。
也可用自动化脚本 benchmark-build.sh 做耗时对比:
#!/bin/bash
# Configuration
BUILD_TYPE=${1:-"release"} # Default to release if no argument is provided
START_TIME=$(date +%s)
echo "==========================================="
echo " React Native Android Build Benchmarking "
echo "==========================================="
echo "Build Type: assemble$BUILD_TYPE"
echo ""
# Step 1: Clean Metro Bundler Cache
echo "🧹 [1/5] Clearing Metro Bundler Cache..."
rm -rf $TMPDIR/metro-*
rm -rf $TMPDIR/haste-map-*
echo " -> Metro cache cleared."
# Step 2: Clean Gradle Cache
echo "🧹 [2/5] Clearing Gradle Daemon & Cache..."
cd android || exit
./gradlew --stop > /dev/null 2>&1
rm -rf .gradle
rm -rf app/build
./gradlew clean > /dev/null 2>&1
cd ..
echo " -> Gradle cache cleared."
# Step 3: Clean Watchman Cache (if installed)
if command -v watchman &> /dev/null; then
echo "🧹 [3/5] Watchman found. Clearing Watchman cache..."
watchman watch-del-all > /dev/null 2>&1
echo " -> Watchman cache cleared."
else
echo "⏩ [3/5] Watchman not installed. Skipping..."
fi
echo ""
echo "🚀 [4/5] Proceeding with Build..."
echo "Starting Gradle Build with --profile..."
# Step 5: Execute build with profiling enabled
cd android || exit
# Using --profile to generate an HTML report of the build process
./gradlew assemble$BUILD_TYPE --profile
# Calculate total time
END_TIME=$(date +%s)
DURATION=$((END_TIME - START_TIME))
MINUTES=$((DURATION / 60))
SECONDS=$((DURATION % 60))
echo ""
echo "==========================================="
echo " RESULTS "
echo "==========================================="
echo "⏱️ Total Benchmarking Time: ${MINUTES}m ${SECONDS}s"
echo "📊 A detailed Gradle profiling report is available at:"
echo " android/build/reports/profile/"
echo " (Open the latest .html file in a browser to see where the time was spent)"
echo "==========================================="
cd ..
使用方式:
chmod +x scripts/benchmark-build.sh
./scripts/benchmark-build.sh # 默认 release
./scripts/benchmark-build.sh debug # 对 debug 做基准
快速上手:一次跑完优化流程
在项目中落地全部优化的推荐顺序:
# 1. Create scripts directory and copy the scripts from this guide
mkdir -p scripts
# 2. Setup ccache (run once)
chmod +x scripts/setup-ccache.sh
./scripts/setup-ccache.sh
# 3. Optimize Gradle (run once or after fresh clone)
chmod +x scripts/optimize-gradle.sh
./scripts/optimize-gradle.sh
# 4. Update metro.config.js for Metro optimization
# Add dynamic worker allocation (see Section 2)
# 5. Add active architecture flag to package.json
# Add "--active-arch-only" to your dev script (see Section 4)
# 6. Build with benchmarking
chmod +x scripts/benchmark-build.sh
./scripts/benchmark-build.sh
首次完整构建之后,借助 ccache 命中,后续构建通常会明显更快。
总结
| 优化项 | 预期收益 |
|---|---|
| Gradle 并行 + 内存 | Android 构建约快 30%–50% |
Metro maxWorkers | JS 打包约 2–4 倍 |
| ccache | 首次构建之后常再快 50%+ |
| 仅当前架构 | debug 构建约 2–3 倍 |
四项叠加,在现代多核机器上,release 从 20+ 分钟 压到 约 2–5 分钟 是合理预期;Apple Silicon 上往往还能更快。先跑一轮优化后的构建并持续看 profiling 报告,长期会省很多时间。
原文站点