@rxbenefits/auth0-nextjs
v1.0.0
Published
Shared Auth0 authentication library for RxBenefits Next.js applications
Maintainers
Readme
@rxbenefits/auth0-nextjs
Shared Auth0 authentication library for RxBenefits Next.js applications. Provides seamless authentication across micro frontends deployed on the same domain.
Features
✅ Shared Session - All apps on the same domain share Auth0 session cookies ✅ Auto Token Injection - API handlers automatically include bearer tokens ✅ Simple Integration - Same code works for shell and all MFEs ✅ TypeScript - Full type safety ✅ Route Protection - Built-in middleware for protected routes ✅ SSO Support - Single sign-on across all applications
Installation
npm install @rxbenefits/auth0-nextjsPeer Dependencies
This package requires:
@auth0/nextjs-auth0^3.0.0next>=13.0.0react>=18.0.0
npm install @auth0/nextjs-auth0Quick Start
1. Environment Configuration
Create .env.local in your application:
AUTH0_SECRET=<generate-with-openssl-rand-hex-32>
AUTH0_BASE_URL=https://adminportal.rxbenefits.com
AUTH0_ISSUER_BASE_URL=https://your-tenant.auth0.com
AUTH0_CLIENT_ID=<your-client-id>
AUTH0_CLIENT_SECRET=<your-client-secret>
NEXT_PUBLIC_API_URL=https://api.rxbenefits.com2. Wrap Your App
pages/_app.tsx or app/layout.tsx:
import { RxAuthProvider } from '@rxbenefits/auth0-nextjs';
export default function App({ Component, pageProps }) {
return (
<RxAuthProvider>
<Component {...pageProps} />
</RxAuthProvider>
);
}3. Add Auth0 Handler
pages/api/auth/[...auth0].ts:
import { handleAuth } from '@auth0/nextjs-auth0';
export default handleAuth();4. Protect Routes (Optional)
middleware.ts:
import { withAuthMiddleware, defaultAuthMiddlewareConfig } from '@rxbenefits/auth0-nextjs';
export default withAuthMiddleware();
export const config = defaultAuthMiddlewareConfig;5. Create API Routes with Auto Token Injection
pages/api/organizations.ts:
import { createAuthApiHandler } from '@rxbenefits/auth0-nextjs';
export default createAuthApiHandler({
backendUrl: process.env.NEXT_PUBLIC_API_URL
});That's it! Your API calls now automatically include Auth0 bearer tokens.
Usage Examples
Using the Auth Hook
import { useRxAuth } from '@rxbenefits/auth0-nextjs';
function MyComponent() {
const { user, isLoading, error, login, logout, isAuthenticated } = useRxAuth();
if (isLoading) return <div>Loading...</div>;
if (error) return <div>Error: {error.message}</div>;
return (
<div>
{isAuthenticated ? (
<>
<p>Welcome, {user.name}!</p>
<button onClick={() => logout()}>Logout</button>
</>
) : (
<button onClick={() => login()}>Login</button>
)}
</div>
);
}Custom API Handler
import { createAuthApiHandler } from '@rxbenefits/auth0-nextjs';
export default createAuthApiHandler({
// Dynamic backend URL
backendUrl: (req) => {
if (req.url?.includes('/ben-admin/')) {
return process.env.BEN_ADMIN_API_URL!;
}
return process.env.NEXT_PUBLIC_API_URL!;
},
// Custom headers
customHeaders: {
'X-App-Name': 'Ben Admin MFE'
},
// Transform response
transformResponse: (data) => {
return {
...data,
timestamp: new Date().toISOString()
};
}
});Simple API Handler
import { createSimpleAuthApiHandler } from '@rxbenefits/auth0-nextjs';
// Just pass the backend URL
export default createSimpleAuthApiHandler(process.env.NEXT_PUBLIC_API_URL!);Custom Middleware
import { withAuthMiddleware } from '@rxbenefits/auth0-nextjs';
export default withAuthMiddleware({
// Skip auth for specific paths
beforeAuth: (req) => {
if (req.nextUrl.pathname.startsWith('/public')) {
return false; // Skip auth
}
return true; // Require auth
},
// Add custom logic after auth
afterAuth: (req, res) => {
// Add custom headers
res.headers.set('X-Authenticated', 'true');
return res;
}
});Permission Checks
import { useRxAuth } from '@rxbenefits/auth0-nextjs';
function AdminPanel() {
const { hasPermission, hasRole } = useRxAuth();
if (!hasPermission('admin:write')) {
return <div>Access Denied</div>;
}
if (!hasRole('admin')) {
return <div>Admin role required</div>;
}
return <div>Admin Panel Content</div>;
}API Reference
RxAuthProvider
Provider component that wraps your application with Auth0 authentication.
<RxAuthProvider
loginUrl="/custom-login" // Optional
profileUrl="/custom-profile" // Optional
>
{children}
</RxAuthProvider>createAuthApiHandler(options)
Creates an API route handler with automatic token injection.
Options:
backendUrl- Backend API base URL (string or function)pathResolver- Custom path resolver functioncustomHeaders- Additional headers (object or function)requireAuth- Whether to require authentication (default: true)transformResponse- Response transformation function
withAuthMiddleware(options)
Creates authentication middleware for route protection.
Options:
loginUrl- Custom login redirect URLbeforeAuth- Function to execute before auth checkafterAuth- Function to execute after successful auth
useRxAuth()
Hook for accessing authentication state and methods.
Returns:
user- Authenticated user objectisLoading- Loading stateerror- Error object if auth failedisAuthenticated- Boolean authentication statuslogin(returnTo?)- Function to redirect to loginlogout(returnTo?)- Function to logouthasPermission(permission)- Check user permissionhasRole(role)- Check user role
Architecture
Same Domain Deployment
All applications must be deployed on the same domain for shared session cookies:
adminportal.rxbenefits.com/ ← Shell
adminportal.rxbenefits.com/ben-admin ← MFE 1
adminportal.rxbenefits.com/admin-tools ← MFE 2How It Works
- User logs in → Auth0 session cookie set on
.rxbenefits.com - All apps can access the same session cookie
- Each app independently calls
getAccessToken()from shared session - Tokens are automatically injected into API calls
Independent Development
Each MFE can run standalone with its own Auth0 configuration:
# Shell
cd admin-portal-shell
npm run dev # http://localhost:3000
# Ben Admin MFE
cd ben-admin-mfe
npm run dev # http://localhost:3001In development, each app has its own session. In production (same domain), they share the session.
Production Deployment
Auth0 Configuration
Configure allowed callback URLs for all apps:
https://adminportal.rxbenefits.com/api/auth/callback
https://adminportal.rxbenefits.com/ben-admin/api/auth/callback
https://adminportal.rxbenefits.com/admin-tools/api/auth/callbackEnvironment Variables
Each app needs the same Auth0 configuration:
AUTH0_SECRET=<same-for-all-apps>
AUTH0_BASE_URL=https://adminportal.rxbenefits.com
AUTH0_ISSUER_BASE_URL=https://your-tenant.auth0.com
AUTH0_CLIENT_ID=<same-for-all-apps>
AUTH0_CLIENT_SECRET=<same-for-all-apps>Troubleshooting
"Missing authentication token" errors
Cause: API handler can't access Auth0 session Fix: Ensure all apps are on the same domain in production
CORS errors
Cause: Different domains in development Fix: Expected in dev. Will work in production on same domain.
Token not found
Cause: User not logged in or session expired
Fix: Redirect to /api/auth/login
License
MIT © RxBenefits
Support
For issues and questions:
- GitHub Issues: https://github.com/RxBenefits/auth0-nextjs/issues
- Internal Slack: #engineering
Built with ❤️ by RxBenefits Engineering
