Skip to content

Fix SSO session, MFA and provisioning accuracy in 13-3 - #449

Merged
mtantawy merged 2 commits into
mainfrom
fix/sso-mfa-session-accuracy
Aug 6, 2026
Merged

Fix SSO session, MFA and provisioning accuracy in 13-3#449
mtantawy merged 2 commits into
mainfrom
fix/sso-mfa-session-accuracy

Conversation

@mtantawy

@mtantawy mtantawy commented Aug 6, 2026

Copy link
Copy Markdown
Member

Corrects inaccuracies in Access Controls and SSO (13-3), found while answering a customer SSO question. Everything here was verified against the production Auth0 tenant and the post-login Action, not inferred.

What's fixed

1. Session Management — the SSO claim was backwards

The article said:

Customers using SSO inherit session controls from their identity provider; values configured in the IdP take precedence over Light's defaults.

Auth0 maintains its own session, and our tenant-level inactivity and maximum session limits apply to every user including SSO users. The IdP governs how users authenticate; it does not extend our session lifetime. As written, a customer would plan around their own IdP timeout and be wrong.

2. MFA section only covered Light's internal access

It described MFA for "administrative and engineering access to production systems" — i.e. our staff. Nothing told customers that their users get an authenticator-app prompt, that it applies on top of their own SSO/IdP MFA, or that recovery codes aren't enabled so a lost device needs an admin reset. This is the first thing a customer's IT team asks and the article was silent on it.

Now also states who is prompted: any role beyond Reimbursement and Invoice approver. Added after review at @tiagoengel's request — note that Cardholder is not exempt, contrary to the recollection in the review thread.

3. Provisioning was undocumented

Users are never auto-provisioned by the identity provider on first sign-in — an unknown email is denied outright. Confirmed in code (getUserForLoginByEmail throws UserNotFoundByEmailException) with a covering integration test. The new User Provisioning section separates this from HRM-based auto-provisioning via Finch, which is supported.

Deliberately not changed — needs a check

  • Session numbers. Current values are 3 days inactivity / 7 days maximum for persistent sessions. Kept qualitative to match the article's existing style and avoid a number that silently rots — happy to state them if we'd rather be concrete, since customers do ask.
  • "Anomaly detection" under Account Lockout. The claim that unusual sign-ins are "flagged for additional verification" describes Adaptive MFA, which is not enabled on our tenant (paid add-on). Auth0's separate Attack Protection features may cover some of this, but I haven't checked those settings, so I left the wording alone rather than replace one unverified claim with another. Someone with dashboard access should confirm.

Unrelated drift worth a separate look

The Notion record for this article documents an accuracy pass (Local currency vs "base currency", Dunning vs "Invoice-to-cash", the hardcoded "at least two approvers" example, the permissions-matrix count) that is not in the git source — lines 79, 91 and 104 still carry the old text. Those edits appear to have been made in Notion only. Out of scope here, but the two copies are out of sync.

Note before merging

sync-to-cms.yml fires on push to main, so merging publishes straight to the live knowledge base.

Three corrections to the Access Controls and SSO article, verified against
the production Auth0 tenant and the post-login Action:

- Session Management stated that IdP session values "take precedence over
  Light's defaults". This is backwards: Light's session limits apply to all
  users including SSO users, and the IdP does not extend them.

- The MFA section described only Light's internal administrative access, so
  customers had no indication that their own users are prompted for a second
  factor — including when signing in through SSO.

- SSO setup did not mention that users are never auto-provisioned on first
  sign-in. Accounts must exist in Light beforehand or authentication is
  denied, which is a common go-live surprise.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 06cd546c3c

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".


- **Authenticator app**: Users verify with a one-time password from an authenticator app such as Google Authenticator.
- **Applies in addition to SSO**: Signing in through your identity provider does not replace Light's MFA step. If your identity provider also enforces MFA, users complete both.
- **Remember this device**: Users can choose to be remembered, which suppresses the prompt on subsequent sign-ins until the session reaches its inactivity or maximum lifetime (see [Session Management](#session-management)).

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Decouple remembered MFA from the session lifetime

When a user selects Remember this device, Auth0 records that choice in a separate remember-browser cookie; expiring Light's Auth0 application session does not necessarily expire that cookie. Consequently, after the inactivity or maximum lifetime triggers a new authentication transaction, the remembered browser can still bypass the MFA prompt. Tying MFA remembrance to these session limits gives customers the incorrect expectation that every session expiration forces MFA again, so this should describe the independently configured remember-device lifetime instead.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Accepted, wording changed. I had based the coupling on an Auth0 support article stating that tenant session settings apply to MFA cookies as well as session cookies — but that page is scoped to ephemeral sessions, so it does not generalise.

Tenant logs do show MFA events at roughly the same volume as successful logins, but that is equally consistent with users simply not selecting "remember this device", so it does not establish the coupling either. Removed the mechanism claim rather than assert it: the bullet now says the prompt is suppressed "for a limited period".

@mtantawy
mtantawy requested a review from tiagoengel August 6, 2026 14:18
@mtantawy

mtantawy commented Aug 6, 2026

Copy link
Copy Markdown
Member Author

@tiagoengel could you please have a look and confirm these changes are actually correct?
I had claude base them on the docs we have, the code, and manual investigations against our setup on Auth0

@tiagoengel tiagoengel left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good @mtantawy, just a few small comments


### MFA for your users

Light also applies its own MFA step to users signing in to the application:

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is missing that not all roles require it. I think reimbursement role and card holder don't require it. Don't remember exactly, but this would be defined in the auth0 action code.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch, added. One correction: Cardholder is not exempt — the only exempt roles are REIMBURSEMENT and INVOICE_APPROVER, and the check is "every role the user holds is in that set", so a Cardholder does get prompted.

Worth flagging since the belief that Cardholders skip MFA is wrong in the unsafe direction if it reaches a customer.


SSO controls how users authenticate — it does not create their Light accounts. Users are **not** provisioned automatically on first sign-in, so each user must already exist in Light before they can sign in through SSO.

Create users in advance under **Business partners > Users**, using the same email address they will present from your identity provider. A user who authenticates successfully at your identity provider but has no matching Light account will be denied access.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might be worth mentioning we support auto provisioning by integrating with HRM systems, but not JIT provisioning from the identity provider

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

got it, thanks man!

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added — the User Provisioning section now separates HRM auto-provisioning (supported, via Finch: imports employees, keeps active/inactive in step, assigns a default role) from JIT provisioning by the IdP (not supported), with a link to 11-8-hrm-finch.

…ording

- State which users are prompted for MFA. Any role beyond Reimbursement and
  Invoice approver requires a second factor; users limited to those two do
  not. Raised by @tiagoengel, who recalled Cardholder as exempt — it is not.

- Distinguish HRM-based auto-provisioning (supported, via Finch) from
  just-in-time provisioning by the identity provider (not supported), and
  link to the HRM integration article.

- Drop the claim that "remember this device" lapses when the Light session
  reaches its inactivity or maximum lifetime. Auth0 stores that choice in a
  separate remember-browser cookie, and the coupling is not established well
  enough to state in customer documentation.
@mtantawy
mtantawy merged commit fb00abb into main Aug 6, 2026
6 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