You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Commit 0b6d5d5
Browse filesBrowse the repository at this point in the historyBrowse files
Moves better-auth, @better-auth/oauth-provider, @better-auth/sso and
@better-auth/stripe (and packages/auth) from 1.6.27 to 1.7.12, which carries
the 1.7.7 fixes for the magic-link, OAuth proxy, device-authorization and
rate-limit advisories. Each place 1.7 changes behavior Sim relies on is adapted
so connects, sign-ins, the MCP OAuth provider and enterprise SSO keep working.
Dependencies
- @better-auth/core calls z.validate, added in zod 4.5; the root override keeps
zod on 4.3.6, so a version-pinned patch restores 1.6's safeParse form.
- The global @xmldom/xmldom 0.8.15 override is dropped: @better-auth/sso needs
0.9.12, and samlify, xml-crypto, mammoth, officeparser and plist keep 0.8.15.
- The oauth-provider 1.6.27 resource patch is obsolete and removed.
Integration connectors
- Generic OAuth no longer serves /oauth2/*; the registered
/api/auth/oauth2/callback/:id URIs are forwarded to core's /callback/:id, so
no provider registration changes. Clients link through linkSocial.
- Custom getToken uses the registered redirect URI; Google connectors use
explicit endpoints instead of discovery; scope rewrites move into the token
exchange; reserved authorization params (scope, nonce) are passed as options;
pkce stays off where it was off.
- Connector callbacks only complete an authenticated link and never sign up or
sign in a user; linking counts the profile email as verified.
- Account hooks identify connector callbacks by the account's provider, since
hook contexts carry the route pattern.
MCP OAuth provider
- Resources stay out of 1.7's static resource model via a signed sim_resource
parameter; public clients are recognized by token_endpoint_auth_method none;
dynamic registration infers the application type; registrations keep their
requested scopes; DPoP is refused and metadata advertises only what Sim
honors; access tokens revoked at sign-out are rejected.
- Migration 0447 adds 1.7's columns and tables expand-only, so 1.6 and 1.7 pods
share the schema during rollout. Runtime schema validation is off because
migrations own Sim's schema.
Enterprise SSO
- The legacy SAML ACS URL is forwarded to /sso/saml2/sp/acs/:id, so IdPs need
no change; new providers advertise the new URL.
- Registration matches 1.7's strict schemas (no mapping.id; idpMetadata as
metadata or entityID) and checks 1.7's sign-in policy on save.
- Migration 0448 spells out entityID for certificate-only providers and clears
wantAssertionsSigned where the SP metadata never asked for signed
assertions, keeping 1.6's accept-any-IdP-signature policy.
- POST sign-in/email-otp is refused: 1.7 deletes every linked account of an
unverified user there.
Copy file name to clipboardExpand all lines: apps/desktop/README.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -67,7 +67,7 @@ The main process and two preloads are bundled by esbuild into `dist/main.cjs`, `
67
67
2.`apps/sim/app/desktop/auth/page.tsx` requires a browser session (redirects through `/login?callbackUrl=…`) and renders a **Continue** gesture gate; only that click mints a one-time token (`POST /api/desktop/auth/handoff`) and sends the browser to the loopback (`http://127.0.0.1:<port>/auth/callback?token=…&state=…`, RFC 8252 §7.3). The gate is the security boundary — state and port are attacker-choosable in a crafted link, so a bare GET must never mint. The loopback is the single hand-back channel: no OS scheme registration, works identically in dev and packaged builds. Interception of loopback is mitigated the way PKCE mitigates it: the token is single-use, short-TTL, and bound to a 128-bit state the app compares in constant time. (RFC 8252's *most*-preferred callback is claimed-`https` / macOS universal links, which bind the OS to a verified app identity — a future hardening step that needs an associated-domains entitlement + `apple-app-site-association` on the origin.)
68
68
3. The loopback fires the callback in the main process: the app validates the state, then a renderer in the app partition POSTs the token to `/api/auth/one-time-token/verify` (same-origin ⇒ trustedOrigins/CSRF pass; better-auth sets the session cookie and burns the token) and loads `/workspace`.
69
69
-**The app gets its own session, never the browser's.** The token is minted by `POST /api/desktop/auth/handoff` (`apps/sim/lib/auth/desktop-handoff.ts`), which creates a *new* session row for the user and points the one-time token at that. Better-auth's own `generateOneTimeToken` binds to the *calling* session, so using it directly made the app and the authorizing browser share one row: signing out of either deleted the row the other was still presenting, and — because the session cookie cache is not revalidated against the database — the survivor kept looking signed in while every database-backed session resolution failed (the socket handshake logged `Session not found` and 401-looped). A session per device is what better-auth's own device authorization grant does and what RFC 8252 assumes: sign-out, revocation, and expiry apply to one surface at a time. **Do not "simplify" this back to `generateOneTimeToken`.**
70
-
- Integration connects are **same-window redirects** (`client.oauth2.link`), not popups. Unknown provider hosts stay in-window (lenient default); Google/Microsoft connects get a native dialog offering to finish in the browser — the browser is signed in after the login handoff, tokens land server-side, the app just refreshes.
70
+
- Integration connects are **same-window redirects** (`client.linkSocial`), not popups. Unknown provider hosts stay in-window (lenient default); Google/Microsoft connects get a native dialog offering to finish in the browser — the browser is signed in after the login handoff, tokens land server-side, the app just refreshes.
71
71
- The MCP OAuth popup (`mcp-oauth-*`) is allowed as a same-partition child so `window.opener.postMessage` keeps working.
72
72
- Sign-out **revokes server-side first** (`POST /api/auth/sign-out` from the app-origin renderer — a main-process `session.fetch` would be rejected by better-auth's origin check), then clears cookies/localStorage/IndexedDB/cache/service workers plus any pending handoff state. The revoke is not optional: since the app owns its own session row, clearing the partition alone would strand a live 30-day credential that nothing can revoke. Two signals trigger teardown: the `/login?fromLogout=true` navigation (fast path) **and** deletion of the better-auth session cookie confirmed by a `get-session` probe (robust backstop — catches every sign-out path, not just the settings one, and rotation can't cause a false teardown). API 401s (probe-confirmed) surface a native re-auth prompt.
Copy file name to clipboardExpand all lines: apps/docs/content/docs/cli/organizations.mdx
+2-2Lines changed: 2 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -912,7 +912,7 @@ sim organizations sso providers save [options]
912
912
|`--domain <value>`| Yes | Email domain already verified by this organization. |
913
913
|`--jit-provisioning-enabled`| No | Allow SSO sign-in to provision organization membership, subject to eligibility and available seats. Defaults to true. |
914
914
|`--no-jit-provisioning-enabled`| No | Send --jit-provisioning-enabled as false. |
915
-
|`--mapping <json\|@file>`| No | Identity-provider claims mapped to user fields. Defaults to {"id":"sub","email":"email","name":"name","image":"picture"}. (JSON, or @path / @- to read a file or stdin). |
915
+
|`--mapping <json\|@file>`| No | Identity-provider claims mapped to user fields. Defaults to {"email":"email","name":"name","image":"picture"}. (JSON, or @path / @- to read a file or stdin). |
916
916
|`--client-id <value>`| Conditional | Identity provider client identifier. Available when providerType is oidc. Required when providerType is oidc. |
917
917
|`--client-secret <value\|@file>`| Conditional | Write-only OIDC client secret; the redacted marker from providers get preserves an existing secret. Passing it inline exposes it to shell history and process listings. Required when --provider-type is oidc (@path / @- reads a file or stdin verbatim, including trailing newlines; @@value for a literal leading @). |
918
918
|`--scopes <json\|@file>`| No | OIDC scopes; offline_access is omitted. Available when providerType is oidc. Defaults to ["openid","profile","email"]. (JSON, or @path / @- to read a file or stdin). |
@@ -926,7 +926,7 @@ sim organizations sso providers save [options]
926
926
|`--jwks-endpoint <value>`| No | Optional signing-key endpoint; otherwise resolved through issuer discovery. Available when providerType is oidc. |
927
927
|`--entry-point <value>`| Conditional | Identity provider SAML sign-in endpoint. Available when providerType is saml. Required when providerType is saml. |
928
928
|`--cert <value>`| Conditional | Identity provider signing certificate. Available when providerType is saml. Required when providerType is saml. |
929
-
|`--callback-url <value>`| No | SAML callback URL; defaults to this provider’s Sim callback. Available when providerType is saml. |
929
+
|`--callback-url <value>`| No | SAML ACS URL advertised to the identity provider; defaults to this provider’s Sim ACS URL. Available when providerType is saml. |
930
930
|`--audience <value>`| No | SAML audience; omission preserves the saved value. Available when providerType is saml. |
931
931
|`--want-assertions-signed`| No | Require signed assertions; omission preserves the saved value. Available when providerType is saml. |
932
932
|`--no-want-assertions-signed`| No | Send --want-assertions-signed as false. |
Copy file name to clipboardExpand all lines: apps/docs/content/docs/cli/reference.mdx
+2-2Lines changed: 2 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -4179,7 +4179,7 @@ sim organizations sso providers save [options]
4179
4179
|`--domain <value>`| Yes | Email domain already verified by this organization. |
4180
4180
|`--jit-provisioning-enabled`| No | Allow SSO sign-in to provision organization membership, subject to eligibility and available seats. Defaults to true. |
4181
4181
|`--no-jit-provisioning-enabled`| No | Send --jit-provisioning-enabled as false. |
4182
-
|`--mapping <json\|@file>`| No | Identity-provider claims mapped to user fields. Defaults to {"id":"sub","email":"email","name":"name","image":"picture"}. (JSON, or @path / @- to read a file or stdin). |
4182
+
|`--mapping <json\|@file>`| No | Identity-provider claims mapped to user fields. Defaults to {"email":"email","name":"name","image":"picture"}. (JSON, or @path / @- to read a file or stdin). |
4183
4183
|`--client-id <value>`| Conditional | Identity provider client identifier. Available when providerType is oidc. Required when providerType is oidc. |
4184
4184
|`--client-secret <value\|@file>`| Conditional | Write-only OIDC client secret; the redacted marker from providers get preserves an existing secret. Passing it inline exposes it to shell history and process listings. Required when --provider-type is oidc (@path / @- reads a file or stdin verbatim, including trailing newlines; @@value for a literal leading @). |
4185
4185
|`--scopes <json\|@file>`| No | OIDC scopes; offline_access is omitted. Available when providerType is oidc. Defaults to ["openid","profile","email"]. (JSON, or @path / @- to read a file or stdin). |
@@ -4193,7 +4193,7 @@ sim organizations sso providers save [options]
4193
4193
|`--jwks-endpoint <value>`| No | Optional signing-key endpoint; otherwise resolved through issuer discovery. Available when providerType is oidc. |
4194
4194
|`--entry-point <value>`| Conditional | Identity provider SAML sign-in endpoint. Available when providerType is saml. Required when providerType is saml. |
4195
4195
|`--cert <value>`| Conditional | Identity provider signing certificate. Available when providerType is saml. Required when providerType is saml. |
4196
-
|`--callback-url <value>`| No | SAML callback URL; defaults to this provider’s Sim callback. Available when providerType is saml. |
4196
+
|`--callback-url <value>`| No | SAML ACS URL advertised to the identity provider; defaults to this provider’s Sim ACS URL. Available when providerType is saml. |
4197
4197
|`--audience <value>`| No | SAML audience; omission preserves the saved value. Available when providerType is saml. |
4198
4198
|`--want-assertions-signed`| No | Require signed assertions; omission preserves the saved value. Available when providerType is saml. |
4199
4199
|`--no-want-assertions-signed`| No | Send --want-assertions-signed as false. |
Copy file name to clipboardExpand all lines: apps/docs/content/docs/platform/enterprise/sso.mdx
+6-6Lines changed: 6 additions & 6 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -49,11 +49,11 @@ Use OIDC when your provider supports OpenID Connect, or SAML 2.0 for a SAML conn
49
49
|**Domain**| The verified email domain served by this connection, such as `acme.com`|
50
50
|**On first SSO sign-in**|**Automatic** adds new organization members; **Invite only** authenticates without adding membership. See [membership behavior](#membership-and-account-linking). |
51
51
52
-
For OIDC, also enter **Client ID** and **Client secret**. Sim discovers authorization, token, UserInfo, and JWKS endpoints from `{issuer}/.well-known/openid-configuration`. Under **Advanced options**, you can set **Scopes** (default `openid,profile,email`) and override authorization, token, or JWKS endpoints if discovery does not supply usable values.
52
+
For OIDC, also enter **Client ID** and **Client secret**. Sim discovers authorization, token, UserInfo, and JWKS endpoints from `{issuer}/.well-known/openid-configuration`. The issuer must match the `iss` claim of the provider's ID tokens exactly. Under **Advanced options**, you can set **Scopes** (default `openid,profile,email`) and override authorization, token, or JWKS endpoints if discovery does not supply usable values.
53
53
54
-
For SAML, also enter **Entry point URL**, the provider's SSO service URL, and **Identity provider certificate**, its Base64 X.509 certificate. Under **Advanced options**, you can configure Audience, Callback URL override, signed-assertion requirements, NameID format, and IdP metadata XML. Metadata does not replace the required certificate.
54
+
For SAML, also enter **Entry point URL**, the provider's SSO service URL, and **Identity provider certificate**, its Base64 X.509 certificate. Under **Advanced options**, you can configure Audience, Callback URL override, signed-assertion requirements, NameID format, and IdP metadata XML. Metadata does not replace the required certificate. When signed assertions are required, the identity provider must sign the assertion itself; a signature on the response alone is rejected.
55
55
56
-
**Attribute mapping** lets either protocol override the email, name, and stable user-ID claim names. Leave a mapping blank to use the protocol default.
56
+
**Attribute mapping** lets either protocol override the emailand name claim names. Leave a mapping blank to use the protocol default. Sim identifies each user by the OIDC `sub` claim or the SAML NameID, so choose a NameID format that stays stable for each person.
57
57
58
58
### Register the callback URL
59
59
@@ -62,9 +62,9 @@ Copy **Callback URL** for OIDC or **ACS URL (Reply URL)** for SAML, then registe
Sim Cloud uses `www.sim.ai`; self-hosted deployments use their public domain. Use your chosen **Provider ID** in both systems. For SAML, register the **SP Entity ID** as the provider's audience/Entity ID. If you set a **Callback URL override**, Sim's copyable ACS URL uses that override.
67
+
Sim Cloud uses `www.sim.ai`; self-hosted deployments use their public domain. SAML providers saved before the ACS URL changed keep `/api/auth/sso/saml2/callback/{provider-id}`, which still works, so their identity provider needs no change. Use your chosen **Provider ID** in both systems. For SAML, register the **SP Entity ID** as the provider's audience/Entity ID. If you set a **Callback URL override**, Sim's copyable ACS URL uses that override.
68
68
69
69
## Provider guides
70
70
@@ -186,7 +186,7 @@ See [Microsoft SAML setup](https://learn.microsoft.com/en-us/entra/identity/ente
186
186
3. Set **Relying party identifier** to Sim's **SP Entity ID**. Sim Cloud normally shows `https://www.sim.ai`; copy the value from your own deployment.
187
187
4. Add a **SAML Assertion Consumer Service** endpoint with HTTP POST binding:
5. Under **Certificates**, export the **Token-signing certificate** using **View Certificate → Details → Copy to File → Base-64 encoded X.509 (.CER)**. Paste the text, including its header and footer, into Sim.
192
192
6. Copy the **Federation Service identifier** from **Service → Federation Service Properties**, and the SSO endpoint, such as `https://adfs.acme.com/adfs/ls`.
0 commit comments