Skip to main content

Flask instrumentation for Watchlog APM with JSON OTLP export

Project description

flask_watchlog_apm

🔗 Website: https://watchlog.io

flask_watchlog_apm is a lightweight APM integration for Flask, built on OpenTelemetry. It provides:

  • Auto-instrumentation for Flask routes and underlying HTTP calls
  • Manual custom spans via the OpenTelemetry API
  • JSON-over-HTTP exporter (OTLP) compatible with Watchlog Agent
  • Environment detection (local vs in-cluster Kubernetes)
  • Configurable sampling, error-only and slow-only span export

Installation

Install from PyPI:

pip install flask_watchlog_apm

Or directly from GitHub:

pip install git+https://github.com/Watchlog-monitoring/flask_watchlog_apm.git

Quick Start

Initialize the APM before registering any routes:

# main.py
from flask import Flask
from flask_watchlog_apm.instrument import instrument_app

app = Flask(__name__)

# 1) Initialize Watchlog APM
instrument_app(
    app,
    service_name="my-flask-service",   # your service name
    headers={"Authorization": "Bearer <token>"},
    sample_rate=0.5,                   # random sample rate (0.0–1.0, capped at 0.3)
    send_error_spans=True,             # always export error spans
    error_tps=10,                      # max 10 error spans per second
    slow_threshold_ms=100              # always export spans >100ms
)

# 2) Define your routes
@app.route("/")
def hello():
    return "Hello, Watchlog APM!"

# 3) Run your app
if __name__ == "__main__":
    app.run(host="0.0.0.0", port=6000, debug=True)

What happens?

  1. Flask endpoints and outbound HTTP calls (via requests) are auto-instrumented.
  2. Spans are batched and sent as JSON to your Watchlog Agent (local or in-cluster).
  3. Configurable filters—sampling, error-only, slow-only—are applied.

Configuration Options

Parameter Type Default Description
service_name str required Name of your Flask service
otlp_endpoint str http://localhost:3774/apm Base OTLP URL (overrides auto-detection if different from default)
headers dict {} Additional HTTP headers for OTLP requests
batch_max_size int 200 Maximum spans per batch
batch_delay_ms int 5000 Delay in milliseconds between batch exports
sample_rate float 1.0 Random sampling rate (0.0–1.0, internal cap at 0.3)
send_error_spans bool False If True, always export spans with non-OK status
error_tps int None Max error spans to export per second (None = unlimited)
slow_threshold_ms int 0 If >0, always export spans slower than this threshold (ms)
export_timeout float 10.0 HTTP request timeout (seconds) for exporter POSTs

Manual Custom Spans

Use the OpenTelemetry API to create custom spans:

from opentelemetry import trace

tracer = trace.get_tracer(__name__)

@app.route("/db")
def fetch_db():
    with tracer.start_as_current_span("db.query", attributes={"db.system":"postgresql"}):
        # your DB logic here
        return "db query done"

Environment Detection

The package automatically detects the runtime environment:

  • Local (non-K8s): sends to http://localhost:3774/apm
  • Kubernetes (in-cluster): sends to http://watchlog-python-agent.monitoring.svc.cluster.local:3774/apm

Detection checks in order:

  1. Existence of /var/run/secrets/kubernetes.io/serviceaccount/token
  2. Presence of kubepods in /proc/1/cgroup
  3. DNS lookup of kubernetes.default.svc.cluster.local

Manual Override: You can override the endpoint by passing otlp_endpoint option in instrument_app() function


Docker Setup

When running your Flask app in Docker, you need to configure the correct agent endpoint.

Using otlp_endpoint Option (Recommended for Docker)

# main.py
from flask import Flask
from flask_watchlog_apm.instrument import instrument_app

app = Flask(__name__)

# Initialize Watchlog APM with explicit agent URL for Docker
instrument_app(
    app,
    service_name="my-flask-service",
    otlp_endpoint="http://watchlog-agent:3774/apm",  # Use container name
    sample_rate=0.5,
    send_error_spans=True,
    error_tps=10,
    slow_threshold_ms=100
)

@app.route("/")
def hello():
    return "Hello, Watchlog APM!"

if __name__ == "__main__":
    app.run(host="0.0.0.0", port=6000, debug=True)

Docker Compose Example:

version: '3.8'

services:
  watchlog-agent:
    image: watchlog/agent:latest
    container_name: watchlog-agent
    ports:
      - "3774:3774"
    environment:
      - WATCHLOG_APIKEY=your-api-key
      - WATCHLOG_SERVER=https://log.watchlog.ir
    networks:
      - app-network

  flask-app:
    build: .
    container_name: flask-app
    ports:
      - "6000:6000"
    environment:
      - FLASK_ENV=production
    depends_on:
      - watchlog-agent
    networks:
      - app-network

networks:
  app-network:
    driver: bridge

Docker Run Example:

# 1. Create network
docker network create app-network

# 2. Run Watchlog Agent
docker run -d \
  --name watchlog-agent \
  --network app-network \
  -p 3774:3774 \
  -e WATCHLOG_APIKEY="your-api-key" \
  -e WATCHLOG_SERVER="https://log.watchlog.ir" \
  watchlog/agent:latest

# 3. Run Flask app (make sure your code sets otlp_endpoint='http://watchlog-agent:3774/apm')
docker run -d \
  --name flask-app \
  --network app-network \
  -p 6000:6000 \
  my-flask-app

Important Notes:

  • When using Docker, use the container name as the hostname (e.g., watchlog-agent)
  • Both containers must be on the same Docker network
  • The agent must be running before your app starts
  • Set the otlp_endpoint option in your code to point to the agent container
  • If otlp_endpoint is not provided (or set to default), auto-detection will be used

License

MIT © Mohammadreza

Built for Watchlog.io

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

flask_watchlog_apm-1.1.0.tar.gz (6.6 kB view details)

Uploaded Source

File details

Details for the file flask_watchlog_apm-1.1.0.tar.gz.

File metadata

  • Download URL: flask_watchlog_apm-1.1.0.tar.gz
  • Upload date:
  • Size: 6.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.12.4

File hashes

Hashes for flask_watchlog_apm-1.1.0.tar.gz
Algorithm Hash digest
SHA256 259808067e7101338f723ef40e21098d5054f43def3839859c0821fd16ead6a0
MD5 75e76c9d54decb42a116bc018942e090
BLAKE2b-256 602e3d8f264e667af9c50bccaf8905c5d2777ffb19773ab89332c0d51532dfad

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page