RESTful API controlled and n8n-ready Jabber bot
421
RESTful API for file virus scanning using ClamAV.
/files/scan)/files/upload)/health, /ready)/metrics)/swagger) and OpenAPI specification (/swagger.yaml)# Clone the repository
git clone <repository-url>
cd clamav-api
# Run
go run ./cmd/server
Create a configs/config.yaml file:
app:
host: "0.0.0.0"
port: 8080
max_file_size: 100 # MB
clamav:
host: "localhost"
port: 3310
timeout: 60s
auth:
api_key: "your-secret-api-key"
webhook:
url: "http://localhost:8081/webhook"
timeout: 30s
retry_count: 3
storage:
temp_dir: "/tmp/clamav-api"
| Variable | Description | Default Value |
|---|---|---|
CONFIG_PATH | Path to config.yaml | configs/config.yaml |
GET /health
Response:
{"status": "ok"}
GET /ready
Response:
{
"status": "ok",
"services": {
"clamav": "ok"
}
}
GET /info
POST /files/scan
Header: API-Key: your-api-key
Content-Type: multipart/form-data
file: <binary>
Response:
{
"file_id": "550e8400-e29b-41d4-a716-446655440000",
"file_name": "document.pdf",
"file_size": 1024000,
"result": "clean",
"duration_ms": 150,
"scanned_at": "2026-03-21T12:00:00Z"
}
POST /files/upload
Header: API-Key: your-api-key
Content-Type: multipart/form-data
file: <binary>
Response (HTTP 202):
{
"file_id": "550e8400-e29b-41d4-a716-446655440002",
"file_name": "large_file.zip",
"file_size": 52428800,
"message": "File uploaded and queued for scanning",
"received_at": "2026-03-21T12:00:00Z"
}
For asynchronous scanning, the result is sent to the configured URL:
{
"file_id": "550e8400-e29b-41d4-a716-446655440002",
"file_name": "large_file.zip",
"file_size": 52428800,
"result": "clean",
"scanned_at": "2026-03-21T12:00:30Z",
"duration_ms": 500
}
GET /metrics
Available metrics:
clamav_http_requests_total - HTTP request counterclamav_http_request_duration_seconds - request duration histogramclamav_files_scanned_total - scanned files counterclamav_file_size_bytes - file size histogram# Build
docker build -t clamav-api .
# Run
docker run -p 8080:8080 \
-v $(pwd)/configs/config.yaml:/etc/clamav-api/config.yaml \
clamav-api
Run all services (ClamAV + API + webhook):
docker-compose up -d
View logs:
docker-compose logs -f
Stop:
docker-compose down
A Helm chart is provided under helm/ to deploy ClamAV, the API, and the
Prometheus exporter to a Kubernetes cluster.
kubectl configured against a target clustermetrics-server installed in the cluster (required only if you enable the
HorizontalPodAutoscaler via autoscaling.enabled=true)# Required: set a non-empty API key
helm install clamav-api ./helm \
--namespace clamav-api --create-namespace \
--set authApiKey=change-me-to-a-strong-secret
# Upgrade later
helm upgrade clamav-api ./helm --set authApiKey=change-me-to-a-strong-secret
authApiKeyis required —helm template/install fails if it is empty, because the API rejects an empty key at startup.
# Disable persistence (uses emptyDir instead of a PVC)
--set persistence.enabled=false
# Point Ingress at a specific IngressClass (default: cluster default)
--set ingress.className=nginx
# Enable autoscaling for the API Deployment
--set autoscaling.enabled=true \
--set autoscaling.maxReplicas=15
# Tune resource limits
--set resources.clamavApi.limits.memory=512Mi
| Key | Default | Description |
|---|---|---|
authApiKey | "" (required) | API key; rendered into a Secret |
replicaCount.clamavApi | 2 | API replicas (overridden by HPA when enabled) |
replicaCount.clamav | 1 | ClamAV replicas (uses a ReadWriteOnce PVC) |
persistence.enabled | true | Create PVC for ClamAV DB; false → emptyDir |
resources.* | see values.yaml | CPU/memory requests & limits per container |
autoscaling.enabled | false | Deploy a HorizontalPodAutoscaler for the API |
ingress.enabled | true | Create an Ingress for the API |
ingress.className | "" | IngressClass; empty → cluster default |
Both Deployments run with a hardened securityContext: containers run as
non-root, drop all Linux capabilities, disable privilege escalation, enable the
RuntimeDefault seccomp profile, and use a read-only root filesystem (writable
paths are provided via emptyDir volumes).
helm template clamav-api ./helm --set authApiKey=test
helm lint ./helm
go test ./tests/... -v
.
├── cmd/
│ └── server/
│ └── main.go # Entry point
├── internal/
│ ├── config/ # Configuration (viper)
│ ├── handler/ # HTTP handlers
│ ├── middleware/ # Auth, logging, metrics
│ ├── clamscan/ # ClamAV client
│ └── model/ # Data models
├── tests/ # Tests
├── configs/
│ └── config.yaml # Configuration
├── docs/
│ └── openapi.yaml # OpenAPI specification
└── Dockerfile
MIT
Content type
Image
Digest
sha256:2443992d9…
Size
31 MB
Last updated
3 months ago
docker pull aleskapot/jabber-bot