Easy OAuth is the most developer-friendly OAuth authentication library for Node.js applications. Implement Google, Facebook, GitHub, Twitter, LinkedIn, Apple, and Microsoft login in just 3 lines of code!
Perfect for any Node.js backend framework - Express, Fastify, Koa, Hono, Next.js API Routes, and more.
- π Super Simple API - Just 2 methods:
auth.url()andauth.callback() - π― 7 Providers Built-in - Google, Facebook, GitHub, Twitter, LinkedIn, Apple, Microsoft
- πͺ TypeScript Native - Full type safety with exported types
- π Normalized Response - Consistent user object across all providers
- π¦ Zero Dependencies - Lightweight and fast
- π¨ Framework Agnostic - Works with Express, Fastify, Koa, Hono, Next.js API, and any Node.js framework
- π‘οΈ Production Ready - Battle-tested OAuth implementations
npm install multi-oauthyarn add multi-oauthpnpm add multi-oauthimport auth from 'multi-oauth';
import express from 'express';
const app = express();
// Step 1: Configure providers
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID!,
clientSecret: process.env.GOOGLE_CLIENT_SECRET!
},
github: {
clientId: process.env.GITHUB_CLIENT_ID!,
clientSecret: process.env.GITHUB_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/callback'
});
// Step 2: Redirect to OAuth provider
app.get('/login/:provider', (req, res) => {
const authUrl = auth.url(req.params.provider);
res.redirect(authUrl);
});
// Step 3: Handle callback
app.get('/callback/:provider', async (req, res) => {
try {
const user = await auth.callback(req.params.provider, req);
res.json(user);
} catch (error) {
res.status(400).json({ error: error.message });
}
});
app.listen(3000, () => console.log('Server running on port 3000'));const auth = require('multi-oauth').default;
const express = require('express');
const app = express();
// Configure providers
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID,
clientSecret: process.env.GOOGLE_CLIENT_SECRET
},
facebook: {
clientId: process.env.FACEBOOK_CLIENT_ID,
clientSecret: process.env.FACEBOOK_CLIENT_SECRET
}
},
redirectUri: 'http://localhost:3000/callback'
});
// Login route
app.get('/login/:provider', (req, res) => {
res.redirect(auth.url(req.params.provider));
});
// Callback route
app.get('/callback/:provider', async (req, res) => {
try {
const user = await auth.callback(req.params.provider, req);
res.json(user);
} catch (error) {
res.status(400).json({ error: error.message });
}
});
app.listen(3000);| Provider | Status | Scopes |
|---|---|---|
| β Ready | openid, profile, email |
|
| β Ready | email, public_profile |
|
| GitHub | β Ready | user:email |
| β Ready | tweet.read, users.read |
|
| β Ready | openid, profile, email |
|
| Apple | β Ready | name, email |
| Microsoft | β Ready | openid, profile, email, User.Read |
Configure the OAuth manager with your provider credentials.
auth.configure({
providers: {
google: {
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
scope: ['openid', 'profile', 'email'] // Optional: custom scopes
}
},
redirectUri: 'http://localhost:3000/callback'
});Generate the OAuth authorization URL for a provider.
const authUrl = auth.url('google');
const authUrlWithState = auth.url('google', 'custom-state-value');Handle the OAuth callback and get the user profile.
const user = await auth.callback('google', req);Returns a normalized user object:
{
id: string; // Unique user ID from provider
name: string; // User's display name
email?: string; // User's email (if available)
avatar?: string; // Profile picture URL (if available)
provider: string; // Provider name (e.g., 'google')
raw: any; // Original response from provider
}- Go to Google Cloud Console
- Create a new project or select existing one
- Enable Google+ API
- Create OAuth 2.0 credentials
- Add authorized redirect URI:
http://localhost:3000/callback/google
google: {
clientId: 'xxx.apps.googleusercontent.com',
clientSecret: 'GOCSPX-xxx',
scope: ['openid', 'profile', 'email'] // Optional
}- Go to Facebook Developers
- Create a new app
- Add Facebook Login product
- Get App ID and App Secret
- Add redirect URI in settings
facebook: {
clientId: 'YOUR_APP_ID',
clientSecret: 'YOUR_APP_SECRET',
scope: ['email', 'public_profile'] // Optional
}- Go to GitHub Settings β Developer settings β OAuth Apps
- Create a new OAuth App
- Get Client ID and Client Secret
- Set callback URL:
http://localhost:3000/callback/github
github: {
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
scope: ['user:email'] // Optional
}- Go to Twitter Developer Portal
- Create a new app
- Enable OAuth 2.0
- Get Client ID and Client Secret
- Add callback URL
twitter: {
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
scope: ['tweet.read', 'users.read'] // Optional
}- Go to LinkedIn Developers
- Create a new app
- Get Client ID and Client Secret
- Add redirect URL
linkedin: {
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
scope: ['openid', 'profile', 'email'] // Optional
}- Go to Apple Developer
- Create a Services ID
- Configure Sign in with Apple
- Get Service ID and Key
apple: {
clientId: 'YOUR_SERVICE_ID',
clientSecret: 'YOUR_PRIVATE_KEY',
scope: ['name', 'email'] // Optional
}- Go to Azure Portal
- Register a new application
- Get Application (client) ID
- Create a client secret
- Add redirect URI
microsoft: {
clientId: 'YOUR_CLIENT_ID',
clientSecret: 'YOUR_CLIENT_SECRET',
scope: ['openid', 'profile', 'email', 'User.Read'] // Optional
}import auth from 'multi-oauth';
import express from 'express';
const app = express();
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID!,
clientSecret: process.env.GOOGLE_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/callback'
});
app.get('/login/:provider', (req, res) => {
res.redirect(auth.url(req.params.provider));
});
app.get('/callback/:provider', async (req, res) => {
try {
const user = await auth.callback(req.params.provider, req);
// Store user in session
req.session.user = user;
res.redirect('/dashboard');
} catch (error) {
res.redirect('/login?error=' + error.message);
}
});
app.listen(3000);import auth from 'multi-oauth';
import fastify from 'fastify';
const app = fastify();
auth.configure({
providers: {
github: {
clientId: process.env.GITHUB_CLIENT_ID!,
clientSecret: process.env.GITHUB_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/callback'
});
app.get('/login/:provider', async (request, reply) => {
const { provider } = request.params;
const authUrl = auth.url(provider);
reply.redirect(authUrl);
});
app.get('/callback/:provider', async (request, reply) => {
const { provider } = request.params;
const user = await auth.callback(provider, request);
reply.send(user);
});import auth from 'multi-oauth';
import Koa from 'koa';
import Router from 'koa-router';
const app = new Koa();
const router = new Router();
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID!,
clientSecret: process.env.GOOGLE_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/callback'
});
router.get('/login/:provider', (ctx) => {
ctx.redirect(auth.url(ctx.params.provider));
});
router.get('/callback/:provider', async (ctx) => {
const user = await auth.callback(ctx.params.provider, ctx.request);
ctx.body = user;
});
app.use(router.routes());// pages/api/login/[provider].ts
import auth from 'multi-oauth';
import type { NextApiRequest, NextApiResponse } from 'next';
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID!,
clientSecret: process.env.GOOGLE_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/api/callback'
});
export default function handler(req: NextApiRequest, res: NextApiResponse) {
const { provider } = req.query;
res.redirect(auth.url(provider as string));
}
// pages/api/callback/[provider].ts
export default async function handler(req: NextApiRequest, res: NextApiResponse) {
const { provider } = req.query;
const user = await auth.callback(provider as string, req);
// Handle user (set session, JWT, etc.)
res.json(user);
}import auth from 'multi-oauth';
import { Hono } from 'hono';
const app = new Hono();
auth.configure({
providers: {
google: {
clientId: process.env.GOOGLE_CLIENT_ID!,
clientSecret: process.env.GOOGLE_CLIENT_SECRET!
}
},
redirectUri: 'http://localhost:3000/callback'
});
app.get('/login/:provider', (c) => {
return c.redirect(auth.url(c.req.param('provider')));
});
app.get('/callback/:provider', async (c) => {
const user = await auth.callback(c.req.param('provider'), c.req);
return c.json(user);
});app.get('/callback/:provider', async (req, res) => {
try {
const user = await auth.callback(req.params.provider, req);
res.json(user);
} catch (error) {
if (error.message.includes('not configured')) {
res.status(500).json({ error: 'Provider not configured' });
} else if (error.message.includes('code not found')) {
res.status(400).json({ error: 'Authorization failed' });
} else if (error.message.includes('Token exchange failed')) {
res.status(401).json({ error: 'Invalid credentials' });
} else {
res.status(500).json({ error: 'Authentication failed' });
}
}
});Create a .env file:
# Google OAuth
GOOGLE_CLIENT_ID=xxx.apps.googleusercontent.com
GOOGLE_CLIENT_SECRET=GOCSPX-xxx
# GitHub OAuth
GITHUB_CLIENT_ID=Iv1.xxx
GITHUB_CLIENT_SECRET=xxx
# Facebook OAuth
FACEBOOK_CLIENT_ID=xxx
FACEBOOK_CLIENT_SECRET=xxx
# Twitter OAuth
TWITTER_CLIENT_ID=xxx
TWITTER_CLIENT_SECRET=xxx
# LinkedIn OAuth
LINKEDIN_CLIENT_ID=xxx
LINKEDIN_CLIENT_SECRET=xxx
# Microsoft OAuth
MICROSOFT_CLIENT_ID=xxx
MICROSOFT_CLIENT_SECRET=xxx
# Apple Sign In
APPLE_CLIENT_ID=xxx
APPLE_CLIENT_SECRET=xxxYou can create custom OAuth providers by extending the BaseOAuthProvider:
import { BaseOAuthProvider, OAuthUser } from 'multi-oauth';
class CustomOAuthProvider extends BaseOAuthProvider {
getName(): string {
return 'custom';
}
getAuthUrl(): string {
return 'https://custom.com/oauth/authorize';
}
getTokenUrl(): string {
return 'https://custom.com/oauth/token';
}
getUserProfileUrl(): string {
return 'https://custom.com/api/user';
}
getDefaultScopes(): string[] {
return ['read', 'email'];
}
normalizeUser(profile: any): OAuthUser {
return {
id: profile.id,
name: profile.full_name,
email: profile.email_address,
avatar: profile.avatar_url,
provider: 'custom',
raw: profile
};
}
}All types are exported for your convenience:
import type {
OAuthUser,
OAuthConfig,
ProviderConfig,
ProviderName,
OAuthRequest,
TokenResponse
} from 'multi-oauth';
// Use types in your application
function saveUser(user: OAuthUser) {
// Your code here
}
const config: OAuthConfig = {
providers: {
google: {
clientId: 'xxx',
clientSecret: 'xxx'
}
},
redirectUri: 'http://localhost:3000/callback'
};Most providers return email by default. Some providers (like GitHub) might require additional scopes or API calls:
github: {
clientId: 'xxx',
clientSecret: 'xxx',
scope: ['user:email'] // Request email access
}Yes! Easy OAuth is production-ready. Make sure to:
- Use HTTPS in production
- Store client secrets securely (use environment variables)
- Implement proper session management
- Handle errors appropriately
app.get('/login/:provider', (req, res) => {
const state = generateRandomString(); // Your implementation
req.session.oauthState = state;
res.redirect(auth.url(req.params.provider, state));
});
app.get('/callback/:provider', async (req, res) => {
// Verify state
if (req.query.state !== req.session.oauthState) {
return res.status(400).json({ error: 'Invalid state' });
}
const user = await auth.callback(req.params.provider, req);
res.json(user);
});Yes! The library is written in TypeScript but compiles to JavaScript. You can use it in any Node.js project:
const auth = require('multi-oauth').default;
// Use normallyauth.configure({
providers: {
google: {
clientId: 'xxx',
clientSecret: 'xxx',
scope: ['openid', 'profile', 'email', 'https://www.googleapis.com/auth/calendar']
}
},
redirectUri: 'http://localhost:3000/callback'
});Contributions are welcome! Please follow these steps:
- Fork the repository
- Create a feature branch:
git checkout -b feature/my-feature - Commit your changes:
git commit -am 'Add new feature' - Push to the branch:
git push origin feature/my-feature - Submit a pull request
# Clone the repository
git clone https://github.com/zaghamabbas786/multi-oauth.git
# Install dependencies
npm install
# Build the project
npm run build
# Watch mode
npm run watchMIT Β© [Your Name]
If you find Easy OAuth useful, please give us a star on GitHub! β
- Passport.js - More comprehensive but complex
- NextAuth.js - For Next.js specific projects
- Grant - OAuth middleware
- π« Email: zaghama96@gmail.com
- π Issues: GitHub Issues
Made with β€οΈ by developers, for developers.
Keywords: oauth, oauth2, authentication, google login, facebook login, github login, twitter login, linkedin login, apple login, microsoft login, social login, sso, single sign on, node.js authentication, express oauth, nextjs oauth, typescript oauth, simple oauth, easy authentication