Build #1317
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Build | |
| on: | |
| schedule: | |
| - cron: '0 3 * * *' | |
| workflow_dispatch: | |
| inputs: | |
| platform: | |
| description: Platform | |
| required: false | |
| jobs: | |
| preflight: | |
| name: Preflight | |
| runs-on: ubuntu-latest | |
| outputs: | |
| should_build: ${{ steps.gate.outputs.should_build }} | |
| head_sha: ${{ steps.gate.outputs.head_sha }} | |
| short_sha: ${{ steps.gate.outputs.short_sha }} | |
| build_id: ${{ steps.gate.outputs.build_id }} | |
| built_at: ${{ steps.gate.outputs.built_at }} | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - id: gate | |
| env: | |
| GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
| run: | | |
| HEAD=$(git rev-parse HEAD) | |
| SHORT=$(git rev-parse --short HEAD) | |
| BUILD_ID="nightly-$(date -u +%Y%m%d)-${SHORT}" | |
| BUILT_AT=$(date -u +%Y-%m-%dT%H:%M:%SZ) | |
| # Nightly rebuilds unconditionally on schedule. builder.sh re-clones | |
| # OpenIPC/firmware at HEAD on every run, so the relevant inputs are | |
| # mostly outside this repo (firmware HEAD, toolchain release, kernel | |
| # tarball, vendor osdrv, individual package upstreams). The previous | |
| # gate skipped when only this repo's HEAD matched the last published | |
| # nightly, which made upstream fixes (e.g. an openhisilicon mipi_rx | |
| # regression fix that lands in firmware) invisible to users until | |
| # something here happened to change. Always build on schedule. | |
| echo "Build: $BUILD_ID (event=${{ github.event_name }})" | |
| echo "should_build=true" >> "$GITHUB_OUTPUT" | |
| echo "head_sha=$HEAD" >> "$GITHUB_OUTPUT" | |
| echo "short_sha=$SHORT" >> "$GITHUB_OUTPUT" | |
| echo "build_id=$BUILD_ID" >> "$GITHUB_OUTPUT" | |
| echo "built_at=$BUILT_AT" >> "$GITHUB_OUTPUT" | |
| buildroot: | |
| name: Firmware | |
| needs: preflight | |
| if: needs.preflight.outputs.should_build == 'true' | |
| runs-on: ubuntu-latest | |
| env: | |
| BUILD_ID: ${{ needs.preflight.outputs.build_id }} | |
| BUILD_SHA: ${{ needs.preflight.outputs.head_sha }} | |
| BUILD_PLATFORM: ${{ matrix.platform }} | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| platform: | |
| - gk7202v300_lite_cootli_camv0103 | |
| - gk7202v300_lite_ipg-g3-wr | |
| - gk7202v300_lite_xg521 | |
| - gk7205v200_lite_tiandy-tc-c321n | |
| - gk7205v200_lite_vixand-ipc-1 | |
| - gk7205v200_lite_vixand-iph-5-4g | |
| - gk7205v210_lite_tiandy-tc-c32qn | |
| - gk7205v210_lite_vixand-ivg-g3s | |
| - gk7205v210_lite_vixand-ivg-g4f-a | |
| - gk7205v210_lite_vixand-ivg-g4f-a-w | |
| - gk7205v210_lite_vixand-ivg-g4h | |
| - gk7205v300_lite_vixand-ivg-g6s | |
| - gk7205v300_lite_vixand-ivg-g6s-w | |
| - hi3516cv200_lite_trassir-tr-d4121ir1-v2 | |
| - hi3516ev300_ultimate_rostelecom-ipc8232swc-we | |
| - hi3516ev300_ultimate_rvi-1ncmw2028 | |
| - hi3518ev200_lite_smartwares-cip-37210 | |
| - hi3518ev200_lite_switcam-hs303 | |
| - hi3518ev200_lite_switcam-hs303-v2 | |
| - hi3518ev200_lite_vstarcam-c8892wip | |
| - hi3518ev200_lite_qtech-qvc-ipc-136w | |
| - hi3518ev300_lite_bathhouse | |
| - hi3518ev300_lite_xiaomi-mjsxj02hl | |
| - hi3518ev200_ultimate_lenovo-snowman-1080p | |
| - ssc30kd_lite_cmcc-ds-ytj5301 | |
| - ssc325_lite_imilab-ec3-cmsxj25a | |
| - ssc325_lite_imou-c22cp | |
| - ssc325_lite_tp-link-tapo-c310-v1 | |
| - ssc325_lite_trassir-tr-w2c1-v1 | |
| - ssc325de_lite_imou-c22ep-s2 | |
| - ssc333_lite_meari-speed-6s | |
| - ssc333_lite_tp-link-tapo-c110-v2 | |
| - ssc333_lite_tp-link-tapo-c110-v26 | |
| - ssc333_lite_babysense-see-hd-ip206 | |
| - ssc333_lite_vstarcam-c43s_b | |
| - ssc335_lite_tp-link-tapo-c110-v1 | |
| - ssc335_lite_tp-link-tapo-c310-v220 | |
| - ssc335_lite_trassir-tr-w2c1-v2 | |
| - ssc335de_lite_dahua-hfw1230sp-v2 | |
| - ssc335de_lite_imou-c22e-s2-v2 | |
| - ssc335de_lite_uniview-c1l-2wn-g | |
| - ssc337_lite_h3c-tc2101 | |
| - ssc337_lite_tiandy-tc-c321n-v2 | |
| - ssc337_lite_tp-link-tapo-c110-v1 | |
| - ssc337de_ultimate_foscam-x5 | |
| - ssc338q_fpv_caddx-fly | |
| - ssc338q_fpv_emax-wyvern-link | |
| - ssc338q_fpv_openipc-mario-aio | |
| - ssc338q_fpv_openipc-thinker-aio | |
| - ssc338q_fpv_openipc-urllc-aio | |
| - ssc338q_fpv_runcam-wifilink | |
| - ssc377qe_fpv_ccdcam-im50q01-tipoman | |
| - t10_lite_hb-wifi-z6 | |
| - t10_lite_jvs-ingt10-gqs60ep | |
| - t20_ultimate_azarton-c1 | |
| - t20_lite_ec37-t11 | |
| - t31_lite_vstarcam-cs55 | |
| - t21_lite_chinamobile-hdc-51-a5-v12 | |
| - t21_lite_smartwares-cip-37210at | |
| - t21_lite_xyx-06s | |
| - t21_lite_wansview-q5-1080p | |
| - t23_lite_jooan-a6m-u | |
| - t23_lite_jooan-q3r-u | |
| - t23_lite_lsc-3215672 | |
| - t31_lite_aceline-aip-o4 | |
| - t31_lite_wansview-q5-2k | |
| - t31_lite_aoni-ep01j05 | |
| - t31_lite_chinamobile-hdc-51-a6-v11 | |
| - t31_lite_cmcc-hdc-51-a6-v10 | |
| - t31_lite_chinatelecom-y4h-50 | |
| - t31_lite_wyze-v3b | |
| - t31_lite_xiaomi-mjsxj03hl | |
| - t31_lite_xiaomi-mjsxj03hl-jxq03 | |
| - t31_lite_tuya-gv7630-t31-ptz | |
| - t31_ultimate_azarton-c1-t31x | |
| - t31_ultimate_gcraftsman-gca50 | |
| - t31_lite_zte-k540 | |
| - t40_lite_movols-mo-805p | |
| # APFPV | |
| - ssc30kq_apfpv_greg-generic-bu-eu | |
| - ssc30kq_apfpv_greg-generic-cu-eu | |
| - ssc338q_apfpv | |
| - ssc338q_apfpv_greg-generic-bu-eu | |
| - ssc338q_apfpv_greg-generic-cu-eu | |
| - ssc378qe_apfpv | |
| # FPV | |
| - hi3516ev200_fpv | |
| - hi3516ev300_fpv | |
| - hi3536dv100_fpv | |
| - gk7205v200_fpv | |
| - gk7205v210_fpv | |
| - gk7205v300_fpv | |
| - ssc30kq_fpv | |
| - ssc338q_fpv | |
| - ssc378qe_fpv | |
| # Ruby | |
| - ssc30kq_rubyfpv_generic | |
| - ssc338q_rubyfpv_generic | |
| - ssc338q_rubyfpv_thinker_internal_wifi | |
| # LTE | |
| - hi3516ev200_lte | |
| - hi3516ev300_lte | |
| - gk7205v200_lte | |
| - gk7205v300_lte | |
| # Venc | |
| - gk7205v200_venc | |
| - gk7205v210_venc | |
| - gk7205v300_venc | |
| # Mini | |
| - hi3516cv300_mini | |
| - hi3518ev200_mini | |
| steps: | |
| - name: Checkout source | |
| uses: actions/checkout@v4 | |
| - name: Prepare firmware | |
| run: | | |
| echo "nameserver 8.8.8.8" | sudo tee /etc/resolv.conf | |
| echo CACHE_DATE=$(date +%m) >> ${GITHUB_ENV} | |
| INPUT=${{inputs.platform}} | |
| MATRIX=$(echo ${{matrix.platform}} | cut -d_ -f1) | |
| if [ -z ${INPUT} ] || [ ${INPUT} = ${MATRIX} ]; then | |
| echo RUN=${MATRIX} >> ${GITHUB_ENV} | |
| fi | |
| - name: Setup ccache | |
| if: env.RUN | |
| uses: actions/cache@v4 | |
| with: | |
| path: /tmp/ccache | |
| key: ${{matrix.platform}}-${{env.CACHE_DATE}} | |
| # builder.sh does `rm -rf openipc` at the top of every run to force a | |
| # clean re-clone of OpenIPC/firmware, which also nukes the default | |
| # `openipc/output/dl/` directory Buildroot uses for downloaded source | |
| # tarballs. Without a cache, every cron run re-downloads ~1-3 GB of | |
| # tarballs from upstream mirrors — and any one of them randomly | |
| # failing (e.g. cgit `snapshot/` URLs that regenerate tarballs per | |
| # request with shifting sha256, like wireguard-tools on | |
| # git.zx2c4.com) takes down the matrix entry for that board. See | |
| # kaeru wireguard-zx2c4-tarball-regeneration-hash-drift for the | |
| # specific incident this caching addresses. | |
| # | |
| # Cache to /tmp/builder-dl (outside the openipc/ tree so builder.sh's | |
| # rm -rf doesn't touch it) and point Buildroot at it via BR2_DL_DIR | |
| # env var (honored per Buildroot manual section "Location of source | |
| # tarballs"). Mirrors OpenIPC/firmware/.github/workflows/build.yml's | |
| # output/dl cache, adapted for builder's clean-clone behavior. | |
| - name: Setup dl cache | |
| if: env.RUN | |
| uses: actions/cache@v4 | |
| with: | |
| path: /tmp/builder-dl | |
| key: builder-dl-${{env.CACHE_DATE}} | |
| restore-keys: builder-dl- | |
| - name: Build firmware | |
| if: env.RUN | |
| run: | | |
| export GIT_HASH=$(git rev-parse --short ${GITHUB_SHA}) | |
| export GIT_BRANCH=${GITHUB_REF_NAME} | |
| echo GIT_HASH=${GIT_HASH} >> ${GITHUB_ENV} | |
| echo GIT_BRANCH=${GIT_BRANCH} >> ${GITHUB_ENV} | |
| mkdir -p /tmp/ccache | |
| ln -s /tmp/ccache ${HOME}/.ccache | |
| mkdir -p /tmp/builder-dl | |
| export BR2_DL_DIR=/tmp/builder-dl | |
| NAME=${{matrix.platform}} | |
| # Retry budget for transient upstream toolchain/CDN flakes | |
| # (matches OpenIPC/firmware/.github/workflows/build.yml). | |
| backoffs="30 60 120 300 600 1200" | |
| attempt=1 | |
| for sleep_for in $backoffs ""; do | |
| bash builder.sh ${NAME} && break | |
| if [ -z "$sleep_for" ]; then | |
| echo "::error::build failed after ${attempt} attempts" | |
| exit 1 | |
| fi | |
| echo "::warning::attempt ${attempt} failed, retrying after ${sleep_for}s" | |
| sleep "$sleep_for" | |
| attempt=$((attempt + 1)) | |
| done | |
| cd openipc | |
| TIME=$(date -d @${SECONDS} +%M:%S) | |
| echo TIME=${TIME} >> ${GITHUB_ENV} | |
| COMMON=$(echo ${NAME} | awk -F_ '{print NF-1}') | |
| NORFW=$(find output/images -name openipc*nor*) | |
| if [ ! -z ${NORFW} ]; then | |
| if [ ${COMMON} -eq 1 ]; then | |
| echo NORFW=openipc/${NORFW} >> ${GITHUB_ENV} | |
| else | |
| mv ${NORFW} ../${NAME}-nor.tgz | |
| echo NORFW=${NAME}-nor.tgz >> ${GITHUB_ENV} | |
| fi | |
| fi | |
| NANDFW=$(find output/images -name openipc*nand*) | |
| if [ ! -z ${NANDFW} ]; then | |
| if [ ${COMMON} -eq 1 ]; then | |
| echo NANDFW=openipc/${NANDFW} >> ${GITHUB_ENV} | |
| else | |
| mv ${NANDFW} ../${NAME}-nand.tgz | |
| echo NANDFW=${NAME}-nand.tgz >> ${GITHUB_ENV} | |
| fi | |
| fi | |
| if [ -z ${NORFW} ] && [ -z ${NANDFW} ]; then | |
| exit 1 | |
| fi | |
| - name: Upload firmware (dated) | |
| if: env.NORFW || env.NANDFW | |
| uses: softprops/action-gh-release@v2 | |
| with: | |
| tag_name: ${{ needs.preflight.outputs.build_id }} | |
| prerelease: true | |
| body: | | |
| sha=${{ needs.preflight.outputs.head_sha }} | |
| short=${{ needs.preflight.outputs.short_sha }} | |
| built_at=${{ needs.preflight.outputs.built_at }} | |
| files: | | |
| ${{env.NORFW}} | |
| ${{env.NANDFW}} | |
| - name: Upload firmware (rolling nightly) | |
| if: env.NORFW || env.NANDFW | |
| uses: softprops/action-gh-release@v2 | |
| with: | |
| tag_name: nightly | |
| body: | | |
| sha=${{ needs.preflight.outputs.head_sha }} | |
| short=${{ needs.preflight.outputs.short_sha }} | |
| built_at=${{ needs.preflight.outputs.built_at }} | |
| files: | | |
| ${{env.NORFW}} | |
| ${{env.NANDFW}} | |
| - name: Upload firmware (latest — legacy alias) | |
| if: env.NORFW || env.NANDFW | |
| uses: softprops/action-gh-release@v2 | |
| with: | |
| tag_name: latest | |
| files: | | |
| ${{env.NORFW}} | |
| ${{env.NANDFW}} | |
| - name: Send binary | |
| if: env.NORFW | |
| run: | | |
| TG_MSG="Build: ${BUILD_ID}\nCommit: ${GIT_HASH}\nBranch: ${GIT_BRANCH}\nTime: ${TIME}\n\n" | |
| TG_ICON="\xE2\x9C\x85 GitHub Actions" | |
| TG_HEADER=$(echo -e ${TG_MSG}${TG_ICON}) | |
| TG_TOKEN=${{secrets.TELEGRAM_TOKEN_BOT_OPENIPC}} | |
| TG_CHANNEL=${{secrets.TELEGRAM_CHANNEL_OPENIPC_DEV}} | |
| HTTP=$(curl -s -o /dev/null -w %{http_code} https://api.telegram.org/bot${TG_TOKEN}/sendDocument -F chat_id=${TG_CHANNEL} -F caption="${TG_HEADER}" -F document=@${NORFW}) | |
| echo Telegram response: ${HTTP} |