docs: make OAuth proxy content clearer (#8190)

Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: Taesu <bytaesu@users.noreply.github.com>
This commit is contained in:
Taesu
2026-03-13 23:46:35 -07:00
committed by Alex Yang
co-authored by Cursor Agent Taesu
parent 60eacd43dd
commit 3e11027de7
+43 -25
View File
@@ -3,49 +3,67 @@ title: OAuth Proxy
description: OAuth Proxy plugin for Better Auth
---
A proxy plugin, that allows you to proxy OAuth requests. Useful for development and preview deployments where the redirect URL can't be known in advance to add to the OAuth provider.
A proxy plugin that allows you to proxy OAuth requests. Useful for development and preview deployments where the redirect URL can't be known in advance to add to the OAuth provider.
## Installation
<Steps>
<Step>
### Add the plugin to your **auth** config
### Add the plugin to your auth config
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import { oAuthProxy } from "better-auth/plugins" // [!code highlight]
export const auth = betterAuth({
plugins: [
oAuthProxy({ // [!code highlight]
productionURL: "https://my-main-app.com", // Optional - if the URL isn't inferred correctly // [!code highlight]
currentURL: "http://localhost:3000", // Optional - if the URL isn't inferred correctly // [!code highlight]
}), // [!code highlight]
]
})
plugins: [
oAuthProxy({ // [!code highlight]
productionURL: "https://my-production-app.com", // [!code highlight]
}), // [!code highlight]
],
socialProviders: {
github: {
clientId: process.env.GITHUB_CLIENT_ID || "",
clientSecret: process.env.GITHUB_CLIENT_SECRET || "",
},
},
})
```
The plugin will automatically route OAuth requests through your production server.
</Step>
<Step>
### Add redirect URL to your OAuth provider
### Register the callback URL with your OAuth provider
For the proxy server to work properly, you’ll need to pass the redirect URL of your main production app registered with the OAuth provider in your social provider config. This needs to be done for each social provider you want to proxy requests for.
In your OAuth provider's developer console (e.g. GitHub, Google), register the callback URL using your **production** domain. For example:
```ts
```
https://my-production-app.com/api/auth/callback/github
```
Only the production callback URL needs to be registered. The plugin handles routing OAuth requests from preview and development environments through production automatically.
</Step>
<Step>
### Add trusted origins
Since preview and development servers redirect through production, you need to add them as `trustedOrigins` in your auth config:
```ts title="auth.ts"
export const auth = betterAuth({
plugins: [
oAuthProxy(),
],
socialProviders: {
github: {
clientId: "your-client-id",
clientSecret: "your-client-secret",
redirectURI: "https://my-main-app.com/api/auth/callback/github" // [!code highlight]
}
}
})
// ...other config
trustedOrigins: [ // [!code highlight]
"http://localhost:3000", // [!code highlight]
"https://my-app-*-preview.example.com", // [!code highlight]
], // [!code highlight]
})
```
</Step>
</Steps>
<Callout type="info">
All environments (production, preview, development) must share the same `BETTER_AUTH_SECRET`. The plugin uses it to encrypt and decrypt data passed between servers during the OAuth flow.
</Callout>
## How it works
The plugin allows you to use a single OAuth client (registered with your production URL) across multiple environments like preview deployments or local development.
@@ -73,8 +91,8 @@ This plugin is intended for development and preview environments. If `baseURL` a
## Options
**productionURL**: If this value matches the `baseURL` in your auth config, requests will not be proxied. Defaults to the `BETTER_AUTH_URL` environment variable.
**productionURL**: The URL of your production server. If this value matches the `baseURL` in your auth config, requests will not be proxied. Defaults to the `BETTER_AUTH_URL` environment variable.
**currentURL**: The application's current URL is automatically determined by the plugin. It first checks for the request URL if invoked by a client, then it checks the base URL from popular hosting providers, and finally falls back to the `baseURL` in your auth config. If the URL isn't inferred correctly, you can specify it manually here.
**currentURL**: The application's current URL is automatically determined by the plugin. It first checks the request URL, then vendor-specific environment variables from popular hosting providers, and finally falls back to the `baseURL` in your auth config. You only need to set this if the URL isn't being inferred correctly in your environment.
**maxAge**: Maximum age in seconds for encrypted profile payloads. Payloads older than this will be rejected to prevent replay attacks. Keep this value short (e.g., 30-60 seconds) to minimize the window for potential replay attacks while still allowing normal OAuth flows. Defaults to `60` seconds.