From cb4bfb51ff2799e8c0ddff7b8cf2c2213a6b685f Mon Sep 17 00:00:00 2001 From: JohnBraham Date: Wed, 11 Nov 2026 22:42:54 +0000 Subject: [PATCH 1/2] Add Forge 26.1.2 to the release workflow --- .github/scripts/test_release_workflow.py | 25 ++++- .github/workflows/artifact-audit-26.1.yml | 100 ++++++++++++++++++ .github/workflows/deploy-release.yml | 56 +++++----- .github/workflows/release-workflow-checks.yml | 2 +- 4 files changed, 151 insertions(+), 32 deletions(-) create mode 100644 .github/workflows/artifact-audit-26.1.yml diff --git a/.github/scripts/test_release_workflow.py b/.github/scripts/test_release_workflow.py index 08ee8a3..a79d9f2 100644 --- a/.github/scripts/test_release_workflow.py +++ b/.github/scripts/test_release_workflow.py @@ -74,13 +74,14 @@ def validate(self, minecraft, names=None, mutation=None, release_exists=False, w '1.20.1': ('120011', 'master-1.20.1', '47.4.28'), '1.20.6': ('120061', 'master-1.20.6', '50.2.14'), '1.21.1': ('121011', 'master-1.21.1', '52.1.20'), - '1.21.11': ('121111', 'master-1.21.11', '61.2.4')}[minecraft] + '1.21.11': ('121111', 'master-1.21.11', '61.2.4'), + '26.1.2': ('2601021', 'master-26.1.2', '64.1.5')}[minecraft] version = '2.4.2.' + suffix files={name:'C'*64 for name in ['main.jar','sources.jar','javadoc.jar','release.pom','CHANGELOG.txt','SHA256SUMS']} receipt={'schema':1,'source':SHA,'version':version,'files':files,'evidence_sha256':'F'*64,'qualified_locally':True,'manual_accepted':True} if local_receipt is not None:receipt=local_receipt values = dict(minecraft_version=minecraft, forge_version=forge, loader_name='forge', loader_code='1', - java_version='21' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17' if minecraft in ('1.18.2','1.19.4','1.20.1') else '16' if minecraft=='1.17.1' else '8', java_toolchain_version='21.0.7+6' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17.0.20.1+1' if minecraft in ('1.18.2','1.19.4','1.20.1') else '16.0.2+7' if minecraft=='1.17.1' else '8.0.502+7', gradle_java_version='21' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17', mod_id='lootablebodies', + java_version='25' if minecraft=='26.1.2' else '21' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17' if minecraft in ('1.18.2','1.19.4','1.20.1') else '16' if minecraft=='1.17.1' else '8', java_toolchain_version='25.0.3+9' if minecraft=='26.1.2' else '21.0.7+6' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17.0.20.1+1' if minecraft in ('1.18.2','1.19.4','1.20.1') else '16.0.2+7' if minecraft=='1.17.1' else '8.0.502+7', gradle_java_version='25' if minecraft=='26.1.2' else '21' if minecraft in ('1.20.6','1.21.1','1.21.11') else '17', mod_id='lootablebodies', mod_artifact='LootableBodies', mod_group='zone.moddev.mc.lootablebodies', mod_license='LGPL-2.1-only', curseforge_project_id='240968', mod_version=version) if mutation: @@ -90,13 +91,13 @@ def validate(self, minecraft, names=None, mutation=None, release_exists=False, w '1.14.4': MATRIX114 + ['Validate release workflow'], '1.15.2': MATRIX115, '1.16.5': MATRIX116}.get(minecraft, []) if names is None else names if minecraft=='1.17.1' and names is None:checks=CORE117+MATRIX117 - if minecraft in ('1.18.2','1.19.4','1.20.1','1.20.6','1.21.1','1.21.11') and names is None:checks=CORE118 + if minecraft in ('1.18.2','1.19.4','1.20.1','1.20.6','1.21.1','1.21.11','26.1.2') and names is None:checks=CORE118 def command(args, **options): if args[0] == 'git': return SHA + '\n' if any('/actions/workflows/native'+code+'.yml/' in args[-1] for code in ['117','118','119','120']): - code={'1.17.1':'117','1.18.2':'118','1.19.4':'119','1.20.1':'120','1.20.6':'120','1.21.1':'120','1.21.11':'120'}[minecraft] + code={'1.17.1':'117','1.18.2':'118','1.19.4':'119','1.20.1':'120','1.20.6':'120','1.21.1':'120','1.21.11':'120','26.1.2':'120'}[minecraft] row=dict(id=int(code),head_sha=SHA,head_branch=branch,event='push',path='.github/workflows/native'+code+'.yml',conclusion='success') if qualification:row.update(qualification) return json.dumps({'workflow_runs':[row]}) @@ -104,7 +105,7 @@ def command(args, **options): audit = {'id': 1, 'display_title': 'Audit ' + minecraft + ' artifacts from ' + SHA, 'conclusion': 'success' if audit_success else 'failure', 'event': 'workflow_run', 'head_sha': 'c' * 40, 'head_branch': 'master-1.12', - 'path': '.github/workflows/artifact-audit-1.21.yml'} + 'path': '.github/workflows/artifact-audit-26.1.yml' if minecraft=='26.1.2' else '.github/workflows/artifact-audit-1.21.yml'} if audit_run is not None: audit.update(audit_run) return json.dumps({'workflow_runs': [audit]}) @@ -209,6 +210,20 @@ def test_12111_requires_the_exact_archive_and_dispatcher(self): self.validate('1.21.11', **options) self.assertNotEqual(0, self.select('2.4.15.261021')[0]) + def test_2612_uses_java25_exact_archives_and_current_dispatcher(self): + self.assertEqual((0, {'minecraft_version':'26.1.2','source_branch':'master-26.1.2'}), self.select('2.4.15.2601021')) + self.validate('26.1.2', audit_run={'event':'workflow_dispatch'}) + for options in ({'mutation':{'java_version':'21'}}, {'mutation':{'java_toolchain_version':'25.0.2+10'}}, + {'audit_success':False}, {'qualification':{'head_branch':'master-1.21.11'}}, + {'local_receipt':{'manual_accepted':False}}, {'audit_run':{'head_sha':'d'*40}}, + {'audit_run':{'path':'.github/workflows/artifact-audit-1.21.yml'}}): + with self.subTest(options=options), self.assertRaises(SystemExit):self.validate('26.1.2', **options) + workflow=WORKFLOW.read_text() + self.assertIn("needs.preflight.outputs.minecraft_version == '26.1.2' && 'Java 25'",workflow) + for line in workflow.splitlines(): + if 'if: needs.preflight.outputs.minecraft_version !=' in line: + self.assertIn("!= '26.1.2'",line) + def test_routes_all_supported_versions(self): for suffix, minecraft, branch in [('110021', '1.10.2', '1.10.2'), ('111021', '1.11.2', '1.11.2-dev'), ('112021', '1.12.2', 'master-1.12'), ('113021', '1.13.2', 'master-1.13.2'), ('114041', '1.14.4', 'master-1.14.4')]: with self.subTest(minecraft=minecraft): diff --git a/.github/workflows/artifact-audit-26.1.yml b/.github/workflows/artifact-audit-26.1.yml new file mode 100644 index 0000000..4be2b91 --- /dev/null +++ b/.github/workflows/artifact-audit-26.1.yml @@ -0,0 +1,100 @@ +name: Audit LootableBodies 26.1 artifacts +run-name: Audit 26.1.2 artifacts from ${{ github.event.workflow_run.head_sha || inputs.source_sha }} +on: + workflow_run: + workflows: [LootableBodies 1.20 CI, LootableBodies 26.1.2 CI] + types: [completed] + workflow_dispatch: + inputs: + minecraft_version: + description: Minecraft version of the merged archive build + type: choice + default: '26.1.2' + options: ['26.1.2'] + source_run: + description: Successful archive build run ID + required: true + type: string + source_sha: + description: Exact merged source SHA + required: true + type: string +permissions: + contents: read + actions: read +jobs: + audit: + if: >- + github.repository == 'MinecraftModDevelopmentMods/LootableBodies' && + github.ref == 'refs/heads/master-1.12' && + (github.event_name == 'workflow_dispatch' || + (github.event.workflow_run.conclusion == 'success' && github.event.workflow_run.event == 'push' && + (github.event.workflow_run.head_branch == 'master-26.1.2' && github.event.workflow_run.name == 'LootableBodies 26.1.2 CI'))) + runs-on: ubuntu-latest + timeout-minutes: 30 + steps: + - name: Verify the exact merged archive build + id: source + env: + GH_TOKEN: ${{ github.token }} + TARGET_VERSION: ${{ inputs.minecraft_version || '26.1.2' }} + SOURCE_RUN: ${{ github.event.workflow_run.id || inputs.source_run }} + SOURCE_SHA: ${{ github.event.workflow_run.head_sha || inputs.source_sha }} + run: | + python3 - <<'PY' + import json, os, re, subprocess + + repo = 'MinecraftModDevelopmentMods/LootableBodies' + run_id = os.environ['SOURCE_RUN'] + source = os.environ['SOURCE_SHA'] + if not re.fullmatch(r'[1-9][0-9]*', run_id) or not re.fullmatch(r'[a-f0-9]{40}', source): + raise SystemExit('An exact build run ID and source SHA are required') + + def api(path): + return json.loads(subprocess.check_output(['gh', 'api', f'repos/{repo}/{path}'])) + + run = api(f'actions/runs/{run_id}') + target = os.environ.get('TARGET_VERSION', '26.1.2') + if target not in ('26.1.2',): + raise SystemExit('Unsupported archive audit target') + source_branch = 'master-' + target + branch = api('git/ref/heads/' + source_branch) + if (str(run['id']) != run_id or run['head_repository']['full_name'] != repo or + run['event'] != 'push' or run['head_branch'] != source_branch or run['head_sha'] != source or + run['path'] != '.github/workflows/native120.yml' or run['status'] != 'completed' or + run['conclusion'] != 'success' or branch['object']['sha'] != source): + raise SystemExit('The selected run is not the successful build of the current merged source') + with open(os.environ['GITHUB_OUTPUT'], 'a') as out: + out.write(f'run={run_id}\nsha={source}\nversion={target}\n') + PY + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7 + with: + ref: ${{ steps.source.outputs.sha }} + persist-credentials: false + - uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8 + with: + name: LootableBodies-${{ steps.source.outputs.version }}-${{ steps.source.outputs.sha }} + run-id: ${{ steps.source.outputs.run }} + github-token: ${{ github.token }} + path: audited + - name: Independently verify every locally qualified byte + env: + SOURCE_SHA: ${{ steps.source.outputs.sha }} + run: | + python3 -B tools/native120_build.py --bundle audited + python3 - <<'PY' + import json,os + from pathlib import Path + accepted=json.loads(Path('.github/release120.json').read_text()) + Path('independent-audit.json').write_text(json.dumps({'source':os.environ['SOURCE_SHA'],'files':accepted['files'],'all_six_exact':True,'identical_to_locally_audited_bundle':True},indent=2)+'\n') + PY + # Exact hashes reuse the local classfile/licence/identity/mapping audit. + # This independent receipt is a byte match, not a fresh gameplay run or + # another Gradle/Forge preparation. The build job audits new archives. + - name: Retain independent audit evidence + if: always() + uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7 + with: + name: native120-independent-audit-${{ steps.source.outputs.sha }} + if-no-files-found: error + path: independent-audit.json diff --git a/.github/workflows/deploy-release.yml b/.github/workflows/deploy-release.yml index 509dc98..8f57740 100644 --- a/.github/workflows/deploy-release.yml +++ b/.github/workflows/deploy-release.yml @@ -5,7 +5,7 @@ on: workflow_dispatch: inputs: release_version: - description: Complete version from gradle.properties, ending in 110021, 111021, 112021, 113021, 114041, 115021, 116051, 117011, 118021, 119041, 120011, 120061, 121011 or 121111. + description: Complete version from gradle.properties, ending in 110021, 111021, 112021, 113021, 114041, 115021, 116051, 117011, 118021, 119041, 120011, 120061, 121011, 121111 or 2601021. required: true type: string curseforge_release_level: @@ -20,7 +20,7 @@ on: default: false type: boolean local_qualification: - description: Hash-bound local qualification receipt, required for the 1.17.1, 1.18.2, 1.19.4, 1.20.1, 1.20.6, 1.21.1 and 1.21.11 releases. + description: Hash-bound local qualification receipt, required for the 1.17.1, 1.18.2, 1.19.4, 1.20.1, 1.20.6, 1.21.1, 1.21.11 and 26.1.2 releases. required: false default: '' type: string @@ -54,7 +54,7 @@ jobs: set -euo pipefail [[ "$GITHUB_REPOSITORY" == 'MinecraftModDevelopmentMods/LootableBodies' ]] [[ "$GITHUB_REF" == 'refs/heads/master-1.12' ]] - [[ "$RELEASE_VERSION" =~ ^(0|[1-9][0-9]*)\.(0|[1-9][0-9]*)\.(0|[1-9][0-9]*)\.(110021|111021|112021|113021|114041|115021|116051|117011|118021|119041|120011|120061|121011|121111)$ ]] + [[ "$RELEASE_VERSION" =~ ^(0|[1-9][0-9]*)\.(0|[1-9][0-9]*)\.(0|[1-9][0-9]*)\.(110021|111021|112021|113021|114041|115021|116051|117011|118021|119041|120011|120061|121011|121111|2601021)$ ]] case "$RELEASE_VERSION" in *.110021) minecraft_version=1.10.2; source_branch=1.10.2 ;; *.111021) minecraft_version=1.11.2; source_branch=1.11.2-dev ;; @@ -70,6 +70,7 @@ jobs: *.120061) minecraft_version=1.20.6; source_branch=master-1.20.6 ;; *.121011) minecraft_version=1.21.1; source_branch=master-1.21.1 ;; *.121111) minecraft_version=1.21.11; source_branch=master-1.21.11 ;; + *.2601021) minecraft_version=26.1.2; source_branch=master-26.1.2 ;; *) exit 1 ;; esac echo "minecraft_version=$minecraft_version" >> "$GITHUB_OUTPUT" @@ -108,16 +109,17 @@ jobs: '1.20.1': ('master-1.20.1', '47.4.28', '120011'), '1.20.6': ('master-1.20.6', '50.2.14', '120061'), '1.21.1': ('master-1.21.1', '52.1.20', '121011'), - '1.21.11': ('master-1.21.11', '61.2.4', '121111')} + '1.21.11': ('master-1.21.11', '61.2.4', '121111'), + '26.1.2': ('master-26.1.2', '64.1.5', '2601021')} branch, forge, suffix = targets[minecraft] if os.environ['SOURCE_BRANCH'] != branch: raise SystemExit('The selected branch does not match its Minecraft version') native17 = minecraft == '1.17.1' - archive_only = minecraft in ('1.18.2', '1.19.4', '1.20.1', '1.20.6', '1.21.1', '1.21.11') + archive_only = minecraft in ('1.18.2', '1.19.4', '1.20.1', '1.20.6', '1.21.1', '1.21.11', '26.1.2') locally_qualified = native17 or archive_only expected = {'minecraft_version': minecraft, 'forge_version': forge, - 'loader_name': 'forge', 'loader_code': '1', 'java_version': '21' if minecraft in ('1.20.6', '1.21.1', '1.21.11') else '17' if archive_only else '16' if native17 else '8', - 'java_toolchain_version': '21.0.7+6' if minecraft in ('1.20.6', '1.21.1', '1.21.11') else '17.0.20.1+1' if archive_only else '16.0.2+7' if native17 else '8.0.502+7', 'gradle_java_version': '21' if minecraft in ('1.20.6', '1.21.1', '1.21.11') else '17', + 'loader_name': 'forge', 'loader_code': '1', 'java_version': '25' if minecraft == '26.1.2' else '21' if minecraft in ('1.20.6', '1.21.1', '1.21.11', '26.1.2') else '17' if archive_only else '16' if native17 else '8', + 'java_toolchain_version': '25.0.3+9' if minecraft == '26.1.2' else '21.0.7+6' if minecraft in ('1.20.6', '1.21.1', '1.21.11', '26.1.2') else '17.0.20.1+1' if archive_only else '16.0.2+7' if native17 else '8.0.502+7', 'gradle_java_version': '25' if minecraft == '26.1.2' else '21' if minecraft in ('1.20.6', '1.21.1', '1.21.11', '26.1.2') else '17', 'mod_id': 'lootablebodies', 'mod_artifact': 'LootableBodies', 'mod_group': 'zone.moddev.mc.lootablebodies', 'mod_license': 'LGPL-2.1-only', 'curseforge_project_id': '240968'} @@ -157,7 +159,7 @@ jobs: except (ValueError,TypeError): raise SystemExit('A local qualification receipt is required') keys={'schema','source','version','files','evidence_sha256','qualified_locally','manual_accepted'} - target_code={'1.17.1':'117','1.18.2':'118','1.19.4':'119','1.20.1':'120','1.20.6':'120','1.21.1':'120','1.21.11':'120'}[minecraft] + target_code={'1.17.1':'117','1.18.2':'118','1.19.4':'119','1.20.1':'120','1.20.6':'120','1.21.1':'120','1.21.11':'120','26.1.2':'120'}[minecraft] metadata=json.loads(Path(f'.github/release{target_code}.json').read_text()) accepted=metadata['files'] if archive_only and (metadata.get('local_qualification_complete') is not True or metadata.get('qualification_integrity_status')!='verified'): @@ -181,15 +183,15 @@ jobs: matching = [check for check in checks if check['name'] == name] if not matching or max(matching, key=lambda c: c['id'])['conclusion'] != 'success': raise SystemExit(f'The selected commit has no successful {name} check') - if minecraft in ('1.11.2', '1.12.2', '1.13.2', '1.14.4', '1.15.2', '1.16.5', '1.17.1', '1.18.2', '1.19.4', '1.20.1', '1.20.6', '1.21.1', '1.21.11'): + if minecraft in ('1.11.2', '1.12.2', '1.13.2', '1.14.4', '1.15.2', '1.16.5', '1.17.1', '1.18.2', '1.19.4', '1.20.1', '1.20.6', '1.21.1', '1.21.11', '26.1.2'): target = minecraft.rsplit('.', 1)[0] - event_query = '' if minecraft in ('1.21.1', '1.21.11') else '&event=workflow_run' + event_query = '' if minecraft in ('1.21.1', '1.21.11', '26.1.2') else '&event=workflow_run' audits = json.loads(subprocess.check_output(['gh', 'api', f'repos/{repo}/actions/workflows/artifact-audit-{target}.yml/runs?per_page=100{event_query}'], text=True))['workflow_runs'] matching = [run for run in audits if run['display_title'] == f'Audit {minecraft} artifacts from {sha}' - and (minecraft not in ('1.21.1', '1.21.11') or (run['event'] in ('workflow_run', 'workflow_dispatch') + and (minecraft not in ('1.21.1', '1.21.11', '26.1.2') or (run['event'] in ('workflow_run', 'workflow_dispatch') and run['head_branch'] == 'master-1.12' and run['head_sha'] == os.environ['GITHUB_SHA'] - and run['path'] == '.github/workflows/artifact-audit-1.21.yml'))] + and run['path'] == ('.github/workflows/artifact-audit-26.1.yml' if minecraft == '26.1.2' else '.github/workflows/artifact-audit-1.21.yml')))] if not matching or max(matching, key=lambda run: run['id'])['conclusion'] != 'success': raise SystemExit('The selected commit has no successful independent artifact audit') release = subprocess.run(['gh', 'api', f'repos/{repo}/releases/tags/{version}'], capture_output=True, text=True) @@ -219,25 +221,25 @@ jobs: with: ref: ${{ needs.preflight.outputs.release_sha }} - name: Install Mavenizer Java - if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' uses: actions/setup-java@b6effb05e454b25005698d916606bdc6ffcbf961 # v5 with: distribution: temurin java-version: '25.0.3+9.0.LTS' - name: Install production Java - if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' uses: actions/setup-java@b6effb05e454b25005698d916606bdc6ffcbf961 # v5 with: distribution: temurin - java-version: ${{ needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.17.1' && '16.0.2+7' || '8.0.502+7' }} + java-version: ${{ needs.preflight.outputs.minecraft_version == '26.1.2' && '25.0.3+9.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.17.1' && '16.0.2+7' || '8.0.502+7' }} - name: Install Gradle Java - if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' uses: actions/setup-java@b6effb05e454b25005698d916606bdc6ffcbf961 # v5 with: distribution: temurin - java-version: ${{ needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || '17.0.1+12' }} + java-version: ${{ needs.preflight.outputs.minecraft_version == '26.1.2' && '25.0.3+9.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || '17.0.1+12' }} - name: Pin the production toolchain - if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' run: | if [[ '${{ needs.preflight.outputs.minecraft_version }}' == '1.18.2' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.19.4' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.20.1' ]]; then echo "LOOTABLEBODIES_JAVA17_HOME=$JAVA_HOME_17_X64" >> "$GITHUB_ENV" @@ -248,7 +250,7 @@ jobs: fi echo "LOOTABLEBODIES_MAVENIZER_JAVA_HOME=$JAVA_HOME_25_X64" >> "$GITHUB_ENV" - name: Set up Gradle - if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' uses: gradle/actions/setup-gradle@9c971963bec38e04b3d30dcc455b5382be2fdbfb # v6 - name: Download the qualified native117 six-file bundle if: needs.preflight.outputs.minecraft_version == '1.17.1' @@ -293,7 +295,7 @@ jobs: if: needs.preflight.outputs.minecraft_version == '1.19.4' run: python3 -B tools/native119_build.py --bundle build/release/bundle - name: Download the qualified native120 six-file bundle - if: needs.preflight.outputs.minecraft_version == '1.20.1' || needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11' + if: needs.preflight.outputs.minecraft_version == '1.20.1' || needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11' || needs.preflight.outputs.minecraft_version == '26.1.2' uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8 with: name: LootableBodies-${{ needs.preflight.outputs.minecraft_version }}-${{ needs.preflight.outputs.release_sha }} @@ -301,10 +303,10 @@ jobs: github-token: ${{ github.token }} path: build/release/bundle - name: Verify all six native120 bytes before publication - if: needs.preflight.outputs.minecraft_version == '1.20.1' || needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11' + if: needs.preflight.outputs.minecraft_version == '1.20.1' || needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11' || needs.preflight.outputs.minecraft_version == '26.1.2' run: python3 -B tools/native120_build.py --bundle build/release/bundle - name: Build, test and audit the release - if: needs.preflight.outputs.minecraft_version != '1.17.1' && needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' + if: needs.preflight.outputs.minecraft_version != '1.17.1' && needs.preflight.outputs.minecraft_version != '1.18.2' && needs.preflight.outputs.minecraft_version != '1.19.4' && needs.preflight.outputs.minecraft_version != '1.20.1' && needs.preflight.outputs.minecraft_version != '1.20.6' && needs.preflight.outputs.minecraft_version != '1.21.1' && needs.preflight.outputs.minecraft_version != '1.21.11' && needs.preflight.outputs.minecraft_version != '26.1.2' run: | chmod +x ./gradlew ./gradlew clean build javadoc verifyEclipseProductionClasspath prepareReleaseBundle \ @@ -409,15 +411,17 @@ jobs: uses: actions/setup-java@b6effb05e454b25005698d916606bdc6ffcbf961 # v5 with: distribution: temurin - java-version: ${{ (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && '21.0.7+6.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.17.1' && '16.0.2+7' || '8.0.502+7' }} + java-version: ${{ needs.preflight.outputs.minecraft_version == '26.1.2' && '25.0.3+9.0.LTS' || (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && '21.0.7+6.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.17.1' && '16.0.2+7' || '8.0.502+7' }} - name: Install Gradle Java uses: actions/setup-java@b6effb05e454b25005698d916606bdc6ffcbf961 # v5 with: distribution: temurin - java-version: ${{ (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && '21.0.7+6.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || '17.0.1+12' }} + java-version: ${{ needs.preflight.outputs.minecraft_version == '26.1.2' && '25.0.3+9.0.LTS' || (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && '21.0.7+6.0.LTS' || needs.preflight.outputs.minecraft_version == '1.18.2' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.19.4' && '17.0.20+101' || needs.preflight.outputs.minecraft_version == '1.20.1' && '17.0.20+101' || '17.0.1+12' }} - name: Pin the production toolchain run: | - if [[ '${{ needs.preflight.outputs.minecraft_version }}' == '1.20.6' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.21.1' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.21.11' ]]; then + if [[ '${{ needs.preflight.outputs.minecraft_version }}' == '26.1.2' ]]; then + echo "LOOTABLEBODIES_JAVA25_HOME=$JAVA_HOME_25_X64" >> "$GITHUB_ENV" + elif [[ '${{ needs.preflight.outputs.minecraft_version }}' == '1.20.6' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.21.1' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.21.11' ]]; then echo "LOOTABLEBODIES_JAVA21_HOME=$JAVA_HOME_21_X64" >> "$GITHUB_ENV" elif [[ '${{ needs.preflight.outputs.minecraft_version }}' == '1.18.2' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.19.4' || '${{ needs.preflight.outputs.minecraft_version }}' == '1.20.1' ]]; then echo "LOOTABLEBODIES_JAVA17_HOME=$JAVA_HOME_17_X64" >> "$GITHUB_ENV" @@ -477,7 +481,7 @@ jobs: game-versions: ${{ needs.preflight.outputs.minecraft_version }} game-version-filter: none environment: client | server - java: ${{ (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && 'Java 21' || needs.preflight.outputs.minecraft_version == '1.19.4' && 'Java 17' || needs.preflight.outputs.minecraft_version == '1.20.1' && 'Java 17' || needs.preflight.outputs.minecraft_version == '1.17.1' && 'Java 16' || 'Java 8' }} + java: ${{ needs.preflight.outputs.minecraft_version == '26.1.2' && 'Java 25' || (needs.preflight.outputs.minecraft_version == '1.20.6' || needs.preflight.outputs.minecraft_version == '1.21.1' || needs.preflight.outputs.minecraft_version == '1.21.11') && 'Java 21' || needs.preflight.outputs.minecraft_version == '1.19.4' && 'Java 17' || needs.preflight.outputs.minecraft_version == '1.20.1' && 'Java 17' || needs.preflight.outputs.minecraft_version == '1.17.1' && 'Java 16' || 'Java 8' }} fail-mode: fail files: | ${{ runner.temp }}/release-input/LootableBodies-${{ needs.preflight.outputs.release_version }}.jar diff --git a/.github/workflows/release-workflow-checks.yml b/.github/workflows/release-workflow-checks.yml index 7339bbd..683890f 100644 --- a/.github/workflows/release-workflow-checks.yml +++ b/.github/workflows/release-workflow-checks.yml @@ -24,7 +24,7 @@ jobs: - name: Check release workflow syntax run: >- "$RUNNER_TEMP/actionlint/actionlint" -shellcheck= -pyflakes= - .github/workflows/build.yml .github/workflows/migration-matrix.yml .github/workflows/deploy-release.yml .github/workflows/release-workflow-checks.yml .github/workflows/artifact-audit-1.11.yml .github/workflows/artifact-audit-1.12.yml .github/workflows/artifact-audit-1.13.yml .github/workflows/artifact-audit-1.14.yml .github/workflows/artifact-audit-1.15.yml .github/workflows/artifact-audit-1.16.yml .github/workflows/artifact-audit-1.17.yml .github/workflows/artifact-audit-1.18.yml .github/workflows/artifact-audit-1.19.yml .github/workflows/artifact-audit-1.20.yml .github/workflows/artifact-audit-1.21.yml + .github/workflows/build.yml .github/workflows/migration-matrix.yml .github/workflows/deploy-release.yml .github/workflows/release-workflow-checks.yml .github/workflows/artifact-audit-1.11.yml .github/workflows/artifact-audit-1.12.yml .github/workflows/artifact-audit-1.13.yml .github/workflows/artifact-audit-1.14.yml .github/workflows/artifact-audit-1.15.yml .github/workflows/artifact-audit-1.16.yml .github/workflows/artifact-audit-1.17.yml .github/workflows/artifact-audit-1.18.yml .github/workflows/artifact-audit-1.19.yml .github/workflows/artifact-audit-1.20.yml .github/workflows/artifact-audit-1.21.yml .github/workflows/artifact-audit-26.1.yml - name: Test version selection and publication checks run: python3 .github/scripts/test_release_workflow.py -v From 2cdc434af6fc22ed1dc47c8c9fb63e6ebc8e7c65 Mon Sep 17 00:00:00 2001 From: JohnBraham Date: Wed, 11 Nov 2026 22:44:45 +0000 Subject: [PATCH 2/2] Keep release audit changes out of legacy gameplay checks --- .github/scripts/release_scope.py | 2 +- .github/scripts/test_release_scope.py | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/.github/scripts/release_scope.py b/.github/scripts/release_scope.py index 7e2e312..a87be9e 100644 --- a/.github/scripts/release_scope.py +++ b/.github/scripts/release_scope.py @@ -23,7 +23,7 @@ def runtime_required(paths,manual=False,workflow_pairs=None): '.github/scripts/test_release_workflow.py','.github/scripts/release_scope.py','.github/scripts/test_release_scope.py'} pairs=workflow_pairs or {} for name in paths: - if name in allowed or re.fullmatch(r'\.github/workflows/artifact-audit-1\.\d+\.yml',name):continue + if name in allowed or re.fullmatch(r'\.github/workflows/artifact-audit-(?:1\.\d+|26\.1)\.yml',name):continue if name not in ('.github/workflows/build.yml','.github/workflows/migration-matrix.yml') or name not in pairs: return True before,after=pairs[name] diff --git a/.github/scripts/test_release_scope.py b/.github/scripts/test_release_scope.py index 8551cbb..6bd66f4 100644 --- a/.github/scripts/test_release_scope.py +++ b/.github/scripts/test_release_scope.py @@ -7,6 +7,10 @@ def test_only_release_routes_use_the_small_checks(self): self.assertFalse(runtime_required(['.github/workflows/deploy-release.yml','.github/scripts/test_release_workflow.py'])) def test_new_target_audit_uses_the_small_checks(self): self.assertFalse(runtime_required(['.github/workflows/artifact-audit-1.16.yml'])) + def test_native26_artifact_audit_changes_do_not_launch_old_games(self): + self.assertFalse(runtime_required(['.github/workflows/artifact-audit-26.1.yml'])) + for path in ['.github/workflows/artifact-audit-26.1.yml.bak', '.github/workflows/unreviewed-26.1.yml']: + with self.subTest(path=path):self.assertTrue(runtime_required([path])) def test_source_build_and_unknown_files_require_runtime(self): for name in ['src/main/java/Corpse.java','src/test/java/CorpseTest.java','tools/fixture_login.py','gradle/release.gradle','gradle.properties','build.gradle','README.md','settings.gradle','.github/workflows/codeql-analysis.yml','other.txt']: with self.subTest(name=name):self.assertTrue(runtime_required([name]))