# `simready-benchmark stamp` Schemas and Ownership

Authoritative source: `runner/stamper.py` (USD-side) +
`runner/validation_writer.py` (JSON-side). This is a curated reference.

## Command

```bash
simready-benchmark stamp --output-dir <PATH>
```

Refer to the CLI's stamp subcommand parser (`cli/stamp_cmd.py:register_stamp()`)
for the authoritative flag list. `--output-dir DIR` is required; it points at
the `_testing/` directory from a prior run.

A related single-asset entry point:

```bash
simready-benchmark stamp-one ...
```

Used internally by NVCF dispatch and by tooling that stamps one asset at a
time. End-user runs use the fleet-wide `stamp` subcommand.

## Output Layout

```
_testing/
└── results/
    └── <asset-dir>/                                  # mirror of the asset source path
        ├── <asset>.usd                               # mirror copy carrying the stamp
        └── .simready/
            ├── validation.json                       # runtime_tests[] replaced
            └── runtime/<test_name>/result.json       # per-test artifact (source of the stamp data)
```

The original asset's source directory is never written to.

## USD Stamp Schema

```
customLayerData = {
    dictionary SimReady_Metadata = {
        dictionary runtime_testing = {
            dictionary tested_features = {
                dictionary "<ISO-timestamp>" = {
                    dictionary "<FEATURE_ID>" = {
                        bool   passed  = ...
                        string version = "<semver>"
                        dictionary tests = {
                            dictionary "<test_script_path>" = { bool passed = ... }
                        }
                    }
                }
            }
        }
    }
}
```

Re-stamping appends a sibling entry under `tested_features.<ISO>`; older runs
are preserved.

## validation.json Merge Schema

```python
write_validation_runtime_tests(target_path: str, runtime_tests: list[dict]) -> None
```

Reads the existing file (or creates it), REPLACES the `runtime_tests` key
with the provided list, and atomically writes it back. All other top-level
keys are preserved verbatim (atomic rename, no partial writes).

Each element of `runtime_tests`:

```json
{
  "test_name": "<str>",
  "passed":    "<bool>",
  "timestamp": "<ISO-8601>",
  "metrics":   { /* per-test metric dict; can be {} */ }
}
```

## Metadata Ownership Across the SimReady Suite

`customLayerData["SimReady_Metadata"]`:

| Sub-key | Owner |
|---|---|
| `validation` | `simready.validate` (SDK validator) |
| `asset_type` | `simready.validate` |
| `runtime_testing` | `simready.test` |
| (preserved top-level keys: `asset_dir`, `asset_name`, `source_file`, `usd_date_generated`, `used_dsrs_exporter`, `profile`, legacy `simready_benchmark`) | SDK validator / DSRS exporter |

`.simready/validation.json`:

| Key | Owner |
|---|---|
| `schema_version`, `asset_name`, `profile`, `passed`, `issues`, `checks`, `info` | SDK validator (`simready.validate`) |
| `runtime_tests[]` | `simready.test` |

`simready.test` reads and writes ONLY the keys listed above; it never touches
the SDK-owned keys.

## Stamping Events on the Event Stream

While a stamp runs, the fleet stamper emits events to
`_testing/state/events.jsonl`. The reporter consumes these to build the
per-asset Stamping panel in the HTML report.

| Event type | Meaning |
|---|---|
| `asset_stamp_prestate` | Pre-stamp snapshot of the asset's `customLayerData`. |
| `asset_stamped` | Stamp completed successfully. |
| `asset_stamp_skipped` | Stamp skipped because the asset has no result.json files (or no features to record). |
| `asset_stamp_failed` | Stamp threw (for example, a USD lock or a permission error). Run continues. |
| `asset_stamp_warned` | Stamp succeeded but emitted a non-fatal warning. |
| `asset_stamp_partial` | USD stamped but validation.json write failed (or vice versa). |
