Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/scatterlab/android-prebuilt.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ env ORG_GRADLE_PROJECT_react.internal.useHermesStable=true \
- `isSnapshot`을 켜지 않는다. 켜면 버전에 `-SNAPSHOT`이 붙어 좌표가 어긋난다.
- ABI는 기본값(`armeabi-v7a,arm64-v8a,x86,x86_64`)을 그대로 둔다. 소비자의 `reactNativeArchitectures`와 같아야 한다.
- Debug·Release 두 variant는 `components.default` 멀티 variant 퍼블리시로 한 번에 나온다(`publish.gradle`).
- 빌드는 상류와 같은 `reactnativecommunity/react-native-android` 컨테이너에서 돈다 — 러너 이미지에 Android SDK·NDK·CMake가 없다. **digest로 고정**한다: 툴체인이 밑에서 움직이면 같은 커밋의 두 빌드가 달라지고, 이 워크플로가 증명하려는 것이 바로 그 동일성이다. base가 고정이면 요구 툴체인도 고정이므로 **base를 올릴 때만** 다시 핀한다.
- 빌드는 **zeta 의 네이티브 Android 출고가 도는 러너**(`[self-hosted, zeta-app-builder]`)에서 돈다 — SDK·NDK·CMake 가 이미 있고 조직 TLS 프록시도 이미 신뢰한다. 상류처럼 `reactnativecommunity/react-native-android` 컨테이너를 쓰는 길은 막혀 있다: dind ARC 러너의 잡 컨테이너 안에서는 git 이 github.com 을 검증하지 못하고(조직이 자체 CA로 TLS를 종단한다), `volumes:` 로도 못 고친다 — dind는 **docker 데몬 쪽** 파일시스템을 마운트하지 그 CA를 가진 러너의 것을 마운트하지 않는다. `ANDROID_HOME` 은 `deploy-native.yml` 과 같은 값을 쓴다.
- ccache를 러너에 유지한다. 없으면 매 실행이 전체 C++ 재컴파일이다.
- 빌드 산출물은 수 GB다. `if: always()`로 정리한다.

Expand Down
64 changes: 27 additions & 37 deletions .github/workflows/scatterlab-prebuild-android.yml
Original file line number Diff line number Diff line change
Expand Up @@ -118,60 +118,50 @@ jobs:

build:
needs: prepare
runs-on: arc-messenger-dev
# The runner image carries no Android SDK, NDK or CMake, and ReactAndroid needs all
# three. Upstream builds these same artifacts inside this image (`publish-npm.yml`'s
# `build_android`), so it is the toolchain the sources expect. `arc-messenger-dev` is a
# dind scale set, so it can run a job container.
# zeta 의 네이티브 Android 출고가 도는 러너다 (`zeta-frontend` 의 `deploy-native.yml`).
# SDK·NDK·CMake 가 이미 깔려 있고, 조직 TLS 프록시도 이미 신뢰한다.
#
# Pinned by digest, not `:latest`: this workflow exists to prove the AAR was built from
# the sources its version claims, and a toolchain that moves underneath makes two builds
# of the same commit differ. `VERSION_NAME` is pinned to the upstream base, so the NDK
# and CMake this needs are fixed too - re-pin when the base moves, not before.
# sha256:24ca7ab5... is `v21.0` (2026-06-19), which `:latest` pointed at.
container:
image: reactnativecommunity/react-native-android@sha256:24ca7ab5a70ec0b78a81bdc5eeea5924c2531531d53971b6f2321aff08446c36
env:
TERM: 'dumb'
# Gradle mis-decompresses tar.gz inside containers under some locales.
# https://github.com/gradle/gradle/issues/23391#issuecomment-1878979127
LC_ALL: C.UTF8
GRADLE_OPTS: '-Dorg.gradle.daemon=false'
# The image's git could not verify github.com ("CAfile: none") while the host runner
# reaches the same URL fine - the trust the host has is not inside the container.
# Mounting the host's bundle covers both causes: an image without ca-certificates,
# and an org TLS proxy whose CA only the host trusts.
volumes:
- /etc/ssl/certs:/etc/ssl/certs:ro
# 상류는 이 아티팩트를 `reactnativecommunity/react-native-android` 컨테이너에서 빌드하고
# 그게 소스가 전제하는 툴체인이지만, 그 길은 막혔다: dind ARC 러너의 잡 컨테이너 안에서는
# git 이 github.com 을 검증하지 못한다(조직이 자체 CA 로 TLS 를 종단한다). `volumes:` 로는
# 못 고친다 — dind 는 **docker 데몬 쪽**(사이드카) 파일시스템을 마운트하지, 그 CA 를 가진
# 러너의 것을 마운트하지 않는다. 컨테이너 안에서 맞추려면 git·node·JVM 트러스트스토어를
# 따로 손봐야 한다. 이미 동작하는 러너를 쓰는 편이 낫다.
runs-on: [self-hosted, zeta-app-builder]
env:
# deploy-native.yml 과 같은 값. 두 러너(gaudi·zeta-app-builder)의 유저명이 모두
# scatterlab 이라 절대 경로가 그대로 유효하다.
ANDROID_HOME: /Users/scatterlab/Library/Android/sdk
ANDROID_SDK_ROOT: /Users/scatterlab/Library/Android/sdk
permissions:
contents: write
outputs:
sha256: ${{ steps.pack.outputs.sha256 }}
steps:
# Printed before the first network step so a TLS failure carries its evidence instead
# of costing another run to diagnose. Never fails the job.
- name: Diagnose TLS trust inside the container
continue-on-error: true
run: |
echo "certs in /etc/ssl/certs: $(find /etc/ssl/certs -type f -o -type l 2>/dev/null | wc -l)"
echo "SSL_CERT_FILE=${SSL_CERT_FILE:-unset} GIT_SSL_CAINFO=${GIT_SSL_CAINFO:-unset}"
git config --get http.sslCAInfo || echo "http.sslCAInfo unset"
echo "github.com -> $(curl -sS -o /dev/null -w '%{http_code}' --connect-timeout 5 --max-time 30 https://github.com 2>&1 || true)"
echo "repo1.maven.org -> $(curl -sS -o /dev/null -w '%{http_code}' --connect-timeout 5 --max-time 30 https://repo1.maven.org/maven2/ 2>&1 || true)"

- uses: actions/checkout@v4

- name: Setup git safe folders
run: git config --global --add safe.directory '*'

# 맥 러너는 matrix 잡들이 $HOME 을 공유하고 yarn 1 전역 캐시는 동시성 안전하지 않다
# (iOS prebuild 에서 두 번 밟았다). setup-node 보다 먼저 export 해야 그 안의 중첩
# yarn 호출까지 덮인다.
- name: Isolate the yarn cache
run: echo "YARN_CACHE_FOLDER=$RUNNER_TEMP/yarn-cache" >> "$GITHUB_ENV"

- uses: ./.github/actions/setup-node
- uses: ./.github/actions/yarn-install

# Without a warm ccache every run is a full C++ rebuild of ReactCommon.
# CCACHE_DIR is set explicitly: ccache's default differs per platform, and the cache
# action needs the same path the compiler actually writes to.
- name: Point ccache at a known directory
run: echo "CCACHE_DIR=$RUNNER_TEMP/ccache" >> "$GITHUB_ENV"

- name: Restore the Android ccache
uses: actions/cache/restore@v4
with:
path: ~/.cache/ccache
path: ${{ runner.temp }}/ccache
key: scatterlab-ccache-android-${{ hashFiles('packages/react-native/ReactAndroid/**/*.cpp', 'packages/react-native/ReactAndroid/**/*.h', 'packages/react-native/ReactCommon/**/*.cpp', 'packages/react-native/ReactAndroid/**/CMakeLists.txt', 'packages/react-native/ReactCommon/**/CMakeLists.txt') }}
restore-keys: scatterlab-ccache-android-

Expand Down Expand Up @@ -340,7 +330,7 @@ jobs:
if: always()
uses: actions/cache/save@v4
with:
path: ~/.cache/ccache
path: ${{ runner.temp }}/ccache
key: scatterlab-ccache-android-${{ hashFiles('packages/react-native/ReactAndroid/**/*.cpp', 'packages/react-native/ReactAndroid/**/*.h', 'packages/react-native/ReactCommon/**/*.cpp', 'packages/react-native/ReactAndroid/**/CMakeLists.txt', 'packages/react-native/ReactCommon/**/CMakeLists.txt') }}

# A shared runner: the build products are several GB.
Expand Down