agentsclimarketplace

Source command megaminx tpu merge

Skill Erlemar/cayley-puzzles/.agents/skills/source-command-megaminx-tpu-merge

Pull the latest cayleypy-tpu-beam-smoke kernel output, aggregate per-rank JSONs, merge with current best, verify, and prep for submission.From its SKILL.md

Install
npx -y skills add Erlemar/cayley-puzzles --skill source-command-megaminx-tpu-merge

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

2 things to look at

  • no licenseNo license file was found in the repository. Code published without one is not open source by default, so using it at work is a question for whoever answers licensing questions where you are.
  • 0 stars0 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

SKILL.md

6.3 KB, ~1.8k tokens by cl100k_base, as published. Nobody here has run it

source-command-megaminx-tpu-merge

Use this skill when the user asks to run the migrated source command megaminx-tpu-merge.

Command Template

/megaminx-tpu-merge

Bundles the recurring TPU post-completion ritual we run after every kernel finishes (or hits Kaggle's ~9h kill). Used 5+ times across v15 → v19a-fix.

Usage

  • /megaminx-tpu-merge <out_name> — pulls Kaggle output, aggregates ranks, merges with current best, writes megaminx/submissions/<out_name>.csv.
  • /megaminx-tpu-merge merge_tpu_v19b — typical use after v19b kernel.
  • /megaminx-tpu-merge merge_tpu_v19b base=megaminx/submissions/...csv — explicit base CSV.

Defaults

  • Kernel slug: artgor/cayleypy-tpu-beam-smoke.
  • Working dir: C:\Users\<user>\AppData\Local\Temp\<out_name>.
  • Base: latest merge_*.csv in megaminx/submissions/ (smallest move count).
  • Output: megaminx/submissions/<out_name>.csv.
  • Standalone (TPU-only) output: megaminx/submissions/<out_name>_standalone.csv.

Execution

1. Pull kernel output

export KAGGLE_API_TOKEN=$KAGGLE_API_TOKEN PYTHONUTF8=1 PYTHONIOENCODING=utf-8
mkdir -p /tmp/<out_name>
.venv/Scripts/kaggle.exe kernels output artgor/cayleypy-tpu-beam-smoke -p /tmp/<out_name> 2>&1 | tail -3

If KernelWorkerStatus.RUNNING: ABORT — kernel hasn't finished yet.

2. Aggregate per-rank JSONs + map to move names

NOTE: MINGW /tmp/<dir> maps to C:\Users\<user>\AppData\Local\Temp\<dir> — Python on Windows needs the Windows-native path.

PYTHONUTF8=1 .venv/Scripts/python.exe -c "
import json, glob, csv, sys
sys.path.insert(0, 'megaminx/src'); sys.path.insert(0, 'src')
from megaminx.puzzle import Megaminx
puz = Megaminx.load('megaminx/data/puzzle_info.json')
MOVE_NAMES = list(puz.move_names)

base = r'C:\Users\<user>\AppData\Local\Temp\<out_name>'
records = []
for path in sorted(glob.glob(base + r'\rank_*_final.json')) + sorted(glob.glob(base + r'\rank_*_partial.json')):
    with open(path) as f:
        records.extend(json.load(f))

# Dedupe (final supersedes partial; same data anyway)
seen = set(); unique = []
for r in records:
    key = (r['pid'], r['rot_idx'])
    if key in seen: continue
    seen.add(key); unique.append(r)

# Group by pid, take min over verified rotations
by_pid = {}
for r in unique:
    if not r.get('verify_ok'): continue
    by_pid.setdefault(r['pid'], []).append(r)
print(f'records: {len(unique)}  pids covered: {len(by_pid)}')

best_per_pid = {pid: min(recs, key=lambda r: r['path_len'])['path_idx_orig']
                for pid, recs in by_pid.items()}

# Write standalone TPU CSV
with open('megaminx/submissions/<out_name>_standalone.csv', 'w', newline='') as f:
    w = csv.writer(f); w.writerow(['initial_state_id', 'path'])
    for pid in range(1001):
        if pid in best_per_pid:
            names = [MOVE_NAMES[m] for m in best_per_pid[pid]]
            w.writerow([pid, '.'.join(names)])
        else:
            w.writerow([pid, ''])
print(f'wrote standalone CSV')
"

Report: total records, pids covered, distribution of rotations-per-pid (helps sanity check that K coverage is reasonable).

3. Merge with current best

PYTHONUTF8=1 .venv/Scripts/python.exe -c "
import csv
from collections import Counter

def load_paths(p):
    return {int(r['initial_state_id']): r['path'].split('.') if r['path'] else []
            for r in csv.DictReader(open(p))}

best = load_paths('<base>')
tpu = load_paths('megaminx/submissions/<out_name>_standalone.csv')

bucket_wins = Counter(); bucket_savings = Counter()
wins = 0; total_savings = 0
for pid in range(1001):
    bp = best.get(pid, [])
    tp = tpu.get(pid, [])
    if tp and len(tp) < len(bp):
        wins += 1; total_savings += len(bp) - len(tp)
        bucket_wins[pid // 100] += 1
        bucket_savings[pid // 100] += len(bp) - len(tp)

base_total = sum(len(v) for v in best.values())
print(f'current best: {base_total} moves')
print(f'TPU wins: {wins} pids, saved {total_savings} moves')
print()
print('per-bucket wins:')
for b in sorted(bucket_wins.keys()):
    print(f'  bucket {b}: {bucket_wins[b]:3} wins, {bucket_savings[b]:5} saved')

with open('megaminx/submissions/<out_name>.csv', 'w', newline='') as f:
    w = csv.writer(f); w.writerow(['initial_state_id', 'path'])
    for pid in range(1001):
        bp = best.get(pid, [])
        tp = tpu.get(pid, [])
        chosen = tp if (tp and len(tp) < len(bp)) else bp
        w.writerow([pid, '.'.join(chosen)])
print(f'wrote merge CSV (delta -{total_savings})')
"

4. Verify merged

PYTHONUTF8=1 .venv/Scripts/python.exe -c "
import sys
sys.path.insert(0, 'megaminx/src'); sys.path.insert(0, 'src')
from megaminx.puzzle import Megaminx
from cayley.verify import verify_submission
from pathlib import Path
puz = Megaminx.load(Path('megaminx/data/puzzle_info.json'))
r = verify_submission(puz, Path('megaminx/data/test.csv'),
                      Path('megaminx/submissions/<out_name>.csv'))
print(f'verify: {r.n_valid}/{r.n_total} valid, total {r.total_moves:,}')
sys.exit(0 if r.all_valid else 1)
"

Anything other than 1001/1001 valid: STOP. Investigate before submitting.

5. Report and suggest next step

Print:

TPU merge ready: megaminx/submissions/<out_name>.csv = <new_total> (delta -<savings> vs <base_total>)
Suggested next: /megaminx-submit <out_name>.csv "<description>"

DO NOT submit automatically.

Gotchas

  • Windows path conversion: MINGW /tmp/foo ≠ Windows C:\Users\...\Temp\foo. Use Python on the Windows path explicitly. cygpath -w /tmp/foo works.
  • Empty path rows in standalone CSV are expected for pids the kernel didn't reach. The merge with current best fills them in.
  • Partial pids (fewer than K rotations completed) are still useful — take min over what's available. Often 3/4 rotations is enough.
  • verify_ok=False rotations happen rarely; the conjugation-translated path failed CPU verification. Skip those when taking min; other rotations cover the pid.

Cost reference

Aggregation + merge typically takes 30s-2min depending on JSON size:

kernel sizeaggregatemerge
5 pids smoke~2s~1s
500 pids partial~30s~5s
1001 pids full~1min~10s

What ships with it

Read from the repository

Just SKILL.md. No reference files, no scripts.

Keep looking

Skills are one crate of 325,949. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.