API guide
Everything the dashboard does is available over HTTPS at https://links.t-api.de/v1 — the macOS app and the browser extension are thin clients on this same API. Authenticated endpoints live on that host only; requests on other hosts return 404 before auth runs.
The machine-readable contract is OpenAPI 3.1. This guide is the human version, with copy-paste examples.
Authentication
Pass a personal API key (starts with tl_, created under API keys in the dashboard) or a Ternis Auth SSO access token as a Bearer token:
curl https://links.t-api.de/v1/links \
-H "Authorization: Bearer tl_your_key_here"
Keys are stored as hashes — the full key is shown once at creation. Revoke keys you no longer use, via the dashboard or DELETE /v1/api-keys/{key} below.
Check compatibility first: GET /v1/ is public (no auth) and reports the active version:
curl https://links.t-api.de/v1/
# {"version":1,"status":"active","latest_version":1,...}
Conventions
- Versioning: every response carries
API-VersionandAPI-Latest-Versionheaders. Deprecated versions addDeprecation: trueplusSunset; retired versions answer410with{ message, version, latest_version }. - Errors are
{ "message": "…" }, or{ "message": "…", "errors": { … } }for validation failures. Rate limits answer429with aRetry-Afterheader — back off and retry. - Pagination: list endpoints return Laravel paginators (
data,current_page,last_page,total). - IDs are ULID strings. Timestamps are ISO-8601.
Links
# List your links (admins see everything; ?scope=mine restricts to own; ?tag= filters)
curl "https://links.t-api.de/v1/links?tag=launch" \
-H "Authorization: Bearer tl_your_key_here"
# Only links made with one API key (?api_key_id=<ulid>; ?api_key_id=none = dashboard-created)
curl "https://links.t-api.de/v1/links?api_key_id=<key-ulid>" \
-H "Authorization: Bearer tl_your_key_here"
# Create (custom slug optional; plan minimum length applies; domains must be verified)
curl -X POST https://links.t-api.de/v1/links \
-H "Authorization: Bearer tl_your_key_here" \
-H "Content-Type: application/json" \
-d '{"destination_url": "https://example.com/very-long-page", "domain_id": "<ulid>", "slug": "my-launch", "tags": ["launch"]}'
Every link created with a personal key stores that key (api_key_id, exposed as api_key with name/prefix on responses) and logs it in the activity history (link.created with api_key_id, api_key_name, api_key_prefix, auth_via). SSO-token calls leave api_key_id empty. Filter the dashboard list by origin (All origins / Dashboard only / one key) or open a key's dedicated page under API keys.
Show / update / deactivate (deleting stops resolution; stats stay)
curl https://links.t-api.de/v1/links/
-H "Authorization: Bearer tl_your_key_here"
-H "Content-Type: application/json"
-d '{"description": "Launch page"}'
curl -X DELETE https://links.t-api.de/v1/links/
No account and just scripting something quick? `POST /v1/links/public` creates guest links without any key — auto-generated slugs, fair-use limits, public system domains only:
```bash
curl -X POST https://links.t-api.de/v1/links/public \
-H "Content-Type: application/json" \
-d '{"destination_url": "https://example.com/quick-share"}'
Click analytics
# Raw click rows (paginated)
curl https://links.t-api.de/v1/links/<ulid>/clicks -H "Authorization: Bearer tl_your_key_here"
# Aggregates: totals, unique visitors, top referrers/countries, per-day counts
curl https://links.t-api.de/v1/links/<ulid>/clicks/summary -H "Authorization: Bearer tl_your_key_here"
These are the same numbers the dashboard charts are drawn from.
QR codes
# Any public URL, no auth (SVG default, ?format=png for PNG)
curl "https://links.t-api.de/v1/qr?url=https%3A%2F%2Fexample.com&format=png"
# QR for one of your links (auth; encodes the short URL)
curl "https://links.t-api.de/v1/links/<ulid>/qr?format=png" \
-H "Authorization: Bearer tl_your_key_here"
Domains
# Active system domains plus your own
curl https://links.t-api.de/v1/domains -H "Authorization: Bearer tl_your_key_here"
# Register a custom hostname (eligible plans only; starts unverified)
curl -X POST https://links.t-api.de/v1/domains \
-H "Authorization: Bearer tl_your_key_here" \
-H "Content-Type: application/json" \
-d '{"hostname": "links.example.com"}'
# → 201 with DNS TXT verification instructions until verified
# Publish the TXT record, then verify (200 {verified:true} or 422 {verified:false})
curl -X POST https://links.t-api.de/v1/domains/<ulid>/verify \
-H "Authorization: Bearer tl_your_key_here"
# Deactivate your domain (links and analytics are preserved)
curl -X DELETE https://links.t-api.de/v1/domains/<ulid> -H "Authorization: Bearer tl_your_key_here"
API keys
# List your keys (newest first; digests are never exposed)
curl https://links.t-api.de/v1/api-keys -H "Authorization: Bearer tl_your_key_here"
# Create — the raw token comes back as api_key exactly once
# show_on_dashboard=false hides the key's links from the main
# dashboard list (they stay on the key's own page)
curl -X POST https://links.t-api.de/v1/api-keys \
-H "Authorization: Bearer tl_your_key_here" \
-H "Content-Type: application/json" \
-d '{"name": "ci-runner", "show_on_dashboard": false}'
# Rename or toggle dashboard visibility (nothing is moved or deleted)
curl -X PATCH https://links.t-api.de/v1/api-keys/<ulid> \
-H "Authorization: Bearer tl_your_key_here" \
-H "Content-Type: application/json" \
-d '{"show_on_dashboard": true}'
# Revoke
curl -X DELETE https://links.t-api.de/v1/api-keys/<ulid> -H "Authorization: Bearer tl_your_key_here"
Request logging
Every /v1/* request (public or authenticated, success or error) writes one row to the API request log: method, host, path (no query string), status, duration, IP hash, truncated user-agent, plus user and key IDs when authenticated. Bodies, tokens and raw IPs are never stored; rows are kept indefinitely and are not deleted on request (see Privacy Policy).
Notifications
Your in-app inbox (security events, moderation decisions), newest first:
curl https://links.t-api.de/v1/notifications -H "Authorization: Bearer tl_your_key_here"
# Mark one read, or everything at once
curl -X POST https://links.t-api.de/v1/notifications/<id>/read \
-H "Authorization: Bearer tl_your_key_here"
curl -X POST https://links.t-api.de/v1/notifications/read \
-H "Authorization: Bearer tl_your_key_here"
Activity
Your personal history — actions you performed plus actions others (admins, system) performed on your stuff:
curl https://links.t-api.de/v1/activity -H "Authorization: Bearer tl_your_key_here"
Settings
Theme/layout plus email notification preferences (same rules as the dashboard settings form):
curl https://links.t-api.de/v1/settings -H "Authorization: Bearer tl_your_key_here"
curl -X PATCH https://links.t-api.de/v1/settings \
-H "Authorization: Bearer tl_your_key_here" \
-H "Content-Type: application/json" \
-d '{"theme": "dark", "nav_layout": "top", "notify_security_email": true}'