Files
fidelity-ai-workspace/project-knowledge/02-work-items/pdiap-15838.md

12 KiB

type, project, status, ticket, title, systems, workstreams, people, related, updated, tags
type project status ticket title systems workstreams people related updated tags
work-item fidelity active PDIAP-15838 Remove Apollo for iOS
xflowsdk
rest-migration
jeff-dewitte
bruce-meeks
adam-abdelhadi
tauf
jeffrey-oleary
aylwing-olivas
launchdarkly
github-copilot
2026-04-29
work-item
fidelity
rest
graphql

PDIAP-15838 - Remove Apollo for iOS

Status

  • Draft PR open for internal review
  • PR merge should wait until the previous REST-toggle implementation has been QA-tested and active in production with REST enabled for all consumers for 30 days without issues
  • Sized at 8 points

Context

  • This ticket covers the REST migration cleanup on iOS.
  • The approved title is Remove Apollo for iOS.

Approved Scope

  • Remove Apollo from iOS.
  • Remove GraphQL-specific networking code.
  • Remove related tests and mocks.
  • Remove transport feature flags so REST remains.

Current Guidance

  • Do not frame this ticket as directly tied to the UIKit-removal spike.
  • Do not imply it is dependent on or part of dismissal-sequencing work.
  • Keep the migration framing explicit: REST remains behind a feature flag until otherwise confirmed, and GraphQL fallback context still matters when describing the overall migration.
  • Keep the REST-activation investigation context as useful background, but focus current updates on Apollo-removal cleanup, validation, and merge sequencing.
  • For standups and concise status updates, center the story on Apollo-removal progress and the PicoSDK transitive dependency path; omit extra exploratory asks unless they directly affect the story outcome or create a blocker.
  • Jeff confirmed this investigation should stay ahead of Adam's separate service-side flow report for now and asked for faster progress.
  • Current local evidence shows the LaunchDarkly boolean evaluating to true, with payload and context present from the iOS side; remaining uncertainty is around production-side context interpretation, timing/caching, or downstream transport gating.
  • Use the current support path while direct Flagship LaunchDarkly access is missing: monitor the Tauf thread, follow the outreach path to Jeffrey O'Leary, package the scenario for GitHub Copilot with build settings and tool details, and ask Aylwing for a quick perspective if available.
  • Adam later reported that the latest build is activating REST correctly, so the story context returned to the planned GraphQL-removal and related LaunchDarkly-toggle cleanup work.
  • Keep the real-device-only scenario in mind as a useful fallback hypothesis if the issue returns: environment-specific differences such as LaunchDarkly context, timing, or cached toggle state may explain behavior that does not reproduce in the simulator.
  • Adam was the reported source of the REST activation problem, and his side validates behavior on real devices.
  • Current codebase analysis suggests the main remaining source-level blockers are no longer transport selection but residual Apollo model/runtime coupling: XFlow.Slot usage in the page interactor/worker path, NetworkClient references still touched by init/session lifecycle, and Apollo/AppSync config surface that may still behave like public API.
  • Follow-up analysis suggested XFlow.Slot might be the only Apollo-generated production model still used outside the GraphQL-generated folder, but local trial changes surfaced additional Apollo-dependent models/build errors. Treat the XFlow.Slot simplification as a promising first step, not as a fully validated statement about the whole codebase.
  • The suggested simplification is to remove the current round-trip stagedValues() -> [String: String] -> XFlow.Slot -> [String: String] -> XFlowUpdateSlotsRequest.slots and instead pass [String: String] straight through to XFlowUpdateSlotsRequest.slots, keeping SlotVariable: Encodable in the REST model layer for request serialization.
  • The next AI follow-up should focus only on the first step and ask GitHub Copilot to corroborate residual Apollo-model dependencies by using xcodebuild failures, not just static reference search.
  • Follow-up enum validation indicates at least some Apollo-generated enum types can likely be replaced with native Swift enum Name: String definitions without preserving Apollo EnumType behavior. For the currently checked production callers, Copilot reported no Apollo-specific enum API dependency for XFlow.ContentType, XFlow.ScreenshotFormat, and XFlow.NextTransitionType; current behavior relies on rawValue, equality/switch use, and init?(rawValue:)-style parsing.
  • The currently observed fallback behavior is simple and code-local: unknown ContentType values are skipped by converter guards, unknown ScreenshotFormat values fall back to PDF in downstream callers, and unknown NextTransitionType values currently propagate as nil where the target property is optional.
  • Design direction for the Phase 1 Apollo cleanup: prefer replacing XFlow.Slot with a native Swift Slot model instead of collapsing it to [String: String] through the full production path. Keep [String: String] only at the boundary where the REST request/DTO is built in the worker or transport layer.
  • The current implementation state is cleaner on the model side: Apollo-generated production models have now been replaced with native Swift models/enums for the active path, so the next focus should move from model decoupling to remaining Apollo runtime/infrastructure dependencies.
  • The XFlowInitManager runtime/init cleanup step has now been applied successfully: the three NetworkClient.shared.updateAppSyncURL(...) calls were removed from the start/session lifecycle paths, getAppSyncEndPoint() was removed after becoming unused, and the project still compiles with getEndPoint() left intact for current REST selection.
  • NetworkClient.swift can likely stay temporarily in the tree as a disconnected compatibility shim until broader package/project cleanup, and XFlowInitManagerConfig.swift may need to keep AppSync getter/config surface temporarily to avoid an accidental public API break.
  • Follow-up runtime scan now suggests GraphQL/NetworkClient.swift has no live production callers and only self-references remain inside the file. The proposed next removal order is to delete GraphQL/NetworkClient.swift first, build/reference-check, then delete GraphQL/ApolloGeneratedCode, while keeping the AppSync members in XFlowInitManagerConfig.swift temporarily as compatibility-only surface.
  • Current local state after broader cleanup: runtime Apollo decoupling and most Apollo-specific test cleanup now appear complete, production code compiles cleanly aside from a pre-existing environment issue, and no live Apollo imports/references remain in production code. Remaining work is mainly package/build cleanup plus the deferred compatibility API surface in XFlowInitManagerConfig.swift.
  • Current local state now also indicates the test target compiles cleanly after a minimal follow-up update to XFlowTransportSelectionTests.swift, preserving REST-relevant transport tests while removing obsolete GraphQL/Apollo assertions. The remaining Apollo-removal work appears concentrated in package/build cleanup plus the deferred compatibility API surface in XFlowInitManagerConfig.swift.
  • Latest follow-up says the Apollo package/build cleanup has also now been applied: direct Apollo dependency references were removed from package/build ownership surfaces, leaving the main remaining follow-up as Fid4 validation plus any later decision on whether to deprecate/remove the temporary AppSync compatibility getters in XFlowInitManagerConfig.swift.
  • Apollo source-level cleanup appears sequenced as: replace XFlow.Slot with a transport-agnostic model first, decouple XFlowInitManager from NetworkClient while preserving current REST endpoint behavior, then remove runtime GraphQL code, project wiring, Apollo-only tests/scripts/docs, and finally treat any transitive PicoSDK Apollo dependency as a separate dependency-exit task.
  • Apollo may still remain in the pod graph transitively through PicoSDK even after source-level cleanup, so "Apollo removed" should be framed carefully unless the dependency graph is also cleared.
  • Latest local follow-up suggests SampleApp depends on PicoSDK, and that transitive dependency may still be the practical reason Apollo remains in the pod graph. Newer PicoSDK versions no longer depend on Apollo, but the upgrade path does involve real breaking changes. The current investigation is to determine how SampleApp can absorb those changes by comparing against how Fid4 currently uses PicoSDK for the two specific flows that still depend on it.
  • Jeff later confirmed that this PicoSDK / SampleApp cleanup is in scope for PDIAP-15838 because Apollo needs to be removed from the project, including the transitive sample-app path. Keep the nuance explicit that this update affects SampleApp, not the XFlowSDK production runtime directly.
  • David updated SampleApp to use the newer PicoSDK path, removing Apollo from the transitive sample-app dependency path and re-enabling the FGO and FidFolios flows for testing in SampleApp.
  • The SampleApp Pico changes now more closely mirror how Pico is already used in Fid4.
  • A draft PR has been opened for PDIAP-15838 - Remove Apollo for iOS; after internal review, the link should be sent to Bruce.
  • Internal review found and resolved PicoSDK integration concerns: TransactionContextManager(resolver:) handles Pico setup internally in PicoSDK 4.3.18 through lazy resolver-based initialization, the resolver already exists on XFlowSampleAppViewModel, and PicoInterface was minimally patched so the async completion path avoids a strong self capture and returns through MainActor.run for UI-state safety.
  • The REST kill-switch removal is intentional for permanent GraphQL deprecation, but merge timing is gated: the previous REST-toggle implementation should first be QA-tested and active in production with REST enabled for all consumers for 30 days without issues.
  • Merge sequencing is now explicitly gated by backend production readiness: Bruce reinforced that the GraphQL/Apollo removal PR should not merge until the backend is in production because GraphQL fallback is still needed before then.
  • Bruce clarified that the current SDK-side updates are not REST behavior changes; the functional REST/backend fix is on the Flagship/Fid4 side, while SDK updates are cleanup, more graceful error handling, logging, and replacing a deprecated logger interface.
  • Bruce asked whether iOS Fid4 has a release-build optimization or code-minification concept comparable to Android; treat this as a validation/build-configuration question until clarified, not as evidence of a known iOS minification issue.
  • Jeff clarified the validation ask: inspect whether Fid4 has simulator-versus-physical-device or generated-build differences in build settings/schemes/configurations, including any optimized-build-size or release-style settings that could explain behavior seen in generated builds but not when running locally.
  • Current likely Fid4 build differences to report: Trunk/generated builds use the Release configuration while local runs are usually Debug; optimization settings such as SWIFT_OPTIMIZATION_LEVEL and GCC_OPTIMIZATION_LEVEL can differ; Jenkins uses a generated build-overrides xcconfig that local builds do not use and may affect values such as secrets; and CocoaPods dependency resolution can vary depending on the local specs repo state.

Sequencing

  • This story remains sequenced before PDIAP-15836.