OAuth (Google & GitHub)
Configuring Google and GitHub OAuth providers.
Raypx supports social sign-in with Google and GitHub. OAuth providers are loaded dynamically based on which environment variables are set, and each provider can be individually toggled with feature flags.
Google OAuth
Step 1: Create OAuth Credentials
- Go to the Google Cloud Console.
- Create a new project (or select an existing one).
- Navigate to APIs & Services > Credentials.
- Click Create Credentials > OAuth 2.0 Client ID.
- Set Application type to "Web application".
- Add Authorized redirect URIs:
http://localhost:3000/api/auth/callback/google(and your production URL). - Copy the Client ID and Client Secret.
Step 2: Set Environment Variables
VITE_PUBLIC_AUTH_GOOGLE_ID=your-google-client-id.apps.googleusercontent.com
AUTH_GOOGLE_SECRET=your-google-client-secret
VITE_PUBLIC_AUTH_GOOGLE_ENABLED=true| Variable | Required | Description |
|---|---|---|
VITE_PUBLIC_AUTH_GOOGLE_ID | Yes | Google OAuth Client ID (exposed to client). |
AUTH_GOOGLE_SECRET | Yes | Google OAuth Client Secret (server-only). |
VITE_PUBLIC_AUTH_GOOGLE_ENABLED | No | Set to "false" to disable Google sign-in. Defaults to enabled. |
GitHub OAuth
Step 1: Create OAuth App
- Go to GitHub Developer Settings.
- Click New OAuth App.
- Set Application name to your app name.
- Set Homepage URL to your app's URL.
- Set Authorization callback URL to
http://localhost:3000/api/auth/callback/github. - Copy the Client ID and generate a Client Secret.
Step 2: Set Environment Variables
AUTH_GITHUB_ID=your-github-client-id
AUTH_GITHUB_SECRET=your-github-client-secret
VITE_PUBLIC_AUTH_GITHUB_ENABLED=true| Variable | Required | Description |
|---|---|---|
AUTH_GITHUB_ID | Yes | GitHub OAuth Client ID (server-only). |
AUTH_GITHUB_SECRET | Yes | GitHub OAuth Client Secret (server-only). |
VITE_PUBLIC_AUTH_GITHUB_ENABLED | No | Set to "false" to disable GitHub sign-in. Defaults to enabled. |
Feature Flags
Both OAuth providers can be toggled independently without removing credentials:
# Disable Google (even if credentials are set)
VITE_PUBLIC_AUTH_GOOGLE_ENABLED=false
# Disable GitHub
VITE_PUBLIC_AUTH_GITHUB_ENABLED=falseThe sign-in form checks these flags at render time and only shows the corresponding SocialButton when the provider is enabled.
Dynamic Provider Loading
OAuth providers are loaded dynamically in createAuth(). If credentials are missing, the provider is simply not registered:
const socialProviders: Record<string, unknown> = {}
if (env.VITE_PUBLIC_AUTH_GOOGLE_ID && env.AUTH_GOOGLE_SECRET) {
socialProviders.google = {
clientId: env.VITE_PUBLIC_AUTH_GOOGLE_ID,
clientSecret: env.AUTH_GOOGLE_SECRET,
}
}
if (env.AUTH_GITHUB_ID && env.AUTH_GITHUB_SECRET) {
socialProviders.github = {
clientId: env.AUTH_GITHUB_ID,
clientSecret: env.AUTH_GITHUB_SECRET,
}
}
return betterAuth({
socialProviders: Object.keys(socialProviders).length > 0
? socialProviders
: undefined,
// ...
})This approach means you can safely commit .env.example with empty OAuth values. The providers will simply not appear in the sign-in UI until you configure real credentials.
Client Usage
SocialButton Component
Raypx provides a SocialButton component that handles OAuth sign-in:
import { SocialButton } from "@/components/social-button"
import { authClient } from "@/lib/auth-client"
<SocialButton
provider="google"
onClick={() => {
authClient.signIn.social(
{ provider: "google" },
{
onSuccess: () => navigate({ to: "/dashboard" }),
onError: (error) => {
toast.error(error.error.message || "Google sign-in failed")
},
},
)
}}
/>Direct API Usage
You can also call signIn.social() directly without the SocialButton component:
// Google
authClient.signIn.social({ provider: "google" }, { onSuccess, onError })
// GitHub
authClient.signIn.social({ provider: "github" }, { onSuccess, onError })Conditional Rendering
The sign-in form only renders social buttons when the corresponding provider is enabled. Here is the pattern used in the built-in SignInForm:
const googleEnabled =
typeof window !== "undefined" &&
import.meta.env.VITE_PUBLIC_AUTH_GOOGLE_ID &&
import.meta.env.VITE_PUBLIC_AUTH_GOOGLE_ENABLED !== "false"
const githubEnabled =
typeof window !== "undefined" &&
import.meta.env.VITE_PUBLIC_AUTH_GITHUB_ENABLED !== "false"GitHub OAuth requires AUTH_GITHUB_ID and AUTH_GITHUB_SECRET to be set server-side. Unlike Google, these are not exposed to the client -- the client-side check only looks at the VITE_PUBLIC_AUTH_GITHUB_ENABLED flag.