- security review: T-19.6-37 closed by sm-mfa-plugin v0.1.1, F-1 deferred
with the corrected reason for the activate-by-code mint path
- validation map: plan 04 Tasks 5 and 6 green
- todo for F-1; deferred items: tag message resolved, F-1 deferred
- 19.6-SECURITY-REVIEW.md: T-19.6-01..38 mapped to their tests or accepted
dispositions, the D-14 passkey section, D-18 hardening, ASVS notes, log
sweep, residual risks and open finding F-1 (activate-by-code)
- 19.6-VALIDATION.md: validated, one row per task of plans 01-04 with its
gate stage and tests
- mfa stage: the seven Docker-free decision tests by name
- docker stage: the sixteen Postgres decision tests of sm-mfa-plugin,
TestEveryLoginPathIsGated included, and TestSocialGate
- userplugin stage: TestLoginGates (also under -race), TestDeviceAuthURL,
TestDeviceDisplayName and TestDeviceCodes in classes
- docker stage: the gate order, password-change sources, reset action and
device-flow tests, and TestDeviceAuthSessionsMigration in updates
- stages go, userplugin, mfa, sociallogin, demo, demo-web, bm, fonoteka,
docker and docs across the seven repositories the phase touched
- go test -json detector refuses fail, skip, zero tests and missing names;
--self-test proves it, the additive and migration checks and the docker
NOT RUN rule on planted input
sm-demo-app mounts golem15.mfa v0.1.0 at user v0.1.12, sociallogin v0.1.4
and the two-factor UI (0eb1f60..bb24207, pushed with the 19 earlier
commits as 18597e5..bb24207, not deployed). The summary records the
"proceed" reply, the push checks and the tests. deferred-items.md gains the
private sm-mfa-plugin repository's effect on the demo's release build, and
a pending todo tracks the demo's leftover journal and oauthserver moves.
- WebAuthn and passkeys committed in sm-mfa-plugin (2662252, 6c8916f),
demo two-factor UI in vue-demo-app (44a5229)
- sociallogin D-09 change kept as a patch: the checkout is jin's
- deferred items: sociallogin gofmt finding, no demo type check
pquerna/otp v1.5.0, go-webauthn/webauthn v0.18.2 and boombuler/barcode
v1.1.0 (QR, with the plugin's own SVG writer), imported only by
sm-mfa-plugin and gated by a blocking human package check.
SEO moves to sm-seo-plugin and sm-sitemap-plugin on three generic
framework seams (form extensions with field placement, record events,
signpost content descriptors), following the mpseo pattern. Phase 32 is
split into 32/33/34.
pact.MCPGrant gains BackendUserID, the backend account the consent page
showed. pier gives an OAuth identity a backend subject (on resolution and
after a link event) only while the user's link names that account; a link
to anyone else, or no recorded account, gives none, so a link changed after
the consent never re-targets the grant.
The custom-element-in-form rule that keeps Esc, / and ? out of a plugin
field type's closed shadow root also applies to a focusable widget that
is not an input. The header comment and isEditableTarget now state the
trade-off and why the rule is not narrowed to plugin field types.
The README said a revoked personal API token fires the backend subject
event. admin:token:revoke runs in its own process, where no MCP endpoint
listens, so it fires none; its token's sessions end at the next
verification. Say so in the events entry and the command table.
An action whose Applies failed was dropped with no signal, so a section
whose Status succeeded showed a normal card with a button silently
missing. The section is now also sent with error: true, and My account
shows its error line. The error field's description, the cabana README
and the My account docs say so; the OpenAPI document and the SPA schema
types are regenerated.
Browsers strip tab and newline from URLs, so "/\t/host" passed the
SPA's same-origin check and resolved off-site. The check now refuses any
ASCII control character first, as Go's url.Parse does on the server, and
an absolute URL must parse with a host, so both sides apply one rule.
validatePluginTokenScope checked the trimmed name with
pact.ValidTokenScopeName while compileTokenScopes registered the
untrimmed one, so " blog:read" booted, was listed under its padded name
and could never be granted, and the duplicate check depended on
registration order. The name is now validated exactly as registered,
which is the shared rule pact.ValidTokenScopeName states.
The save shortcuts blurred document.activeElement before clicking. With
focus on an input inside a shadow root that is the host, and blur() on a
host that is not itself focused does nothing (spec, Firefox), so a plugin
field type committing on the native change event lost the typed value.
The shortcut now focuses the button first, as a pointer press does, which
unfocuses the inner input in open and closed roots, and gives focus back
to the innermost element reached through open shadow roots.
For a store without Reserve (only a test wrapper reaches this; both shipped
stores reserve), serveNew now calls Put right after the Count check and
before the server is built, and a failed connect or initialize deletes the
record again. The session is therefore never in the local map without its
record, so a reaper pass in between cannot close it as expired. The cap of
this fallback stays check-then-act, as its comment now says.