diff --git a/docs/match-artifacts.md b/docs/match-artifacts.md
index 65e8329..31cdb70 100644
--- a/docs/match-artifacts.md
+++ b/docs/match-artifacts.md
@@ -83,17 +83,17 @@ flowchart LR
subgraph dSummaries["$MM_HOME/logs/gameSummaries/"]
direction TB
- fBoard[/"board-round_*.png
the board, once a phase
PNG 2037×1260 · 3.3 MB × 31
new: keep the victory frame, as the share card"/]:::mmKept
+ fBoard[/"board-round_*.png
the board, once a phase
PNG 2037×1260 · 1.6–3.3 MB each × 31
new: keep the victory frame, as the share card"/]:::mmKept
fMini[/"minimap-round_*.png
PNG 394×251 · 28 KB × 46
new: drop, they are the GIF's frames"/]:::mmGone
fGif[/"minimap-<uuid>.gif
the whole match, animated
GIF · 2.14 MB"/]:::mmKept
end
subgraph dLogs["$MM_HOME/logs/"]
direction TB
- fActions[/"game_actions_N.tsv
every action and attack,
attacker → target
TSV, 34 cols · ~1 MB · new: keep"/]:::mmKept
- fGamelog[/"gamelog.html
the full round-by-round report
HTML · 1.76 MB · new: keep"/]:::mmKept
+ fActions[/"game_actions_N.tsv
every action and attack,
attacker → target
TSV, 34 cols · 15 KB–1 MB · new: keep"/]:::mmKept
+ fGamelog[/"gamelog.html
the full round-by-round report
HTML · 125 KB–1.76 MB · new: keep"/]:::mmKept
fStatus[/"entitystatus.txt
record sheets at the end
text · 18.6 KB · new: keep"/]:::mmKept
- fMul[/"salvage.mul · Bot_*.mul
what was destroyed
MUL XML · 13 KB · 6.4 KB · new: keep"/]:::mmKept
+ fMul[/"salvage.mul · Bot_*.mul
whichever MULs the game wrote
MUL XML · 2–13 KB each · new: keep"/]:::mmKept
fMmLog[/"megamek.log
the client's own logging
text · 226 KB"/]:::mmKept
fUnified[/"unified_log.log + .gz
root logger, third parties too
text · 3 KB + rollovers"/]:::mmKept
fRanker[/"bot_path_ranker.log
Princess ranking every move
text · 745 KB"/]:::mmGone
@@ -186,6 +186,11 @@ flowchart LR
consumers -.->|"nothing writes these yet"| records
```
+Sizes on the boxes are one match's, and a match's size varies by an order of
+magnitude with its length — see [what a real match actually
+weighs](#what-a-real-match-actually-weighs) for the same layout measured in
+production.
+
Three things the layout makes visible.
**`launch/` is the only class that is complete before the match is played.** It
@@ -202,6 +207,11 @@ she considered, and the autosaves are MegaMek's serialization at one version.
## Captured today
+Sizes in this section and the next are from one 8-round match and a desktop
+MegaMek install. They are the large end; [what a real match actually
+weighs](#what-a-real-match-actually-weighs) has the same files measured in
+production, where a short match runs an order of magnitude smaller.
+
Uploaded to `matches//` by `container/lib/collect.sh` in
[arena][collect], under the four upload keys the launch manifest carries.
@@ -305,7 +315,7 @@ matches//
game_actions_N.tsv every action and attack, attacker → target
gamelog.html the full round-by-round report
entitystatus.txt record sheets at the end
- salvage.mul Bot_*.mul what was destroyed, in MUL
+ salvage.mul Bot_*.mul whichever MULs the game wrote
minimap.gif the match, animated
derived/ ours: extracted, rendered or selected by arena
result.json outcome, teams, per-unit state
@@ -406,7 +416,7 @@ expire.
| Result: `units[]` | **Record, condensed** | 5.8 KB per unit is critical slots, equipment mounts and ammo bins. Keep chassis, model, BV, status, damage level, crew and armour percentage — about 300 B per unit, so a 12-unit match is ~4 KB rather than ~70 KB |
| Result: full per-unit detail | **`derived/`, referenced** | A record sheet is worth reading once, by one person, on a page. Not worth putting on the firehose |
| `game_actions_N.tsv` | **`raw/`, and extract from it** | Kills with attribution, damage dealt and taken, accuracy. The extracted figures go in the record; the TSV is the evidence they were read from |
-| `gamelog.html`, `entitystatus.txt`, `salvage.mul`, `Bot_*.mul` | **`raw/`** | MegaMek's own account, in formats it can read back. ~1.8 MB for all four |
+| `gamelog.html`, `entitystatus.txt`, and whichever MULs the game wrote | **`raw/`** | MegaMek's own account, in formats it can read back. Well under 2 MB together |
| Board renders | **`derived/socials/share-card.png`, the victory frame only** | One is read, thirty-one are uploaded. Keeping the frame we chose saves ~99 MB a match |
| Minimap frames | **Drop** | They are the GIF's own frames |
| Minimap GIF | **`raw/`; blob only if asked for** | 2.14 MB is a lot to ask a player's PDS to hold for a replay nobody has requested yet |
@@ -438,6 +448,10 @@ about it.
| What the match was given | not kept | ~2 KB |
| **Per match** | **~110 MB** | **~9 MB** |
+Those are the 8-round match's figures. A shorter one is smaller throughout —
+the first production match came to 2.2 MB — but the ratio holds, because what
+the change removes is per-phase renders and what it adds is kilobytes.
+
## What has to change first
**Only one of these has a deadline**
@@ -485,16 +499,65 @@ about it.
change: new upload keys in the launch manifest, matching keys in `matches`,
and a deploy where an arena image using the old keys still works.
+## What a real match actually weighs
+
+The first match through this layout, in production, on 2026-08-20:
+
+| | | |
+|---|---|---|
+| `launch/identity.json` | JSON | 333 B |
+| `launch/scenario.mms` | text | 1.2 KiB |
+| `raw/game_actions_0.tsv` | TSV | 15.5 KiB |
+| `raw/entitystatus.txt` | text | 5.3 KiB |
+| `raw/Bot_@lance.blue.mul` | MUL XML | 2.1 KiB |
+| `raw/gamelog.html` | HTML | 125.2 KiB |
+| `raw/minimap.gif` | GIF | 204.3 KiB |
+| `derived/result.json` | JSON | 69.4 KiB |
+| `derived/socials/share-card.png` | PNG | 1.6 MiB |
+| `diagnostics/megamek.log` | text | 36 KiB |
+| `diagnostics/unified_log.log` | text | 36 KiB |
+| `diagnostics/stats-summary.txt` | text | 1.1 KiB |
+| `manifest.json`, two `camo-.png` | JSON, PNG | 8.2 KiB |
+| **total** | **15 objects** | **2.2 MB** |
+
+Everything above this section was measured somewhere else: one 8-round match
+captured out of a container by hand, and a desktop MegaMek install's `logs/`,
+which is what a person's own long games leave behind. Those numbers are larger
+across the board — `gamelog.html` at 1.76 MB against 125 KiB here,
+`game_actions_N.tsv` at ~1 MB against 15.5 KiB, a board render at 3.3 MB
+against the 1.6 MiB this match's share card weighs.
+
+Both are true and neither is the constant. What scales is what you would
+expect: rounds, units, and board size. The desktop figures are a long match's
+shape and the production figure is a short one's, so read the tables above as
+an upper bound and this as a floor.
+
+What does not change is the ratio the layout was argued from. This match
+uploaded one board render; the old layout would have uploaded every phase's,
+which at this match's own size is some 50 MB against a 2.2 MB total. Whatever
+a match weighs, nearly all of it used to be pictures nothing read.
+
+Two smaller corrections from the same listing. `salvage.mul` did not appear at
+all — the MULs are written per player, and this match produced only
+`Bot_@lance.blue.mul`, so the pair should be read as "whichever MULs the game
+wrote" rather than as two files that always arrive. And `derived/turns/` is
+empty: this match uploaded no turn reports, which is not explained yet. The
+observer is enabled in every manifest headquarters writes and the entrypoint
+starts both it and the uploader, so the container log is what settles whether
+the observer never spooled or the upload path is at fault.
+
## Re-measuring
-The sizes here come from one real match — 8 rounds, two forces — and from a
-real MegaMek install's `logs/` and `savegames/`. They are a shape, not a
-constant: board renders scale with board size, turn reports and `game_actions`
-scale with rounds and units, and `units[]` scales with unit count.
+ ./scripts/matches/artifacts.sh # infra
+
+That prints every object a match left, with sizes, grouped by class — which is
+where the table above came from. `./scripts/matches/list.sh` gives the match
+ids, and both are in the infra repo.
-To take the numbers again, keep a container's `state/` and `MM_HOME/logs/`
-after a match and measure them directly. `du -sh` per glob is the whole method;
-the counts above are `n` files of mean size, and both matter, because the
-expensive artifacts here are expensive by count.
+For anything the container did not upload, there is no substitute for looking
+inside one: keep a container's `state/` and `MM_HOME/logs/` after a match and
+measure them with `du`. That is how the amber rows in the inventory above were
+counted, and it is the only way to count them, since by definition they never
+leave.
[collect]: https://tangled.org/lance.blue/arena