# OAuth clients for your app

October 1, 2026 · Console

Until now, the only orders that reached your application were orders built for users you provisioned. If people signed in to your app or assistant with their own Layout account, their orders were invisible to you: no webhooks, no order reads, nothing in the console. A new console page fixes that.

## What changed

- **An OAuth clients page.** The console has a new **OAuth clients** page. Create a client with a name and up to ten redirect URIs, and you get a `client_id`. Each application can have up to ten clients.
- **Public clients with PKCE.** Authorization code with PKCE (S256), no client secret to keep. Each redirect URI must be https, or http on localhost for development, and Layout sends the code only to an exact match.
- **Their orders reach you.** An order a person places through your client reaches your [webhooks](https://developer.layout.link/reference/webhooks), `GET /v1/events`, `GET /v1/orders/:id` and the console's Orders page, the same as an order for a user you provisioned.

## How it connects

The person approves your app on Layout's consent screen, and your MCP client then acts as that person.

## What you see for each person

- **A stable id.** `user.id` on a webhook is a `usr_` id that stays the same for that person in your application and differs in every other one. It is not a provisioned user, so `POST /v1/users/:id/grant` does not accept it.
- **Webhooks while they are connected.** Once a person disconnects your app, their new events stop. `GET /v1/orders/:id` and the console keep showing the orders they already placed.
- **Deleting a client** closes it to new connections and stops every connected person from refreshing. An access token already issued keeps working for up to ten minutes, and orders it places in that time send no webhooks. Every order the client placed stays readable.

## Sandbox and production

The environment follows the person, not the client. An order is sandbox only when the person is a sandbox account that can sign in, and Layout issues those by hand. The test accounts on the console's Sandbox test accounts page are for users you provision and cannot sign in through OAuth.

**Testing with your own Layout account places a real order.** Your account is a production account, so it cannot connect through your client until your application is approved: the consent step returns `unauthorized_client`. Once it is approved, confirming charges your card and sends the order to the restaurant.

## What to do

If people sign in to your product with their own Layout account, create a client on the OAuth clients page and use its `client_id` in your MCP client's authorization flow. A client you registered yourself through dynamic registration still connects, but it belongs to no application, so its orders never reach you, and there is no way to claim one. Move to a client you create in the console. For a sign-in sandbox account, email [developer@layout.link](mailto:developer@layout.link).

If your webhook handler looks every `user.id` up among the users you provisioned, let it accept ids it has not seen: those are people who connected through your client.

## Breaking changes

None. Nothing changes for an application that creates no OAuth client. See [OAuth clients](https://developer.layout.link/reference/authentication#oauth-clients).
