From 4f08bbfce79699871f639315e9f0124fbd7c4da1 Mon Sep 17 00:00:00 2001 From: Justin Hernandez Date: Tue, 10 Mar 2026 17:41:26 -0700 Subject: [PATCH] update specs (#1837) --- .../native-consolidation/CONTRACTS.md | 1 + .../workstreams/native-consolidation/PLAN.md | 4 + .../workstreams/native-consolidation/SPEC.md | 87 ++++++++++++++----- .../plans/NC-01-phase-0-safety-rails.md | 9 +- .../plans/NC-02-phase-1-mrz-unification.md | 16 ++-- .../plans/NC-06-external-mrz-nfc-inventory.md | 71 +++++++++++++++ 6 files changed, 155 insertions(+), 33 deletions(-) create mode 100644 specs/projects/sdk/workstreams/native-consolidation/plans/NC-06-external-mrz-nfc-inventory.md diff --git a/specs/projects/sdk/workstreams/native-consolidation/CONTRACTS.md b/specs/projects/sdk/workstreams/native-consolidation/CONTRACTS.md index 3365589ed..4b759f2f2 100644 --- a/specs/projects/sdk/workstreams/native-consolidation/CONTRACTS.md +++ b/specs/projects/sdk/workstreams/native-consolidation/CONTRACTS.md @@ -69,3 +69,4 @@ The following are intentionally excluded from this file until automated tests en - ObjC shim-level selector parity tables - PassportReader native payload key-by-key parity - Analytics provider-specific integration behavior +- Cross-repo ownership between `selfapp`, `selfxyz/NFCPassportReader`, and `selfxyz/android-passport-nfc-reader` diff --git a/specs/projects/sdk/workstreams/native-consolidation/PLAN.md b/specs/projects/sdk/workstreams/native-consolidation/PLAN.md index 665974c63..d2ea87534 100644 --- a/specs/projects/sdk/workstreams/native-consolidation/PLAN.md +++ b/specs/projects/sdk/workstreams/native-consolidation/PLAN.md @@ -1,6 +1,8 @@ # Native Consolidation Phase 1 Plan (iOS MRZ) > Historical phase-specific plan. Active PR pickup now lives in [`plans/NC-02-phase-1-mrz-unification.md`](./plans/NC-02-phase-1-mrz-unification.md). Keep this file for implementation detail history and validation notes. +> +> This file documents the repo-local `app/ios` and `packages/mobile-sdk-alpha/ios/SelfSDK` MRZ wrapper consolidation that shipped in PR #1823. It is not the current decision record for cross-repo MRZ/NFC ownership; that follow-up now lives under [`plans/NC-06-external-mrz-nfc-inventory.md`](./plans/NC-06-external-mrz-nfc-inventory.md). ## Objective @@ -91,6 +93,8 @@ Open a follow-up to evaluate migrating the shared helpers into `self-sdk-swift` - Move `MrzScanEngine`, `MrzOcrCorrection`, `MrzResultMapper` into self-sdk-swift - Make both RN consumers import from self-sdk-swift instead of local copies +This future work is now blocked on the external inventory and owner handoff in NC-06. + ## Guardrails - No JS bridge surface changes in Phase 1. diff --git a/specs/projects/sdk/workstreams/native-consolidation/SPEC.md b/specs/projects/sdk/workstreams/native-consolidation/SPEC.md index 6fdfc42ca..ac2ec4bcf 100644 --- a/specs/projects/sdk/workstreams/native-consolidation/SPEC.md +++ b/specs/projects/sdk/workstreams/native-consolidation/SPEC.md @@ -3,7 +3,7 @@ > Last updated: 2026-03-10 > Owner: SDK Platform > Parent: [SDK Overview](../../OVERVIEW.md) -> Status: In Progress (Phase 0 Done, Phase 1 Done, Phase 2 Done, Phases 3-4 Ready) +> Status: In Progress (Phase 0 Done, Phase 1 Done, Phase 2 Done, external inventory handoff ready, local Phases 3-4 pending) ## North Star @@ -13,12 +13,13 @@ ## Why This Exists -Current native code is duplicated across multiple package/app surfaces, especially on iOS: +Current native code is duplicated across multiple package/app surfaces, especially on iOS, and some of the source material still lives outside this repo: - MRZ camera stack duplicated between app and SDK variants. - Passport reader bridge duplicated with partial behavioral divergence. - ObjC bridge shims duplicated with mostly naming-only changes. - State/copy mappings duplicated across scanner UIs. +- Android and Swift dependency repos still contain overlapping MRZ/NFC implementations that can drift from the local wrappers. This creates drift risk, review overhead, and slow bug-fix propagation. @@ -28,27 +29,50 @@ This creates drift risk, review overhead, and slow bug-fix propagation. - Rewriting host app business logic in TypeScript as part of this effort. - Android architecture rewrites unrelated to MRZ/NFC duplication. - Re-doing Android MRZ consolidation already shipped in RN test app (PR #1817). +- Deciding the final cross-repo MRZ/NFC architecture without the external-repo inventory and owner sign-off. ## Consolidation Inventory ### High-value duplicates -| Area | Primary Files | Current Risk | -| ------------------------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------- | -| iOS MRZ scanner module/view pipeline | `app/ios/MRZScannerModule.swift`, `app/ios/LiveMRZScannerView.swift`, `app/ios/MRZScanner.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfMRZScannerModule.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfLiveMRZScannerView.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfMRZScanner.swift` | High drift risk | -| iOS PassportReader bridge | `app/ios/PassportReader.swift`, `app/ios/PassportReader.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.m` | High regression risk if deleted blindly | -| RN test app MRZ UI mapping constants | `packages/rn-sdk-test-app/ios/SelfRNTestApp/SelfMRZScannerModule.swift`, `packages/kmp-sdk-test-app/composeApp/src/iosMain/kotlin/xyz/self/testapp/screens/MrzScanScreen.ios.kt` | Medium (UX drift) | +| Area | Primary Files | Current Risk | +| --------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------- | +| iOS MRZ scanner module/view pipeline | `app/ios/MRZScannerModule.swift`, `app/ios/LiveMRZScannerView.swift`, `app/ios/MrzScanEngine.swift`, `app/ios/MrzOcrCorrection.swift`, `app/ios/MrzResultMapper.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfMRZScannerModule.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfLiveMRZScannerView.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/MrzScanEngine.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/MrzOcrCorrection.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/MrzResultMapper.swift` | Local drift reduced; cross-repo drift remains | +| iOS PassportReader bridge | `app/ios/PassportReader.swift`, `app/ios/PassportReader.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.swift`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.m` | High regression risk if deleted blindly | +| RN test app MRZ UI mapping constants | `packages/rn-sdk-test-app/ios/SelfRNTestApp/SelfMRZScannerModule.swift`, `packages/kmp-sdk-test-app/composeApp/src/iosMain/kotlin/xyz/self/testapp/screens/MrzScanScreen.ios.kt` | Medium (UX drift) | +| External Android MRZ + NFC sample stack | `app/android/android-passport-nfc-reader/app/src/main/java/example/jllarraz/com/passportreader/mlkit/OcrMrzDetectorProcessor.kt`, `app/android/android-passport-nfc-reader/app/src/main/java/example/jllarraz/com/passportreader/ui/activities/CameraActivity.kt`, `app/android/android-passport-nfc-reader/app/src/main/java/example/jllarraz/com/passportreader/utils/NFCDocumentTag.kt`, `app/android/android-passport-nfc-reader/app/src/main/java/example/jllarraz/com/passportreader/utils/PassportNFC.kt` | High unknowns until inventoried | ### Android status (explicit) - RN test app Android MRZ consolidation is complete (PR #1817; `SelfMrzParser.kt` removed, scanner delegated to `CameraMrzBridgeHandler`). -- This initiative is primarily iOS-focused unless new Android duplication is identified. +- `app/android/android-passport-nfc-reader` is a checked-out clone of `selfxyz/android-passport-nfc-reader` on `main` at `63c846b`; it still contains both ML Kit MRZ OCR and JMRTD-based NFC reading logic. +- `app/android/react-native-passport-reader` remains a separate Android NFC bridge with BAC/PACE/session logic and analytics hooks. +- This initiative stays locally iOS-heavy, but final deletion/guardrail work cannot assume Android is already clean. ### Medium-value duplicates -| Area | Primary Files | Current Risk | -| ---------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------- | -| ObjC bridge shim duplication | `app/ios/MRZScannerModule.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfMRZScannerModule.m`, `app/ios/PassportReader.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.m` | Low runtime risk, medium maintenance cost | +| Area | Primary Files | Current Risk | +| ------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------- | +| ObjC bridge shim duplication | `app/ios/MRZScannerModule.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/SelfMRZScannerModule.m`, `app/ios/PassportReader.m`, `packages/mobile-sdk-alpha/ios/SelfSDK/PassportReader.m` | Low runtime risk, medium maintenance cost | +| Swift helper overlap outside app/sdk | `packages/self-sdk-swift/Sources/SelfSdkSwift/Helpers/MrzCameraHelper.swift`, `packages/self-sdk-swift/Sources/SelfSdkSwift/Helpers/NfcPassportHelper.swift`, external `selfxyz/NFCPassportReader` dependency | Medium; ownership split is unclear | + +## Ownership Split + +- Local wrapper consolidation in `selfapp` is complete through PR #1823 for MRZ and through NC-03 for `PassportReaderCore`. +- Cross-repo MRZ/NFC consolidation is now a separate owner track. Seshanth owns the remaining MRZ/NFC consolidation work that spans `selfapp`, `NFCPassportReader`, and `android-passport-nfc-reader`. +- This workstream will not implement further MRZ/NFC consolidation beyond documentation, inventory, and parity notes unless ownership changes explicitly. +- Until Seshanth's consolidation plan lands, this workstream should only perform documentation, parity, and low-risk cleanup. Do not delete local MRZ/NFC code based on repo-local evidence alone. + +## External Source Inventory + +These repos or checked-out mirrors may still contain source-of-truth logic that affects consolidation decisions: + +| Surface | Location | What it currently appears to own | Notes | +| ------------------------------ | --------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------ | +| iOS NFC dependency | `selfxyz/NFCPassportReader` (referenced by `app/ios/Podfile` and `packages/self-sdk-swift/Package.swift`) | NFC passport reading runtime, display/progress messaging, crypto/auth details | Not vendored as editable source in this repo; treat as an external dependency during consolidation planning. | +| Android passport reader sample | `selfxyz/android-passport-nfc-reader` (`app/android/android-passport-nfc-reader`) | ML Kit MRZ OCR, camera activity flow, JMRTD BAC/PACE/NFC reading, certificate verification helpers | Needs explicit inventory before any "single Android source of truth" claim. | +| Legacy RN Android NFC bridge | `app/android/react-native-passport-reader` | React Native Android NFC bridge, BAC/PACE fallback, analytics/session hooks | May share behavior with app Android and should be part of the audit even if it is not the final owner. | +| Swift companion helpers | `packages/self-sdk-swift/Sources/SelfSdkSwift/Helpers/` | KMP-oriented MRZ and NFC helper implementations | Current repo-local source for KMP iOS helpers, but not yet the declared single source for app/mobile-sdk-alpha wrappers. | ## Design Principles @@ -66,13 +90,14 @@ This creates drift risk, review overhead, and slow bug-fix propagation. ## Backlog -| ID | Title | Status | Priority | Depends On | Plan | PR | -| ----- | -------------------------------------------------- | ------ | -------- | ---------- | ---------------------------------------------------------------------------------------------------- | ----- | -| NC-01 | Phase 0 safety rails and bridge contract baselines | Done | High | - | [plans/NC-01-phase-0-safety-rails.md](./plans/NC-01-phase-0-safety-rails.md) | #1822 | -| NC-02 | Phase 1 MRZ core unification and build validation | Done | High | NC-01 | [plans/NC-02-phase-1-mrz-unification.md](./plans/NC-02-phase-1-mrz-unification.md) | #1823 | -| NC-03 | Phase 2 PassportReader parity bridge | Done | High | NC-02 | [plans/NC-03-phase-2-passport-reader-parity.md](./plans/NC-03-phase-2-passport-reader-parity.md) | - | -| NC-04 | Phase 3 ObjC shim cleanup | Ready | Medium | NC-03 | [plans/NC-04-phase-3-shim-cleanup.md](./plans/NC-04-phase-3-shim-cleanup.md) | - | -| NC-05 | Phase 4 deletion and CI guardrails | Ready | Medium | NC-04 | [plans/NC-05-phase-4-deletions-and-guardrails.md](./plans/NC-05-phase-4-deletions-and-guardrails.md) | - | +| ID | Title | Status | Priority | Depends On | Plan | PR | +| ----- | --------------------------------------------------- | ------ | -------- | ------------ | ---------------------------------------------------------------------------------------------------- | ----- | +| NC-01 | Phase 0 safety rails and bridge contract baselines | Done | High | - | [plans/NC-01-phase-0-safety-rails.md](./plans/NC-01-phase-0-safety-rails.md) | #1822 | +| NC-02 | Phase 1 MRZ core unification and build validation | Done | High | NC-01 | [plans/NC-02-phase-1-mrz-unification.md](./plans/NC-02-phase-1-mrz-unification.md) | #1823 | +| NC-03 | Phase 2 PassportReader parity bridge | Done | High | NC-02 | [plans/NC-03-phase-2-passport-reader-parity.md](./plans/NC-03-phase-2-passport-reader-parity.md) | - | +| NC-06 | External MRZ/NFC source inventory and owner handoff | Ready | High | NC-03 | [plans/NC-06-external-mrz-nfc-inventory.md](./plans/NC-06-external-mrz-nfc-inventory.md) | - | +| NC-04 | Phase 3 ObjC shim cleanup | Ready | Medium | NC-03, NC-06 | [plans/NC-04-phase-3-shim-cleanup.md](./plans/NC-04-phase-3-shim-cleanup.md) | - | +| NC-05 | Phase 4 deletion and CI guardrails | Ready | Medium | NC-04, NC-06 | [plans/NC-05-phase-4-deletions-and-guardrails.md](./plans/NC-05-phase-4-deletions-and-guardrails.md) | - | Allowed statuses: `Ready`, `In Progress`, `Blocked`, `Deferred`, `Done` @@ -83,6 +108,7 @@ Allowed statuses: `Ready`, `In Progress`, `Blocked`, `Deferred`, `Done` | [plans/NC-01-phase-0-safety-rails.md](./plans/NC-01-phase-0-safety-rails.md) | NC-01 | Done | | [plans/NC-02-phase-1-mrz-unification.md](./plans/NC-02-phase-1-mrz-unification.md) | NC-02 | Done | | [plans/NC-03-phase-2-passport-reader-parity.md](./plans/NC-03-phase-2-passport-reader-parity.md) | NC-03 | Done | +| [plans/NC-06-external-mrz-nfc-inventory.md](./plans/NC-06-external-mrz-nfc-inventory.md) | NC-06 | Ready | | [plans/NC-04-phase-3-shim-cleanup.md](./plans/NC-04-phase-3-shim-cleanup.md) | NC-04 | Ready | | [plans/NC-05-phase-4-deletions-and-guardrails.md](./plans/NC-05-phase-4-deletions-and-guardrails.md) | NC-05 | Ready | @@ -92,6 +118,7 @@ Allowed statuses: `Ready`, `In Progress`, `Blocked`, `Deferred`, `Done` - [ ] Every open phase has a linked plan file - [ ] Conflicting implementation directions are reconciled in this file - [ ] CONTRACTS.md stays aligned with the active phase +- [ ] External repo ownership and source-of-truth assumptions are documented before deletion work starts ## Testing Strategy @@ -152,6 +179,10 @@ MRZ scanning requires a camera. NFC reading requires hardware. These cannot be a The RN test app MRZ consolidation shipped without baseline tests. It relied on build verification and manual Android testing. iOS manual testing is still pending. The risk was acceptable because the RN test app is not production, but this approach does not scale to `app/` and `mobile-sdk-alpha/` consolidation. Phase 0 retroactively covers the RN test app contracts so future regressions are caught. +### Lesson from Local MRZ Wrapper Consolidation (PR #1823) + +PR #1823 reduced duplication between `app/ios` and `packages/mobile-sdk-alpha/ios/SelfSDK/` by extracting identical helper files (`MrzScanEngine.swift`, `MrzOcrCorrection.swift`, `MrzResultMapper.swift`) and keeping wrapper-specific UI/module naming local. That closed the repo-local wrapper gap, but it did not prove that `selfapp` is the global source of truth for MRZ/NFC behavior across external Swift/Android repos. + ## Phased Plan ### Phase 0 — Baseline + Safety Rails @@ -273,6 +304,9 @@ The RN test app MRZ consolidation shipped without baseline tests. It relied on b **Goal:** Collapse ObjC shim duplication and prepare deprecations. +**Precondition note:** Do not start Phase 3 until NC-06 records whether any external consumer still relies on legacy names, selectors, or wrapper-local behavior. +**Scope note:** Phase 3 does not include new MRZ/NFC consolidation work. That track is reserved for Seshanth. + **Implementation direction:** - Keep only required ObjC bridge files; convert redundant shims to generated/templated or delete where Swift-only exposure is sufficient. @@ -296,6 +330,9 @@ The RN test app MRZ consolidation shipped without baseline tests. It relied on b **Goal:** Delete deprecated duplicate files and lock consolidation. +**Precondition note:** Deletion is blocked on NC-06. External repos can still be the effective owner of MRZ/NFC behavior even when this repo's wrappers look redundant. +**Scope note:** Do not use Phase 4 to absorb or replace Seshanth's MRZ/NFC consolidation work. Only clean up code proven redundant after his track resolves ownership. + **Implementation direction:** - Remove old duplicated scanner/passport files that are no longer referenced. @@ -320,8 +357,9 @@ The RN test app MRZ consolidation shipped without baseline tests. It relied on b 1. PR A: Phase 0 safety rails + baseline tests. 2. PR B: Phase 1 MRZ core unification only. 3. PR C: Phase 2 PassportReader parity and shared core. -4. PR D: Phase 3 shim cleanup. -5. PR E: Phase 4 deletions and CI guardrails. +4. PR D: NC-06 external MRZ/NFC inventory and ownership handoff. +5. PR E: Phase 3 shim cleanup. +6. PR F: Phase 4 deletions and CI guardrails. Do not combine PR C with B; PassportReader carries higher regression risk. @@ -341,10 +379,17 @@ Do not combine PR C with B; PassportReader carries higher regression risk. - **Risk:** Consolidation ships without proving behavioral equivalence. - **Mitigation:** Layer 1 tests are a merge gate. Layer 4 manual sign-off is required in every consolidation PR. Lesson learned from PRs #1817/#1821 — don't repeat "consolidate first, test later." +- **Risk:** This repo deletes or freezes code that is still effectively sourced from `NFCPassportReader` or `android-passport-nfc-reader`. + - **Mitigation:** NC-06 inventories those repos before Phase 3/4. Any cross-repo behavior ownership decision must be explicit, not inferred from local wrappers. + +- **Risk:** The workstream spec causes parallel ownership conflicts by implying local MRZ/NFC implementation work is still up for grabs. + - **Mitigation:** Treat MRZ/NFC consolidation implementation as Seshanth-owned. This spec only tracks local parity state, external inventory, and cleanup preconditions. + ## Definition of Done (Initiative) -- [x] One canonical MRZ scanner implementation used by app/sdk wrappers. +- [x] App/mobile-sdk-alpha MRZ wrappers use the same helper structure merged in PR #1823. - [ ] One canonical PassportReader implementation with parity-preserving wrappers. +- [ ] External MRZ/NFC source inventory is documented and ownership is assigned. - [ ] Duplicate ObjC shims minimized. - [ ] Legacy duplicate files deleted. - [ ] All Layer 1-3 tests green across affected targets. diff --git a/specs/projects/sdk/workstreams/native-consolidation/plans/NC-01-phase-0-safety-rails.md b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-01-phase-0-safety-rails.md index 60520f787..9d0b89988 100644 --- a/specs/projects/sdk/workstreams/native-consolidation/plans/NC-01-phase-0-safety-rails.md +++ b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-01-phase-0-safety-rails.md @@ -1,7 +1,7 @@ # Phase 0 Safety Rails and Contract Baselines > Last updated: 2026-03-10 -> Status: Ready +> Status: Done - Workstream: native-consolidation - Backlog IDs: NC-01 @@ -53,10 +53,11 @@ yarn workspace @selfxyz/rn-sdk-test-app test --watchman=false ## Definition of Done -- [ ] Layer 1 tests exist and pass -- [ ] CONTRACTS.md exists and is linked -- [ ] Backlog row updated +- [x] Layer 1 tests exist and pass +- [x] CONTRACTS.md exists and is linked +- [x] Backlog row updated ## Status Log - 2026-03-10: Created during spec refactor. +- 2026-03-10: Marked done to match merged Phase 0 safety-rail work in PR #1822. diff --git a/specs/projects/sdk/workstreams/native-consolidation/plans/NC-02-phase-1-mrz-unification.md b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-02-phase-1-mrz-unification.md index ea7d4bc8e..e37d597ed 100644 --- a/specs/projects/sdk/workstreams/native-consolidation/plans/NC-02-phase-1-mrz-unification.md +++ b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-02-phase-1-mrz-unification.md @@ -1,7 +1,7 @@ # Phase 1 MRZ Core Unification and Validation > Last updated: 2026-03-10 -> Status: In Progress +> Status: Done - Workstream: native-consolidation - Backlog IDs: NC-02 @@ -11,14 +11,13 @@ ## Why -- MRZ duplication is the current active phase in this workstream. +- MRZ duplication was the active local phase in this workstream and shipped in PR #1823. - The earlier plan exists, but pickup should no longer require reading a giant phase narrative. ## Scope -- Finish MRZ wrapper consolidation work already in flight. -- Complete remaining build validation and status reconciliation. -- Record the chosen canonicalization approach in one place. +- Record the merged MRZ wrapper consolidation state in one place. +- Reconcile status and validation notes after PR #1823. ## Out of Scope @@ -55,10 +54,11 @@ yarn workspace @selfxyz/rn-sdk-test-app test --watchman=false ## Definition of Done -- [ ] Remaining iOS build validation completed -- [ ] `SPEC.md` and plan agree on the canonicalization approach -- [ ] Backlog row updated +- [x] Remaining iOS build validation completed or explicitly called out +- [x] `SPEC.md` and plan agree on the canonicalization approach +- [x] Backlog row updated ## Status Log - 2026-03-10: Created to replace implicit "current phase" pickup. +- 2026-03-10: Marked done after PR #1823 merged; future cross-repo MRZ follow-up moved to NC-06. diff --git a/specs/projects/sdk/workstreams/native-consolidation/plans/NC-06-external-mrz-nfc-inventory.md b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-06-external-mrz-nfc-inventory.md new file mode 100644 index 000000000..8c39ff338 --- /dev/null +++ b/specs/projects/sdk/workstreams/native-consolidation/plans/NC-06-external-mrz-nfc-inventory.md @@ -0,0 +1,71 @@ +# External MRZ/NFC Source Inventory and Owner Handoff + +> Last updated: 2026-03-10 +> Status: Ready + +- Workstream: native-consolidation +- Backlog IDs: NC-06 +- Owner: SDK Platform for documentation, Seshanth for MRZ/NFC consolidation implementation +- Branch: TBD +- PR: TBD + +## Why + +- Local wrapper consolidation is no longer the main unknown. +- Remaining MRZ/NFC risk is that source-of-truth logic still spans external repos and checked-out mirrors. +- Phase 3 and Phase 4 should not delete code based only on repo-local evidence. +- The purpose of this plan is to support Seshanth's track, not to replace or absorb it. + +## Scope + +- Inventory MRZ and NFC logic that lives outside the local `app/ios` and `packages/mobile-sdk-alpha/ios/SelfSDK` wrappers. +- Record which repo currently owns each behavior: OCR/parsing, camera UX state mapping, MRZ-key derivation, NFC BAC/PACE flow, certificate serialization, analytics/session hooks. +- Update `SPEC.md` and `CONTRACTS.md` with explicit ownership notes and any new constraints. +- Preserve a clear boundary: this plan does not execute consolidation changes that belong to Seshanth. + +## Out of Scope + +- Rewriting the external repos +- Deleting local wrappers +- Changing bridge contracts + +## Files to Modify + +- `specs/projects/sdk/workstreams/native-consolidation/SPEC.md` +- `specs/projects/sdk/workstreams/native-consolidation/CONTRACTS.md` +- optional handoff notes if a follow-up spec is needed + +## Files Not to Modify + +- `app/ios/**` +- `packages/mobile-sdk-alpha/ios/SelfSDK/**` +- external repo runtime code unless this plan is replaced by an implementation PR + +## Preconditions + +- NC-03 is done and the current local parity state is documented. + +## Implementation Notes + +- Treat `selfxyz/NFCPassportReader` as an external dependency even if only referenced indirectly in this repo. +- Use the checked-out mirror at `app/android/android-passport-nfc-reader` as the local evidence source for Android external logic. +- If ownership is still ambiguous after the inventory, document the ambiguity and block deletion work instead of guessing. +- If Seshanth provides a completed consolidation plan or merged implementation later, update this spec to reference that work instead of creating a parallel local plan. + +## Validation + +```bash +git -C app/android/android-passport-nfc-reader rev-parse --short HEAD +rg -n "MRZ|mrz|BAC|PACE|PassportReader|NFC" app/android/android-passport-nfc-reader app/android/react-native-passport-reader packages/self-sdk-swift +``` + +## Definition of Done + +- [ ] External MRZ/NFC logic inventory is captured in `SPEC.md` +- [ ] Cross-repo ownership assumptions are explicit +- [ ] NC-04 and NC-05 dependencies reflect the inventory result + +## Status Log + +- 2026-03-10: Created after local MRZ consolidation merged and MRZ/NFC ownership shifted to a separate cross-repo track. +- 2026-03-10: Updated to make the handoff explicit: this plan supports Seshanth's consolidation work and should not compete with it.