Create an App
Register your application in Square Experience Cloud to get a client id and, if needed, a secret.
Every Base IdP integration starts the same way: you register an app in Square Experience Cloud. The registration is where Base IdP stores everything about your app — redirect URIs, scopes, audience, allowed auth methods, the display name on the consent screen. After this step you have a client id (and possibly a secret) to hand to the SDK. From that point on the SDK reads the rest of the configuration from the registration at runtime.
You do this once per environment per app. Production gets a production registration. Local development gets its own. Staging gets its own. The credentials are not interchangeable.
Open Square Experience Cloud
Go to Square Experience Cloud and click Create App. You will be asked for a display name, the application type, and the redirect URIs your app will use.
The display name is what users see on the consent screen and in audit logs. Pick something a real user would recognize, not an internal code name.
Pick the application type
The application type tells Base IdP what kind of client you are registering, which in turn decides whether you get a secret.
| Type | What it is | Gets a secret? |
|---|---|---|
native | iOS, Android, desktop, Electron — anything that runs on a user's device. | No. Public client, PKCE only. |
spa | Single-page apps running in a browser. | No. Public client, PKCE only. |
web | Server-rendered apps that exchange codes on a backend. | Yes. Confidential client. |
machine | Backend services that authenticate as themselves. | Yes. Confidential client. |
A common mistake is registering a mobile app as web because it has a
companion server. The mobile app itself is native. The companion server, if
it exchanges codes or verifies tokens, is web (or it does not need its own
registration at all if it only verifies).
Set the redirect URIs
The redirect URI is where Base IdP sends the user after a successful login. It
must match exactly what your app passes in the authorize request. No wildcards.
No trailing-slash differences. No http vs https confusion.
Mobile redirect URIs
For a mobile app, the redirect URI uses a custom URL scheme that your app registers with the OS. The scheme is whatever you want, as long as it is unique to your app.
myapp://auth/callback
twende-partners://auth/callback
zhio-driver://oauth/returnYou then register the scheme in ios/Runner/Info.plist and
android/app/src/main/AndroidManifest.xml (or the equivalent for your toolkit)
so the OS knows to hand the URL back to your app.
Web redirect URIs
For a web app, the redirect URI is a normal HTTPS URL on your domain.
https://app.example.com/api/auth/callback
http://localhost:3000/api/auth/callbackRegister all of them — production, staging, and every local-dev host you use. Base IdP will only redirect to one that is in the list.
Copy your credentials
When the registration is saved, you get back:
client_id— public. Safe to ship in a frontend bundle. This is the value you paste intoBASE_IDP_CLIENT_ID.client_secret— only forwebandmachineapps. This value must never leave a server. If it ends up in a Git repo or a mobile bundle, rotate it immediately.
BASE_IDP_CLIENT_ID=sq_live_yourapp_abc123
BASE_IDP_CLIENT_SECRET=sqk_3b7157c3d69f11a4af17d6c955ae31fd1fe3183e10b329c1ef4220c3badc0c18BASE_IDP_CLIENT_ID=sq_live_yourapp_abc123Credentials come from the console, never invented
Never hardcode, generate, or guess a client_id or client_secret. They are
issued by Base IdP at registration time. A secret in a public bundle is a
leaked secret — rotate it the moment you realize.
Verify the registration is live
Once the registration is saved, you can verify Base IdP knows about it by running the CLI's test command against your client id.
npx base-idp test --client-id sq_live_yourapp_abc123If the registration is active you see:
Testing Base IdP connection to https://authlayer.squareexp.com...
healthz: 200 OK
discovery: 200 OK
client-config: 200 OK
IdP is reachable.A client-config: 404 here means the client id does not resolve. A 403 means
the app is registered but disabled. Both are registration problems, not code
problems — fix them in the console before you write a line of integration.
What you do not need to copy
Once registered, Base IdP knows your app's settings and serves them from the client-config endpoint at runtime. You do not paste any of this into env.
| Resolved at runtime | Source |
|---|---|
| Issuer | SDK default, override only for local dev |
| Audience | Carried in the token, resolved from client config |
| Allowed scopes | POST /v1/client-config |
| Allowed redirect URIs | POST /v1/client-config |
| Allowed auth methods | POST /v1/client-config |
| Public signing keys | GET /v1/keys/paseto-v4-public |
If a tutorial or README anywhere asks you to put an issuer URL, an audience
string, or a list of scopes into a .env file, that document is out of date.
None of those values belong in your repository.
Editing the registration later
When you need to add a new redirect URI (because you ship a new local port, or deploy to staging) you go back to the console and add it. There is no code change in your app. The SDK re-fetches the client config the next time it needs to.
This is also how you change scopes, swap the consent-screen logo, or rotate the secret. Always in the console, never in code.