nix-hashes.yml 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162
  1. name: nix-hashes
  2. permissions:
  3. contents: write
  4. on:
  5. workflow_dispatch:
  6. push:
  7. branches: [dev, beta]
  8. paths:
  9. - "bun.lock"
  10. - "package.json"
  11. - "packages/*/package.json"
  12. - "flake.lock"
  13. - "nix/node_modules.nix"
  14. - "nix/scripts/**"
  15. - "patches/**"
  16. - ".github/workflows/nix-hashes.yml"
  17. concurrency:
  18. group: ${{ github.workflow }}-${{ github.ref }}
  19. cancel-in-progress: true
  20. jobs:
  21. # Native runners required: bun install cross-compilation flags (--os/--cpu)
  22. # do not produce byte-identical node_modules as native installs.
  23. compute-hash:
  24. strategy:
  25. fail-fast: false
  26. matrix:
  27. include:
  28. - system: x86_64-linux
  29. runner: blacksmith-4vcpu-ubuntu-2404
  30. - system: aarch64-linux
  31. runner: blacksmith-4vcpu-ubuntu-2404-arm
  32. - system: x86_64-darwin
  33. runner: macos-15-intel
  34. - system: aarch64-darwin
  35. runner: macos-latest
  36. runs-on: ${{ matrix.runner }}
  37. steps:
  38. - name: Checkout repository
  39. uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
  40. - name: Setup Nix
  41. uses: nixbuild/nix-quick-install-action@2c9db80fb984ceb1bcaa77cdda3fdf8cfba92035 # v34
  42. - name: Compute node_modules hash
  43. id: hash
  44. env:
  45. SYSTEM: ${{ matrix.system }}
  46. run: |
  47. set -euo pipefail
  48. BUILD_LOG=$(mktemp)
  49. trap 'rm -f "$BUILD_LOG"' EXIT
  50. HASH=""
  51. MAX_ATTEMPTS=3
  52. for ((ATTEMPT = 1; ATTEMPT <= MAX_ATTEMPTS; ATTEMPT++)); do
  53. # Build with fakeHash to trigger hash mismatch and reveal correct hash
  54. nix build ".#packages.${SYSTEM}.node_modules_updater" --no-link 2>&1 | tee "$BUILD_LOG" || true
  55. HASH="$(nix run --inputs-from . nixpkgs#gnugrep -- -oP 'got:\s*\Ksha256-[A-Za-z0-9+/=]+' "$BUILD_LOG" | tail -n1 || true)"
  56. [ -n "$HASH" ] && break
  57. if [ "$ATTEMPT" -lt "$MAX_ATTEMPTS" ]; then
  58. echo "::warning::Attempt ${ATTEMPT}/${MAX_ATTEMPTS} produced no hash for ${SYSTEM}; retrying in $((ATTEMPT * 10))s"
  59. sleep $((ATTEMPT * 10))
  60. fi
  61. done
  62. if [ -z "$HASH" ]; then
  63. echo "::error::Failed to compute hash for ${SYSTEM} after ${MAX_ATTEMPTS} attempts"
  64. cat "$BUILD_LOG"
  65. exit 1
  66. fi
  67. echo "$HASH" > hash.txt
  68. echo "Computed hash for ${SYSTEM}: $HASH"
  69. - name: Upload hash
  70. uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
  71. with:
  72. name: hash-${{ matrix.system }}
  73. path: hash.txt
  74. retention-days: 1
  75. update-hashes:
  76. needs: compute-hash
  77. if: github.event_name != 'pull_request'
  78. runs-on: blacksmith-4vcpu-ubuntu-2404
  79. steps:
  80. - name: Checkout repository
  81. uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4.3.1
  82. with:
  83. persist-credentials: false
  84. fetch-depth: 0
  85. ref: ${{ github.ref_name }}
  86. - name: Setup git committer
  87. uses: ./.github/actions/setup-git-committer
  88. with:
  89. opencode-app-id: ${{ vars.OPENCODE_APP_ID }}
  90. opencode-app-secret: ${{ secrets.OPENCODE_APP_SECRET }}
  91. - name: Pull latest changes
  92. run: |
  93. git pull --rebase --autostash origin "$GITHUB_REF_NAME"
  94. - name: Download hash artifacts
  95. uses: actions/download-artifact@d3f86a106a0bac45b974a628896c90dbdf5c8093 # v4.3.0
  96. with:
  97. path: hashes
  98. pattern: hash-*
  99. - name: Update hashes.json
  100. run: |
  101. set -euo pipefail
  102. HASH_FILE="nix/hashes.json"
  103. [ -f "$HASH_FILE" ] || echo '{"nodeModules":{}}' > "$HASH_FILE"
  104. for SYSTEM in x86_64-linux aarch64-linux x86_64-darwin aarch64-darwin; do
  105. FILE="hashes/hash-${SYSTEM}/hash.txt"
  106. if [ -f "$FILE" ]; then
  107. HASH="$(tr -d '[:space:]' < "$FILE")"
  108. echo "${SYSTEM}: ${HASH}"
  109. jq --arg sys "$SYSTEM" --arg h "$HASH" '.nodeModules[$sys] = $h' "$HASH_FILE" > tmp.json
  110. mv tmp.json "$HASH_FILE"
  111. else
  112. echo "::warning::Missing hash for ${SYSTEM}"
  113. fi
  114. done
  115. cat "$HASH_FILE"
  116. - name: Commit changes
  117. run: |
  118. set -euo pipefail
  119. HASH_FILE="nix/hashes.json"
  120. if [ -z "$(git status --short -- "$HASH_FILE")" ]; then
  121. echo "No changes to commit"
  122. echo "### Nix hashes" >> "$GITHUB_STEP_SUMMARY"
  123. echo "Status: no changes" >> "$GITHUB_STEP_SUMMARY"
  124. exit 0
  125. fi
  126. git add "$HASH_FILE"
  127. git commit -m "chore: update nix node_modules hashes"
  128. git pull --rebase --autostash origin "$GITHUB_REF_NAME"
  129. git push origin HEAD:"$GITHUB_REF_NAME"
  130. echo "### Nix hashes" >> "$GITHUB_STEP_SUMMARY"
  131. echo "Status: committed $(git rev-parse --short HEAD)" >> "$GITHUB_STEP_SUMMARY"