Auth0 Log Streams / Webhooks to a Private SIEM Collector via Skooh
Forward Auth0 authentication logs to your internal SIEM for security monitoring and incident investigation.
Overview
Auth0 Log Streams send authentication events to external systems: successful logins, failed attempts, MFA challenges, and more. For compliance and security, these logs need to reach your internal SIEM.
Setting Up
1. Create Skooh Endpoint
Create an endpoint named "Auth0 Logs" in Skooh.
2. Run the Skooh Proxy
Using the Desktop App:
- Download the Skooh Desktop App
- Enter your API key and hook token
- Set forwarding URL (e.g., `http://localhost:8080/collect/auth0\`)
- Click Connect
Using Docker:
docker run -d \\
--name skooh-auth0 \\
-e SKOOH_TOKEN=auth0-logs \\
-e SKOOH_API_KEY=your_api_key \\
-e FORWARD_URL=http://siem:8080/collect/auth0 \\
--restart unless-stopped \\
skooh/proxy
3. Configure Auth0 Log Stream
Note: See Auth0's Log Streams documentation for current setup instructions.
In Auth0 Dashboard:
- Go to Logs → Streams
- Click Create Log Stream
- Choose Custom Webhook
- Enter your Skooh URL
- Set Content-Type to `application/json`
- Set Content Format to `JSON Array`
Handling Auth0 Logs
Auth0 sends batches of log events:
app.post('/collect/auth0', express.json(), async (req, res) => {
const logs = req.body; // Array of log events
for (const log of logs) {
await processAuthLog(log);
}
res.status(200).send('OK');
});
async function processAuthLog(log) {
const {
type,
date,
user_id,
user_name,
connection,
ip,
user_agent,
details
} = log;
// Forward to SIEM
await siemClient.ingest({
source: 'auth0',
event_type: log.type,
timestamp: log.date,
user: {
id: user_id,
email: user_name
},
connection: connection,
network: {
client_ip: ip,
user_agent: user_agent
},
details: details
});
// Alert on critical events
if (isCriticalEvent(log)) {
await notifySecurityTeam(log);
}
}
Important Auth0 Event Types
const EVENT_TYPES = {
// Successful authentication
's': 'Success Login',
'ss': 'Success Silent Auth',
'ssa': 'Success Exchange',
// Failed authentication
'f': 'Failed Login',
'fp': 'Failed Login (incorrect password)',
'fu': 'Failed Login (invalid user)',
// MFA
'gd_auth_succeed': 'MFA Success',
'gd_auth_failed': 'MFA Failed',
// User lifecycle
'sapi': 'API Operation Success',
'fapi': 'API Operation Failed',
// Security
'limit_wc': 'Rate Limit on Wrong Credentials',
'pwd_leak': 'Password Leaked',
};
function isCriticalEvent(log) {
const criticalTypes = ['pwd_leak', 'limit_wc', 'fapi'];
return criticalTypes.includes(log.type);
}
Adding Authorization
Secure your webhook endpoint:
app.post('/collect/auth0', express.json(), (req, res) => {
// Auth0 can send an Authorization header
const authHeader = req.headers['authorization'];
const expectedToken = process.env.AUTH0_WEBHOOK_TOKEN;
if (authHeader !== \`Bearer \${expectedToken}\`) {
return res.status(401).send('Unauthorized');
}
// Process logs...
});
Configure the Authorization header in Auth0 Log Stream settings.
Replay for Incident Investigation
Security incident? Use Skooh replay:
- Identify the time window of the incident
- Filter webhooks in Skooh dashboard
- Replay events to your analysis tools
- Investigate without affecting production Auth0
Example investigation queries you can build:
// After replaying to your analysis DB
const suspiciousActivity = await db.auth0Logs.find({
user_id: compromisedUserId,
date: { $gte: incidentStart, $lte: incidentEnd }
}).sort({ date: 1 });
// Build timeline
suspiciousActivity.forEach(event => {
console.log(\`\${event.date}: \${EVENT_TYPES[event.type]} from \${event.ip}\`);
});
High Availability
For production SIEM collection:
# Run multiple proxy instances
docker run -d --name skooh-auth0-1 ...
docker run -d --name skooh-auth0-2 ...
# Use load balancer for FORWARD_URL
FORWARD_URL=http://siem-lb:8080/collect/auth0
Written by Skooh Team