FetchNode Python & Django SDK
Official Python and Django client SDK for FetchNode — the focused operations workspace for developers and teams managing multiple production Django websites.
FetchNode captures unhandled exceptions, error logs, slow database queries, N+1 query patterns, Celery background tasks, and authoritative business conversions with zero bloat and privacy-safe defaults.
Table of Contents
- Installation
- Quickstart (Django)
- Configuration Options
- Telemetry & Usage
- Privacy & Security Defaults
- Testing in Development
- Compatibility
- Links & Resources
- License
Installation
Version 0.4.3 fixes the default ingest endpoint and Django startup discovery for automatic logging. See the SDK changelog for changes and upgrade instructions.
Install via pip:
pip install fetchnode
Or using uv:
uv add fetchnode
(For Celery support, you can optionally install fetchnode[celery])
Quickstart (Django)
1. Add to INSTALLED_APPS
In your Django settings.py:
INSTALLED_APPS = [
# ...
"fetchnode",
]
2. Add the Middleware
Add FetchNodeMiddleware near the top of your MIDDLEWARE list for comprehensive request, query, and exception coverage:
MIDDLEWARE = [
"fetchnode.middleware.FetchNodeMiddleware",
"django.middleware.security.SecurityMiddleware",
# ...
]
3. Configure settings.FETCHNODE
import os
FETCHNODE = {
"API_KEY": os.environ.get("FETCHNODE_API_KEY", ""),
"API_URL": "https://fetch-node.com/api/events/ingest/",
"ENVIRONMENT": "production", # e.g. "production", "staging"
}
Set FETCHNODE_API_KEY to your private server key in the deployment environment. Keep it out of source control and browser code. Restart or redeploy Django, then verify a request and test error in FetchNode.
Django will automatically initialize FetchNode upon startup and capture unhandled exceptions, slow queries, and request telemetry.
Configuration Options
Configure via settings.FETCHNODE or environment variables:
| Setting Key | Environment Variable | Default | Description |
|---|---|---|---|
API_KEY |
FETCHNODE_API_KEY |
"" |
Required. Your private server key from project settings. Never use a public browser key here. |
ENDPOINT / API_URL |
FETCHNODE_ENDPOINT |
https://fetch-node.com/api/events/ingest/ |
Processing server URL. Point to your self-hosted instance if applicable. |
ENVIRONMENT |
FETCHNODE_ENVIRONMENT |
"development" |
Active environment name ("production", "staging"). |
RELEASE |
FETCHNODE_RELEASE |
"" |
Release tag or git commit hash (e.g. git rev-parse HEAD). |
ENABLED |
FETCHNODE_ENABLED |
True if API_KEY present |
Master toggle for event sending. |
CAPTURE_TRANSACTIONS |
— | True |
Track request duration and database query counts. |
CAPTURE_BODY |
— | False |
Privacy safeguard: request bodies are excluded by default. |
CAPTURE_HEADERS |
— | False |
Privacy safeguard: request headers are excluded by default. |
QUERY_SLOW_THRESHOLD_MS |
— | 100 |
Minimum execution time (ms) to flag an ORM query as slow. |
N_PLUS_ONE_THRESHOLD |
— | 5 |
Identical SELECT query repetition threshold to flag N+1 issues. |
SENSITIVE_KEYS |
— | (built-in list) | Extra field names to scrub from payloads (additive). |
Telemetry & Usage
Conversion & Lead Tracking
Track authoritative business events server-side (form submissions, payments, lead captures) with automatic session and visitor cookie attribution:
import fetchnode
def contact_view(request):
form = ContactForm(request.POST)
if form.is_valid():
lead = form.save()
# Track authoritative conversion
fetchnode.track(
"lead_submitted",
request=request,
idempotency_key=f"lead:{lead.id}",
properties={"source": "contact_form"},
conversion={"display_name": "Lead submitted", "funnel_order": 1, "primary": True},
)
return redirect("thank_you")
Why idempotency_key matters: Providing an idempotency_key (such as the database record ID or payment provider ID) ensures that retried requests, webhook replays, or browser reloads do not inflate your conversion metrics. FetchNode securely hashes the key client-side to produce a deterministic event ID.
Automatic Error Monitoring
Unhandled exceptions in Django views are caught by FetchNodeMiddleware, decorated with:
- The exact failing line of code and stack trace.
- In-app vs. framework/library frame classification.
- Database query count and execution time during the failing request.
- Correlated request ID and trace ID.
Manual Exception Capture
Capture handled exceptions or background exceptions:
import fetchnode
try:
external_service_call()
except ThirdPartyAPIError as exc:
fetchnode.capture_exception(exc, tags={"provider": "stripe"})
Celery Job Monitoring
FetchNode automatically instruments Celery when installed. You can also explicitly decorate tasks:
from fetchnode import capture_job
@capture_job(name="sync_external_inventory")
def sync_inventory():
...
Logging Handler
Send standard logging.ERROR and logging.CRITICAL records to FetchNode:
LOGGING = {
"version": 1,
"disable_existing_loggers": False,
"handlers": {
"fetchnode": {
"level": "ERROR",
"class": "fetchnode.handlers.FetchNodeHandler",
},
},
"loggers": {
"django": {
"handlers": ["fetchnode"],
"level": "ERROR",
"propagate": True,
},
},
}
Privacy & Security Defaults
FetchNode is engineered with a strict privacy-first architecture:
- Client-side Scrubbing: Sensitive keys (
password,token,secret,api_key,authorization,cookie,csrfmiddlewaretoken) and any compound keys likeuser_passwordorclient_secretare scrubbed before payload transmission. - Safe SQL Normalization: Raw SQL text is stripped of literals and parameters (
SELECT * FROM user WHERE id = 123becomesSELECT * FROM user WHERE id = ?). - No Unintentional PII: Request bodies, query strings, and raw IP addresses are excluded by default.
- Inspectable & Lightweight: The entire client is open-source Python with zero compiled binaries and zero unnecessary dependencies.
Testing in Development
In your local test suite (e.g. pytest or python manage.py test), FetchNode can be disabled by omitting the API key or explicitly setting:
# settings_test.py
FETCHNODE = {
"ENABLED": False,
}
To test that event transmission works in your staging environment, run:
import fetchnode
fetchnode.capture_message("FetchNode verification ping", level="info")
fetchnode.flush()
Compatibility
- Python: 3.10, 3.11, 3.12, 3.13, 3.14
- Django: 4.2 LTS, 5.0, 5.1, 5.2
- Operating Systems: Linux, macOS, Windows
Links & Resources
- Website & Cloud App: fetchnode.com
- Documentation & Setup Guide: fetchnode.com/guide/
- Changelog: fetchnode.com/changelog/
- GitHub Repository: github.com/remcovanwijk040/fetchnode
- Issue Tracker: github.com/remcovanwijk040/fetchnode/issues
License
MIT License. See LICENSE for details.
SDK changelog
0.4.3 — 2026-09-29
Fixed
- Use
https://fetch-node.com/api/events/ingest/as the default ingest endpoint. - Let Django automatically discover the SDK AppConfig when
fetchnodeis inINSTALLED_APPS, so startup installs logging and enabled instrumentation. - Preserve automatic AppConfig discovery for the legacy
fetchnode_clientname. - Correct the documentation URLs to the active FetchNode website.
Documentation
- Configure the private server key through
FETCHNODE_API_KEYand supply an explicit ingest URL. Keep private keys out of browser code and source control. - Show explicit server conversion declarations and non-personal event properties.
- Verify reception after restarting or redeploying Django.
Release checks
- Test the installed wheel outside the repository, including Django AppConfig and automatic logging setup.
- Exercise requests, exceptions, error logs and idempotent conversions against a local FetchNode collector, with project isolation checks.
- Check distribution metadata and the release tag before uploading to PyPI.
Upgrade
python -m pip install --upgrade fetchnode==0.4.3
Update your dependency file or lockfile, restart or redeploy Django, and verify a
request and test error in FetchNode. Existing installations can set API_URL
explicitly if they use their own collector.
Metadata
Release files for fetchnode 0.4.3
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| fetchnode-0.4.3.tar.gz | 23.5 kB | Without provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| fetchnode-0.4.3-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 54.8 kB
Release files / fetchnode-0.4.3.tar.gz
| Download URL | fetchnode-0.4.3.tar.gz |
|---|---|
| Size | 23.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
9749795732f775ba21aa498751da5c215bd298dcebafe9af5a207aaf65b37940
|
|
BLAKE2b-256 checksum How to use checksums |
6f31a33e62a917a438850365735e8065b25f4b8205af1508a7e5c39c9e531ccd
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.9 {"installer":{"name":"uv","version":"0.11.9","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"26.04","id":"resolute","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
|
Release files / fetchnode-0.4.3-py3-none-any.whl
| Download URL | fetchnode-0.4.3-py3-none-any.whl |
|---|---|
| Size | 31.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
8afee690290602ddce071916155a8f78b046a68ab67bae851970574e3f9e4e38
|
|
BLAKE2b-256 checksum How to use checksums |
d43ca0908f383483aaaf1b78afc5369c6e65060bf06afb8e72fe2036ed491b2a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.9 {"installer":{"name":"uv","version":"0.11.9","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"26.04","id":"resolute","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
|
Security for fetchnode 0.4.3
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.