Something went wrong. Try again.
HEXWORK - A Lantern in the Deep: 3D ASCII terminal roguelike RPG in Rust.
Entirely designed and built by Muse Spark 1.3 to evaluate if I like the model.
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381#!/usr/bin/env python3"""Read-only Rust 1.75 contracts. Python 3.11+, PyYAML==6.0.2 for `ci`.
Partitions JSON contains a version and commands (argv lists); it is an auditplan, not an execution log. Compiler/feature/platform gates remain separate."""from __future__ import annotations
import argparsefrom collections import Counterimport hashlibimport jsonfrom pathlib import Pathimport reimport shleximport sysimport tomllib
class ContractError(ValueError): """A named, fail-closed acceptance contract was violated."""
def require(condition, message): if not condition: raise ContractError(message)
def read_json(path): return json.loads(Path(path).read_text())
def read_toml(path): return tomllib.loads(Path(path).read_text())
def minimum(value): return value in ('1.75', '1.75.0')
def verify_msrv_metadata(root, metadata): root = Path(root).resolve() manifest = read_toml(root / 'Cargo.toml') workspace = manifest['workspace'] require(minimum(workspace['package'].get('rust-version')), 'root minimum must be 1.75') dep = workspace['dependencies']['bincode'] require((dep if isinstance(dep, str) else dep.get('version')) == '=2.0.1', 'workspace bincode must be exactly =2.0.1') packages = {p['id']: p for p in metadata['packages']} members = metadata['workspace_members'] require(members and len(set(members)) == len(members), 'invalid workspace members') require(Path(metadata['workspace_root']).resolve() == root, 'metadata workspace root mismatch') reports = [] for member in members: package = packages[member] path = Path(package['manifest_path']).resolve() require(path.is_relative_to(root), 'member outside root') declaration = read_toml(path)['package'].get('rust-version') require(isinstance(declaration, dict) and set(declaration) == {'workspace'} and declaration['workspace'] is True, f'{package["name"]}: missing explicit minimum inheritance') require(minimum(package.get('rust_version')), f'{package["name"]}: metadata minimum mismatch') reports.append(f'{package["name"]}: inherits Rust 1.75') # Check declared members too, so a truncated JSON workspace cannot hide a member. declared = set() excluded = workspace.get('exclude', []) for pattern in workspace['members']: for directory in root.glob(pattern): if directory.is_dir() and (directory / 'Cargo.toml').exists(): if not any(directory.match(p) for p in excluded): declared.add((directory / 'Cargo.toml').resolve()) require(declared == {Path(packages[m]['manifest_path']).resolve() for m in members}, 'declared and metadata workspace members differ') resolve = metadata.get('resolve') require(isinstance(resolve, dict), 'full resolved metadata required (not --no-deps)') nodes = {n['id']: n for n in resolve['nodes']} reachable = set() pending = list(members) while pending: node_id = pending.pop() if node_id in reachable: continue require(node_id in nodes, 'missing resolve node') reachable.add(node_id) pending.extend(nodes[node_id].get('dependencies', [])) lock = read_toml(root / 'Cargo.lock') require(lock.get('version') == 3, 'Cargo.lock must be format 3') for name in ('bincode', 'bincode_derive'): relative = f'vendor/{name}-2.0.1' patch = manifest.get('patch', {}).get('crates-io', {}).get(name, {}) require(patch == {'path': relative}, f'{name}: exact relative vendor patch required') require(relative in excluded, f'{name}: explicit workspace exclusion required') candidates = [p for p in packages.values() if p['name'] == name] require(len(candidates) == 1, f'{name}: missing or ambiguous resolved package') package = candidates[0] require(package['version'] == '2.0.1' and package.get('source') is None, f'{name}: registry/version substitute') expected = root / relative / 'Cargo.toml' require(not (root / relative).is_symlink() and expected.resolve().is_relative_to(root / 'vendor'), f'{name}: vendor path escapes repository') require(Path(package['manifest_path']).resolve() == expected.resolve(), f'{name}: wrong resolved path') require(package['id'] not in members and package['id'] in reachable, f'{name}: inactive patch or vendor workspace member') entries = [p for p in lock['package'] if p['name'] == name] require(len(entries) == 1 and entries[0]['version'] == '2.0.1' and 'source' not in entries[0] and 'checksum' not in entries[0], f'{name}: lock does not activate local package') reports.append(f'{name}: resolved local 2.0.1 patch (not a compilation claim)') return reports
def verify_lock_v3_conversion(before, after): old, new = Path(before).read_bytes(), Path(after).read_bytes() a, b = tomllib.loads(old.decode()), tomllib.loads(new.decode()) require(a.get('version') == 4 and b.get('version') == 3, 'expected top-level 4 to 3 conversion') a['version'] = 3 require(a == b, 'lock package/source/checksum/dependency metadata changed') match = re.search(rb'(?m)^version[ \t]*=[ \t]*(4)(?:[ \t]*(?:#[^\r\n]*)?\r?$)', old) require(match is not None and old[:match.start(1)] + b'3' + old[match.end(1):] == new, 'lock conversion must change only the format integer byte') for package in b.get('package', []): source = package.get('source', '') require(not source or source == 'registry+https://github.com/rust-lang/crates.io-index', 'nonstandard/git source requires format-semantics review')
def verify_lock_stability(before, after): require(Path(before).read_bytes() == Path(after).read_bytes(), 'locked operation rewrote Cargo.lock')
# Frozen from e4cfd4c: crates/hexwork-cli/tests/phase12/v4_compat.rs.FIXTURES = { 'run-v4-7834d52-classic.hexrun': '467e582827b6f09a05aabaee60ba5bd4e85c373e5345a6a7aeee56dbf5c340c3', 'replay-v4-7834d52-classic.hexdemo': 'af28de1eaebcd9b66ec0bb72596f8bca22e2c5726219066e9e8b8d43ba997115', 'run-v4-7834d52-story.hexrun': '1dc214719fecca479a4e868d0da1ea04b974a297dec1370505d1126263fd5af5',}
def verify_fixture_integrity(root): for name, expected in FIXTURES.items(): path = Path(root) / 'crates/hexwork-save/testfixtures' / name require(hashlib.sha256(path.read_bytes()).hexdigest() == expected, f'fixture SHA256 mismatch: {name}')
LIB_KINDS = {'lib', 'rlib', 'dylib', 'cdylib', 'staticlib', 'proc-macro'}
def target_inventory(metadata): packages = {p['id']: p for p in metadata['packages']} inventory = {} cli_ids = [] for member in metadata['workspace_members']: package = packages[member] if package['name'] == 'hexwork-cli': cli_ids.append(member) for target in package['targets']: kinds = tuple(sorted(target['kind'])) key = (member, target['name'], kinds) require(key not in inventory, 'duplicate metadata target') if set(kinds) <= LIB_KINDS and kinds: selector = ['--lib'] elif len(kinds) == 1 and kinds[0] in ('bin', 'test', 'bench', 'example'): selector = ['--' + kinds[0], target['name']] elif kinds == ('custom-build',): selector = None # Cargo builds this implicitly with package targets. else: raise ContractError(f'unsupported metadata target kind: {kinds}') inventory[key] = (package['name'], selector) require(len(cli_ids) == 1, 'exactly one hexwork-cli workspace member required') return inventory
NON_CLI = ['cargo', 'test', '--locked', '--workspace', '--exclude', 'hexwork-cli', '--all-targets']CLI_BASE = ['cargo', 'test', '--locked', '-p', 'hexwork-cli']CI_ALL = ['cargo', 'test', '--locked', '--workspace', '--all-targets']
def make_partitions(metadata): inventory = target_inventory(metadata) commands = [NON_CLI.copy()] for _, (name, selector) in sorted(inventory.items()): if name == 'hexwork-cli' and selector is not None: commands.append(CLI_BASE + selector) plan = {'version': 1, 'commands': commands} verify_target_partition_coverage(metadata, plan) return plan
def verify_target_partition_coverage(metadata, plan): inventory = target_inventory(metadata) require(set(plan) == {'version', 'commands'} and plan['version'] == 1, 'invalid partition schema') commands = plan['commands'] require(isinstance(commands, list) and commands, 'empty partition plan') coverage = Counter() explicit = {key for key, (_, selector) in inventory.items() if selector is not None} for argv in commands: require(isinstance(argv, list) and all(isinstance(x, str) for x in argv), 'commands must be argv arrays') if argv == CI_ALL: selected = explicit elif argv == NON_CLI: selected = {key for key in explicit if inventory[key][0] != 'hexwork-cli'} else: selected = {key for key in explicit if inventory[key][0] == 'hexwork-cli' and argv == CLI_BASE + inventory[key][1]} require(len(selected) == 1, f'unsupported or ambiguous selector: {argv}') coverage.update(selected) require(set(coverage) == explicit and all(count == 1 for count in coverage.values()), 'missing or duplicate target coverage') require(len({tuple(c) for c in commands}) == len(commands), 'duplicate partition command') return [f'{key[0]}::{key[1]} [{",".join(key[2])}]' for key in sorted(explicit)]
COMMON_RUNS = [ 'python3 -m pip install PyYAML==6.0.2', 'python3 vendor/verify.py --root vendor', 'python3 scripts/verify_msrv.py metadata --root . --metadata target/msrv-metadata.json', 'python3 scripts/verify_msrv.py fixtures --root .', 'python3 scripts/verify_msrv.py ci --workflow .github/workflows/ci.yml', "python3 -m unittest discover -s scripts/tests -p 'test_verify_msrv.py'", 'python3 vendor/verify.py --root vendor --self-test',]QUALITY = { 'build': ['cargo fmt --all -- --check', 'cargo clippy --locked --workspace --all-targets -- -D warnings', 'cargo deny check', 'cargo test --locked --workspace --all-targets', 'cargo bench --locked --workspace -- --test', 'cargo build --locked --workspace --release'], 'msrv': ['cargo check --locked --workspace --all-targets', 'cargo test --locked --workspace --all-targets', 'cargo build --locked --workspace --release'],}CAPTURE = 'cargo metadata --locked --format-version 1 > target/msrv-metadata.json'
def verify_ci_msrv_contract(workflow): import yaml require(yaml.__version__ == '6.0.2', 'verification requires PyYAML==6.0.2') try: data = yaml.safe_load(Path(workflow).read_text()) except yaml.YAMLError as error: raise ContractError(f'invalid workflow YAML: {error}') from error require(isinstance(data, dict), 'workflow must be a mapping') # Reject bypasses anywhere, including hidden shell/env settings and extra jobs. text = json.dumps(data) for token in ('--ignore-rust-version', 'RUSTFLAGS', 'CARGO_ENCODED_RUSTFLAGS', 'continue-on-error'): require(token not in text, f'forbidden workflow bypass: {token}') require('env' not in data and 'defaults' not in data, 'global env/shell overrides are not permitted') for job_name, toolchain in [('build', 'stable'), ('msrv', '1.75.0')]: job = data.get('jobs', {}).get(job_name) require(isinstance(job, dict), f'missing {job_name} job') require('if' not in job and 'defaults' not in job, f'{job_name}: conditional/shell override') require(job.get('timeout-minutes') == 180, f'{job_name}: expected 180-minute budget') require(job.get('runs-on') == '${{ matrix.os }}', f'{job_name}: wrong runner') strategy = job.get('strategy', {}) require(strategy.get('matrix') == {'os': ['ubuntu-latest', 'macos-latest']}, f'{job_name}: wrong OS matrix') require(job.get('env') == {'RUSTUP_TOOLCHAIN': toolchain, 'CARGO_TARGET_DIR': f'target/ci-${{{{ matrix.os }}}}-{toolchain}'}, f'{job_name}: wrong job toolchain/target env') steps = job.get('steps', []) require(isinstance(steps, list), 'steps must be a list') runs = [] checkout_actions = [] rust_actions = [] python_actions = [] deny_installed = False for index, step in enumerate(steps): require(isinstance(step, dict), 'step must be a mapping') require(not any(k in step for k in ('if', 'env', 'shell', 'working-directory', 'timeout-minutes')), f'{job_name}: step can bypass frozen execution') uses = step.get('uses') require(('uses' in step) ^ ('run' in step), f'{job_name}: each step must be exactly one action or run command') if 'uses' in step: require('run' not in step, f'{job_name}: action step cannot also run a command') if uses == 'actions/checkout@v4': require(set(step) == {'uses'}, f'{job_name}: checkout must use default action settings') checkout_actions.append(index) elif isinstance(uses, str) and uses.startswith('dtolnay/rust-toolchain@'): require(set(step) <= {'uses', 'with'}, f'{job_name}: invalid rust-toolchain action shape') with_args = step.get('with', {}) require(isinstance(with_args, dict) and set(with_args) <= {'toolchain', 'components'}, f'{job_name}: invalid rust-toolchain action options') rust_actions.append(step) elif uses == 'actions/setup-python@v5': require(set(step) == {'uses', 'with'} and isinstance(step.get('with'), dict) and set(step['with']) == {'python-version'}, f'{job_name}: invalid setup-python action shape') python_actions.append(step) elif uses == 'taiki-e/install-action@v2': require(set(step) == {'uses', 'with'} and step.get('with') == {'tool': 'cargo-deny'}, f'{job_name}: invalid cargo-deny action shape') deny_installed = True else: raise ContractError(f'{job_name}: unrecognized action: {uses}') if 'run' in step: command = step['run'].strip() require(command and not any(s in command for s in ('||', '&&', ';', '`', '$(', '\\\n')), f'{job_name}: wrapper/failure-masking shell') runs.append((index, command)) require(len(checkout_actions) == 1, f'{job_name}: expected exactly one actions/checkout@v4') require(all(checkout_actions[0] < index for index, _ in runs), f'{job_name}: checkout must precede every run step') require(len(rust_actions) == 1, f'{job_name}: expected one toolchain action') action = rust_actions[0] installed = action.get('with', {}).get('toolchain', action['uses'].split('@', 1)[1]) require(installed == toolchain, f'{job_name}: wrong installed toolchain') if job_name == 'build': components = action.get('with', {}).get('components', '') require(set(x.strip() for x in components.split(',')) >= {'rustfmt', 'clippy'}, 'stable lint components missing') require(deny_installed, 'cargo-deny installation missing') require(len(python_actions) == 1 and str(python_actions[0].get('with', {}).get('python-version')) == '3.11', f'{job_name}: Python 3.11 setup missing') required = COMMON_RUNS + QUALITY[job_name] positions = {} for expected in required: matches = [i for i, command in runs if '\n' not in command and shlex.split(command) == shlex.split(expected)] require(len(matches) == 1, f'{job_name}: missing/duplicate exact step: {expected}') positions[expected] = matches[0] captures = [i for i, command in runs if command == CAPTURE or command == 'mkdir -p target\n' + CAPTURE] require(len(captures) == 1, f'{job_name}: exact metadata capture required') capture = captures[0] require(any(i <= capture and (command == 'mkdir -p target' or command == 'mkdir -p target\n' + CAPTURE) for i, command in runs), 'target directory creation missing') require(capture < positions[COMMON_RUNS[2]], 'metadata verification must follow capture') setup = steps.index(python_actions[0]) require(setup < positions[COMMON_RUNS[0]] < min(positions[c] for c in COMMON_RUNS[1:]), 'Python prerequisite ordering') require(steps.index(action) < capture and all(steps.index(action) < positions[c] for c in QUALITY[job_name]), 'Rust setup must precede Cargo commands') allowed = required + [CAPTURE, 'mkdir -p target', 'mkdir -p target\n' + CAPTURE] for _, command in runs: require(any(command == a or ('\n' not in command and '\n' not in a and shlex.split(command) == shlex.split(a)) for a in allowed), f'{job_name}: unsupported extra shell step: {command}') return ['build: stable exhaustive all-target CI', 'msrv: 1.75.0 exhaustive all-target CI']
def main(argv=None): parser = argparse.ArgumentParser(description=__doc__) subs = parser.add_subparsers(dest='command', required=True) for name in ('metadata', 'fixtures'): sub = subs.add_parser(name) sub.add_argument('--root', required=True, type=Path) if name == 'metadata': sub.add_argument('--metadata', required=True, type=Path) for name in ('lock-conversion', 'lock-stable'): sub = subs.add_parser(name) sub.add_argument('--before', required=True, type=Path) sub.add_argument('--after', required=True, type=Path) for name, flag in [('partitions', '--output'), ('verify-partitions', '--plan')]: sub = subs.add_parser(name) sub.add_argument('--metadata', required=True, type=Path) sub.add_argument(flag, required=True, type=Path) subs.add_parser('ci').add_argument('--workflow', required=True, type=Path) args = parser.parse_args(argv) names = {'metadata': 'verify_msrv_metadata', 'fixtures': 'verify_fixture_integrity', 'lock-conversion': 'verify_lock_v3_conversion', 'lock-stable': 'verify_lock_stability', 'partitions': 'verify_target_partition_coverage', 'verify-partitions': 'verify_target_partition_coverage', 'ci': 'verify_ci_msrv_contract'} check = names[args.command] try: if args.command == 'metadata': result = verify_msrv_metadata(args.root, read_json(args.metadata)) elif args.command == 'fixtures': result = verify_fixture_integrity(args.root) elif args.command in ('lock-conversion', 'lock-stable'): result = globals()[check](args.before, args.after) elif args.command == 'partitions': plan = make_partitions(read_json(args.metadata)) args.output.parent.mkdir(parents=True, exist_ok=True) args.output.write_text(json.dumps(plan, indent=2) + '\n') result = [f'wrote {len(plan["commands"])} audited command partitions: {args.output}'] elif args.command == 'verify-partitions': result = verify_target_partition_coverage(read_json(args.metadata), read_json(args.plan)) else: result = verify_ci_msrv_contract(args.workflow) print(f'PASS {check}') for line in result or []: print(line) return 0 except (ContractError, OSError, ValueError, KeyError, TypeError, ImportError) as error: print(f'FAIL {check}: {error}', file=sys.stderr) return 1
if __name__ == '__main__': sys.exit(main())