Files
ruoyi-vue-pro/docs/education/migration/02-api-mapping.md

131 lines
28 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Legacy API Mapping
> Phase 0 static assessment generated on 2026-07-29. No build, test, application startup, PostgreSQL connection, or Flyway migration was executed during this assessment.
> Runtime mapping update 2026-08-01: EDU-027 keeps native Trade order/config contracts authoritative, EDU-028 keeps native Discount/Reward APIs authoritative, EDU-029 activates delivery, EDU-030 activates after-sale/Pay Refund, EDU-031 activates Member-backed brokerage, EDU-032 activates native Promotion Seckill, and EDU-033 activates native Promotion Combination activity/group/Trade Order contracts. Education adds no shadow commerce, refund, commission, or special-order API. Configured target Pay runtime, Bargain/Point and other special orders, legacy commerce/referral/settlement-proof mapping, fulfillment/revocation, and deployed checkout/refund/commission/promotion evidence remain open.
This Phase 0 artifact maps API families rather than all 342 operations. Endpoint-level method/path/request/response mapping remains required before implementing each family.
## Tenant resolution, identity, and student context
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/auth.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/features/tenant/locator.ts, /Users/tiku1/code/tiku-backend/apps/api/src/features/tenant/resolver.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** System + Member + framework tenant support with an Education context adapter
- **Reuse:** System TenantCommonApi/TenantApiImpl, TenantContextHolder, TenantSecurityWebFilter, Member/System authentication and UserTypeEnum, framework tenant injection and tenant-ignore only for explicitly authorized platform operations.
- **Migration conclusion:** decision complete; implementation pending EDU-004
- **Selected contract:** Public inputs are **Tenant Locator Claims**, not authenticated identity. Production browser routing derives a host-only claim from valid HTTP(S) `Origin`, falling back to `Referer`; both are forgeable by non-browser callers and provide browser UX consistency only. A supplied hostname may confirm that claim, and disagreement is a conflict. Headless clients use `tenantHandle`, explicitly defined as the target's unique System tenant `name` under a case-sensitive constrained public contract because no distinct stable Tenant Code exists. Legacy public `tenantName` is rejected rather than silently aliased.
- **Threat model:** Successful resolution returns tenant ID/display name and therefore permits available-tenant existence probing. Only unknown, disabled, and expired tenants are indistinguishable. Reuse public throttling/ingress controls and structured abuse metrics; a deployment requiring spoof resistance needs a future authenticated/signed locator, not trust in Origin/Referer or forwarding-header controls.
- **Normalization and compatibility:** Host identity is lowercase, trimmed, trailing-dot-free, bracket-free for IPv6, and independent of all ports. DNS hosts, IPv4, and IPv6 are accepted when valid; credentials, paths, multi-value input, malformed authorities, and unsupported schemes are rejected. Canonical `system_tenant.websites` values for this resolver are host-only. Scheme/path/port-bearing stored values do not silently normalize or match; configuration correction is required, or a separate Flyway/data ticket if automated correction is later approved.
- **Local activation:** Only `yudao.education.tenant-resolution.local-development-enabled=true` enables local/request-host fallback; default and absence are false, and profiles are not authoritative. With the flag true, code-less configured local-host resolution is allowed and an explicit handle takes precedence.
- **Authenticated context:** `/education/context` accepts only a Student Principal: an authenticated `LoginUser` with `userType == UserTypeEnum.MEMBER`. User and tenant IDs remain security/tenant-context derived. `TenantSecurityWebFilter` already fills a missing tenant from the authenticated principal, rejects principal/request-tenant mismatch, requires a tenant for non-ignored URLs, and validates tenant availability; EDU-004 preserves rather than duplicates these checks.
- **Ownership and seam:** Login-method metadata belongs to Member authentication, not System tenant metadata or Education. EDU-004 removes/deprecates Education `loginMethods` unless a minimal Member-owned interface is proven necessary. Retain generic System-owned `TenantCommonApi`; make lookup methods required and add focused `TenantApiImpl` contract tests. `EducationTenantController` remains the public claim-consistency/redaction adapter.
- **Exact public wire contract:** Framework business responses remain HTTP 200. Invalid/malformed/missing/local-forbidden claim is code `1005001003`, message `租户识别请求无效`, null data. Domain/handle or requested-host conflict is code `1005001008`, message `租户识别信息冲突`, null data. Unknown/disabled/expired is code `1005001004`, message `当前租户不可用`, null data, with identical shape. Success is code 0 and data contains only `tenantId` and `displayName`; never expose or echo handle, websites, expiry, package, status, private config, or login methods.
- **Required EDU-004 verification:** Education HTTP tests cover Origin resolution, Referer fallback, forged-header threat-model naming, malformed Origin, Origin/requested-host conflict, untrusted arbitrary hostname, explicit handle, legacy tenantName rejection, unavailable-state exact wire equivalence, host normalization, canonical/non-canonical website behavior, local flag false/true and precedence, domain/handle conflict, anonymous/ADMIN/MEMBER context, redaction, and abuse-control attachment/metrics where a reusable seam exists. System owns adapter contract tests; framework owns existing missing-tenant and authenticated mismatch tests.
- **Decision evidence:** [`issues/EDU-003-tenant-resolution-decision.md`](issues/EDU-003-tenant-resolution-decision.md). Static only; no production or database change was made.
## Student core learning loop
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/learning.module.ts:23-113, /Users/tiku1/code/tiku-backend/apps/api/src/features/learning/use-cases.ts, /Users/tiku1/code/tiku-backend/apps/api/src/features/learning/access.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Education
- **Reuse:** Education provider/adapter boundary, Member/System identity, database uniqueness and transactions, framework locks/idempotency only as supplements—not replacements—for atomic database claims.
- **Migration conclusion:** partially migrated
- **Contract gap:** Verified: commit ce02f8a contains committed access/core controllers, safe projections, and focused tests, while native provider/catalog and additional core-loop work are dirty; these statuses must be separated. Verified: native and Scalar providers disagree on malformed/absent options; QuestionCatalogService and SessionResponseAssembler can emit apparently valid empty options. Verified: submit idempotency performs check-then-insert rather than atomic initial reservation. Inference: core-loop completion and concurrency guarantees are not established.
- **Required verification:** Provider-neutral tests across Scalar and Java, browsing/collection/practice-create/restore safe projections, malformed/unavailable/unpublished fail-closed cases, cross-tenant cases, and PostgreSQL concurrent same-key/different-key submit tests.
- **Open decision:** Select the pilot-authoritative provider or require a provider-neutral contract; define valid option structure by question type and absent-option semantics; define atomic submit claim/crash recovery; decide entitlement contract before paid/private practice.
## Education catalog and question content
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/catalog.module.ts:74-138, /Users/tiku1/code/tiku-backend/apps/nest/tenant-content.module.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Education
- **Reuse:** Education Provider boundary, explicit CatalogScopeQuery, framework tenant context, Infra File public API for future assets.
- **Migration conclusion:** partially migrated
- **Contract gap:** Verified: current native reads intentionally run inside TenantUtils.executeIgnore and apply explicit scope predicates; this is a controlled manual-isolation boundary, not proof of a current leak. Verified: V4020 uses ordinary single-column foreign keys, so tenant-owned/public graph consistency is not enforced. Inference: every mapper needs audit and content admission needs composite constraints or equivalent enforcement.
- **Required verification:** Inventory every mapper, provider contract tests, invalid graph insert tests, malformed/unpublished tests, PostgreSQL Flyway syntax/resource-packaging checks, and runtime migration evidence only when executed.
- **Open decision:** Choose Scalar-only, native PostgreSQL, or explicit coexistence; define tenant_id=0 PUBLIC graph semantics and composite-key strategy; decide whether source RLS/functions/triggers are contractual.
## Auth, student profile, and extended learning
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/auth.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/profile.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/learning.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/features/profile/
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Member + System + Education, with Infra composition
- **Reuse:** Member/System auth and profile primitives, System/Infra notifications, Member points/levels where semantics match, Education-specific projections and authorization.
- **Migration conclusion:** pending migration
- **Contract gap:** Verified source inventory shows these are distinct required Phase 0 domains, not merely generic context or secondary engagement. Target ownership and compatibility are not established. Inference: the definition-of-done is unsupported until each endpoint/state family is classified.
- **Required verification:** Endpoint/API mapping, principal and tenant tests, profile redaction, progress/report compatibility, vocabulary state transitions, and explicit retired/product-decision checks.
- **Open decision:** For every Auth/Profile/extended Learning family, assign Member/System/Education/Infra ownership, compatibility requirement, data disposition, and phase; decide vocabulary, analytics, feedback, exam dates, notifications, points, and badges.
## Tenant education operations, appearance, integrations, secrets, and codes
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant-admin-classes.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant-admin-appearance.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant-admin-integrations.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant-admin-secrets.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/tenant-admin-codes.module.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Education + System + Member + Mall/Pay + Infra
- **Reuse:** System Tenant/RBAC/DataPermission/AdminUserApi, Member relationships, Mall/Pay/Member APIs, Infra secret/file/message/audit facilities.
- **Migration conclusion:** partially migrated — class/supervision, appearance, native Pay/System integration and ledgers, learning activation codes, native Mall Product/Coupon, and V4390V4450 normal Trade order/checkout/delivery/after-sale/brokerage/seckill/combination activation delivered
- **Delivered activation-code contracts:** Admin `GET /education/activation-code/batch/page`, `POST /batch`, `PUT /batch/{id}`, `POST /batch/{id}/generate`, `GET /code/page`, and `PUT /code/{id}/disable`; Member-only app `POST /education/activation-code/check` and `POST /education/activation-code/redeem`. Query/manage/generate permissions are independent. Generation returns plaintext once, while persistence and later reads expose only digest/mask. Redemption locks the code row and composes `EducationEntitlementService` with `sourceSystem=ACTIVATION_CODE`.
- **Delivered legacy Pay import contracts:** Pay-owned `POST /pay/legacy-account-import/import` requires App+Channel create permissions and maps one explicitly reviewed `tenant_collect` WeChat/Alipay manifest through native Pay services. `GET /pay/legacy-account-import/page` requires both query permissions and returns the tenant-filtered redacted audit. Same source-account/checksum replays; checksum conflicts, non-equivalent modes/providers, channel-family mismatch, ambiguous rotating keys, and unsafe Alipay endpoints fail closed. The existing Pay App Vben page owns the import modal.
- **Delivered native Pay transaction contracts:** Existing `/pay/order`, `/pay/refund`, and `/pay/notify` query/detail/export/callback contracts and the `pay/order/index`, `pay/refund/index`, and `pay/notify/index` Vben pages are reused. V4340 supplies tenant-scoped PostgreSQL order/extension/refund/notification tables and composite tenant foreign keys; callback processing retains channel-derived `TenantUtils` context and notification retries retain `@TenantJob` execution.
- **Delivered legacy transaction bridge:** `POST /pay/legacy-transaction-import/import` accepts one terminal, reconciled order/payment/refund manifest under `pay:legacy-transaction:import`; `GET /pay/legacy-transaction-import/page` exposes redacted tenant audit under `pay:legacy-transaction:query`. It requires an EDU-021 account mapping, exact cent/status/provider reconciliation, source UUID/checksum idempotency, and explicit optional native Member ID. It writes native Pay ledgers without SDK calls, callbacks, notifications, raw payloads, or error originals. The native order page owns the import/history modal.
- **Delivered native Transfer/Wallet contracts:** Existing `/pay/transfer`, `/pay/wallet`, `/pay/wallet-transaction`, `/pay/wallet-recharge`, and `/pay/wallet-recharge-package` controllers remain authoritative. V4360 activates empty tenant-scoped native ledgers and existing `pay/transfer/index`, `pay/wallet/balance/index`, and `pay/wallet/rechargePackage/index` pages. Five data objects use `TenantBaseDO`, Transfer sync retains `@TenantJob`, wallet locks include tenant ID, administrator reductions use conditional subtraction, and recharge refund has a dedicated permission. No legacy wallet balance is inferred.
- **Delivered native Product contracts:** Existing `/product/brand`, `/product/category`, `/product/property`, `/product/property/value`, `/product/spu`, `/product/comment`, `/product/favorite`, and `/product/browse-history` controllers remain authoritative. V4370 activates nine tenant-scoped Product tables and the existing SPU, Category, Brand, Property, and Comment Vben pages. Nine Product data objects use `TenantBaseDO`; PostgreSQL composite tenant references enforce the catalog graph. The legacy display-only `products` projection is not automatically imported.
- **Delivered native Coupon contracts:** Existing `/promotion/coupon-template`, `/promotion/coupon`, and app coupon controllers remain authoritative. V4380 activates tenant-scoped template/issued-instance persistence, Product SPU/category scope validation, Member lookup/issuance, registration issuance, expiry processing, and the existing template/record Vben pages. Both coupon records use `TenantBaseDO`; the template reference is tenant-qualified. Legacy code campaigns/redemptions are not automatically imported.
- **Delivered native Trade contracts:** Existing `/trade/order`, `/trade/config`, `/app-api/trade/order`, and `/app-api/trade/cart` controllers remain authoritative. V4390 activates tenant-scoped Order/Item/Log/Cart/Config persistence, native `TradeOrderApiImpl`, exact order/config permissions, and the existing Vben pages. Legacy aggregate orders are not automatically imported.
- **Delivered native checkout Promotion contracts:** Existing `/promotion/discount-activity`, `/promotion/reward-activity`, `DiscountActivityApi`, and `RewardActivityApi` remain authoritative. V4400 activates tenant-scoped Discount Activity/Product and Reward Activity persistence, exact action permissions, and the two existing Vben pages. Real empty API lookups are proven on PostgreSQL; no legacy campaigns are inferred.
- **Delivered native delivery contracts:** Existing `/trade/delivery/express`, `/trade/delivery/express-template`, `/trade/delivery/pick-up-store`, app delivery reads, and `TradeDeliveryPriceCalculator` remain authoritative. V4410 activates tenant-scoped company/template/rule/store persistence, Product/Order references, exact permissions, three existing Vben pages, and a real PostgreSQL express-fee calculation; no source delivery data is inferred.
- **Delivered native after-sale contracts:** Existing Member application/cancel/delivery reads, `/trade/after-sale/page`, `/get-detail`, `/agree`, `/disagree`, `/receive`, `/refuse`, `/refund`, Pay refund callback handling, and operation logs remain authoritative. V4420 supplies tenant-scoped persistence/references and exact permissions. Vben now sends `auditReason`, requires `refuseMemo`, shows the application `createTime`, and permission-guards every action.
- **Legacy refund mapping:** `commerce_refund_requests` and `commerce_refund_events` are aggregate UUID records without verified native Member, Order Item, Product/SKU, return-logistics, or Pay Refund identities. V4420 deliberately imports none; mapping follows explicit legacy Product/Member/Order Item reconciliation.
- **Delivered native brokerage contracts:** Existing app/admin relationship, eligibility, team/rank, commission-record, freeze/unfreeze/cancel, withdrawal/audit, Pay Transfer callback, and scheduled job contracts remain authoritative. V4430 supplies tenant-owned persistence, references, exact eight permissions, and corrected user/record/withdrawal pages. Immediate settlements now participate in time-range statistics.
- **Legacy referral/settlement mapping:** Source referral codes/leads/team edges/tracks/QR/CRM assignment and UUID settlement/item/proof/export rows lack verified native Member, Order, relationship, Pay Transfer, and evidence identities. V4430 deliberately imports none; they remain explicit mapping/import work rather than being treated as native-equivalent.
- **Delivered native Seckill contracts:** Existing `/promotion/seckill-config`, `/promotion/seckill-activity`, supporting app reads, Product lookups, atomic stock updates, and Trade Order seckill fields remain authoritative. V4440 supplies empty tenant-owned time/activity/product persistence, Product/Trade references, consistency triggers, exact nine permissions, and corrected activity/config pages. Duplicate SKU, price/stock overrun, invalid time/limit inputs, unsafe restoration, and deletion of an in-use slot fail closed.
- **Source Seckill disposition:** Repository-wide source inventory found no seckill capability. V4440 deliberately starts empty; ordinary products, coupons, and aggregate orders are not reinterpreted as activities.
- **Delivered native Combination contracts:** Existing `/promotion/combination-activity`, `/promotion/combination-record`, supporting app reads/jobs, Product/Member lookups, and Trade Order combination fields remain authoritative. V4450 supplies empty tenant-owned activity/product/record persistence, capacity and reference triggers, exact six permissions, and corrected activity/record pages. Duplicate/mismatched SKUs, price/time/limit errors, cross-activity heads, over-capacity joins, inconsistent orders, and deletion with records fail closed.
- **Source Combination disposition:** The source `combination` token is an education combination-question type, not group buying. V4450 deliberately starts empty; no content question, ordinary product, or aggregate order is reinterpreted as a promotion group.
- **Contract gap:** Native Pay, Product, Coupon, normal Trade order, Promotion discount/reward/seckill/combination, Trade delivery, Trade after-sale, and native Trade brokerage administration are operational. Production bulk export/runbooks, reviewed UUID-to-Member/opening-balance artifacts, explicit legacy commerce/referral/settlement-proof mapping, Bargain/Point and other special-order activation, provider settlement equivalence, XPay/Xunhu replacement, and generic credential encryption remain open. V4310 does not claim legacy activation-code data import. Domains remain System Tenant websites. Tenant PNVS, private encrypted secrets, fulfillment, refund-to-entitlement revocation, and other marketing surfaces remain separate.
- **Required verification:** Permission matrix, row-scope negatives, secret redaction/rotation, integration authorization, legacy import idempotency/audit, and cross-tenant tests. Pay/Coupon/Trade/Seckill/Combination tests are delivered through V4450, including composite after-sale/brokerage/special-order references, state/amount/stock/capacity validation, exact menus, real tenant-isolated service/statistics/concurrency reads and writes, and fail-closed adoption.
- **Open decision:** Compose payments through Pay, products/coupons/promotions/orders/refunds/commissions through Mall Product/Promotion/Trade, and auth providers through System/Member. Continue Bargain/Point and other Promotion families, explicit legacy commerce/referral/settlement-proof imports, production financial/order/refund runbooks, reviewed balances, non-equivalent provider replacement, private secret rotation, automatic fulfillment, and refund revocation separately. Activation codes remain Education-owned learning credentials composed with Mall SPU binding and the entitlement pipeline.
## Platform administration and governance
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/platform-admin-overview.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/platform-admin-permissions.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/platform-admin-*.module.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** System + Pay + Mall + Infra + CRM with Education extensions
- **Reuse:** System RBAC/DataPermission/AdminUserApi, authorized tenant-ignore mechanisms, Pay/Mall/Infra/CRM public APIs, audit/logging.
- **Migration conclusion:** pending migration
- **Contract gap:** Verified source surface is broader than one aggregated platform-admin row. Target seams exist, but object-level ownership, data scopes, and cross-tenant operation policy remain incomplete.
- **Required verification:** Permission matrix, platform-admin integration, cross-tenant negative, audit-redaction, billing/usage reconciliation, and alert/export tests.
- **Open decision:** Define separate Student App, Tenant Admin, Platform Admin, public, and internal policies; map each platform surface to System/Pay/Mall/Infra/CRM/Education or explicit retirement.
## Commercialization and growth
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/commerce-orders.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/commerce-payments.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/commerce-reconciliation.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/referral-growth.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/referral-crm.module.ts
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Mall + Pay + Member + CRM with Education binding
- **Reuse:** Mall/Pay DTO APIs, Member identity/entitlement/points, CRM services, Infra Job/MQ/audit.
- **Migration conclusion:** partially migrated — bounded Education binding/entitlement and activation redemption, native Pay ledgers, terminal legacy aggregate import, tenant-scoped native Mall Product persistence/UI, and native Promotion Coupon template/instance persistence/UI are proven; commerce orchestration remains open
- **Contract gap:** V4340 provides tenant-scoped native transaction ledgers, callbacks, retry tasks, and existing admin UI; V4350 adds bounded terminal import; V4360 activates native Transfer/Wallet ledgers; V4370 activates native Product; V4380 activates native coupon templates/instances without translating legacy code campaigns. These slices do not connect successful purchases to Education entitlements. Explicit legacy product/code-coupon import, production bulk migration, reviewed opening balances, automatic Pay/Mall fulfillment, refund-driven entitlement revocation, legacy activation-code import, Trade/other Promotion families, settlement reconciliation, commissions, dunning, and referral semantics remain unproven. One prior evidence path was malformed; corrected source location is /Users/tiku1/code/tiku-backend/apps/api/src/nest/commerce-reconciliation.module.ts.
- **Required verification:** Native order/refund/notify service, tenant-database, and terminal amount/status/provider mapping contracts are delivered. Production export/reconciliation evidence, callback/idempotency integration, entitlement lifecycle, settlement reconciliation, and education fulfillment contract tests remain required.
- **Open decision:** Keep V4310 activation codes separate from Mall Promotion coupons; confirm automatic issuance, callback, refund, reconciliation, coupon, commission, and referral contracts before broader commerce migration.
## Background processing, assets, and operational platform
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/worker/src/worker-jobs.ts, /Users/tiku1/code/tiku-backend/apps/worker/src/jobs/imports.ts, /Users/tiku1/code/tiku-backend/apps/worker/src/jobs/exports.ts, /Users/tiku1/code/tiku-backend/apps/asset-scanner/src/
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Infra platform plus owning domain modules
- **Reuse:** Infra Job, Redis MQ, File, locks, idempotency, logging, tracing, Excel utilities, tenant propagation.
- **Migration conclusion:** partially migrated
- **Contract gap:** Verified target primitives exist, but durable claim/lease/heartbeat/retry and malware-scanner equivalence are not proven. Education import/export business state is absent or not verified.
- **Required verification:** Concurrent claim/lease/recovery, retries/dead letters, scan fail-closed, file access, tenant propagation, audit, and deployment smoke tests.
- **Open decision:** Confirm Infra claim/lease semantics and scanner ownership, file privacy/retention, legacy asset migration/re-scan, and duplicate-safe at-least-once processing.
## Secondary learning, media, AI, and engagement
- **Legacy locations:** /Users/tiku1/code/tiku-backend/apps/api/src/nest/scoreline.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/video.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/nest/ai.module.ts, /Users/tiku1/code/tiku-backend/apps/api/src/features/profile/
- **Legacy authorization semantics to preserve:** tenant boundary, principal type, visibility, idempotency, state transitions, and redaction as applicable.
- **Target:** Education plus AI/Infra/Member/System
- **Reuse:** AI services, Infra File/notifications, Member points/levels, Education authorization/projections.
- **Migration conclusion:** product decision required
- **Contract gap:** Verified legacy capabilities exist, but target equivalence and priority are not established. These cannot remain an undifferentiated P3 bucket if Phase 0 must give every capability a disposition.
- **Required verification:** Per-capability contract, authorization, entitlement, export/redaction, and migration compatibility tests.
- **Open decision:** For each capability, assign Education, existing platform ownership, explicit retirement, or later product scope; decide entitlement and safe export/redaction requirements.