# Company code and App Link entry

> Superseded for login/switching by the agreed multi-account design in
> `2026-09-11-company-accounts.md`.
> The feature remains disabled; see `../company-accounts-deployment.md`.


## Outcome

One Flutter app connects to independently deployed agencies. A company code,
HTTPS link, and a QR encoding that same link select the same backend. Company
selection never creates membership or authenticates an agent. No client-facing
company list, account-directory lookup, or sequential login probing is added.

## Contract and UX

- Central deployment: `POST /agent-api/company-entry/resolve`, body `{code}`;
  response `{data: {code, name, api_base_url}}`. Codes are uppercase random
  8–32-character alphanumeric values. Only server-configured HTTPS origins are
  returned. Unknown/disabled/malformed codes receive the same public refusal.
- Share `https://app.propertylab.com.my/company/{CODE}`. The browser fallback
  shows installation guidance, code and QR. Android App Links/iOS Universal
  Links deliver the code to Flutter; the app resolves it using the trusted
  build-time directory origin, never a URL supplied in the link.
- Fresh install: company-code screen, then company-labelled email/password
  login. Remember selection securely. Existing users on the build-time backend
  retain credentials and local recordings during upgrade.
- Company switching is available on the signed-out login screen. A link while
  already inside a company asks the user to sign out/change company first;
  it must not interrupt recording or change an active session silently.
- Installation does not promise deferred deep links. Users return to the
  original link after installation, or enter the displayed company code.

## Implementation order

1. Backend config-backed directory, throttling, no-store responses, generic
   browser fallback, QR, platform association files and deployment instructions.
2. Flutter resolver/model/secure selection, company gate, labelled login,
   origin-bound credential/local-account namespaces and background upload origin.
3. Android and iOS HTTPS link registration and cold/warm delivery.
4. Regression tests and review, local commits; cherry-pick backend task commits
   into local `dev-chen`. Mobile work stays in its isolated task branch because
   the original mobile checkout contains unrelated active edits.

## Acceptance checks

- Manual code and link deliver the same verified backend; no company list.
- Reject malformed links, arbitrary hosts/redirects and non-HTTPS destinations.
- Remember selection; restore existing default-backend users without losing data.
- Login/refresh/upload never send company A credentials to B; cloned user UUIDs
  do not share local data. Queued work only runs for its matching company/account.
- Error/retry UI for invalid code, offline resolver, and persistence failures.
- Test backend resolution, privacy, limits and platform association contracts;
  Flutter parser/resolver/storage/gate/login tests plus existing full suite,
  analyze, Android build, repository verification scripts and iOS config checks.

## Deployment boundary

No production deployment, DNS changes, push or app-store publication in this
work. Operators must configure real agency codes/origins, Android release
certificate fingerprints and Apple application identifiers on the central
server, and enable Associated Domains in the Apple signing profile. Actual
OS-verified links require those deployed association files and installed signed
builds; report local checks separately from device verification.

## Completion — 2026-09-10

Implemented the backend registry/landing/QR/association endpoints and the Flutter
company gate, `app_links` integration, remembered company, legacy migration,
company-specific credentials/data scopes and background upload selection.
The legacy Flutter navigator does not process company-link paths; `app_links`
handles cold and warm events while the normal login/navigation flow stays intact.

Validation: backend 42 tests / 248 assertions; App 419 tests; static analysis;
client + SSR build; PHP formatting; Android Production debug build; iOS arm64
simulator build from a non-synced temporary worktree; iOS scheme and plist checks.
The browser landing was visually checked with the compiled QR bundle. The only
PHPUnit warning is the pre-existing deprecated XML configuration schema.

App code commit: `c57ae47` in the separate mobile repo's `codex/company-entry`.
See its `docs/validation/COMPANY-ENTRY-2026-09-10.md` for commands and environment
workarounds. Backend task commits were integrated into local `dev-chen` using
cherry-picks; no unrelated history was merged. The original mobile checkout is
dirty with unrelated recording work, so its edits were preserved and the task
implementation remains on the isolated mobile branch.

Production enablement is separate: real code-to-origin entries, signing
identities/association deployment, signed device builds and device link checks
are still required. No push, production deployment or store publication occurred.
