diff --git a/docs/PROJECT_INDEX.md b/docs/PROJECT_INDEX.md index dcbb6be..21fab47 100644 --- a/docs/PROJECT_INDEX.md +++ b/docs/PROJECT_INDEX.md @@ -14,7 +14,7 @@ Every tenant has three surfaces on this one codebase: ## System overview - **Architecture**: `Component (container) → Facade → Domain Service → Repository/Provider (DI token, swappable mock↔API) → Mock | API`. Enforced by `npm run arch:check` (import boundaries + circular deps), not just convention. Full detail: [ARCHITECTURE.md](ARCHITECTURE.md), governance docs at `docs/architecture/foundation/**` (11 ADRs + 9 standards docs). -- **Seller Management** (optional, not built): typed foundation only — `modules.sellerManagement.enabled` gate on `BootstrapConfig`, disabled by default, zero effect on existing marketplaces. See ADR-011 and `docs/architecture/foundation/Seller-Management-Diagrams.md`. +- **Seller Management** (optional, not built): typed foundation + Phase 1 Backoffice placeholder UI only — `modules.sellerManagement.enabled` gate on `BootstrapConfig`, disabled by default, zero effect on existing marketplaces. Full capability doc: `docs/architecture/foundation/Seller-Management.md`. - **State**: Signals-based facades everywhere, no NgRx (ADR-007). - **Rendering**: Bootstrap JSON → Section Engine → Page Renderer → Widget Host → registered widget component (ADR-005). 100% lazy-loaded routes. - **Theming**: CSS custom properties per tenant, 3 theme stylesheets, never hardcoded hex in a component (ADR-008). Design system spec: [`DESIGN.md`](../DESIGN.md) (root of repo). diff --git a/docs/architecture/foundation/README.md b/docs/architecture/foundation/README.md index 1a7ca9a..558dc34 100644 --- a/docs/architecture/foundation/README.md +++ b/docs/architecture/foundation/README.md @@ -49,6 +49,7 @@ It is a platform runtime that must support unlimited tenants from one Angular ap ### Seller Management (optional, in preparation — not built) +- [Seller-Management.md](Seller-Management.md) — capability overview, start here - [ADR-011](adr/ADR-011-optional-seller-management-module.md) — decision record - [Seller-Management-Diagrams.md](Seller-Management-Diagrams.md) — hierarchy, bootstrap gate, type diagram - [Seller-Management-Domain-Models.md](Seller-Management-Domain-Models.md) — typed models, optional sellerId fields diff --git a/docs/architecture/foundation/Seller-Management.md b/docs/architecture/foundation/Seller-Management.md new file mode 100644 index 0000000..267e752 --- /dev/null +++ b/docs/architecture/foundation/Seller-Management.md @@ -0,0 +1,214 @@ +# Seller Management — Capability Documentation + +Status legend used throughout this document: + +- **Implemented** — exists in source on `feature/seller-management-foundation` today, verified (`tsc`, `arch:check`, or live browser test). +- **Planned** — has a typed contract or explicit ADR decision, but no code reads/writes it yet. +- **Future** — a concept named in this document for roadmap completeness only. No shape, contract, or decision exists yet. Do not build against this section without a new ADR. + +This document is the entry point. Detail lives in its companion docs: +[ADR-011](adr/ADR-011-optional-seller-management-module.md) (decision), +[Seller-Management-Diagrams.md](Seller-Management-Diagrams.md) (hierarchy/bootstrap-gate diagrams), +[Seller-Management-Domain-Models.md](Seller-Management-Domain-Models.md) (every type, field by field), +[Seller-Management-UX-Review.md](Seller-Management-UX-Review.md) (Phase 1 UI review). + +## 1. Overview + +Seller Management is an **optional platform capability** that would let one +marketplace host multiple independent sellers, each with their own +inventory/orders/branding, under one centralized administration. It is not +another tenant — a seller is a child scope beneath exactly one marketplace +(ADR-011). + +**Implemented today:** typed contracts for the whole hierarchy, a disabled- +by-default feature flag, one Backoffice page that explains the capability +and collects interest ("Request Access" / "Learn More"). **Nothing else** — +no CRUD, no backend, no seller-facing UI, no checkout/order behavior change. + +## 2. Architecture & Hierarchy — Implemented (types only) + +``` +Platform + └── Marketplace (tenant) — always present, backend-resolved (ADR-001) + └── Seller (optional) — 0..N per marketplace, backend-resolved (ADR-011) +``` + +Full diagram set: [Seller-Management-Diagrams.md](Seller-Management-Diagrams.md). + +Rules (ADR-011, enforced by review, not yet by any lint rule): +Marketplace is the sole primary tenant. Seller is a child scope, never a +sibling tier. The frontend never resolves seller identity itself — same +rule as tenant resolution. All seller-aware behavior must check one +capability flag, never scattered marketplace/seller conditionals. + +## 3. Marketplace — Implemented (existing, unchanged) + +The marketplace is the existing `TenantConfig` +(`shared/models/config/tenant.model.ts`) — resolved by the backend from +request Host, exactly as before this work started. Seller Management adds a +new `MarketplaceRef` (`core/sellers/models/marketplace-ref.model.ts`): a +minimal `{id, slug, name}` view of a marketplace *as seen from a seller +record*, not a replacement for `TenantConfig`. + +## 4. Seller — Implemented (types only) + +`Seller` (`core/sellers/models/seller.model.ts`): `id`, `marketplace: +MarketplaceRef`, `name`, `slug`, `status: SellerStatus`, optional `branding: +SellerBranding`, `createdAt`/`updatedAt`. No repository, gateway, facade, or +UI reads or writes this type yet — it exists so future CRUD work has a +settled shape instead of inventing one ad hoc. + +**Planned:** a `SellerRepository`/`SellerGateway` pair following the same +mock↔API DI-token pattern every other admin domain already uses +(`BACKEND.md` §8). **Future:** the actual CRUD screens, list/detail pages, +onboarding flow. + +## 5. Roles & Permissions — Implemented (types only) + +`SellerPermissionRole` (`core/sellers/models/seller-permissions.model.ts`): +four values — `marketplaceOwner`, `seller`, `sellerStaff`, `platformAdmin`. +This is a **separate vocabulary** from the existing `AdminRole` (Owner/ +Manager/Support/ReadOnly, `core/auth/models/permission.model.ts`) — not +merged, not wired into any guard. **No authentication or authorization +change exists anywhere in this work.** + +**Planned:** once a real permission model is designed, these roles gate +seller-scoped routes/actions the same way `AdminRole` gates admin routes +today (ADR-009 capability-guard pattern). **Future:** the actual +permission-to-action mapping, custom/finer-grained roles per marketplace. + +## 6. Future Roadmap + +### Feature Flags — Implemented (contract), Planned (real use) + +`BootstrapConfig.modules.sellerManagement.enabled` +(`shared/models/config/platform-modules.model.ts`), default `false` +(`DEFAULT_PLATFORM_MODULES_CONFIG`). Implemented as a typed contract read by +the Phase 1 page (`admin-seller-management-page.component.ts`); no backend +sets it to `true` anywhere today, so it is always `false` in practice. + +### Bootstrap — Implemented (contract), Planned (real data) + +`BootstrapConfig.modules?` and `BootstrapConfig.seller?` (`SellerConfig`, +`shared/models/config/seller.model.ts`) — both optional, both absent in +every real bootstrap response today. When a backend eventually resolves a +seller scope, it populates `seller`; until then this field simply doesn't +exist on the wire. + +### Future API — Future + +No endpoint exists. When built, it should follow `BACKEND.md`'s existing +mock↔API-gateway pattern (§8) rather than a new convention — this is a +statement of intent, not a designed contract. No URL, DTO, or status-code +behavior is decided. + +### Seller Storefronts — Future + +Concept: a seller-branded storefront view within a marketplace (e.g. a +seller's own product listing page reachable from the marketplace). **Not +designed.** No route, component, or URL scheme exists or is decided. + +### Seller Branding — Implemented (types only), Future (usage) + +`SellerBranding` (`core/sellers/models/seller-branding.model.ts`): logo, +banner, description, contacts, address, theme overrides — every field +optional. **Implemented as a type only.** Nothing renders it, nothing falls +back from it to marketplace branding — that precedence logic is **Future** +work, not yet designed. + +### Seller Ownership — Implemented (schema only), Future (logic) + +`sellerId?: string` added to `Item` (storefront), `AdminProduct`, and +`AdminOrder` — optional, absent means marketplace-owned (every existing +product/order today). **No code reads or writes this field anywhere.** +Ownership rules, transfer, and enforcement are **Future** work. + +### Checkout Modes — Future + +Concept: how checkout behaves when a cart contains items from multiple +sellers (e.g. single combined checkout vs. per-seller checkout flows). +**Not designed.** No decision exists on this; today every product is +marketplace-owned and checkout has exactly one flow, unchanged by this work. + +### Unified Orders / Split Orders — Future + +Concept: whether one customer purchase spanning multiple sellers becomes +one order record or splits into one order per seller. **Not designed.** +This is a real business decision (payments, refunds, and reporting all +depend on the answer) with no default assumed — explicitly listed as an +open question for whenever Seller Management moves past preparation. + +## 7. Migration & Compatibility + +### Why existing marketplaces remain unchanged + +- `modules.sellerManagement.enabled` defaults to `false` and no backend + sets it — every marketplace today gets identical behavior whether the + field is present-and-false or entirely absent from its bootstrap + response. +- `BootstrapConfig.modules` and `BootstrapConfig.seller` are optional + fields; no existing field's type changed. +- `sellerId?` on `Item`/`AdminProduct`/`AdminOrder` is optional; no + consumer of any of these three types needed updating, verified by + `tsc --noEmit` staying clean after each change. +- Zero components, facades, services, or routes branch on marketplace or + seller identity anywhere in this work (ADR-011 compliance requirement) — + there is no conditional to accidentally trigger. +- Every commit in this line of work was verified with `tsc --noEmit`, + `arch:check` (import boundaries + circular deps), and — for the UI + commits — a live browser pass, specifically to confirm no regression to + existing pages. + +## 8. Developer Notes + +- All seller domain types live in `core/sellers/models/` (mirrors + `core/products/models`, `core/auth/models`). Extend there, not ad hoc in + feature folders. +- When real seller-aware behavior is eventually built, gate it behind + `modules.sellerManagement.enabled` in one place (a capability guard, + ADR-009's pattern) — never scattered `if` checks on tenant/seller identity. +- The Phase 1 page (`features/admin/seller-management/`) is disposable — + it exists to communicate the capability to merchants, not as a + foundation to extend. Real seller CRUD UI should be planned fresh once + the backend contract exists, not bolted onto this page. + +## 9. Builder Notes + +The Project Editor / Marketplace Builder has **zero seller-awareness** +today. Its draft/publish model (`localStorage`-only, no backend write path +per `BACKEND.md` §1.10) is entirely marketplace-scoped. If/when a seller +needs their own builder-like surface (branding, storefront layout), it must +be designed as its own ADR — do not assume the existing builder can be +reused as-is for a seller scope without that review, since its facades and +schema (ADR-005, ADR-007) were built assuming exactly one config document +per marketplace. + +## 10. Backend Notes + +No backend implementation exists for any part of Seller Management. When +work begins, follow `BACKEND.md`'s established pattern exactly: a +`SellerRepository`/`SellerGateway` behind a DI token, `MockSellerGateway` +first, `ApiSellerGateway` swapped in later, same convention every other +admin domain in this codebase already uses (`BACKEND.md` §8). The typed +models in `core/sellers/models/` are the DTO shapes to implement against — +treat them as the contract, not a suggestion to redesign. + +## Diagrams + +```mermaid +graph LR + A["Types & feature flag
(this + prior 3 commits)"] -->|Implemented| B["Phase 1 UI
(Partners > Seller Management page)"] + B -->|Implemented| C["Backend contract decisions
(BACKEND.md gaps, own ADR)"] + C -->|Future| D["Seller CRUD + real gateway"] + D -->|Future| E["Seller Branding rendering
+ Storefronts"] + E -->|Future| F["Checkout Modes +
Unified/Split Orders"] + + classDef done fill:#2e7d3222,stroke:#2e7d32,color:inherit; + classDef future fill:#6b728022,stroke:#6b7280,color:inherit; + class A,B done; + class C,D,E,F future; +``` + +Rollout is strictly left-to-right — no stage after "Phase 1 UI" has started. +See [Seller-Management-Diagrams.md](Seller-Management-Diagrams.md) for the +hierarchy and bootstrap-gate diagrams (unchanged, still accurate).