Auth Bypass in Restify
How Auth Bypass Manifests in Restify
Auth bypass in Restify applications typically exploits weaknesses in middleware ordering, route configuration, and authentication implementation. Understanding these specific patterns is crucial for securing your API endpoints.
Middleware Ordering Vulnerabilities
Restify's middleware execution order creates a critical attack surface. If authentication middleware isn't properly positioned before route handlers, attackers can access protected endpoints directly. Consider this vulnerable pattern:
const server = restify.createServer();
// Vulnerable: authentication middleware registered AFTER routes
server.get('/public', (req, res) => {
res.send(200, { message: 'Public data' });
});
server.get('/protected', (req, res) => {
// This handler executes BEFORE auth middleware
if (!req.user) {
return res.send(401, { error: 'Unauthorized' });
}
res.send(200, { message: 'Protected data' });
});
// Auth middleware comes too late
server.use(authMiddleware);
An attacker can hit /protected before authentication occurs, potentially receiving a 401 response that confirms endpoint existence without triggering security controls.
Route Parameter Confusion
Restify's route matching can create auth bypass opportunities when parameterized routes overlap with static routes. Consider:
// Vulnerable route ordering
server.get('/users/:id', authMiddleware, (req, res) => {
// Handles /users/123, /users/admin, etc.
res.send(200, getUserData(req.params.id));
});
server.get('/users/profile', (req, res) => {
// No authentication! Anyone can access user profiles
res.send(200, getProfileData());
});
An attacker might exploit this by requesting /users/profile to bypass authentication entirely, accessing sensitive profile data without credentials.
Authorization Bypass via Query Parameters
Restify applications often mishandle query parameters that override path-based authorization. This pattern is particularly dangerous:
server.get('/data/:id', authMiddleware, (req, res) => {
const recordId = req.params.id;
const overrideId = req.query.override || recordId;
// Security flaw: query parameter overrides path-based access
const data = getDataById(overrideId);
res.send(200, data);
});
An authenticated user could access /data/123?override=456 to view records they shouldn't have access to, bypassing authorization checks.
Content-Type Header Manipulation
Restify's content negotiation can be exploited when different content types trigger different authentication flows:
server.post('/upload', (req, res, next) => {
if (req.is('application/json')) {
// JSON requests go through auth
return authMiddleware(req, res, () => next());
}
// Other content types skip auth entirely!
next();
}, (req, res) => {
res.send(200, { message: 'Upload successful' });
});
Attackers can bypass authentication by sending non-JSON content types, exploiting the conditional authentication logic.
Restify-Specific Detection
Detecting auth bypass in Restify applications requires both static analysis and dynamic testing approaches. Here's how to identify these vulnerabilities in your codebase.
Static Code Analysis Patterns
Search your Restify codebase for these specific anti-patterns:
# Look for middleware ordering issues
grep -r "server.use(" . | grep -v "server.pre(" | head -20
# Find routes without authentication
grep -r "server\.(get|post|put|delete|patch)" . |
grep -v "authMiddleware" | grep -v "authenticate"
# Identify parameter-based auth bypasses
grep -r "req\.params" . | grep -v "auth" | head -10
Pay special attention to routes that handle sensitive operations without proper authentication middleware.
Dynamic Testing with middleBrick
middleBrick's black-box scanning approach is particularly effective for detecting auth bypass vulnerabilities in Restify applications. The scanner tests unauthenticated access to endpoints that should require authentication, identifying gaps in your security posture.
To scan your Restify API:
# Install middleBrick CLI
npm install -g middlebrick
# Scan your API endpoint
middlebrick scan https://yourapi.com
The scanner tests for:
- Unauthenticated access to protected endpoints
- Parameter manipulation that bypasses authorization
- Content-type-based authentication bypasses
- Route ordering vulnerabilities
middleBrick provides a security score (A-F) and specific findings with remediation guidance, helping you prioritize fixes based on severity.
Manual Testing Checklist
Complement automated scanning with manual testing:
- Test endpoint accessibility without authentication headers
- Attempt parameter manipulation (
?id=otheruser) - Send requests with different content types
- Verify middleware ordering by examining route definitions
- Check for overlapping route patterns
Document any successful bypasses with request/response examples to help prioritize remediation efforts.
Restify-Specific Remediation
Fixing auth bypass vulnerabilities in Restify requires both architectural changes and specific code patterns. Here are proven remediation strategies.
Proper Middleware Ordering
Always register authentication middleware before route definitions:
const server = restify.createServer();
// Step 1: Register authentication middleware first
server.use(authMiddleware);
server.use(restify.plugins.queryParser());
server.use(restify.plugins.bodyParser());
// Step 2: Define routes - they inherit auth automatically
server.get('/users/:id', (req, res) => {
// req.user is guaranteed to exist
const userId = req.params.id;
if (req.user.id !== userId) {
return res.send(403, { error: 'Forbidden' });
}
res.send(200, getUserData(userId));
});
This ensures all routes automatically inherit authentication without requiring explicit middleware in each handler.
Route Protection Pattern
Implement a centralized route protection function:
function protectedRoute(handler) {
return (req, res, next) => {
if (!req.user) {
return res.send(401, { error: 'Authentication required' });
}
return handler(req, res, next);
};
}
// Usage
server.get('/sensitive-data', protectedRoute((req, res) => {
res.send(200, { data: getSensitiveData() });
}));
This pattern prevents accidental exposure of routes and makes authentication requirements explicit.
Parameter Validation and Authorization
Implement strict parameter validation and authorization checks:
server.get('/data/:id', (req, res, next) => {
const recordId = req.params.id;
const overrideId = req.query.override;
// Block parameter override attacks
if (overrideId && overrideId !== recordId) {
return res.send(400, {
error: 'Parameter override not allowed',
detail: 'Cannot override path parameter with query parameter'
});
}
// Authorization check
if (!canAccessRecord(req.user, recordId)) {
return res.send(403, { error: 'Access denied' });
}
const data = getDataById(recordId);
res.send(200, data);
});
This prevents attackers from manipulating parameters to access unauthorized data.
Content-Type Enforcement
Enforce consistent authentication regardless of content type:
function requireAuth(req, res, next) {
if (!req.user) {
return res.send(401, { error: 'Authentication required' });
}
next();
}
// All routes require auth, regardless of content type
server.post('/upload', requireAuth, (req, res) => {
// Process upload
res.send(200, { message: 'Upload successful' });
});
This eliminates content-type-based authentication bypasses.
Route Collision Prevention
Avoid route pattern collisions by using more specific route definitions:
// Bad: overlapping routes
server.get('/users/:id', authMiddleware, userHandler);
server.get('/users/profile', profileHandler); // No auth!
// Good: explicit route protection
const protectedRoutes = ['/users/:id', '/users/profile', '/admin/*'];
protectedRoutes.forEach(route => {
server.get(route, authMiddleware, (req, res) => {
// Route-specific handlers
if (route.includes('/users/profile')) {
return profileHandler(req, res);
}
// ... other handlers
});
});
This ensures consistent authentication across similar route patterns.
Related CWEs: authentication
| CWE ID | Name | Severity |
|---|---|---|
| CWE-287 | Improper Authentication | CRITICAL |
| CWE-306 | Missing Authentication for Critical Function | CRITICAL |
| CWE-307 | Brute Force | HIGH |
| CWE-308 | Single-Factor Authentication | MEDIUM |
| CWE-309 | Use of Password System for Primary Authentication | MEDIUM |
| CWE-347 | Improper Verification of Cryptographic Signature | HIGH |
| CWE-384 | Session Fixation | HIGH |
| CWE-521 | Weak Password Requirements | MEDIUM |
| CWE-613 | Insufficient Session Expiration | MEDIUM |
| CWE-640 | Weak Password Recovery | HIGH |
Frequently Asked Questions
How can I test if my Restify API has auth bypass vulnerabilities?
middlebrick scan https://yourapi.com. It tests unauthenticated access to protected endpoints and identifies parameter manipulation vulnerabilities. Complement this with manual testing by attempting to access endpoints without authentication headers and manipulating query parameters to bypass authorization.