Files
OpenMaidEngine/tools/test_publish_gitea_release.py
gamer147 f0f5f12ffc
All checks were successful
Core validation / Linux core gate (push) Successful in 1m12s
Linux release build / Linux x64 artifact (push) Successful in 1m36s
Linux release build / Publish tagged Gitea release (push) Has been skipped
Promote verified tag artifacts to Gitea releases
2026-08-03 19:28:51 -04:00

137 lines
5.5 KiB
Python
Executable File

#!/usr/bin/env python3
from __future__ import annotations
import hashlib
import json
import tempfile
import unittest
from pathlib import Path
from typing import Any
import publish_gitea_release
TARGET = "0123456789abcdef0123456789abcdef01234567"
TAG = "v0.1.0"
class FakeApi:
def __init__(self, release: dict[str, Any] | None = None) -> None:
self.release = release
self.assets: list[dict[str, Any]] = []
self.created_payload: dict[str, Any] | None = None
def get_release(self, tag: str) -> dict[str, Any] | None:
self.requested_tag = tag
return self.release
def create_release(self, payload: dict[str, Any]) -> dict[str, Any]:
self.created_payload = payload
self.release = matching_release()
return self.release
def list_assets(self, release_id: int) -> list[dict[str, Any]]:
self.requested_release_id = release_id
return list(self.assets)
def upload(self, release_id: int, asset: Path) -> dict[str, Any]:
uploaded = {"name": asset.name, "size": asset.stat().st_size}
self.assets.append(uploaded)
return uploaded
def matching_release() -> dict[str, Any]:
return {
"id": 17,
"tag_name": TAG,
"target_commitish": TARGET,
"name": f"OpenMaidEngine Himegari {TAG}",
"draft": False,
"prerelease": False,
"html_url": "https://gitea.invalid/releases/tag/v0.1.0",
}
def create_assets(root: Path) -> list[Path]:
archive = root / "OpenMaidEngine-Himegari-linux-x64.tar.gz"
archive.write_bytes(b"synthetic archive")
checksum = root / "OpenMaidEngine-Himegari-linux-x64.tar.gz.sha256"
checksum.write_text(
f"{hashlib.sha256(archive.read_bytes()).hexdigest()} {archive.name}\n",
encoding="ascii",
)
build_info = root / "BUILD-INFO.json"
build_info.write_text(json.dumps({
"schema_version": 1,
"source_commit": TARGET,
"source_dirty": False,
"target": "linux-x64",
}), encoding="utf-8")
ledger = root / "SHA256SUMS"
ledger.write_text(f"{'0' * 64} Himegari.x86_64\n", encoding="ascii")
smoke = root / "package-smoke.log"
smoke.write_text("PACKAGE SMOKE OK: opcodes=548 ffmpeg-abi=3\n", encoding="utf-8")
return [archive, checksum, build_info, ledger, smoke]
class PublishGiteaReleaseTests(unittest.TestCase):
def test_creates_release_and_uploads_verified_asset_set(self) -> None:
with tempfile.TemporaryDirectory() as temporary:
assets = create_assets(Path(temporary))
api = FakeApi()
result = publish_gitea_release.promote_release(api, api.upload, TAG, TARGET, assets)
self.assertEqual(17, result["id"])
self.assertEqual(TAG, api.created_payload["tag_name"])
self.assertEqual(TARGET, api.created_payload["target_commitish"])
self.assertEqual({asset.name for asset in assets}, {asset["name"] for asset in api.assets})
def test_retry_keeps_matching_assets_and_uploads_only_missing(self) -> None:
with tempfile.TemporaryDirectory() as temporary:
assets = create_assets(Path(temporary))
api = FakeApi(matching_release())
api.assets.append({"name": assets[0].name, "size": assets[0].stat().st_size})
uploaded: list[str] = []
def upload(release_id: int, asset: Path) -> dict[str, Any]:
uploaded.append(asset.name)
return api.upload(release_id, asset)
publish_gitea_release.promote_release(api, upload, TAG, TARGET, assets)
self.assertNotIn(assets[0].name, uploaded)
self.assertEqual(len(assets) - 1, len(uploaded))
self.assertIsNone(api.created_payload)
def test_refuses_mismatched_release_and_asset_collision(self) -> None:
with tempfile.TemporaryDirectory() as temporary:
assets = create_assets(Path(temporary))
wrong_release = matching_release()
wrong_release["target_commitish"] = "f" * 40
api = FakeApi(wrong_release)
with self.assertRaisesRegex(ValueError, "does not match"):
publish_gitea_release.promote_release(api, api.upload, TAG, TARGET, assets)
api = FakeApi(matching_release())
api.assets.append({"name": assets[0].name, "size": 999})
with self.assertRaisesRegex(ValueError, "will not be overwritten"):
publish_gitea_release.promote_release(api, api.upload, TAG, TARGET, assets)
def test_refuses_mismatched_build_evidence(self) -> None:
with tempfile.TemporaryDirectory() as temporary:
assets = create_assets(Path(temporary))
by_name = {asset.name: asset for asset in assets}
by_name["OpenMaidEngine-Himegari-linux-x64.tar.gz"].write_bytes(b"changed")
with self.assertRaisesRegex(ValueError, "external SHA-256"):
publish_gitea_release.validate_inputs(TAG, TARGET, assets)
assets = create_assets(Path(temporary))
by_name = {asset.name: asset for asset in assets}
build_info = json.loads(by_name["BUILD-INFO.json"].read_text(encoding="utf-8"))
build_info["source_commit"] = "f" * 40
by_name["BUILD-INFO.json"].write_text(json.dumps(build_info), encoding="utf-8")
with self.assertRaisesRegex(ValueError, "does not match"):
publish_gitea_release.validate_inputs(TAG, TARGET, assets)
if __name__ == "__main__":
unittest.main()