feat(stash): sync templates to dedicated repository #208
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: Validate repository | |
| on: | |
| workflow_call: | |
| inputs: | |
| revision: | |
| description: Exact repository revision to validate | |
| required: true | |
| type: string | |
| push: | |
| branches: | |
| - main | |
| # Resource and documentation changes use their focused publication flows. | |
| paths: | |
| - '.github/**' | |
| - 'py/**' | |
| - 'script/**/*.js' | |
| - 'shell/**/*.sh' | |
| - 'cfg/*.ini' | |
| - 'cfg/yaml/**' | |
| - 'requirements*.txt' | |
| - 'workers/repository-mirror/**' | |
| pull_request: | |
| branches: | |
| - main | |
| paths: | |
| - '.github/**' | |
| - 'py/**' | |
| - 'rule/Custom_Direct.list' | |
| - 'rule/Custom_Proxy.list' | |
| - 'rule/Steam_CDN.list' | |
| - 'rule/Encrypted_DNS.list' | |
| - 'rule/Game_Download_CDN.list' | |
| - 'rule/game_rule/**/*.list' | |
| - 'script/**/*.js' | |
| - 'shell/**/*.sh' | |
| - 'cfg/*.ini' | |
| - 'cfg/yaml/**' | |
| - 'requirements*.txt' | |
| - 'workers/repository-mirror/**' | |
| workflow_dispatch: | |
| permissions: | |
| contents: read | |
| concurrency: | |
| group: >- | |
| validate-${{ inputs.revision && 'snapshot' || 'event' }}-${{ | |
| inputs.revision || github.ref | |
| }} | |
| cancel-in-progress: true | |
| jobs: | |
| dependency-review: | |
| if: github.event_name == 'pull_request' | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 10 | |
| steps: | |
| - name: Reject newly introduced vulnerable dependencies | |
| uses: actions/dependency-review-action@a1d282b36b6f3519aa1f3fc636f609c47dddb294 # v5.0.0 | |
| with: | |
| fail-on-severity: low | |
| fail-on-scopes: development, runtime, unknown | |
| retry-on-snapshot-warnings: true | |
| retry-on-snapshot-warnings-timeout: 120 | |
| show-openssf-scorecard: true | |
| warn-on-openssf-scorecard-level: 5 | |
| show-patched-versions: true | |
| validate: | |
| runs-on: ubuntu-latest | |
| timeout-minutes: 15 | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7 | |
| with: | |
| ref: ${{ inputs.revision || github.sha }} | |
| fetch-depth: 0 | |
| - name: Set up Node.js | |
| uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7.0.0 | |
| with: | |
| node-version: '24' | |
| - name: Validate JavaScript | |
| shell: bash | |
| run: | | |
| git ls-files -z -- '*.js' '*.mjs' '*.cjs' | | |
| xargs -0 -r -n 1 -t node --check | |
| node --test .github/scripts/*.test.cjs | |
| - name: Set up Python | |
| uses: actions/setup-python@5fda3b95a4ea91299a34e894583c3862153e4b97 # v7.0.0 | |
| with: | |
| python-version: '3.13' | |
| - name: Set up pinned Mihomo | |
| uses: ./.github/actions/setup-mihomo | |
| - name: Materialize derived rules for changed sources | |
| if: github.event_name == 'push' || github.event_name == 'pull_request' | |
| shell: bash | |
| env: | |
| EVENT_NAME: ${{ github.event_name }} | |
| EVENT_BEFORE: ${{ github.event.before }} | |
| EVENT_SHA: ${{ github.sha }} | |
| BASE_SHA: ${{ github.event.pull_request.base.sha }} | |
| run: | | |
| set -euo pipefail | |
| if [ "$EVENT_NAME" = "pull_request" ]; then | |
| diff_base="$BASE_SHA" | |
| elif [ -n "$EVENT_BEFORE" ] && [ "${EVENT_BEFORE//0/}" != "" ]; then | |
| diff_base="$EVENT_BEFORE" | |
| else | |
| diff_base="$(git rev-parse "${EVENT_SHA}^")" | |
| fi | |
| source_pathspecs=( | |
| 'rule/Custom_Direct.list' | |
| 'rule/Custom_Proxy.list' | |
| 'rule/Steam_CDN.list' | |
| 'rule/Encrypted_DNS.list' | |
| 'rule/Game_Download_CDN.list' | |
| ':(glob)rule/game_rule/**/*.list' | |
| 'py/generate_rules.py' | |
| ) | |
| if git diff --quiet "$diff_base" "$EVENT_SHA" -- \ | |
| "${source_pathspecs[@]}"; then | |
| echo "No derived-rule source changed." | |
| exit 0 | |
| fi | |
| echo "Materializing derived rules for validation only." | |
| python py/generate_rules.py --mihomo mihomo | |
| - name: Download and verify static analysis tools | |
| env: | |
| SHELLCHECK_VERSION: v0.11.0 | |
| SHELLCHECK_SHA256: 8c3be12b05d5c177a04c29e3c78ce89ac86f1595681cab149b65b97c4e227198 | |
| ACTIONLINT_VERSION: 1.7.12 | |
| ACTIONLINT_SHA256: 8aca8db96f1b94770f1b0d72b6dddcb1ebb8123cb3712530b08cc387b349a3d8 | |
| run: | | |
| set -euo pipefail | |
| shellcheck_archive="shellcheck-${SHELLCHECK_VERSION}.linux.x86_64.tar.xz" | |
| actionlint_archive="actionlint_${ACTIONLINT_VERSION}_linux_amd64.tar.gz" | |
| curl --fail --location --show-error \ | |
| --retry 3 --retry-delay 3 --retry-all-errors --retry-max-time 120 \ | |
| --connect-timeout 15 --max-time 60 \ | |
| --output "$shellcheck_archive" \ | |
| "https://github.com/koalaman/shellcheck/releases/download/${SHELLCHECK_VERSION}/${shellcheck_archive}" | |
| curl --fail --location --show-error \ | |
| --retry 3 --retry-delay 3 --retry-all-errors --retry-max-time 120 \ | |
| --connect-timeout 15 --max-time 60 \ | |
| --output "$actionlint_archive" \ | |
| "https://github.com/rhysd/actionlint/releases/download/v${ACTIONLINT_VERSION}/${actionlint_archive}" | |
| printf '%s %s\n' "$SHELLCHECK_SHA256" "$shellcheck_archive" | sha256sum --check --strict | |
| printf '%s %s\n' "$ACTIONLINT_SHA256" "$actionlint_archive" | sha256sum --check --strict | |
| tar -xJf "$shellcheck_archive" | |
| tar -xzf "$actionlint_archive" | |
| install -m 0755 "shellcheck-${SHELLCHECK_VERSION}/shellcheck" "$RUNNER_TEMP/shellcheck" | |
| install -m 0755 actionlint "$RUNNER_TEMP/actionlint" | |
| - name: Validate scripts and generated rules | |
| run: | | |
| sh -n shell/check_cpu_version.sh | |
| sh -n shell/install_openclash_dev.sh | |
| sh -n shell/install_openclash_dev_update.sh | |
| sh -n .github/scripts/test_installers.sh | |
| shellcheck --shell=sh shell/check_cpu_version.sh shell/install_openclash_dev.sh shell/install_openclash_dev_update.sh .github/scripts/test_installers.sh | |
| actionlint .github/workflows/*.yml | |
| sh shell/check_cpu_version.sh --self-check | |
| python -m unittest discover -s py -p 'test_rule_generation.py' | |
| python -m unittest discover -s .github/scripts -p 'test_*.py' | |
| python .github/scripts/jsdelivr_purge.py check-contract --revision HEAD | |
| sh .github/scripts/test_installers.sh | |
| python py/sync_installer_common.py --check | |
| python py/generate_game_cdn.py --check | |
| python py/update_encrypted_dns.py --check | |
| python py/generate_rules.py --check --mihomo mihomo | |
| python py/generate_stash_configs.py --check | |
| - name: Validate complete Mihomo templates | |
| run: | | |
| for config in cfg/yaml/*.yaml; do | |
| mihomo -t -d "$RUNNER_TEMP/mihomo-config" -f "$config" | |
| done | |
| - name: Build and validate Cloudflare mirror bundle | |
| env: | |
| MIRROR_REVISION: ${{ inputs.revision || github.sha }} | |
| run: | | |
| python .github/scripts/jsdelivr_purge.py build-worker-assets \ | |
| --revision "$MIRROR_REVISION" \ | |
| --output workers/repository-mirror/dist | |
| npm ci --prefix workers/repository-mirror | |
| ( | |
| cd workers/repository-mirror | |
| npm exec -- wrangler deploy \ | |
| --dry-run --outdir "$RUNNER_TEMP/wrangler-dry-run" | |
| ) |