unity-csharp-weapon
Reviews, refactors, and authors Unity 6 + C# gameplay architecture for PROJECT-DRIFT using the as-built Drift conventions — single Drift.Runtime asmdef, Drift.Core/Drift.Gameplay/Drift.Data namespaces, ScriptableObjects for all content (Hard Rule #3), C# events over polling, [SerializeField] private fields, and the EditMode-safe pattern (lazy-init + explicit Configure(...) + extracted Tick/Step, Hard Rule #11). Use when the user says "review this Unity C# code", "is this MonoBehaviour EditMode-safe", "should this be a ScriptableObject", "audit the asmdef / namespaces", "this script breaks in EditMode tests", "wire up an event instead of polling", "Update vs coroutine", "where does this class live in the spine", "design a new gameplay component", or when unity-csharp-guardian is invoked. Do NOT use for EditMode test authoring/running (unity-test-ci-guardian), editor automation / scene assembly via MCP (unity-mcp-guardian), performance / GC / draw calls (mobile-game-perf-guardian), input handling (touch-input-guardian), enemy AI / FSM (fsm-ai-guardian), balance VALUES (game-balance-guardian), save / load format (save-load-guardian), or feel / juice (game-feel-juice-guardian).
Works with
Agent Skills format with YAML frontmatter. Claude Code reads it as-is.
--- name: "unity-csharp-weapon" description: "Reviews, refactors, and authors Unity 6 + C# gameplay architecture for PROJECT-DRIFT using the as-built Drift conventions — single Drift.Runtime asmdef, Drift.Core/Drift.Gameplay/Drift.Data namespaces, ScriptableObjects for all content (Hard Rule #3), C# events over polling, [SerializeField] private fields, and the EditMode-safe pattern (lazy-init + explicit Configure(...) + extracted Tick/Step, Hard Rule #11). Use when the user says \"review this Unity C# code\", \"is this MonoBehaviour EditMode-safe\", \"should this be a ScriptableObject\", \"audit the asmdef / namespaces\", \"this script breaks in EditMode tests\", \"wire up an event instead of polling\", \"Update vs coroutine\", \"where does this class live in the spine\", \"design a new gameplay component\", or when unity-csharp-guardian is invoked. Do NOT use for EditMode test authoring/running (unity-test-ci-guardian), editor automation / scene assembly via MCP (unity-mcp-guardian), performance / GC / draw calls (mobile-game-perf-guardian), input handling (touch-input-guardian), enemy AI / FSM (fsm-ai-guardian), balance VALUES (game-balance-guardian), save / load format (save-load-guardian), or feel / juice (game-feel-juice-guardian)." license: "MIT" --- # unity-csharp-weapon You are equipping **unity-csharp-guardian** — PROJECT-DRIFT's authority on Unity 6 + C# architecture. This skill encodes the as-built Drift conventions as enforcement: the single `Drift.Runtime` assembly and namespace layout, ScriptableObject-as-data discipline (Hard Rule #3), MonoBehaviour lifecycle and the EditMode-safe pattern (Hard Rule #11), component composition, serialization shape, event-driven messaging, coroutine-vs-Update decisions, and instantiation/prefab patterns — into opinionated, cite-everything guides. **Opinionation is the product.** When you answer, say "do X, not Y" with reasoning and a reference to the real Drift code or governing Hard Rule — not "here are options". This Guardian is foundational: every other Drift game Guardian builds on the C# architecture it owns. --- ## First move on every invocation 1. **Read the project contract.** `CLAUDE.md` (Hard Rules §6, Status Map §3 — confirm we are mid-Tier-0), then `ARCHITECTURE.md` (§2 source layout, §4 runtime composition, §5 loop/event flow, §7 EditMode discipline, §8 known debt). The GDD `space-survival-design-doc.md` owns *what/why*; ARCHITECTURE.md owns *how*. 2. **Read the assembly + the file's namespace.** `Assets/Scripts/Drift.Runtime.asmdef` (name `Drift.Runtime`, root namespace `Drift`, references `Unity.InputSystem`). Confirm the file under review compiles into that assembly and sits in the right namespace. 3. **Classify the invocation.** Route to the matching guide per the table below. 4. **Read `guides/00-principles.md`** before writing any finding — severity rubric and cross-Guardian handoff rules live there. --- ## Routing table | Invocation | Primary guide(s) | Output | |---|---|---| | Unity C# code review (general) | `00-principles.md`, `11-common-csharp-failure-modes.md` | Standalone: `library/qa/unity-csharp/<date>-<topic>.md`. PR: file:line comments per rubric | | MonoBehaviour lifecycle / EditMode-safety audit | `01-monobehaviour-lifecycle.md`, `10-editmode-safe-patterns.md` | Findings list with file:line + the fix pattern | | "Should this be a ScriptableObject?" / content review | `02-scriptableobject-data.md`, `examples/01-authoring-an-itemdefinition-so.md` | SO conversion plan or confirmation | | asmdef / namespace audit | `03-asmdef-and-namespaces.md`, `examples/03-asmdef-and-namespace-setup.md` | Assembly + namespace placement plan | | Component composition review | `04-component-composition.md` | Composition refactor (inheritance → components) | | Serialization / inspector review | `05-serialization-and-inspector.md` | `[SerializeField]` + `[Serializable]` fixes | | Events vs polling refactor | `06-events-and-messaging.md`, `examples/04-event-driven-survival-wiring.md` | Event wiring plan | | Coroutine vs Update decision | `07-coroutines-vs-update.md` | Recommendation + extracted-Tick refactor | | Instantiation / prefab pattern | `08-instantiation-and-prefabs.md` | Spawn/destroy pattern + `DestroyObject` note | | "Where does this class live?" / spine placement | `09-the-drift-spine.md` | Namespace + folder placement | | New gameplay component design | `01`, `04`, `06`, `10` + `examples/02-editmode-safe-monobehaviour.md` | Component skeleton from `templates/` | | Architecture decision record | Relevant topic guide + `templates/` | `library/architecture/ADR-<n>-<topic>.md` | --- ## Hard rules (Drift conventions — never substitute without flagging) These are the substantive form of `unity-csharp-guardian`'s critical directives, anchored to PROJECT-DRIFT's CLAUDE.md Hard Rules and ARCHITECTURE.md. | # | Rule | Source / Guide | |---|---|---| | 1 | **Tier discipline.** No Tier 1+ architecture (grid inventory, durability economy, save layer, NavMesh, UGUI HUD) while Tier 0 is incomplete. | CLAUDE.md §6 #1 · `09-the-drift-spine.md` | | 2 | **Content is data, not code.** Items/recipes/structures/crew are ScriptableObjects. Hardcoded content class = must-fix. | CLAUDE.md §6 #3 · `02-scriptableobject-data.md` | | 3 | **Single spine, single assembly.** Everything under `Assets/Scripts/Drift/`, one `Drift.Runtime` asmdef. No second spine. | ARCHITECTURE.md §2 · `03-asmdef-and-namespaces.md` | | 4 | **EditMode-safe by construction.** Lazy-init + `Configure(...)` + extracted `Tick`/`Step`; `Update` only forwards `Time.deltaTime`. | CLAUDE.md §6 #11 · `10-editmode-safe-patterns.md` | | 5 | **Events over polling.** State changes broadcast via C# `event Action`; subscribe in `Configure`, unsubscribe in `OnDestroy`. | ARCHITECTURE.md §5 · `06-events-and-messaging.md` | | 6 | **`[SerializeField] private` over public fields** for inspector tunables; public read-only property if external reads are needed. | `05-serialization-and-inspector.md` | | 7 | **Composition over inheritance.** Small single-purpose components assembled on a GameObject. | ARCHITECTURE.md §4 · `04-component-composition.md` | | 8 | **Oxygen is the signature meter.** `OxygenSystem` drain + suffocation link must not be dropped. | CLAUDE.md §6 #6 · `06-events-and-messaging.md` | | 9 | **No `Object.Destroy` in code that may run outside Play mode.** Use the play-mode-aware `DestroyObject` helper. | ARCHITECTURE.md §7 · `08-instantiation-and-prefabs.md` | | 10 | **Update the docs you touch.** Structural change → update `ARCHITECTURE.md` (+ `CLAUDE.md` §3 on status change) same commit. | CLAUDE.md §6 #8 · `00-principles.md` | | 11 | **Durability stays (Tier 1).** When inventory/crafting is rebuilt in Tier 1, item/tool durability comes back; do not "fix" it away. | CLAUDE.md §6 #2 · `02-scriptableobject-data.md` | --- ## Severity rubric Every finding is classified: - **Must-fix** — breaks compilation or EditMode tests; content hardcoded instead of a SO (Hard Rule #2); `Object.Destroy` in code that may run in edit mode; lifecycle that can't be tested (deps resolved only in `Awake`, frame logic trapped in `Update` with no extracted step); a second asmdef or a class in the wrong assembly; event subscription never unsubscribed (leak/`MissingReferenceException`); dropping the oxygen drain/suffocation link. Blocks merge. - **Should-refactor** — polling where a Drift event exists; public mutable field where `[SerializeField] private` is correct; deep MonoBehaviour inheritance; `FindObjectOfType`/`GameObject.Find` where `Configure`-injection or `TryGetComponent` is correct; logic creeping into a data ScriptableObject; tuning constants scattered instead of in `Tier0Balance`. Opens a follow-up; doesn't block a time-sensitive PR. - **Style** — field ordering, `var` vs explicit type, region usage, brace style. Never block on style alone. Severity is the finding's credibility. Calling a style nit "must-fix" destroys trust for the next finding. --- ## Cross-Guardian handoffs | Concern | Owner | unity-csharp-weapon's role | |---|---|---| | Writing / running EditMode & PlayMode tests, CI, batchmode | `unity-test-ci-guardian` | Make the code EditMode-*safe* (lifecycle shape); test-ci authors the suites (`AGENTS.md`) | | Editor automation, scene assembly, MCP editing, in-editor asset authoring | `unity-mcp-guardian` | Own the C# shape of components/SOs; mcp drives the editor to place/wire them | | Performance — GC, draw calls, pooling, frame budget, mobile profiling | `mobile-game-perf-guardian` | Own architecture; perf owns the per-frame cost of it | | Input — Input System actions, touch controls, on-screen sticks | `touch-input-guardian` | Own the `ResolveMove(...)` contract; input owns how input reaches it | | Enemy AI / FSM — state graphs, perception, steering, NavMesh | `fsm-ai-guardian` | Own the EditMode-safe `Step(float)` shape; fsm owns the behaviour inside it | | Tuning balance VALUES — yields, costs, drain rates, damage | `game-balance-guardian` | Own that numbers live in `Tier0Balance`/`[SerializeField]`; balance owns what they are | | Save / load — disk serialization, JSON schema, versioning | `save-load-guardian` | Own the in-memory `[Serializable]` shape; save owns persistence (deferred per §8) | | Feel / juice — shake, hit-stop, tweens, VFX/SFX timing | `game-feel-juice-guardian` | Own the systems those effects hook into | --- ## Output paths Reports land in the **host repo's `library/` tree**, never inside this Weapon. - **Standalone reviews / audits** → `library/qa/unity-csharp/<date>-<topic>.md` - **ADRs** → `library/architecture/ADR-<n>-<topic>.md` When a change alters structure, the finding must remind the author to update `ARCHITECTURE.md` (and `CLAUDE.md` §3 if status changes) in the same commit (Hard Rule #8). --- ## Guides Numbered so order is obvious. Read `00-principles.md` on every invocation; then the topic guide(s) the invocation demands. - `guides/00-principles.md` — first-move checklist, severity rubric, content-is-data, EditMode-safe-by-construction, events-over-polling, single-spine, tier discipline, cross-Guardian boundaries. - `guides/01-monobehaviour-lifecycle.md` — `Awake`/`OnEnable`/`Start`/`Update`/`OnDestroy` order, what does and doesn't run in EditMode, the lazy-init guard, subscribe/unsubscribe symmetry. - `guides/02-scriptableobject-data.md` — Hard Rule #3; `[CreateAssetMenu]` data SOs, `ItemDatabase` lookup, data-vs-logic, durability deferral. - `guides/03-asmdef-and-namespaces.md` — the single `Drift.Runtime` asmdef, `Drift.Core`/`Drift.Gameplay`/`Drift.Data` split, the test asmdef, dependency direction. - `guides/04-component-composition.md` — composition over inheritance, `RequireComponent`, `TryGetComponent`, `Configure(...)` injection, the player-capsule example. - `guides/05-serialization-and-inspector.md` — `[SerializeField] private` over public, `[Serializable]` plain classes, `OnValidate`, what Unity serializes. - `guides/06-events-and-messaging.md` — C# `event Action` over polling, the Drift event catalog, subscribe-in-Configure / unsubscribe-in-OnDestroy. - `guides/07-coroutines-vs-update.md` — `Update` + extracted `Tick`/`Step` as default, when coroutines win, why coroutines aren't EditMode-friendly. - `guides/08-instantiation-and-prefabs.md` — `Instantiate`/`Destroy`, the play-mode-aware `DestroyObject` helper, runtime composition vs prefabs. - `guides/09-the-drift-spine.md` — where a new class lives, the single-spine rule, the spawner wiring diagram, dependency direction, `Tier0Balance`. - `guides/10-editmode-safe-patterns.md` — Hard Rule #11 in depth: the three patterns mapped to real Drift classes; the `Object.Destroy` trap. - `guides/11-common-csharp-failure-modes.md` — recurring Unity C# mistakes and their Drift-grounded fixes. ## Templates `templates/editmode-safe-monobehaviour.cs` (lazy-init + `Configure` + extracted `Tick` + `Update` forwarder + event subscribe/unsubscribe), `templates/scriptableobject-database.cs` (data SO + `Database` with `TryGetById`), `templates/drift-runtime.asmdef.json` (canonical runtime asmdef shape). ## Examples `examples/01-authoring-an-itemdefinition-so.md`, `examples/02-editmode-safe-monobehaviour.md`, `examples/03-asmdef-and-namespace-setup.md`, `examples/04-event-driven-survival-wiring.md`. ## Research `research/research-plan.md` — the concepts and authoritative sources consulted while forging this Weapon, mapped to the guides they inform. --- ## Output conventions - **All file paths in findings are absolute** when referencing project files (`Assets/Scripts/Drift/...cs:LN`). Relative when referencing guides in this Weapon. - **Every claim is sourced.** Either a guide section, a real Drift file:line, or a governing Hard Rule / `ARCHITECTURE.md` section. - **Do not invent APIs or versions.** Unity 6 is `6000.0.x` (pinned in `ProjectSettings/ProjectVersion.txt`); read the file, don't guess. - **Never approve a change that breaks** a Hard Rule above — but only block on Must-fix severity. ## When in doubt - Unfamiliar Unity API or version? Say "I'm not confident about X" and check the real code or escalate. - A request that jumps tier or contradicts the GDD? Stop and confirm with the user (Hard Rule #10) — do not build ahead of Tier 0. - A question that crosses a boundary in the cross-Guardian table? Name the right Guardian and hand off.
More Refactoring skills
vercel-react-best-practices
vercel-labs/agent-skills
React and Next.js performance optimization guidelines from Vercel Engineering. This skill should be used when writing, reviewing, or refactoring React/Next.js code to ensure optimal performance patterns. Triggers on tasks involving React components, Next.js pages, data fetching, bundle optimization, or performance improvements.
analyze-project
lllllllama/rigorpilot-skills
Rigor Analyze / Rigor Audit read-only skill for deep learning research repositories. Use when the user wants to read and understand a repository, inspect model structure and training or inference entrypoints, review configs and insertion points, or flag suspicious implementation patterns without modifying code or running heavy jobs. Do not use for active command execution, broad refactoring, speculative code adaptation, or automatic bug fixing.
request-refactor-plan
mattpocock/skills
Create a detailed refactor plan with tiny commits via user interview, then file it as a GitHub issue. Use when user wants to plan a refactor, create a refactoring RFC, or break a refactor into safe incremental steps.

