mirror of
https://github.com/kevinveenbirkenbach/computer-playbook.git
synced 2026-11-06 10:59:59 +00:00
The negative control aborted every <host>/logout and then asserted the
admin bearerAuth cookie survives. It failed in run 32597195876, job
Shopware#0, in 5 of 6 executions: the cookie was gone anyway.
The premise was right and the target was wrong. The trace of the failing
run shows all nine sweep aborts landing - 584 ms too late:
51.534 -1 shop/api/oauth/sso/config logoutSso() cut off by the
injected logout redirect
51.538 200 auth/.../openid-connect/logout
52.842 200 auth/.../logout/logout-confirm
53.377 200 logout.<domain>/?sid=... conductor, Clear-Site-Data
53.961 -1 9x <host>/logout sweep, correctly blocked
54.256 200 shop/admin cookie already gone
What deletes the cookie is the Clear-Site-Data header on web-svc-logout's
conductor page - "the ONLY path-agnostic cookie deletion mechanism" per
universal-logout's app.py - and it clears the whole registrable domain,
which is how an origin on logout.<domain> reaches a cookie on
shop.<domain>. The per-app /logout requests are the second mechanism, not
the first. Shopware's own clearAuthState never runs either: the injected
redirect preempts it.
The route now blocks the conductor, which is the honest simulation of
"web-svc-logout never lands". It loads after Keycloak's logout-confirm,
so blocking it cannot disturb that flow.
Two anchors identify it, because one is not enough on every axis.
`lookup('tls', ...)` family-aligns a cross-app reference per consumer
(utils/tls_common.py align_domain_to_consumer), so where web-svc-logout
is onion-primary and this role and Keycloak sit in different families,
the origin resolved here is not the one Keycloak framed. The front-channel
parameters Keycloak appends catch that case. LOGOUT_URL stays optional for
the same reason - an empty lookup must fall through to the second anchor
rather than fail the test.
The sibling's poll message names the real mechanism and keeps the
rationale for its 30s wait, which 5b6d12f12 added for a reproduced
Tor-only failure.
Verified on clearnet evidence only: the failing job skipped every Tor
task, and no Tor run in either pipeline produced a trace, since traces are
retain-on-failure and those jobs were green.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
48 lines
3.9 KiB
Bash
48 lines
3.9 KiB
Bash
ADMIN_PASSWORD={{ lookup('users', 'administrator').password | dotenv_quote }}
|
|
|
|
ADMIN_USERNAME={{ lookup('users', 'administrator').username | dotenv_quote }}
|
|
|
|
APP_BASE_URL={{ lookup('tls', application_id, 'url.base') | dotenv_quote }}
|
|
|
|
BIBER_PASSWORD={{ lookup('users', 'biber').password | dotenv_quote }}
|
|
|
|
BIBER_USERNAME={{ lookup('users', 'biber').username | dotenv_quote }}
|
|
|
|
CANONICAL_DOMAIN={{ lookup('domain', application_id) | dotenv_quote }}
|
|
|
|
# nocheck: playwright-service-gate — the CSP helper gates css through a computed loop variable (personas/utils/csp.js:87-93), never a literal argument, so test_spec_env_gates.py's literal-only regex cannot see the gate
|
|
CSS_SERVICE_ENABLED={{ lookup('config', application_id, 'services.css.enabled') | string | lower }}
|
|
|
|
# nocheck: playwright-service-gate — the only mail wiring in the role is MAILER_DSN in templates/env.j2, rendered behind an email.enabled guard; no persona scenario triggers an outbound send
|
|
EMAIL_SERVICE_ENABLED={{ lookup('config', application_id, 'services.email.enabled') | string | lower }}
|
|
|
|
# nocheck: playwright-service-gate — the role installs no admin-LDAP plugin, so the directory never gets a surface of its own. Where sso is enabled the directory reaches the backend through Keycloak's user federation and the AdminOpenAuth provider; where it is disabled there is no path into Shopware at all, so neither polarity leaves an assertable surface
|
|
LDAP_SERVICE_ENABLED={{ lookup('config', application_id, 'services.ldap.enabled') | string | lower }}
|
|
|
|
LOGOUT_SERVICE_ENABLED={{ lookup('config', application_id, 'services.logout.enabled') | string | lower }}
|
|
LOGOUT_URL={{ lookup('tls', 'web-svc-logout', 'url.base') | dotenv_quote }}
|
|
|
|
# nocheck: playwright-service-gate — the shopware-init console installer aborts without the database, so every scenario already proves it
|
|
MARIADB_SERVICE_ENABLED={{ lookup('config', application_id, 'services.mariadb.enabled') | string | lower }}
|
|
|
|
MATOMO_BASE_URL={{ lookup('tls', 'web-app-matomo', 'url.base') | dotenv_quote }}
|
|
|
|
MATOMO_SERVICE_ENABLED={{ lookup('config', application_id, 'services.matomo.enabled') | string | lower }}
|
|
|
|
# nocheck: playwright-service-gate — storefront product-search index; no persona scenario submits a search query
|
|
OPENSEARCH_SERVICE_ENABLED={{ lookup('config', application_id, 'services.opensearch.enabled') | string | lower }}
|
|
|
|
# nocheck: persona-block-rationale — Shopware's only logout sits in .sw-admin-menu__user-actions, which sw-admin-menu.scss keeps at display:none until its toggle is clicked, and that toggle is a bare div with no role, aria-haspopup or dropdown class, so the shared helper's trigger set cannot open it; the settings fallback misses too because the admin is hash-routed. files/playwright/test-admin-native.js drives the same journey through Shopware's own selectors (see README "Persona contract opt-outs").
|
|
PERSONA_ADMINISTRATOR_BLOCKED=true
|
|
|
|
# nocheck: persona-block-rationale — tasks/01_admin.yml provisions only the administrator in Shopware's user table, and meta/services.yml pins sso.flavor: oidc, so no proxy fronts the storefront and the AdminOpenAuth provider covers the backend alone. biber therefore has no account in any variant; the authenticated backend journey is proven by files/playwright/test-admin-native.js instead (see README "Persona contract opt-outs").
|
|
PERSONA_BIBER_BLOCKED=true
|
|
|
|
# nocheck: playwright-service-gate — session, cache and messenger transport behind every request, no surface of its own
|
|
REDIS_SERVICE_ENABLED={{ lookup('config', application_id, 'services.redis.enabled') | string | lower }}
|
|
|
|
# nocheck: playwright-service-gate — reached only through the Flysystem amazon-s3 adapters; Shopware exposes no object-browser surface
|
|
SEAWEEDFS_SERVICE_ENABLED={{ lookup('config', application_id, 'services.seaweedfs.enabled') | string | lower }}
|
|
|
|
SSO_SERVICE_ENABLED={{ lookup('config', application_id, 'services.sso.enabled') | string | lower }}
|