Skip to content

AKB Backend v0.16.2

Choose a tag to compare

@younglokim-oss younglokim-oss released this 12 Oct 18:14
· 40 commits to main since this release
Immutable release. Only release title and notes can be modified.
6382e9d

Authentication

  • The bundled Keycloak's sign-in pages use AKB's login theme (akb, source in
    frontend/keycloak-theme): AKB's tokens and typeface, light and dark,
    English and Korean. Every page is one card laid out after Astryx's login
    card: the mark and name above it, a centred title, 36px controls, the
    account form with a monochrome primary button, then the identity providers
    under "Or continue with", and language and theme below the card. The frontend image now carries the assembled theme at
    /usr/share/akb/keycloak-theme/akb, outside nginx's web root. The
    standalone-sso overlay and the Helm sso template give the Keycloak
    StatefulSet a login-theme init container, using the frontend Deployment's
    image reference, that copies the theme into an emptyDir mounted read-only
    at /opt/keycloak/themes/akb; Keycloak's own image is unchanged. A new
    receipt profile, bundled-keycloak-v6, makes the realm use it: loginTheme
    akb, internationalization on with en and ko (default en), and the
    administration client attribute akb.login.native-only=true, with which the
    theme draws that client's sign-in page without identity-provider buttons.
    New installs record v6. Existing installs keep their receipt and converge
    read-only (login_presentation=pending_upgrade); the one-time upgrade client
    moves v1–v5 to v6 and sends only those settings, so the realm's other
    settings and the client's secret, redirects and other attributes stay as
    they are. The bootstrap report adds login_presentation (converged,
    drift with a warning, or pending_upgrade), which never blocks startup. A
    Keycloak without the theme serves its built-in pages. The v6 receipt is a new
    row, so an older image still reads its v5 receipt. On the theme's "Page has
    expired" page, a sign-in step the browser requested twice resumes once per
    tab by itself, and from the second time the page explains instead.

  • The bundled Keycloak (the standalone-sso overlay and the Helm sso
    template) no longer serves Keycloak's own client-registration endpoint
    (KC_SPI_CLIENT_REGISTRATION_DEFAULT_ENABLED=false). That endpoint accepts
    a whole client representation, including an authentication-flow override,
    so a client registering itself could run a flow without the brokered-account
    guard. Clients that register themselves, such as MCP clients, use the OpenID
    Connect registration endpoint, which is unchanged and cannot set an
    override. The bootstrap report adds native_client_registration
    (disabled, enabled, or unknown), read with one anonymous request whose
    body is not JSON so it can register nothing; enabled and unknown are
    logged as warnings and never block startup.

  • The bundled Keycloak realm's sign-in flows refuse a realm password to an
    account that arrived through an identity provider. Such an account could
    set one through Keycloak's UPDATE_PASSWORD action (also the account
    console's "set up password") and then sign in with it, without the
    upstream, at the realm's own form (the one AKB's local provider opens) or
    at the password grant, and AKB accepted that form's token as theirs. Every
    identity provider now grants the realm role akb-brokered-account on each
    brokered sign-in, and the realm binds akb browser and akb direct grant,
    copies of Keycloak's built-in flows in which a holder of that role is denied
    after the password step. The guard lives in these realm-bound flows; a
    client given its own authentication-flow override does not use them.
    Accounts without an identity-provider link, the product administrator
    included, sign in as before; creating the password is not blocked, using it
    is. New installs record a bundled-keycloak-v5 receipt. Existing installs
    keep their receipt and converge read-only
    (brokered_account_guard=pending_upgrade); the one-time upgrade client
    moves a v1–v4 install to v5, adds the mapper to every existing provider,
    and grants the role to the accounts each provider already links. Moving
    from v4 leaves the event settings as they are. The upgrade stops before
    changing anything if the realm binds a browser or direct-grant flow other
    than Keycloak's built-in one or AKB's copy
    (keycloak_authentication_flow_binding_unexpected). The v5 receipt is a new
    row, so an older image still reads its v4 receipt after a rollback. The
    bootstrap report adds brokered_account_guard. On v5 the guard is a startup
    gate: a realm whose bound flows no longer deny the role fails with
    keycloak_brokered_account_guard_readback_failed, and one with an enabled
    provider that does not grant it fails with
    keycloak_identity_provider_guard_mapper_missing. Upgrade modes are now
    named upgrade-vN-to-v5, and a callback change on a v5 receipt
    upgrade-v5-callback. Configuring or enabling a provider writes the mapper
    when the realm has the role, and enabling fails closed when it cannot;
    disabling is unaffected, and realms without the role are left alone. The
    permanent akb-sso-manager gains no authority.

  • The bundled Keycloak realm now keeps seven days of user events: login and
    broker outcomes, restarts of an expired login, and credential or broker-link
    changes. New installs record a bundled-keycloak-v4 receipt with the events
    on. Existing installs stay on v3 and keep converging read-only; supplying the
    one-time upgrade client moves a v2 or v3 install to v4. The v4 receipt is a
    new row, so rolling back to an older image still reads its v3 receipt. The
    permanent akb-sso-manager gains no events authority. The bootstrap report
    adds realm_events (converged, drift, or pending_upgrade); drift is
    logged and never blocks startup.

  • Settings → Security (sign out all sessions, delete account) is always
    available according to auth_mode; the account_self_service_enabled
    rollout flag is retired. Existing configs that still set the key keep
    loading, and the value is ignored. Account deletion still requires a healthy
    cleanup worker heartbeat and reports cleanup_unavailable otherwise.

  • POST /api/v1/auth/register rejects passwords shorter than 8 characters
    with 422 invalid_argument, matching the existing change-password minimum.
    Registration and password change also reject passwords over 72 UTF-8 bytes
    (the bcrypt limit) as client errors instead of failing with 500.

Search retrieval

  • Scoped pgvector posting searches choose term-first, scope-first, or bounded
    point lookups while retaining the same filters and exact sparse scores.
    Explicit Native document scopes use separate indexed path and UUID lookups.
  • pgvector dense candidates are sorted by actual distance before rank fusion,
    with iterative HNSW scans enabled for source-type-only filters too.
  • search_retrieval_timeout_secs bounds pgvector pool acquisition, concurrent
    retrieval, payload loading and cleanup (default 30 seconds). Healthy peer
    results survive a timeout; cancellation drains queries without masking
    authorization or schema failures. This is a retrieval budget, not an HTTP
    request timeout.
  • Incomplete search responses keep available hits usable, distinguish an
    incomplete empty response from no matches, and avoid definitive result counts.

Vault-member app installation status

  • Added GET /api/v1/apps/{app_id}/installations/{vault_id}/active for Vault
    owners and members with reader, writer, or admin access. It returns only the
    canonical active boolean, uses the authenticated user identity, checks live
    membership, and disables caching.

Installation execution

  • A newly accepted install or fresh command now persists one sealed,
    single-installation rollout job and its target in the same transaction as the
    command acknowledgement. The existing worker executes the schema plan, an
    app-wide request skips installations that already have a queued target, and
    a command cannot commit accepted without a job. The job records the
    authenticated owner/admin command path.

This compatible patch adds no schema migration. Existing SSO receipts remain
unchanged unless the separate one-time upgrade workflow is run; Keycloak and
frontend image updates are outside this installation rollout.

Deployment verification

The backend installation executor is covered by all seven required CI checks, including real PostgreSQL tests and the app-control-plane shell E2E suite. The paired Reef fix is tracked in dnotitia/reef#522.

Existing Native installations retain their identity and initialization receipts. An API/worker image rollout does not perform the separately documented Keycloak receipt upgrade or deploy the frontend login theme.

Deployed API and worker source: 6382e9daecd11d949c1610eeaf4b21e84470e902. Immutable backend image: 192.168.110.11:5000/akb-backend@sha256:cc2d763b57d3c150226ab44375d76fc2ef0ef82a9284388bdccff23ad944399d. Both deployments passed rollout and readiness with existing resources/Native identity preserved. Production SSO remains enabled; authenticated MCP discovery passed 12/12 requests through an operator port-forward to one API pod; Kubernetes readback separately confirmed both API replicas ready. The local-login shell smoke is not applicable to this SSO deployment; the repository’s real Keycloak CI gate passed before release.