@nexusauth/express-helpers
v0.1.2
Published
Express.js integration helpers for NexusAuth - Middleware and route protection
Downloads
13
Maintainers
Readme
@nexusauth/express-helpers
Express middleware for NexusAuth - Optimized and flexible authentication middleware.
Features
- ✅ Optimized Middleware: Fast session validation
- ✅ Flexible: Required or optional authentication
- ✅ Custom Handlers: Error and unauthorized handlers
- ✅ Helper Functions: Extract user, session, sign out
- ✅ TypeScript Ready: Full type definitions with Request extensions
- ✅ Lightweight: Minimal dependencies
Installation
npm install @nexusauth/core @nexusauth/express-helpers express cookie-parserRequirements
@nexusauth/core: workspace:*express: ^4.0.0 || ^5.0.0cookie-parser: For reading session cookies
Quick Start
import express from 'express';
import cookieParser from 'cookie-parser';
import { auth } from './auth';
import { createAuthMiddleware } from '@nexusauth/express-helpers';
const app = express();
// Required: cookie-parser middleware
app.use(cookieParser());
// Protect all routes
app.use(createAuthMiddleware(auth));
app.get('/protected', (req, res) => {
res.json({ user: req.user });
});
app.listen(3000);Usage
Basic Authentication Middleware
Protect all routes with required authentication:
import { createAuthMiddleware } from '@nexusauth/express-helpers';
// All routes after this require authentication
app.use(createAuthMiddleware(auth));
app.get('/dashboard', (req, res) => {
res.json({ user: req.user });
});Required Authentication
Protect specific routes:
import { requireAuth } from '@nexusauth/express-helpers';
app.get('/profile', requireAuth(auth), (req, res) => {
res.json({ user: req.user });
});Optional Authentication
Attach user if present but don't block unauthenticated requests:
import { optionalAuth } from '@nexusauth/express-helpers';
app.get('/home', optionalAuth(auth), (req, res) => {
if (req.user) {
res.json({ message: `Welcome back, ${req.user.name}` });
} else {
res.json({ message: 'Welcome, guest' });
}
});Helper Functions
Extract user and session from request:
import { requireAuth, getCurrentUser, getCurrentSession } from '@nexusauth/express-helpers';
app.get('/me', requireAuth(auth), (req, res) => {
const user = getCurrentUser(req);
const session = getCurrentSession(req);
res.json({
user,
sessionExpires: session.expires,
});
});Sign Out
Handle user sign out:
import { requireAuth, signOut } from '@nexusauth/express-helpers';
app.post('/logout', requireAuth(auth), async (req, res) => {
await signOut(auth, req, res);
res.json({ message: 'Logged out successfully' });
});Advanced Usage
Custom Error Handlers
import { createAuthMiddleware } from '@nexusauth/express-helpers';
app.use(
createAuthMiddleware(auth, {
onUnauthorized: (req, res, next) => {
res.status(401).json({
error: 'Please log in',
redirectUrl: '/login',
});
},
onError: (error, req, res, next) => {
console.error('Auth error:', error);
res.status(500).json({ error: 'Authentication failed' });
},
})
);Conditional Authentication
Mix protected and public routes:
import { requireAuth, optionalAuth } from '@nexusauth/express-helpers';
// Public route
app.get('/public', (req, res) => {
res.json({ message: 'Public content' });
});
// Optional auth route
app.get('/feed', optionalAuth(auth), (req, res) => {
const user = req.user;
const feed = user ? getPersonalizedFeed(user.id) : getPublicFeed();
res.json({ feed });
});
// Protected route
app.get('/dashboard', requireAuth(auth), (req, res) => {
res.json({ user: req.user });
});Complete Example
Setup
// auth.ts
import { NexusAuth } from '@nexusauth/core';
import { PrismaAdapter } from '@nexusauth/prisma-adapter';
import { GoogleProvider } from '@nexusauth/providers';
import { PrismaClient } from '@prisma/client';
const prisma = new PrismaClient();
export const auth = new NexusAuth({
adapter: PrismaAdapter({ client: prisma }),
providers: [
GoogleProvider({
clientId: process.env.GOOGLE_ID!,
clientSecret: process.env.GOOGLE_SECRET!,
}),
],
secret: process.env.AUTH_SECRET!,
});Express Server
// server.ts
import express from 'express';
import cookieParser from 'cookie-parser';
import { auth } from './auth';
import {
requireAuth,
optionalAuth,
getCurrentUser,
signOut,
} from '@nexusauth/express-helpers';
const app = express();
app.use(express.json());
app.use(cookieParser());
// Public routes
app.get('/', (req, res) => {
res.json({ message: 'Welcome to the API' });
});
app.get('/login', (req, res) => {
res.json({ message: 'Login page' });
});
// Optional auth routes
app.get('/feed', optionalAuth(auth), (req, res) => {
const user = getCurrentUser(req);
if (user) {
res.json({ message: `Personalized feed for ${user.name}` });
} else {
res.json({ message: 'Public feed' });
}
});
// Protected routes
app.get('/profile', requireAuth(auth), (req, res) => {
const user = getCurrentUser(req);
res.json({
id: user.id,
email: user.email,
name: user.name,
});
});
app.patch('/profile', requireAuth(auth), async (req, res) => {
const user = getCurrentUser(req);
const updatedUser = await auth.adapter.updateUser({
id: user.id,
...req.body,
});
res.json({ user: updatedUser });
});
app.post('/logout', requireAuth(auth), async (req, res) => {
await signOut(auth, req, res);
res.json({ message: 'Logged out successfully' });
});
// Error handler
app.use((err: Error, req: express.Request, res: express.Response, next: express.NextFunction) => {
console.error(err);
res.status(500).json({ error: 'Internal server error' });
});
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});Protected API Routes
// routes/users.ts
import { Router } from 'express';
import { requireAuth, getCurrentUser } from '@nexusauth/express-helpers';
import { auth } from '../auth';
const router = Router();
// All routes in this router require authentication
router.use(requireAuth(auth));
router.get('/me', (req, res) => {
const user = getCurrentUser(req);
res.json({ user });
});
router.get('/settings', (req, res) => {
const user = getCurrentUser(req);
res.json({
userId: user.id,
settings: { /* ... */ },
});
});
router.delete('/account', async (req, res) => {
const user = getCurrentUser(req);
await auth.adapter.deleteUserSessions(user.id);
await auth.adapter.deleteUser(user.id);
res.json({ message: 'Account deleted' });
});
export default router;API Reference
Middleware
createAuthMiddleware(auth, options?)
Creates authentication middleware with custom options.
Parameters:
auth: NexusAuth instance (required)options: AuthMiddlewareOptions (optional)required: Boolean (default:true) - Whether authentication is requiredonUnauthorized: Custom unauthorized handleronError: Custom error handler
Returns: Express middleware function
requireAuth(auth, options?)
Creates middleware that requires authentication.
Parameters:
auth: NexusAuth instance (required)options: Omit<AuthMiddlewareOptions, 'required'> (optional)
Returns: Express middleware function
optionalAuth(auth)
Creates middleware that attaches user if present but doesn't block unauthenticated requests.
Parameters:
auth: NexusAuth instance (required)
Returns: Express middleware function
Helper Functions
getCurrentUser(req)
Extract current user from request.
Parameters:
req: Express Request
Returns: User object or null
getCurrentSession(req)
Extract current session from request.
Parameters:
req: Express Request
Returns: Session object or null
signOut(auth, req, res)
Sign out user (delete session and clear cookie).
Parameters:
auth: NexusAuth instancereq: Express Requestres: Express Response
Returns: Promise
TypeScript Support
Request type is automatically extended to include user and session:
import type { Request } from 'express';
app.get('/profile', requireAuth(auth), (req: Request, res) => {
// TypeScript knows about req.user and req.session
const userId = req.user.id;
const expires = req.session.expires;
});peerDependencies
{
"peerDependencies": {
"@nexusauth/core": "workspace:*",
"express": "^4.0.0 || ^5.0.0"
}
}Note: You also need cookie-parser middleware to read session cookies.
License
MIT
