neon-sprawl/docs/decomposition/modules/E7_M3_FactionReputationLedg...

89 lines
6.1 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

# E7.M3 — FactionReputationLedger
## Summary
| Field | Value |
|--------|--------|
| **Module ID** | E7.M3 |
| **Epic** | [Epic 7 — Quest / Faction](../epics/epic_07_quest_faction.md) |
| **Stage target** | Pre-production |
| **Status** | In Progress — **E7M3-01 catalog landed** ([NEO-133](https://linear.app/neon-sprawl/issue/NEO-133)); **E7M3-02 server faction catalog load landed** ([NEO-134](https://linear.app/neon-sprawl/issue/NEO-134)): fail-fast `content/factions/*_factions.json`, `IFactionDefinitionRegistry`, quest faction cross-ref + E7M3 bundle/grid gates; **E7M3-03 faction standing + reputation delta stores landed** ([NEO-135](https://linear.app/neon-sprawl/issue/NEO-135)): `IFactionStandingStore`, `IReputationDeltaStore`, in-memory + Postgres `V009`/`V010`; **E7M3-04 `ReputationOperations` landed** ([NEO-136](https://linear.app/neon-sprawl/issue/NEO-136)): auditable `TryApplyDelta` orchestration ([NEO-136 plan](../../plans/NEO-136-implementation-plan.md)); **E7M3-05 `FactionGateOperations` landed** ([NEO-137](https://linear.app/neon-sprawl/issue/NEO-137)): quest accept gate eval + `faction_gate_blocked` ([NEO-137 plan](../../plans/NEO-137-implementation-plan.md)); **E7M3-06 reward router rep grants landed** ([NEO-138](https://linear.app/neon-sprawl/issue/NEO-138)): `RewardRouterOperations` applies `reputationGrants` idempotently via `ReputationOperations` ([NEO-138 plan](../../plans/NEO-138-implementation-plan.md)); **E7M3-07 faction standing HTTP read landed** ([NEO-139](https://linear.app/neon-sprawl/issue/NEO-139)): `GET …/faction-standing` snapshot API + Bruno ([NEO-139 plan](../../plans/NEO-139-implementation-plan.md)). Slice 3 backlog [E7M3-pre-production-backlog.md](../../plans/E7M3-pre-production-backlog.md): **E7M3-08** [NEO-140](https://linear.app/neon-sprawl/issue/NEO-140) → **E7M3-11** [NEO-143](https://linear.app/neon-sprawl/issue/NEO-143). Upstream: E7.M1 **Ready**, E7.M2 **Ready**. |
| **Linear** | Label **`E7.M3`** · [E7M3-pre-production-backlog.md](../../plans/E7M3-pre-production-backlog.md) |
## Purpose
Character-wide **faction standing**, auditable **reputation deltas**, and **`FactionGateRule`** evaluation for quest accept (and future zone/travel gates via [E4.M1](E4_M1_ZoneGraphAndTravelRules.md)). Rep grants flow through [E7.M2](E7_M2_RewardAndUnlockRouter.md) **`completionRewardBundle`** idempotency.
## Responsibilities
- Persist **`FactionStanding`** per player per faction; apply **`ReputationDelta`** with clamp and audit log.
- Evaluate **`FactionGateRule`** on quest accept — fail closed on unknown faction or tampered rules (startup validation).
- Emit telemetry hook sites: **`reputation_delta`**, **`faction_gate_blocked`**.
## Key contracts
| Contract | Role |
|----------|------|
| `FactionDef` | Faction id, display name, min/max/neutral standing. |
| `FactionStanding` | Current rep per faction for a player. |
| `ReputationDelta` | Signed change with source attribution (quest id, etc.). |
| `FactionGateRule` | Minimum standing required (e.g. on `QuestDef`). |
| `reputationGrants` | Rows on `QuestRewardBundle``factionId` + `amount`. |
## Module dependencies
- **E7.M1** — QuestStateMachine (`TryAccept` gate hook site).
- **E7.M2** — RewardAndUnlockRouter (bundle apply + idempotent delivery store).
## Dependents (by design)
- **E7.M4** — ContractMissionGenerator.
- **E8.M2** — GuildCorpProgressionState.
- **E4.M1** — ZoneGraphAndTravelRules (`TravelRule` faction gates).
## Related implementation slices
Epic 7 **Slice 3** — at least one faction quest line with rep grant + gated accept; auditable deltas; telemetry **`reputation_delta`**, **`faction_gate_blocked`**. Backlog: [E7M3-pre-production-backlog.md](../../plans/E7M3-pre-production-backlog.md).
## Linear backlog (decomposed)
| Slug | Linear |
|------|--------|
| E7M3-01 | [NEO-133](https://linear.app/neon-sprawl/issue/NEO-133) |
| E7M3-02 | [NEO-134](https://linear.app/neon-sprawl/issue/NEO-134) |
| E7M3-03 | [NEO-135](https://linear.app/neon-sprawl/issue/NEO-135) |
| E7M3-04 | [NEO-136](https://linear.app/neon-sprawl/issue/NEO-136) |
| E7M3-05 | [NEO-137](https://linear.app/neon-sprawl/issue/NEO-137) |
| E7M3-06 | [NEO-138](https://linear.app/neon-sprawl/issue/NEO-138) |
| E7M3-07 | [NEO-139](https://linear.app/neon-sprawl/issue/NEO-139) |
| E7M3-08 | [NEO-140](https://linear.app/neon-sprawl/issue/NEO-140) |
| E7M3-09 | [NEO-141](https://linear.app/neon-sprawl/issue/NEO-141) |
| E7M3-10 | [NEO-142](https://linear.app/neon-sprawl/issue/NEO-142) |
| E7M3-11 | [NEO-143](https://linear.app/neon-sprawl/issue/NEO-143) |
## Prototype Slice 3 freeze (E7M3-01)
### Faction catalog
| `FactionDef.id` | `displayName` | Standing band |
|-----------------|---------------|---------------|
| **`prototype_faction_grid_operators`** | Grid Operators | -100…100 (neutral 0) |
| **`prototype_faction_rust_collective`** | Rust Collective | -100…100 (neutral 0) |
### Quest content changes
| `QuestDef.id` | Rep / gate |
|---------------|------------|
| **`prototype_quest_operator_chain`** | **`completionRewardBundle.reputationGrants`**: **`prototype_faction_grid_operators`** **+15** (existing item + skill XP unchanged) |
| **`prototype_quest_grid_contract`** *(new)* | **`prerequisiteQuestIds`**: operator chain; **`factionGateRules`**: Grid Operators **`minStanding` 15**; objective **`inventory_has_item`** **`survey_drone_kit` ×1**; completion rep **Rust Collective +10** |
**Roster:** five quests total (four E7.M1 onboarding + one faction line). E7.M1 four-quest freeze expands under E7M3 CI gates (`PROTOTYPE_E7M3_QUEST_IDS` in `scripts/validate_content.py`).
**CI enforcement (NEO-133):** `scripts/validate_content.py` validates `content/factions/*_factions.json`, five-quest roster, faction cross-refs on gates and `reputationGrants`, E7M3 completion bundle freeze, and grid-contract shape.
## Source anchors
- Master plan: [`neon_sprawl_vision.plan.md`](../../../neon_sprawl_vision.plan.md) — Epic 7, faction reputation.
- Game design: [skills.md — Rep / story](../../../docs/game-design/skills.md) (character-wide faction rep).
- [Module dependency register](module_dependency_register.md)