Completes the rest of Sprint 28 on top of the earlier admin-scoped
a11y/skeleton pass (576f260):
- SeoService.resetToDefaults() now reads real bootstrap.seo.default /
branding instead of hardcoded placeholder text + a broken
/og-image.jpg reference; auto-reapplies via an effect() whenever
bootstrap (re)loads, same pattern as UiRuntimeFacade.
- New public/sitemap.xml (static baseline, documented per-tenant-dynamic
limitation) + public/robots.txt Sitemap directive and admin/editor
Disallow rules.
- Global prefers-reduced-motion override in styles.scss covering every
existing hover-transform/fade-in/shimmer animation in one place.
- New adminProducts/adminUsers/adminMonitoring/adminAnalytics
empty-state i18n keys (en/ru/hy) for this sprint's skeleton/empty-state
consistency fixes.
- docs/KNOWN-ISSUES.md: logged a newly-found, much larger pre-existing
gap (~178 missing adminXxx.* i18n keys across the whole admin
backoffice) - deferred to Sprint 29's translation validation, not
fixed here.
- docs/BACKEND.md: new item 17 (sitemap generation gap).
- docs/ADMIN.md, docs/SPRINT-PLAN.md: rewritten Sprint 28 sections to
describe the full, combined scope (both commits) instead of the
earlier admin-only framing.
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
9.6 KiB
Sprint Plan (working doc, delete after release)
Repo already past old "Sprint 19" (dashboard). Renumbering user's Sprint7+ roadmap to continue actual sequence: Sprint 20 = old "Sprint 7" (Categories) ... Sprint 30 = old "Sprint 17" (Final Release).
Pattern to follow (mirrors admin/products): models/, services/<x>-gateway.interface.ts + <x>-local.gateway.ts (IndexedDB via existing local-storage service), facade/, pages/, components/. Local-only until backend endpoint exists — log gap in docs/BACKEND.md.
Autonomy: no stop-and-ask except missing API contract / business decision / secrets / external config / legal / multi-valid-design-fork. Commit after each sprint, conventional commits, no push. Quality gate before marking sprint done: build, typecheck, lint (if configured), responsive check, a11y pass, docs updated, no dead code, arch:check green.
Notify user: from Sprint 20 (Categories) once product↔category link + admin categories CRUD exist, catalog can start receiving real items (currently admin-products already has categoryId field but no category source of truth — that's the point where "adding items to catalog" becomes real, not mocked dropdown).
Sprint 20 — Category Management ✅ done
- AdminCategory model (id, parentId, title, translations, slug, icon, image, seo, visible, order, draft/published status, soft-delete)
- AdminCategoriesGateway interface + local (in-memory, seeded from BackofficeDataService) gateway, mirrors products gateway
- AdminCategoriesFacade (signals, CRUD, tree ops, slug validation, draft recovery)
- Categories list page: indented tree, native HTML5 DnD reorder, visibility toggle, item counter, empty state, include-deleted filter + restore
- Category editor: name/slug (+ uniqueness validation), translations editor, icon field, image via MediaPickerComponent, SEO fields, breadcrumb preview
- Delete validation (blocked if has children or itemsCount>0) + soft-delete/restore
- Draft/publish workflow + localStorage draft recovery (mirrors Project Editor autosave) + unsaved-changes CanDeactivate guard (mirrors projectEditorDirtyGuard)
- Wired into admin routing (
app.routes.ts, replaced coming-soon placeholder) - Updated
docs/ADMIN.md(new Sprint 20 section),docs/BACKEND.md(categories gap rewritten with real field list) - [~] Responsive/a11y: reuses existing FormField/Input/Table/Button/EmptyState a11y wiring; live-browser click-through blocked by safety classifier on the guarded admin route (see below) — verified via tsc/build/arch:check only
- Commit:
feat(admin): complete category management - Note:
admin/products' category dropdown still uses its ownAdminProductsGateway.loadCategories(), not this new gateway — unification deferred to Sprint 21 (documented in BACKEND.md).
Sprint 21 — Product Management completion ✅ done
- Audit + add missing:
archived(soft, list filter + archive/restore action),barcode,variants(lightweight name|price|quantity),relatedProductIds(checkbox picker) - Wired products to real
AdminCategoriesGateway(AdminProductsLocalGatewaynow seeds fromAdminCategoriesLocalGateway, replacing its ownBackofficeDataServicecategory seed) - Gallery via
MediaPickerComponent(add/remove thumbnails); translation editor already existed (Sprint pre-19); preview (computed discounted price); infinite-scroll toggle on list (facade.loadMore()appends vs pagination) - Updated
docs/ADMIN.md(new Sprint 21 section),docs/BACKEND.md(item 6 rewritten with real field list) - Commit:
feat(admin): complete product management - Known trade-off: related-products picker sources from whatever page is currently loaded in
AdminProductsFacade.products(), not a full catalog search — documented in ADMIN.md, fine at current mock scale.
Sprint 22 — Media System hardening ✅ done
- Folder support (flat, filter-based), tags (edit + filter), search (already existed)
- Resize/compression on upload (canvas downscale + re-encode, raster only) + SVG script-sanitization + file-type/size validation with real surfaced errors
- Confirmed reuse: category images (20), product gallery (21), branding logo/compact-logo/favicon (22, newly wired). Static pages: no image fields (not a gap). Hero: no dedicated field exists.
- Storage abstraction documented (
MediaRepositoryabstract class was already the abstraction) - Commit:
feat(media): reusable media management - Scoped down from ticket: no interactive crop UI (compression/resize only); folders are a flat tag, not a real folder entity/hierarchy.
Sprint 23 — Orders (mock/local, flag backend gap) ✅ done
- AdminOrder model + local gateway (24 seeded synthetic orders, no real data source existed)
- List: search, status filter, pagination, CSV export
- Detail: customer/payment/shipping, itemized total, status timeline, change-status, refund request + cancel (confirm-gated), customer notes + internal notes, print invoice (window.print + @media print)
docs/ADMIN.md(new Sprint 23 section),docs/BACKEND.mditem 7 rewritten- Commit:
feat(admin): order management
Sprint 24 — Transactions (mock/local) ✅ done
- Payments/refunds/QR list, status, history (derived from Sprint 23's seeded orders), export, filters, search, retry failed, fraud flags, per-transaction audit log dialog
docs/ADMIN.md(new Sprint 24 section),docs/BACKEND.mditem 13 added- Commit:
feat(admin): transaction management
Sprint 25 — Users & Roles ✅ done
- Users/roles/permissions models (local, 4 built-in roles), marketplace vs office admin distinction
- Invitations, passwordless login confirmed already real (Telegram QR, AdminAuthService — linked not reimplemented), session/device manager (mocked), per-user audit trail
- Wired into Dashboard Quick Actions + new
/:lang/backoffice/usersroute docs/ADMIN.md(new Sprint 25 section),docs/BACKEND.mditem 14 added- Commit:
feat(admin): users and permissions
Sprint 26 — Monitoring ✅ done
- Audit/security/login/failed-login logs (unified event feed, category filter), API/error/warning feed, queue/webhook mock views, health page (reuses real Sprint 19 healthChecks)
docs/ADMIN.md(new Sprint 26 section),docs/BACKEND.mditem 15 added- Commit:
feat(admin): monitoring center
Sprint 27 — Analytics ✅ done
- Sales/revenue/orders/products/categories (real aggregation over mock order data), visitors/funnels/heatmaps (pending-backend badges, no fabricated data), sales-over-time bar chart, 7/30/90-day ranges, CSV export
docs/ADMIN.md(new Sprint 27 section),docs/BACKEND.mditem 16 added- Commit:
feat(admin): analytics dashboard
Sprint 28 — Marketplace Polish ✅ done
- Skeleton/empty-state consistency:
admin/products,admin/users,admin/monitoring,admin/analyticshad aloadingsignal but no loading/empty UI - wiredapp-skeleton/app-empty-state;admin/categories/admin/orders/admin/transactions/media library got the missing loading skeleton (already had empty-state);admin/dashboard's card component migrated its pre-primitive shimmer<div>toapp-skeleton - A11y: aria-label on every previously-unlabeled
<select>across admin/*; manual audit confirmedDialogComponentfocus trap/Escape/aria-modal already correct and no missing<img>alt text anywhere insrc/app - Animations: global
prefers-reduced-motionoverride added insrc/styles.scss(neutralizes all animation/transition durations + smooth-scroll) - SEO:
SeoService.resetToDefaults()now reads realbootstrap.seo.default/brandinginstead of hardcoded placeholder text + a broken/og-image.jpgreference; re-applies automatically on bootstrap (re)load - Sitemap/robots: new
public/sitemap.xml(static baseline, documented per-tenant-dynamic limitation) +public/robots.txtSitemap:directive and admin/editorDisallowrules - Responsive: confirmed
shared/ui/table's existingoverflow-x: autowrapper covers all admin tables; admin list pages already had per-feature breakpoints, extended consistently docs/ADMIN.mdnew Sprint 28 section (combined result of both commits below)- Found and logged (not fixed - Sprint 29 scope): ~178 missing
adminXxx.*i18n keys across the whole admin backoffice, seedocs/KNOWN-ISSUES.md - Commits:
refactor: marketplace release polish(admin a11y/skeleton pass), plus this session's follow-up completing SEO/sitemap/animations/dashboard-card/KNOWN-ISSUES - Known trade-off: no live Lighthouse/browser run available in this environment (same guarded-admin-route constraint noted in prior sprints) - SEO/a11y/animation fixes above are the manual-audit equivalent of what it would have flagged.
Sprint 29 — Release Candidate
- Dead code cleanup, remove TODOs/console logs/debug code, optimize imports/bundle/images/CSS, translation validation, build/type/lint validation, doc validation, arch review, CHANGELOG + release notes
- Commit:
chore: release candidate
Sprint 30 — Final Release
- Full verify pass (build, routing, responsive, translations, admin, marketplace, editor, media, login, bootstrap, APIs, security assumptions), final report
- Then (only after explicit go-ahead, push is a confirm-required action):
git push
Stop conditions (ask user)
- Real backend API contract needed (orders/transactions/users are local-mock by design per above — flagged, not blocking)
- Ambiguous business rule (e.g. category deletion policy specifics) not inferable from existing product-deletion pattern
- Credentials/external service config
- Legal/product-only decision
- Two equally valid architectures for same feature