added webhooks, moved app name and verison to simple config file
This commit is contained in:
@@ -13,9 +13,10 @@
|
||||
5. [Stats API](#stats-api)
|
||||
6. [Settings API](#settings-api)
|
||||
7. [Alerts API](#alerts-api)
|
||||
8. [Error Handling](#error-handling)
|
||||
9. [Status Codes](#status-codes)
|
||||
10. [Request/Response Examples](#request-response-examples)
|
||||
8. [Webhooks API](#webhooks-api)
|
||||
9. [Error Handling](#error-handling)
|
||||
10. [Status Codes](#status-codes)
|
||||
11. [Request/Response Examples](#request-response-examples)
|
||||
|
||||
---
|
||||
|
||||
@@ -2045,6 +2046,559 @@ curl -X GET http://localhost:5000/api/alerts/health
|
||||
|
||||
---
|
||||
|
||||
## Webhooks API
|
||||
|
||||
Manage webhook configurations for alert notifications with support for various authentication methods and delivery tracking.
|
||||
|
||||
### List Webhooks
|
||||
|
||||
List all configured webhooks with pagination.
|
||||
|
||||
**Endpoint:** `GET /api/webhooks`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Query Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Default | Description |
|
||||
|-----------|------|----------|---------|-------------|
|
||||
| `page` | integer | No | 1 | Page number (1-indexed) |
|
||||
| `per_page` | integer | No | 20 | Items per page (1-100) |
|
||||
| `enabled` | boolean | No | - | Filter by enabled status (true/false) |
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"webhooks": [
|
||||
{
|
||||
"id": 1,
|
||||
"name": "Slack Notifications",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"enabled": true,
|
||||
"auth_type": "none",
|
||||
"auth_token": null,
|
||||
"custom_headers": null,
|
||||
"alert_types": ["cert_expiry", "drift_detection"],
|
||||
"severity_filter": ["critical", "warning"],
|
||||
"timeout": 10,
|
||||
"retry_count": 3,
|
||||
"created_at": "2025-11-18T10:00:00Z",
|
||||
"updated_at": "2025-11-18T10:00:00Z"
|
||||
}
|
||||
],
|
||||
"total": 1,
|
||||
"page": 1,
|
||||
"per_page": 20,
|
||||
"pages": 1
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Examples:**
|
||||
```bash
|
||||
# List all webhooks
|
||||
curl -X GET http://localhost:5000/api/webhooks \
|
||||
-b cookies.txt
|
||||
|
||||
# List only enabled webhooks
|
||||
curl -X GET "http://localhost:5000/api/webhooks?enabled=true" \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Get Webhook
|
||||
|
||||
Get details for a specific webhook.
|
||||
|
||||
**Endpoint:** `GET /api/webhooks/{id}`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Path Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Description |
|
||||
|-----------|------|----------|-------------|
|
||||
| `id` | integer | Yes | Webhook ID |
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"webhook": {
|
||||
"id": 1,
|
||||
"name": "Slack Notifications",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"enabled": true,
|
||||
"auth_type": "bearer",
|
||||
"auth_token": "***ENCRYPTED***",
|
||||
"custom_headers": null,
|
||||
"alert_types": ["cert_expiry"],
|
||||
"severity_filter": ["critical"],
|
||||
"timeout": 10,
|
||||
"retry_count": 3,
|
||||
"created_at": "2025-11-18T10:00:00Z",
|
||||
"updated_at": "2025-11-18T10:00:00Z"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Error Responses:**
|
||||
|
||||
*404 Not Found* - Webhook doesn't exist:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Webhook 1 not found"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Example:**
|
||||
```bash
|
||||
curl -X GET http://localhost:5000/api/webhooks/1 \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Create Webhook
|
||||
|
||||
Create a new webhook configuration.
|
||||
|
||||
**Endpoint:** `POST /api/webhooks`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Request Body:**
|
||||
```json
|
||||
{
|
||||
"name": "Slack Notifications",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"enabled": true,
|
||||
"auth_type": "bearer",
|
||||
"auth_token": "your-secret-token",
|
||||
"custom_headers": {
|
||||
"X-Custom-Header": "value"
|
||||
},
|
||||
"alert_types": ["cert_expiry", "drift_detection"],
|
||||
"severity_filter": ["critical", "warning"],
|
||||
"timeout": 10,
|
||||
"retry_count": 3
|
||||
}
|
||||
```
|
||||
|
||||
**Request Body Fields:**
|
||||
|
||||
| Field | Type | Required | Description |
|
||||
|-------|------|----------|-------------|
|
||||
| `name` | string | Yes | Webhook name |
|
||||
| `url` | string | Yes | Webhook URL |
|
||||
| `enabled` | boolean | No | Whether webhook is enabled (default: true) |
|
||||
| `auth_type` | string | No | Authentication type: none, bearer, basic, custom (default: none) |
|
||||
| `auth_token` | string | No | Authentication token (encrypted when stored) |
|
||||
| `custom_headers` | object | No | JSON object with custom HTTP headers |
|
||||
| `alert_types` | array | No | Array of alert types to filter (empty = all types) |
|
||||
| `severity_filter` | array | No | Array of severities to filter (empty = all severities) |
|
||||
| `timeout` | integer | No | Request timeout in seconds (default: 10) |
|
||||
| `retry_count` | integer | No | Number of retry attempts (default: 3) |
|
||||
|
||||
**Success Response (201 Created):**
|
||||
```json
|
||||
{
|
||||
"status": "success",
|
||||
"message": "Webhook created successfully",
|
||||
"webhook": {
|
||||
"id": 1,
|
||||
"name": "Slack Notifications",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"enabled": true,
|
||||
"auth_type": "bearer",
|
||||
"alert_types": ["cert_expiry"],
|
||||
"severity_filter": ["critical"],
|
||||
"custom_headers": null,
|
||||
"timeout": 10,
|
||||
"retry_count": 3,
|
||||
"created_at": "2025-11-18T10:00:00Z"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Error Responses:**
|
||||
|
||||
*400 Bad Request* - Missing required fields:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "name is required"
|
||||
}
|
||||
```
|
||||
|
||||
*400 Bad Request* - Invalid auth type:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Invalid auth_type. Must be one of: none, bearer, basic, custom"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Examples:**
|
||||
```bash
|
||||
# Create webhook with no authentication
|
||||
curl -X POST http://localhost:5000/api/webhooks \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{
|
||||
"name": "Slack Notifications",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"alert_types": ["cert_expiry", "drift_detection"],
|
||||
"severity_filter": ["critical"]
|
||||
}' \
|
||||
-b cookies.txt
|
||||
|
||||
# Create webhook with bearer token authentication
|
||||
curl -X POST http://localhost:5000/api/webhooks \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{
|
||||
"name": "Custom API",
|
||||
"url": "https://api.example.com/webhook",
|
||||
"auth_type": "bearer",
|
||||
"auth_token": "your-secret-token"
|
||||
}' \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Update Webhook
|
||||
|
||||
Update an existing webhook configuration.
|
||||
|
||||
**Endpoint:** `PUT /api/webhooks/{id}`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Path Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Description |
|
||||
|-----------|------|----------|-------------|
|
||||
| `id` | integer | Yes | Webhook ID |
|
||||
|
||||
**Request Body:**
|
||||
```json
|
||||
{
|
||||
"name": "Updated Name",
|
||||
"enabled": false,
|
||||
"timeout": 15
|
||||
}
|
||||
```
|
||||
|
||||
**Note:** All fields are optional. Only provided fields will be updated.
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"status": "success",
|
||||
"message": "Webhook updated successfully",
|
||||
"webhook": {
|
||||
"id": 1,
|
||||
"name": "Updated Name",
|
||||
"url": "https://hooks.slack.com/services/XXX/YYY/ZZZ",
|
||||
"enabled": false,
|
||||
"auth_type": "none",
|
||||
"alert_types": ["cert_expiry"],
|
||||
"severity_filter": ["critical"],
|
||||
"custom_headers": null,
|
||||
"timeout": 15,
|
||||
"retry_count": 3,
|
||||
"updated_at": "2025-11-18T11:00:00Z"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Error Responses:**
|
||||
|
||||
*404 Not Found* - Webhook doesn't exist:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Webhook 1 not found"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Example:**
|
||||
```bash
|
||||
# Disable a webhook
|
||||
curl -X PUT http://localhost:5000/api/webhooks/1 \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"enabled":false}' \
|
||||
-b cookies.txt
|
||||
|
||||
# Update timeout and retry count
|
||||
curl -X PUT http://localhost:5000/api/webhooks/1 \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"timeout":20,"retry_count":5}' \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Delete Webhook
|
||||
|
||||
Delete a webhook and all associated delivery logs.
|
||||
|
||||
**Endpoint:** `DELETE /api/webhooks/{id}`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Path Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Description |
|
||||
|-----------|------|----------|-------------|
|
||||
| `id` | integer | Yes | Webhook ID |
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"status": "success",
|
||||
"message": "Webhook 1 deleted successfully"
|
||||
}
|
||||
```
|
||||
|
||||
**Error Responses:**
|
||||
|
||||
*404 Not Found* - Webhook doesn't exist:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Webhook 1 not found"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Example:**
|
||||
```bash
|
||||
curl -X DELETE http://localhost:5000/api/webhooks/1 \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Test Webhook
|
||||
|
||||
Send a test payload to a webhook to verify configuration.
|
||||
|
||||
**Endpoint:** `POST /api/webhooks/{id}/test`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Path Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Description |
|
||||
|-----------|------|----------|-------------|
|
||||
| `id` | integer | Yes | Webhook ID to test |
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"status": "success",
|
||||
"message": "HTTP 200",
|
||||
"status_code": 200,
|
||||
"response_body": "ok"
|
||||
}
|
||||
```
|
||||
|
||||
**Error Response (failure to connect):**
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Connection error: Failed to resolve hostname",
|
||||
"status_code": null
|
||||
}
|
||||
```
|
||||
|
||||
**Test Payload Format:**
|
||||
```json
|
||||
{
|
||||
"event": "webhook.test",
|
||||
"message": "This is a test webhook from SneakyScanner",
|
||||
"timestamp": "2025-11-18T10:00:00Z",
|
||||
"webhook": {
|
||||
"id": 1,
|
||||
"name": "Slack Notifications"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Example:**
|
||||
```bash
|
||||
curl -X POST http://localhost:5000/api/webhooks/1/test \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Get Webhook Delivery Logs
|
||||
|
||||
Get delivery history for a specific webhook.
|
||||
|
||||
**Endpoint:** `GET /api/webhooks/{id}/logs`
|
||||
|
||||
**Authentication:** Required
|
||||
|
||||
**Path Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Description |
|
||||
|-----------|------|----------|-------------|
|
||||
| `id` | integer | Yes | Webhook ID |
|
||||
|
||||
**Query Parameters:**
|
||||
|
||||
| Parameter | Type | Required | Default | Description |
|
||||
|-----------|------|----------|---------|-------------|
|
||||
| `page` | integer | No | 1 | Page number (1-indexed) |
|
||||
| `per_page` | integer | No | 20 | Items per page (1-100) |
|
||||
| `status` | string | No | - | Filter by status (success/failed) |
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"webhook_id": 1,
|
||||
"webhook_name": "Slack Notifications",
|
||||
"logs": [
|
||||
{
|
||||
"id": 101,
|
||||
"alert_id": 42,
|
||||
"alert_type": "cert_expiry",
|
||||
"alert_message": "Certificate expires in 15 days",
|
||||
"status": "success",
|
||||
"response_code": 200,
|
||||
"response_body": "ok",
|
||||
"error_message": null,
|
||||
"attempt_number": 1,
|
||||
"delivered_at": "2025-11-18T10:30:00Z"
|
||||
},
|
||||
{
|
||||
"id": 100,
|
||||
"alert_id": 41,
|
||||
"alert_type": "drift_detection",
|
||||
"alert_message": "Port drift detected",
|
||||
"status": "failed",
|
||||
"response_code": null,
|
||||
"response_body": null,
|
||||
"error_message": "Request timeout after 10 seconds",
|
||||
"attempt_number": 3,
|
||||
"delivered_at": "2025-11-18T09:00:00Z"
|
||||
}
|
||||
],
|
||||
"total": 2,
|
||||
"page": 1,
|
||||
"per_page": 20,
|
||||
"pages": 1
|
||||
}
|
||||
```
|
||||
|
||||
**Error Responses:**
|
||||
|
||||
*404 Not Found* - Webhook doesn't exist:
|
||||
```json
|
||||
{
|
||||
"status": "error",
|
||||
"message": "Webhook 1 not found"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Examples:**
|
||||
```bash
|
||||
# Get all delivery logs
|
||||
curl -X GET http://localhost:5000/api/webhooks/1/logs \
|
||||
-b cookies.txt
|
||||
|
||||
# Get only failed deliveries
|
||||
curl -X GET "http://localhost:5000/api/webhooks/1/logs?status=failed" \
|
||||
-b cookies.txt
|
||||
|
||||
# Get page 2
|
||||
curl -X GET "http://localhost:5000/api/webhooks/1/logs?page=2" \
|
||||
-b cookies.txt
|
||||
```
|
||||
|
||||
### Webhook Payload Format
|
||||
|
||||
When alerts are triggered, webhooks receive JSON payloads in this format:
|
||||
|
||||
```json
|
||||
{
|
||||
"event": "alert.created",
|
||||
"alert": {
|
||||
"id": 123,
|
||||
"type": "cert_expiry",
|
||||
"severity": "warning",
|
||||
"message": "Certificate for 192.168.1.10:443 expires in 15 days",
|
||||
"ip_address": "192.168.1.10",
|
||||
"port": 443,
|
||||
"acknowledged": false,
|
||||
"created_at": "2025-11-18T10:30:00Z"
|
||||
},
|
||||
"scan": {
|
||||
"id": 42,
|
||||
"title": "Production Network Scan",
|
||||
"timestamp": "2025-11-18T10:00:00Z",
|
||||
"status": "completed"
|
||||
},
|
||||
"rule": {
|
||||
"id": 3,
|
||||
"name": "Certificate Expiry Warning",
|
||||
"type": "cert_expiry",
|
||||
"threshold": 30
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Authentication Types
|
||||
|
||||
**None:**
|
||||
- No authentication headers added
|
||||
|
||||
**Bearer Token:**
|
||||
- Adds `Authorization: Bearer <token>` header
|
||||
- Token is encrypted in database
|
||||
|
||||
**Basic Authentication:**
|
||||
- Format: `username:password` in auth_token field
|
||||
- Automatically converts to HTTP Basic Auth
|
||||
- Credentials encrypted in database
|
||||
|
||||
**Custom Headers:**
|
||||
- Define any custom HTTP headers
|
||||
- Useful for API keys or custom authentication schemes
|
||||
- Example:
|
||||
```json
|
||||
{
|
||||
"X-API-Key": "your-api-key",
|
||||
"X-Custom-Header": "value"
|
||||
}
|
||||
```
|
||||
|
||||
### Retry Logic
|
||||
|
||||
Failed webhook deliveries are automatically retried with exponential backoff:
|
||||
|
||||
- **Attempt 1:** Immediate
|
||||
- **Attempt 2:** After 2 seconds
|
||||
- **Attempt 3:** After 4 seconds
|
||||
- **Attempt 4:** After 8 seconds
|
||||
- **Maximum delay:** 60 seconds
|
||||
|
||||
Retry count is configurable per webhook (0-5 attempts).
|
||||
|
||||
### Health Check
|
||||
|
||||
Check API health status.
|
||||
|
||||
**Endpoint:** `GET /api/webhooks/health`
|
||||
|
||||
**Authentication:** Not required
|
||||
|
||||
**Success Response (200 OK):**
|
||||
```json
|
||||
{
|
||||
"status": "healthy",
|
||||
"api": "webhooks",
|
||||
"version": "1.0.0-phase5"
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Example:**
|
||||
```bash
|
||||
curl -X GET http://localhost:5000/api/webhooks/health
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Error Handling
|
||||
|
||||
### Error Response Format
|
||||
@@ -2283,10 +2837,11 @@ API versioning will be implemented in future phases. For now, the API is conside
|
||||
- **Stats API** - Trends, summaries, historical data
|
||||
- **Settings API** - Application configuration, password management
|
||||
- **Alerts API** - Full implementation with filtering, acknowledgment, rules management, and statistics
|
||||
- **Webhooks API** - Webhook management, delivery tracking, authentication support, retry logic
|
||||
|
||||
### Endpoint Count
|
||||
- Total endpoints: 55+
|
||||
- Authenticated endpoints: 50+
|
||||
- Total endpoints: 65+
|
||||
- Authenticated endpoints: 60+
|
||||
- Public endpoints: 5 (login, setup, health checks)
|
||||
|
||||
---
|
||||
|
||||
Reference in New Issue
Block a user