@maiguard-hq/id-react
v1.1.2
Published
The MaiGuard ID sign-in button as a React component
Downloads
211
Readme
@maiguard-hq/id-react
"Continue with MaiGuard ID" as a React component.
npm install @maiguard-hq/id-react @maiguard-hq/idimport { MaiGuardIdButton } from "@maiguard-hq/id-react";
<MaiGuardIdButton
clientId="mgid_…"
redirectUri={window.location.origin + "/auth/callback"}
onSuccess={({ code, verifier }) => postToYourBackend({ code, verifier })}
onError={(err) => setError(err.message)}
/>The component renders the official button and manages PKCE, the popup, state validation, and the code handoff.
@maiguard-hq/id is a peer dependency, so install both.
What onSuccess receives
By default, { code, state, verifier } to hand to your own backend, which exchanges it with the client
secret (@maiguard-hq/id-node does that half) and
mints your own session. The browser never holds a durable credential.
Send the verifier along with the code. The SDK always requests with a code_challenge, so the token
endpoint always requires the matching code_verifier, confidential clients included. A code sent without
it cannot be spent and the exchange fails with invalid_grant.
With exchange, the component completes the exchange itself with PKCE and gives you the profile instead.
For an SPA with no backend:
<MaiGuardIdButton clientId="mgid_…" redirectUri={…} exchange onSuccess={(user) => setUser(user)} />
// { sub, profileType, email, name, accessToken, idToken }Keep those tokens in memory. Anything in localStorage is readable by every script on the page.
Key the account on sub
sub identifies the person. email and name describe the selected profile: under a business
profile they are the business's shared support address and legal name, identical for every member of it.
Keying an account on the email merges colleagues into one another.
Props
| Prop | Type |
| --- | --- |
| clientId | string, required |
| redirectUri | string, required, must exactly match one registered on the app |
| issuer | string, optional OIDC issuer override supplied by MaiGuard |
| scope | string, defaults to openid profile email |
| theme | brand (default), dark, light, outline |
| size | small, medium, large |
| text | continue_with, signin_with, signup_with |
| shape | rounded, pill |
| width | number of pixels, or "full" |
| mode | popup (default) or redirect |
| carry | your own JSON, returned by parseRedirect after a redirect |
| storage / storageTtlMs | where redirect mode parks the verifier; local survives a callback landing in another tab |
| authorizeUrl | skips discovery when the consent screen URL is all the app needs |
| exchange | boolean, exchange in the browser instead of returning a code |
| onSuccess / onError | callbacks |
| className / style | applied to the wrapper element |
Typed, with onSuccess narrowing on exchange.
Notes
The component delegates rendering to the core SDK so the official button remains consistent across host applications and frameworks.
Your callbacks are held in refs, so a parent that re-renders on every keystroke will not tear the button down and orphan an open popup mid-sign-in.
Changing clientId, redirectUri, issuer, mode, a string scope, or any appearance prop re-renders
the button. carry and a function scope deliberately do not: an object or arrow literal gets a new
identity every render, so depending on them would remount the button constantly. They are read from refs at
click time, so the current value is always used.
Before it works
Add your site's origin to the app's Allowed origins in the MaiGuard ID developer console. It defaults
to the origins of your redirect URIs, so it is usually already correct. A popup from an origin that is not
on the list is refused with ORIGIN_NOT_ALLOWED, and the error names the origins that would work.
Docs
https://docs.maiguard.com/maiguard-id-sdk
MIT
