System Admin App Backend Discovery
This runbook describes the System Admin code lookup used by the Employee App. Code changes implement the API and management page; EKS ingress and production acceptance remain deployment work.
Public and internal boundaries
The new anonymous App operations are the exact POST /api/public/v1/backend-discovery/resolve, POST /api/public/v2/app-versions/check, and POST /api/public/v2/app-bundles/resolve paths, each with its exact OPTIONS preflight. Their request contracts and rate limits are separate. Other methods, query strings, trailing slashes, encoded paths, administrator APIs and static System Admin pages do not cross the existing SYSADMIN_ALLOWED_IPS boundary. The old /api/public/v1/app-versions/check path is a temporary legacy route during client cutover; it keeps the old contract and is not part of the new integration. See the version-management runbook for the version routes.
/healthz and /readyz are infrastructure probes for their own service. The Employee App must not call them. Discovery reads the System Admin database and never probes the customer API, uses its internal service token, or uses transient health state to select a backend.
Before release, configure EKS ingress/WAF so only the exact discovery operation is publicly reachable. Keep administrator routes behind the existing network restriction. Review the ingress proxy chain: Fastify currently trusts proxy headers, so the trusted ingress must overwrite forwarded IP headers before requests reach System Admin.
CORS origins
Set SYSADMIN_APP_DISCOVERY_ORIGINS to a comma-separated list of exact origins used by both public App routes. Do not use * or credentials. An empty value blocks callers that send an Origin header; clients without an Origin header, such as native HTTP clients, can still call the public endpoint.
The current Capacitor configuration uses http://localhost for Android. Capacitor's default iOS origin is capacitor://localhost. Add only origins used by the target App build, plus the exact deployed web-app origin if a browser client is shipped. The preflight allows only POST and Content-Type; Authorization is not needed for code lookup.
API URL and verification
Configure an origin-only customer API URL in the System Admin page. Production URLs must use HTTPS. The existing SDK appends /trpc and /trpc-ws, so the discovery URL must not contain a path prefix. It must be a public DNS host; the server rejects IP literals and common internal host suffixes but does not resolve DNS to check its destination.
Before publishing, an authorized System Admin must recently reauthenticate, confirm the exact public URL routes through the approved EKS ingress to the intended business backend, and record an internal evidence reference. The server binds that attestation to the public URL, configured ENV identity and publication revision. A public URL change, ENV identity change, endpoint removal, and explicit unpublishing invalidate it. An internal URL change only refreshes Sysadmin health and does not require republication when the configured identity and public URL stay unchanged. Do not use /healthz as proof of backend identity; a successful health response or TLS certificate alone is not sufficient.
The server-side request body limit is 1 KiB and the in-process limit is 60 requests per IP per minute. The in-process limit is per Pod and its memory table is bounded; configure an EKS-wide WAF or ingress limit before exposing the route. Choose and record the production limit with the deployment owner.
Migration, release and rollback
- Back up the independent System Admin database and apply the new migration using the existing System Admin migration procedure.
- Deploy the application and configure exact EKS path exposure,
SYSADMIN_ALLOWED_IPS, and reviewedSYSADMIN_APP_DISCOVERY_ORIGINSvalues. - Confirm the public URL, DNS, ingress target, configured endpoint ID, App origins and WAF limits. Keep publication disabled until this check has an approved evidence location and verifier.
- In System Admin, create a hospital code for a configured endpoint, configure its App URL, then publish it with the evidence reference. Check the public resolver from the actual iOS, Android and web transports used by the release.
- If a code or route must be withdrawn, use 게시 중지 in the System Admin page or block the exact public route at ingress. Unpublishing stops future discovery; it does not revoke customer business sessions.
The migration preserves code reservations and publication evidence and intentionally has no destructive down path. Roll back with explicit unpublishing and a reviewed forward migration if schema correction is needed. QR deep links and Employee App credential switching are separate work; this release does not implement them.