From 5c47de8445961f948073e911977af0da750812a0 Mon Sep 17 00:00:00 2001 From: wtclaude Date: Thu, 8 Oct 2026 23:53:12 -0500 Subject: [PATCH 1/3] docs(runicnpc): example outfits and full durability (D323, D324) Decisions from the 9d player walk, 2026-10-09: each example profile wears its own outfit, and the example kits' items are written at full durability read from the item definitions. API.md's note on the example kits says both. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01E14m6SuuY6i1vASFeGDBeY --- runicnpc/API.md | 3 ++- runicnpc/PLAN.md | 2 ++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/runicnpc/API.md b/runicnpc/API.md index cfa9736..d0a2e7f 100644 --- a/runicnpc/API.md +++ b/runicnpc/API.md @@ -403,7 +403,8 @@ route is walked back and forth. An NPC joins the route at its nearest point. - `data/RunicNPC/state.json` (API 5): `examplesWritten`, set on the first load. That load writes the four example kits (`rnpc_raider`, `rnpc_campguard`, `rnpc_sniper`, `rnpc_juggernaut`) into Kits' own data file, each where its name is free and each needing the permission `kits.runicnpc` (Kits' prefix, since Kits registers it), which nobody is granted, so no player can - claim one. On a server no site manages it also adds the four example profiles (`raider`, `campguard`, `sniper`, + claim one. Each wears its own outfit (D323), and every item is written at this Rust's full durability for it + (D324). On a server no site manages it also adds the four example profiles (`raider`, `campguard`, `sniper`, `juggernaut`). Then it reloads Kits, which reloads RunicNPC with it. **Nothing is written again, even if you delete them** (D280, D284, D289). - **A Kits reload reloads RunicNPC** on both frameworks, because RunicNPC requires Kits, and the NPCs it had spawned diff --git a/runicnpc/PLAN.md b/runicnpc/PLAN.md index c8584a9..dfc1140 100644 --- a/runicnpc/PLAN.md +++ b/runicnpc/PLAN.md @@ -145,6 +145,8 @@ architectural or design decision is implemented. | **D320** | **Rust's own animals count as animal kills again.** They are now `Rust.Ai.Gen2.BaseNPC2` (stag, boar, wolf, bears, big cats, crocodile, farm animals, critters, sea life), not the `BaseNpc` the bridge tested, so no animal kill counted as an animal or an NPC kill. Every `BaseNPC2` but `ScientistNPC2` is an animal; `ScientistNPC2`, the one person among them, is a human NPC kill. Found by the 9d server-side walk (stage 9d; the org lead: "Fix the animal kill things"). | Leaving it for later. | | **D321** | **A heal on another player counts again.** `OnHealingItemUse` is `(tool, fromPlayer, toTarget)`; the bridge's two-parameter handler read the healer as the target and dropped every heal as healing yourself, so "Players healed" counted revives only. The bridge reads the target, and one act of help counts once whichever of its two hooks comes first (a syringe revive raises the heal first) (stage 9d; the org lead chose the fix from an example). | Only revives count; dropping the title. | | **D322** | **An event's zone enforces its flags.** ZoneManager 3.1.14 subscribes the hooks behind its flags only for the zones it had when it loaded, so a zone opened later through its API enforced none of them: the walk shot a player dead in a PvpGod zone and built in a NoBuild one. RunicGatewayZones 0.2.0 has ZoneManager run its own `UpdateHookSubscriptions` a tick after any zone is made, the same moment it already enters the players inside (stage 9d; the org lead asked for the ZoneManager patch). | Patching ZoneManager's file; asking ZoneManager's author. | +| **D323** | **Each example profile wears its own outfit; the weapons of D289 stay.** The raider wears scrap armour (coffee-can helmet, roadsign jacket and kilt, hoodie, pants, boots, leather gloves); the camp guard metal (metal facemask and chest plate, long-sleeve shirt, pants, boots, roadsign gloves); the sniper hide (boonie hat, balaclava, hide poncho, pants and boots); the Juggernaut heavy plate, as before. Three shared one hoodie, pants and boots, so they read alike in game. Only a first load writes them (D284): no live server has RunicNPC yet, and the test rigs were given them by resetting `examplesWritten` (9d player walk, 2026-10-09). | One outfit for all; replacing a server's kits that still match the old ones. | +| **D324** | **An example kit's items are written at full durability, read from this Rust's item definitions when the kits are written.** Kits sets an item's condition and maximum straight from its file. The writer put 0 on armour (a metal facemask 0 of 320, heavy plate 0 of 1,000, so it barely protected) and 100 on every weapon whatever its real maximum (an M249's is 500). Now an item with a condition gets the definition's maximum and one without gets 0. The harness checks it (`s6.examples.fullCondition`). | A fixed table of maximums, which a Rust update would make stale. | **Borrowing, not copying.** NpcSpawn states no licence at all, so its source grants us nothing and is read only as a description of *what* can be done in Rust. HumanNPC is MIT on uMod, which is GPL-compatible, but §1.2 rules out its From df44a10982ce07632fa43b702fcc4b669f6f6f6d Mon Sep 17 00:00:00 2001 From: wtclaude Date: Fri, 9 Oct 2026 00:11:51 -0500 Subject: [PATCH 2/3] docs(runicnpc): rnpc here stands the NPC a metre in front (D325) Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01E14m6SuuY6i1vASFeGDBeY --- runicnpc/COMMANDS.md | 2 +- runicnpc/PLAN.md | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/runicnpc/COMMANDS.md b/runicnpc/COMMANDS.md index 8af7c8d..c735795 100644 --- a/runicnpc/COMMANDS.md +++ b/runicnpc/COMMANDS.md @@ -31,7 +31,7 @@ a number (`bandit-1`) and can be renamed. | Command | Does | Permission | |---|---|---| | `/rnpc place [options]` | Places the profile's NPCs where you are looking, and answers with the placement's name and the cost warning. | `runicnpc.place` | -| `/rnpc here [options]` | The same, where you stand. | `runicnpc.place` | +| `/rnpc here [options]` | The same, a metre in front of you and facing you. If something is in the way, or there is no ground or navmesh there, it stands where you do and the reply says so. Like `place`, it makes a placement that respawns until you remove it. | `runicnpc.place` | | `/rnpc remove [placement]` | Removes a placement and its NPCs: the one you name, or the one the NPC you are looking at belongs to. | `runicnpc.place` | | `/rnpc rename ` | Renames a placement. Its live NPCs stay where they are. | `runicnpc.place` | | `/rnpc near [radius]` | Lists the placements and live NPCs around you, with distances and any note (waiting, off the navmesh). | `runicnpc.place` | diff --git a/runicnpc/PLAN.md b/runicnpc/PLAN.md index dfc1140..99612c9 100644 --- a/runicnpc/PLAN.md +++ b/runicnpc/PLAN.md @@ -147,6 +147,7 @@ architectural or design decision is implemented. | **D322** | **An event's zone enforces its flags.** ZoneManager 3.1.14 subscribes the hooks behind its flags only for the zones it had when it loaded, so a zone opened later through its API enforced none of them: the walk shot a player dead in a PvpGod zone and built in a NoBuild one. RunicGatewayZones 0.2.0 has ZoneManager run its own `UpdateHookSubscriptions` a tick after any zone is made, the same moment it already enters the players inside (stage 9d; the org lead asked for the ZoneManager patch). | Patching ZoneManager's file; asking ZoneManager's author. | | **D323** | **Each example profile wears its own outfit; the weapons of D289 stay.** The raider wears scrap armour (coffee-can helmet, roadsign jacket and kilt, hoodie, pants, boots, leather gloves); the camp guard metal (metal facemask and chest plate, long-sleeve shirt, pants, boots, roadsign gloves); the sniper hide (boonie hat, balaclava, hide poncho, pants and boots); the Juggernaut heavy plate, as before. Three shared one hoodie, pants and boots, so they read alike in game. Only a first load writes them (D284): no live server has RunicNPC yet, and the test rigs were given them by resetting `examplesWritten` (9d player walk, 2026-10-09). | One outfit for all; replacing a server's kits that still match the old ones. | | **D324** | **An example kit's items are written at full durability, read from this Rust's item definitions when the kits are written.** Kits sets an item's condition and maximum straight from its file. The writer put 0 on armour (a metal facemask 0 of 320, heavy plate 0 of 1,000, so it barely protected) and 100 on every weapon whatever its real maximum (an M249's is 500). Now an item with a condition gets the definition's maximum and one without gets 0. The harness checks it (`s6.examples.fullCondition`). | A fixed table of maximums, which a Rust update would make stale. | +| **D325** | **`/rnpc here` stands the NPC 1 m in front of the admin, facing them, not at their feet.** At their feet it spawned inside the admin, looking away (9d player walk). The spot must fit: nothing at chest height in the way, ground no more than 2 m below, and navmesh for one that walks. Otherwise it falls back to the admin's own spot and the reply says so. The harness checks the distance (`cmd.chat.here`). | 1.5 m or 3 m in front; refusing when the spot does not fit. | **Borrowing, not copying.** NpcSpawn states no licence at all, so its source grants us nothing and is read only as a description of *what* can be done in Rust. HumanNPC is MIT on uMod, which is GPL-compatible, but §1.2 rules out its @@ -386,7 +387,7 @@ permissions reach the site's permission manager through the inventory, like any | Command | Does | Permission | |---|---|---| | `/rnpc place [key=value ...]` | Places at the spot you are looking at, persistent, and answers with its name (D241). Options in any order (D242): `count=`, `respawn=` (seconds), `mode=each\|group`, `move=wander\|monument\|route:`, `radius=` | `runicnpc.place` | -| `/rnpc here [key=value ...]` | The same, where you stand | `runicnpc.place` | +| `/rnpc here [key=value ...]` | The same, a metre in front of you, facing you; where you stand if that spot does not fit (D325) | `runicnpc.place` | | `/rnpc remove [placement]` | Removes a placement and its NPCs: the one named, or that of the NPC you are looking at | `runicnpc.place` | | `/rnpc rename ` | Renames a placement (D241) | `runicnpc.place` | | `/rnpc near [radius]` | Lists placements (by name) and live NPCs near you | `runicnpc.place` | From 0c1d8d3b1601139e89bb5cc97617ec7355849581 Mon Sep 17 00:00:00 2001 From: wtclaude Date: Fri, 9 Oct 2026 01:07:27 -0500 Subject: [PATCH 3/3] docs(runicnpc): 9d player session, all fifteen rows pass The org lead played every client-only row on both rigs on 2026-10-09 (Rust 25797215, Oxide 2.0.7815, Carbon 2.0.262). Records the results, the decisions the session made (D323-D325), what was asked for next (dome stack 3, the PopupNotifications banner), the Carbon Kits-reload finding, and two walk artifacts. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01E14m6SuuY6i1vASFeGDBeY --- runicnpc/PLAN.md | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/runicnpc/PLAN.md b/runicnpc/PLAN.md index 99612c9..dc1b861 100644 --- a/runicnpc/PLAN.md +++ b/runicnpc/PLAN.md @@ -1778,6 +1778,32 @@ stand-in. Each result was then read on the site, in the browser and in the app. messages and the dome by day and night, and a chat title (Carbon, which has BetterChat). The installer's path waits for the release (9e). +**9d, the player session (2026-10-09).** The org lead played every row, on Rust 25797215 with Oxide 2.0.7815 and +Carbon 2.0.262. **All fifteen pass** (seven on Oxide, eight on Carbon): + +- **Death screen:** "Road Bandit" with a revolver at 2.8 m (Oxide), and the Juggernaut on Carbon. The portrait slot + shows Rust's own logo, as for any killer without a Steam account, so the profile's name costs nothing. +- **`/rnpc` in chat:** the verb list, "Placed …" with the cost warning, `remove`, all readable. **Boss bar:** steady, + with the help line and its two adds, the enraged line, and the death line. **Press E:** the window opens and + closes cleanly (Oxide). **Locked crate:** dropped showing 17 minutes. **Rockets and grenades:** each hook fired + and counted; a lobbed grenade raises `OnExplosiveDropped`, which counts too. **Zone:** enter and leave messages + in chat and as a popup, and the dome. **Chat title (Carbon):** "[Player] Exterminator whitlocktech". + +What the session changed or asked for: + +- **D323 and D324** (each example its own outfit; every item at full durability) and **D325** (`/rnpc here` stands + the NPC a metre in front, facing you). The four kits were rewritten on both rigs by resetting `examplesWritten`. +- **Asked for, to build next:** the default dome stacks **3** spheres, not 1 (chosen by eye at noon), and a + recommended PopupNotifications look: a banner across the top (left 0.15, bottom 0.87, width 0.7, height 0.07), + no close button, Roboto Condensed Bold at 18. The docs show it, and the installer and the Pterodactyl egg write + it where PopupNotifications' config is missing or still at the plugin's defaults. +- **Found, not fixed:** on Carbon, the automatic Kits reload after the first load wrote the example kits did not + take: `s6bossc` stayed refused ("no kit 'rnpc_juggernaut'") until Kits was reloaded by hand. It was a hot load, + not a boot, so a fresh server may not see it. Oxide was fine. +- **Walk artifacts, not faults:** the harness's own players (`11400000001` and up) hold NPC kills on the rigs' + leaderboards, which pushed the org lead out of a top-3 title rule until it was widened for the session. + `/rnpc here` makes a placement that respawns, so a boss placed that way comes back until it is removed. + **9e. The cutover and release (D311, D313).** Only after the walk passes. In order: `runicnpc-rust` `edge` → `main` as v1.0.0 (its Gitea release is the only download); `rust-plugins`, `rust-link` and `installer` `edge` → `main`, and the bundle that pins all four; `module-rust` `edge` → `main` with RunicNPC required. Each release is checked