Skip to content

PD-5900 - #2907

Merged
cryptalith merged 8 commits into
mainfrom
lmendoa/PD-5900
Aug 21, 2026
Merged

PD-5900#2907
cryptalith merged 8 commits into
mainfrom
lmendoa/PD-5900

Conversation

@cryptalith

Copy link
Copy Markdown
Member

No description provided.

Shows an interstitial after standard sign in to users with exactly one email
address on their record, prompting them to add a backup. It runs first in the
interstitial chain (backup email, then public domains, then affiliations) and
is gated by the LOGIN_BACKUP_EMAIL_INTERSTITIAL togglz. Sign in flow only.

Panel follows the Figma: primary email with its Professional/Personal category
(from email-domain/find-category), backup email field, and the three inline
errors from the AC. The confirmation is a success notice at the top of the
record, matching the other interstitials.

Accessibility fixes for this dialog: it now has an accessible name and
aria-modal, the decline control is a button so keyboard users can dismiss it
(disableClose blocks Esc), and inline errors are announced. Panel padding moved
to the dialog surface, which also had no padding at all on mobile.

Adds the first analytics for the interstitial subsystem: an 'interstitial' RUM
journey reporting shown, added, dismissed, validation error and save error, so
add and dismiss rates are measurable. The shown event is emitted from the shared
manager, so all three interstitials get a comparable denominator.

Also makes the XSRF preload interceptor run on every browser instead of only
Firefox. Without a cookie the first mutating request goes out with no
x-xsrf-token header, 403s, and only sets the cookie as a side effect, which made
addInterstitialFlag fail and local sign in take two attempts. The reload it
falls back to is now guarded so it cannot loop. Recording an interstitial visit
no longer gates the dialog opening either, so a failed flag POST cannot hide the
interstitial while marking it as seen.
Material reserves a fixed block below every mat-form-field for hints and
errors. The inline errors here are siblings outside the field, following the
convention used elsewhere, so that reserved space was only a gap. Reuses the
global no-hint class to drop it.

Label, field and message now sit in an 8px flex stack, matching the design,
instead of 4px above the field and a large gap below.

Also splits the two error reds the design distinguishes: the label and field
outline take state-warning-darkest, the message state-warning-dark. Adds the
explicit 18px line height, since the orc-font-* classes never set one.
Extend the backup email interstitial to the OAuth flow behind the new
OAUTH_BACKUP_EMAIL_INTERSTITIAL flag.

Pull the duplicated URL checks out of the two XSRF interceptors into a
shared xsrf-urls module, and rename InterstitialBackupAdded to the
generic InterstitialCompleted now that more than one interstitial
reports a completion.
The two branches rewrote the same block of XsrfFallbackInterceptor. This
branch had lifted the URL and cookie decisions into xsrf-urls.ts so the
preload interceptor could share them; main (#2896) had added host based
matching, a second cookie to fall back on, and a csrf.json bootstrap that
retries the request once. Both are kept: the helpers now match by host, and
the interceptor calls them and then runs main's bootstrap.

Host matching alone mislabels the local proxy, where the auth server is
/auth/ on our own host and everything else is the web backend, so
isAuthServerUrl compares the base path too. That is the one behaviour that
is neither branch's, and it has a spec.
showInterstitial() attaches the interstitial into the cdkPortalOutlet and
then clears showAuthorizationComponent. The outlet lives inside the
mat-card, whose *ngIf only tested showAuthorizationComponent and
showAuthorizationError, so both went false and Angular destroyed the card
along with the interstitial that had just been attached to it. The user
was left on a blank page with the OAuth redirect never happening.

showInterstital was already set for this purpose but was never read by
the template.

This affects every interstitial on the OAuth flow, not just backup email.

The existing interstitial spec stubs the portal outlet, so it never
rendered the template and could not catch this. The added test renders it
and asserts the card survives the flag flip.
@amontenegro

Copy link
Copy Markdown
Member

# Conflicts:
#	src/app/authorize/pages/authorize/authorize.component.spec.ts
#	src/app/core/login-interstitials-manager/interstitial-observability.service.ts
#	src/app/rum/interstitial-observability.md
#	src/locale/messages.lr.xlf
#	src/locale/messages.rl.xlf
#	src/locale/messages.xlf
#	src/locale/messages.xx.xlf
The sign in flow closes the dialog and /my-orcid shows an "added" notice.
The OAuth flow renders the interstitial inline and then sends the user
straight on to the client, so that notice is never seen and a successful
add had no confirmation at all.

Adds the confirmation from the design: heading, the address that was
added, a pointer to the record, and a "Continue to <client>" button that
ends the interstitial and lets the redirect run. The client name comes
from the oauth session; without one the button reads "Continue".

Reuses the afterSummit() seam the domains and affiliations interstitials
already use for their success screens, so the dialog subclass overrides
it and the sign in flow is unchanged.

interstitial.visitYourOrcidRecord and interstitial.continueTo already
exist with exactly this copy and are reused.

Adds a dialog spec, which did not exist, covering the case that matters
most here: the dialog must close on success rather than showing the
confirmation, so the panel and the record notice never both appear.
@cryptalith
cryptalith merged commit b12b1ff into main Aug 21, 2026
10 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants