# Contributing — dataset refresh (pinned, fail-closed) `kaomoji.json` is built from [kaomojikan/kaomoji-data](https://github.com/kaomojikan/kaomoji-data) (MIT). The build is **always bound to a full 40-character upstream commit** — never a mutable branch or tag. A branch can move after review; a commit cannot. The current pin and its file hashes are recorded in [`build/dataset-source.json`](build/dataset-source.json). `build/build_kaomoji_dataset.py` enforces this fail-closed: - `--upstream-commit` must be a full 40-character SHA; a branch or tag is refused. - Network mode downloads the two source files **at that commit** (`raw.githubusercontent.com///…`), then verifies the commit still resolves and that each file matches the git blob object SHA in GitHub's tree for that commit. - Offline mode (`--src-dir`) requires the checkout's `git rev-parse HEAD` to equal the requested commit — i.e. the checkout must be **in detached mode at the pinned commit**. A bare copy (no `.git`) is accepted only when its files match the recorded SHA-256 hashes. - Whenever the provenance record covers the requested commit, every source file is cross-checked against its recorded SHA-256 before building. - Any mismatch aborts the build with a non-zero exit. An upstream refresh is therefore a reviewable, replayable change: **new full commit SHA → rebuild → new `kaomoji.json` + new `build/dataset-source.json` → new plugin commit**. ## Refresh procedure The commands below are for maintainers/refreshers. They document the exact pinned workflow; the enforcement lives in the builder (fail-closed on every step). 1. Find the upstream commit you want (its full SHA, e.g. via the repository commit list). 2. Fetch that exact commit in detached mode. Either: ```text git clone --filter=blob:none https://github.com/kaomojikan/kaomoji-data /tmp/kaomoji-data git -C /tmp/kaomoji-data checkout --detach git -C /tmp/kaomoji-data rev-parse HEAD # must print ``` or use no local clone at all and let the builder download the files at the pinned commit itself (network mode, step 4). 3. Verify the pin. The SHA printed in step 2 must equal the SHA you intend; if the builder records a new provenance entry it will carry this SHA and date. 4. Build (from the Kaomarchy repository root). Offline, from the checkout: ```text python3 build/build_kaomoji_dataset.py --src-dir /tmp/kaomoji-data --upstream-commit --out kaomoji.json ``` or online, straight from the pinned commit (downloads + verifies): ```text python3 build/build_kaomoji_dataset.py --upstream-commit --out kaomoji.json ``` Both modes rewrite `build/dataset-source.json` with the new commit, commit date, and SHA-256 / git-blob hashes. 5. Sanity-check the filter logic and review the diff: ```text node build/test_search.js git diff -- kaomoji.json build/dataset-source.json ``` Spot-check a few entries against the upstream content at that commit. 6. Commit `kaomoji.json` **and** `build/dataset-source.json` together, with a message that names the new upstream commit (e.g. "Dataset: kaomoji-data @ "). ## Notes - No network access happens at plugin runtime; this procedure only runs during an explicit refresh. - The plugin install path (`omarchy plugin add …`) never fetches upstream — it installs the committed dataset from this repository. - The upstream file URLs in the old `build/build_kaomoji_dataset.py` docstring were mutable `main`-branch links; they have been replaced by the pinned-commit mechanism above.