From c9765da311cb2d1bd026c42b2a6e45076dd37699 Mon Sep 17 00:00:00 2001 From: VinPropane Date: Mon, 30 Mar 2026 18:55:46 -0400 Subject: [PATCH] =?UTF-8?q?docs:=20PvP=20=C3=97=20combat=20engine=20integr?= =?UTF-8?q?ation=20(#4)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add pvp_combat_integration.md: single E5.M1 pipeline for PvE/PvP; E6.M1 gate before player-target hostility; stub for PvE-only milestones; shared kernel + profiles escape hatch; deny reason / telemetry notes; E6.M3 ordering after resolution. Register cross-cutting subsection; links from E5.M1, E6.M1, client_server_authority, contracts, decomposition README, tech_stack. Fix E6.M1 master plan link markup. Made-with: Cursor --- docs/architecture/tech_stack.md | 1 + docs/decomposition/README.md | 2 +- .../modules/E5_M1_CombatRulesEngine.md | 4 +- .../E6_M1_PvPEligibilityAndFlagState.md | 29 ++++++----- .../modules/client_server_authority.md | 2 + docs/decomposition/modules/contracts.md | 1 + .../modules/module_dependency_register.md | 6 ++- .../modules/pvp_combat_integration.md | 51 +++++++++++++++++++ 8 files changed, 81 insertions(+), 15 deletions(-) create mode 100644 docs/decomposition/modules/pvp_combat_integration.md diff --git a/docs/architecture/tech_stack.md b/docs/architecture/tech_stack.md index 58bcbc7..d628f3d 100644 --- a/docs/architecture/tech_stack.md +++ b/docs/architecture/tech_stack.md @@ -113,3 +113,4 @@ Revisit this document if: - [`docs/decomposition/README.md`](../decomposition/README.md) — epic/module decomposition - [`docs/decomposition/modules/contracts.md`](../decomposition/modules/contracts.md) — contract kinds (wire, content, telemetry), repo layout, versioning vs. register “Contract needed” - [`docs/decomposition/modules/client_server_authority.md`](../decomposition/modules/client_server_authority.md) — intents vs authoritative state; movement, camera, combat, economy ownership +- [`docs/decomposition/modules/pvp_combat_integration.md`](../decomposition/modules/pvp_combat_integration.md) — E5.M1 combat engine × E6.M1 PvP eligibility (single pipeline, deny reasons) diff --git a/docs/decomposition/README.md b/docs/decomposition/README.md index b5e6794..217ca75 100644 --- a/docs/decomposition/README.md +++ b/docs/decomposition/README.md @@ -9,7 +9,7 @@ This workspace contains detailed planning artifacts derived from the finalized m ## Folder Layout - `epics/` - One file per epic with implementation slices. -- `modules/` - [Contract definitions](modules/contracts.md), [client vs server authority](modules/client_server_authority.md), [full module dependency register](modules/module_dependency_register.md) (all epic modules), [per-module docs](modules/module_dependency_register.md#per-module-documentation), and interface notes. +- `modules/` - [Contract definitions](modules/contracts.md), [client vs server authority](modules/client_server_authority.md), [PvP × combat engine](modules/pvp_combat_integration.md), [full module dependency register](modules/module_dependency_register.md) (all epic modules), [per-module docs](modules/module_dependency_register.md#per-module-documentation), and interface notes. - `milestones/` - Phase-gated implementation tracks and pass/fail checklists. ## Working Rules diff --git a/docs/decomposition/modules/E5_M1_CombatRulesEngine.md b/docs/decomposition/modules/E5_M1_CombatRulesEngine.md index 483320d..722e3d4 100644 --- a/docs/decomposition/modules/E5_M1_CombatRulesEngine.md +++ b/docs/decomposition/modules/E5_M1_CombatRulesEngine.md @@ -15,10 +15,12 @@ Core tab-target combat resolution: valid actions against a locked target, hit resolution, cooldown and resource timing, and threat state as needed for prototype encounters. Presents readable outcomes in fixed isometric view and feeds XP awards through [E2.M2](E2_M2_XpAwardAndLevelEngine.md). +**PvP:** Single engine for PvE and PvP; player-target hostility **gates** on [E6.M1](E6_M1_PvPEligibilityAndFlagState.md). See [PvP and the combat engine](pvp_combat_integration.md). + ## Responsibilities - Combat state machine for tab-target flow (attacks, abilities per prototype scope). -- Validate and apply `CombatAction`; produce `CombatResolution` for UI and logs. +- Validate and apply `CombatAction`; produce `CombatResolution` for UI and logs (include **PvP deny reasons** when player targets are blocked; see [pvp_combat_integration.md](pvp_combat_integration.md)). - Integrate with targeting/interaction from **E1.M3** (target lock, valid target checks). - Award combat XP via E2.M2 integration where specified in slices. diff --git a/docs/decomposition/modules/E6_M1_PvPEligibilityAndFlagState.md b/docs/decomposition/modules/E6_M1_PvPEligibilityAndFlagState.md index 9575a6f..4d27b0c 100644 --- a/docs/decomposition/modules/E6_M1_PvPEligibilityAndFlagState.md +++ b/docs/decomposition/modules/E6_M1_PvPEligibilityAndFlagState.md @@ -2,12 +2,14 @@ ## Summary -| Field | Value | -|--------|--------| -| **Module ID** | E6.M1 | -| **Epic** | [Epic 6 — PvP Security](../epics/epic_06_pvp_security.md) | -| **Stage target** | Prototype | -| **Status** | Planned (see [dependency register](module_dependency_register.md)) | + +| Field | Value | +| ---------------- | ------------------------------------------------------------------ | +| **Module ID** | E6.M1 | +| **Epic** | [Epic 6 — PvP Security](../epics/epic_06_pvp_security.md) | +| **Stage target** | Prototype | +| **Status** | Planned (see [dependency register](module_dependency_register.md)) | + ## Purpose @@ -21,11 +23,13 @@ Server-enforced rules for whether player-versus-player combat is allowed: driven ## Key contracts -| Contract | Role | -|----------|------| -| `PvPFlagState` | Current opt-in and effective PvP capability for an actor in context. | -| `EligibilityRule` | Policy mapping from tier + context to allow/deny. | -| `PvPStateChanged` | Event for subscribers (UX, analytics, combat deny reasons). | + +| Contract | Role | +| ----------------- | -------------------------------------------------------------------- | +| `PvPFlagState` | Current opt-in and effective PvP capability for an actor in context. | +| `EligibilityRule` | Policy mapping from tier + context to allow/deny. | +| `PvPStateChanged` | Event for subscribers (UX, analytics, combat deny reasons). | + ## Module dependencies @@ -35,7 +39,7 @@ Server-enforced rules for whether player-versus-player combat is allowed: driven - **E6.M2** — ConsentAndRiskUxSignals: prompts and HUD indicators. - **E6.M3** — LossPenaltyAndAntiGriefRules: builds on eligibility and zone context. -- **Combat resolution** — E5.M1 (or dedicated PvP branch) consults eligibility before applying player-vs-player actions (integration detail per implementation). +- **Combat resolution** — [E5.M1](E5_M1_CombatRulesEngine.md) consults E6.M1 **in the same pipeline** before applying player-target hostility; see [PvP and the combat engine](pvp_combat_integration.md). ## Related implementation slices @@ -50,3 +54,4 @@ See Epic 6 **Slice 1 — Zone-based PvP flag core**: high-sec blocks player comb - Master plan: [`neon_sprawl_vision.plan.md`](../../../neon_sprawl_vision.plan.md) — Core Epic Map, Epic 6. - [Module dependency register](module_dependency_register.md) + diff --git a/docs/decomposition/modules/client_server_authority.md b/docs/decomposition/modules/client_server_authority.md index 990c501..325a591 100644 --- a/docs/decomposition/modules/client_server_authority.md +++ b/docs/decomposition/modules/client_server_authority.md @@ -52,6 +52,7 @@ Naming on the wire may use `*Command` or `*Intent` for client→server and `*Sta - **Never trust** client-supplied **damage**, **healing**, **crit rolls**, or **death** outcomes as source of truth. - **Trust** only what the client can **observe** as intent: which action, which target, timing within tolerance—then **recompute** everything server-side from `SkillDef`, stats, and combat state. +- **Player targets:** Before applying hostile effects to another player, consult [E6.M1](E6_M1_PvPEligibilityAndFlagState.md) in-process; one combat engine for PvE and PvP — [details](pvp_combat_integration.md). ### Economy, crafting, inventory, quests, zones, PvP @@ -79,4 +80,5 @@ Revisit when the first **Protobuf** game channel and a **multiplayer** milestone - [`docs/architecture/tech_stack.md`](../../architecture/tech_stack.md) — server-authoritative critical paths, intents vs state - [contracts.md](contracts.md) — wire vs content artifacts +- [PvP and the combat engine](pvp_combat_integration.md) — E5.M1 × E6.M1 integration shape - [Module dependency register](module_dependency_register.md) diff --git a/docs/decomposition/modules/contracts.md b/docs/decomposition/modules/contracts.md index b038627..b03bcf8 100644 --- a/docs/decomposition/modules/contracts.md +++ b/docs/decomposition/modules/contracts.md @@ -80,6 +80,7 @@ A module’s register **Status** can move to **Ready** when the contracts it **e - [tech stack](../../architecture/tech_stack.md) — Protobuf vs JSON spike, content validation, client/server split - [Client vs server authority](client_server_authority.md) — intents vs state, E1/E5 defaults, deferred networking choices +- [PvP and the combat engine](pvp_combat_integration.md) — E5.M1 gating with E6.M1, deny reasons - [Module dependency register](module_dependency_register.md) - [Decomposition README](../README.md) diff --git a/docs/decomposition/modules/module_dependency_register.md b/docs/decomposition/modules/module_dependency_register.md index 3c13292..6d566bd 100644 --- a/docs/decomposition/modules/module_dependency_register.md +++ b/docs/decomposition/modules/module_dependency_register.md @@ -2,7 +2,7 @@ Tracks cross-epic dependencies and contract readiness. Every **Depends On** module ID in this table has its own row (closed graph). -**Contract** means a stable boundary with a defined artifact (Protobuf wire message, JSON Schema content file, telemetry catalog entry, or server-internal type until promoted). See **[What a contract is](contracts.md)** for kinds, repo layout, and versioning. **Authority** (who owns `PositionState`, camera, combat outcomes): **[Client vs server authority](client_server_authority.md)**. +**Contract** means a stable boundary with a defined artifact (Protobuf wire message, JSON Schema content file, telemetry catalog entry, or server-internal type until promoted). See **[What a contract is](contracts.md)** for kinds, repo layout, and versioning. **Authority** (who owns `PositionState`, camera, combat outcomes): **[Client vs server authority](client_server_authority.md)**. **PvP × combat:** **[PvP and the combat engine](pvp_combat_integration.md)**. Fleshed-out scope, contracts, and integration notes live in **per-module documents** (see [Per-module documentation](#per-module-documentation)). @@ -65,6 +65,10 @@ Fleshed-out scope, contracts, and integration notes live in **per-module documen | E6.M3 | LossPenaltyAndAntiGriefRules | E6.M1, E9.M4 | PvPLossRule, SpawnProtectionState, GriefingStrike | Pre-production | Planned | | E6.M4 | RewardParityEnforcer | E3.M2, E5.M3, E7.M2 | RewardParityMap, EquivalentPowerBand, ParityViolationAlert | Prototype | Planned | +### Cross-cutting: combat and PvP eligibility + +When hostile actions can target **players**, [E5.M1 — CombatRulesEngine](E5_M1_CombatRulesEngine.md) **must** consult [E6.M1 — PvPEligibilityAndFlagState](E6_M1_PvPEligibilityAndFlagState.md) in the same server handling path before applying effects. **PvE-only** milestones may use a **stub** that denies all player-target hostility until PvP is enabled. Shape and deny reasons: **[PvP and the combat engine](pvp_combat_integration.md)**. + ### Epic 7 — Quest / Faction | Module ID | Module Name | Depends On | Contract Needed | Phase Required | Status | diff --git a/docs/decomposition/modules/pvp_combat_integration.md b/docs/decomposition/modules/pvp_combat_integration.md new file mode 100644 index 0000000..fe99936 --- /dev/null +++ b/docs/decomposition/modules/pvp_combat_integration.md @@ -0,0 +1,51 @@ +# PvP and the combat engine (#4) + +This doc fixes **how** [E6.M1 — PvPEligibilityAndFlagState](E6_M1_PvPEligibilityAndFlagState.md) connects to [E5.M1 — CombatRulesEngine](E5_M1_CombatRulesEngine.md): one pipeline vs a forked “PvP combat” module, and how denials surface on the wire. + +Complements [client_server_authority.md](client_server_authority.md) (authority) and [contracts.md](contracts.md) (artifact types). + +--- + +## Decision: single combat rules engine + +**Default for Neon Sprawl:** **E5.M1** is the **only** combat resolution engine for tab-target play. **Player vs player** uses the **same** code path as **player vs NPC** for formulas that should stay aligned (hit checks, cooldowns, resources, ability application), with **extra gating** when the target (or victims in an AoE) include **players**. + +**Do not** introduce a separate “PvP combat engine” for the prototype unless design later proves **irreconcilable** rule divergence. If that happens, prefer a **shared resolution kernel** (pure functions / shared module) plus **policy profiles** (PvE vs PvP) rather than two divergent engines. + +**Rationale:** One engine reduces duplicate bugs, keeps `CombatAction` / `CombatResolution` as a single wire story, and matches optional-PvP product goals (PvP is policy on top of the same abilities, not a different game). + +--- + +## Where E6.M1 plugs in + +- **When:** During **validation** of a `CombatAction` (or internal equivalent) **before** applying damage, debuffs, displacement, or other hostile effects to another **player** character. +- **Who calls whom:** **E5.M1** calls into **E6.M1** (or an abstraction it owns, implemented by E6.M1) — e.g. `CanApplyHostility(attacker, target, actionContext) → Allow | Deny(reason)`. +- **Consistency:** Use **current server** eligibility and zone policy for that tick/request; avoid stale client-only flags. If eligibility is cached per session, invalidate on zone transition and on `PvPStateChanged`. + +**NPC targets:** No E6.M1 check for ordinary PvE (unless a future rule ties NPC combat to zone policy — then call out explicitly). + +**Register note:** Epic 5 lists E5.M1 dependencies as E1.M3 and E2.M2 only. **Enabling player-target hostility** adds a **logical** dependency on E6.M1; PvE-only milestones may ship with a **stub** implementation that denies all player-target hostility until Epic 6 wiring lands. See [cross-cutting note in the dependency register](module_dependency_register.md#cross-cutting-combat-and-pvp-eligibility). + +--- + +## Deny reasons and telemetry + +PvP blocks must be **first-class** in combat outcomes, not silent failures: + +- Extend the combat deny / `CombatResolution` reason set (or parallel field) with stable codes such as: `pvp_forbidden_in_zone`, `attacker_pvp_not_eligible`, `target_pvp_not_eligible`, `pvp_consent_required`, `pvp_flag_mismatch` (exact names to be frozen when Protobuf enums are defined). +- Align high-signal events with [E9.M1](E9_M1_TelemetryEventSchema.md) (e.g. ability denied with reason) and Epic 6 hooks (`pvp_state_changed`, zone enter/exit) without double-counting. + +--- + +## E6.M3 and beyond + +**E6.M3** (loss, spawn protection, grief strikes) applies **after** hostility is **allowed** by E6.M1 and **resolved** by E5.M1 (e.g. on death in PvP context). Order: **eligibility → combat resolution → loss/anti-grief rules**. + +--- + +## Related docs + +- [E5.M1 — CombatRulesEngine](E5_M1_CombatRulesEngine.md) +- [E6.M1 — PvPEligibilityAndFlagState](E6_M1_PvPEligibilityAndFlagState.md) +- [Client vs server authority](client_server_authority.md) +- [Module dependency register](module_dependency_register.md)