Skip to content

osrforge.workdir

The per-module working directory: layout paths, run.json I/O, and the artifact writer.

No other module builds workdir paths by hand, and every JSON artifact goes through write_json_artifact — pinning the byte format once means the byte-stability tests never chase formatting noise.

StageTracker

StageTracker()

Accumulates one tracked stage's token usage and model identity.

Yielded by track_stage; stage functions call add_usage and set_model once per provider response.

Start with zero usage and no model identity.

usage instance-attribute

usage = TokenUsage()

provider instance-attribute

provider: str | None = None

model_id instance-attribute

model_id: str | None = None

add_usage

add_usage(usage: TokenUsage) -> None

Accumulate one response's token usage.

Call exactly once per provider response — FoundryProvider already folds schema-retry attempts into each response's usage, so summing anywhere else double-counts.

Parameters:

Name Type Description Default
usage TokenUsage

The response's usage.

required

set_model

set_model(provider: str, model_id: str) -> None

Record the provider and model identity from a response.

Last write wins — if a deployment updates mid-run, run.json records the most recent response's model_id.

Parameters:

Name Type Description Default
provider str

The provider class name (type(provider).__name__).

required
model_id str

The model identifier the service returned.

required

Workdir

Workdir(root: Path)

One conversion's working directory, owning the pinned layout.

Attributes:

Name Type Description
root

The workdir root, e.g. my-module.forge/.

Bind to a workdir root without touching the filesystem.

Parameters:

Name Type Description Default
root Path

The workdir root directory.

required

root instance-attribute

root = root

source_pdf property

source_pdf: Path

The copied source module.

run_json property

run_json: Path

The run metadata file.

pages_dir property

pages_dir: Path

Per-page renders and text layers.

stages_dir property

stages_dir: Path

Cached raw model-stage outputs.

survey_json property

survey_json: Path

The survey stage's cache.

monsters_json property

monsters_json: Path

The monsters stage's cache.

statblocks_json property

statblocks_json: Path

The stat-block pass's cache (written by the monsters stage).

mapread_json property

mapread_json: Path

The map-reading stage's cache.

overrides_yaml property

overrides_yaml: Path

The human correction file.

previews_dir property

previews_dir: Path

Rendered SVG level maps.

previews_index property

previews_index: Path

The previews index page: each level's SVG beside its surveyed map pages.

report_json property

report_json: Path

The extraction report.

adventure_json property

adventure_json: Path

The stamped osrlib adventure document.

areas_json

areas_json(dungeon_id: str, level_number: int) -> Path

Return the content stage's cache path for one level.

Filename unambiguity is guaranteed by the canonical slug alphabet — no dots or slashes in dungeon ids.

Parameters:

Name Type Description Default
dungeon_id str

The canonical dungeon id.

required
level_number int

The 1-based level number.

required

Returns:

Type Description
Path

stages/areas.<dungeon>.<level>.json.

preview_svg

preview_svg(dungeon_id: str, level_number: int) -> Path

Return the preview path for one level.

Filename unambiguity is again guaranteed by the canonical slug alphabet — no dots or slashes in dungeon ids.

Parameters:

Name Type Description Default
dungeon_id str

The canonical dungeon id.

required
level_number int

The 1-based level number.

required

Returns:

Type Description
Path

previews/<dungeon>.<level>.svg.

page_png

page_png(page_number: int) -> Path

Return the render path for a page.

Parameters:

Name Type Description Default
page_number int

The 1-based page number.

required

Returns:

Type Description
Path

pages/NNNN.png, zero-padded to 4 digits.

page_txt

page_txt(page_number: int) -> Path

Return the text-layer path for a page.

Parameters:

Name Type Description Default
page_number int

The 1-based page number.

required

Returns:

Type Description
Path

pages/NNNN.txt, zero-padded to 4 digits.

area_caches

area_caches() -> list[Path]

Return every content-stage cache file, sorted.

Only the per-level areas.*.json caches — not survey.json, monsters.json, statblocks.json, or mapread.json. The upstream stages' clearing rule: survey() (on success) and content() (upfront) unlink these and monsters.json and statblocks.json — a re-run of either can change the encounter-name population, orphaning old resolutions and stat blocks exactly as it orphans old area caches. mapread.json depends on the survey alone, so only survey() clears it.

Returns:

Type Description
list[Path]

The stages/areas.*.json paths, sorted by name.

read_run

read_run() -> RunMeta

Load and validate run.json.

Returns:

Type Description
RunMeta

The run metadata.

write_run

write_run(run: RunMeta) -> None

Write run.json in the pinned artifact format.

Parameters:

Name Type Description Default
run RunMeta

The run metadata to persist.

required

track_stage

track_stage(workdir: Workdir, stage: Stage) -> Generator[StageTracker]

Own one stage's running → completed/failed choreography in run.json.

On enter, writes the stage running with started_at. On clean exit, writes completed with finished_at, the accumulated usage, and — when the tracker saw a response — the run's provider/model identity. On exception, writes failed with error=str(exc), the usage spent so far, and finished_at, then re-raises, leaving upstream artifacts untouched.

Timestamps are legal here and only here: run.json is operational metadata, and keeping timestamps out of every other artifact is part of what byte-stability rests on.

Parameters:

Name Type Description Default
workdir Workdir

The workdir whose run.json records the stage.

required
stage Stage

The stage being run.

required

Yields:

Type Description
Generator[StageTracker]

The tracker the stage function feeds per-response usage and identity.

write_json_artifact

write_json_artifact(path: Path, artifact: BaseModel | Mapping[str, object]) -> None

Write a JSON artifact in the pinned byte format.

The format: model_dump(mode="json") for models, UTF-8, 2-space indent, keys in model-declaration (or mapping-insertion) order — no sorting; pydantic order is deterministic — and a trailing newline.

Parameters:

Name Type Description Default
path Path

The destination file.

required
artifact BaseModel | Mapping[str, object]

A pydantic model, or an already-serialized mapping (osrlib's stamped adventure.json document is a plain dict).

required