Issue Ticca Portal / Documentation / Endpoint contract
Sign in

Documentation

One subsection per page, so each topic stays readable. Use the tabs above to move between them.

How requests are signed

Every route is protected by a shared secret. The caller computes hex(HMAC-SHA256(access_key, path + "?" + query)) and sends it as a header. The scheme and host are deliberately excluded, so the signature stays valid behind proxies and load balancers.

X-Issue-Ticca-Signature: 1f0c9a…   # hex HMAC-SHA256 of "/issue-ticca/monitoring/?page=2"

The portal signs with the access key stored on the app's settings page, which is why that value must match the app's ISSUE_TICCA['ACCESS_KEY'] exactly.

Routes

PathReturns
/issue-ticca/health/ System health — Aggregated status of every configured subsystem (database, redis, rabbitmq, celery).
/issue-ticca/database-probe/ Database probe — Single-subsystem database check.
/issue-ticca/monitoring/ Incident log — Paginated incident log for exceptions and slow responses.
/issue-ticca/monitoring/open-by-type/ Open incidents by type — Open incident counts grouped by exception type.
/issue-ticca/monitoring/open-by-method/ Open incidents by endpoint — Open incident counts grouped by affected request URL.
/issue-ticca/stats/users/ Active users — In-process active-user counters.
/issue-ticca/stats/users/hourly/ Hourly activity — Unique users and request counts per hour, pruned to the retention window.

Paths are relative to the app's base URL and mount prefix. monitoring/ accepts ?status=, ?kind=, ?method=, ?page= and ?page_size= (capped at 100).

Status codes the portal treats specially

200 Data returned. Sync continues.
503 with a body The system is up but unhealthy. This is data, not a failure — the body carries the health report and the sync succeeds.
503 with error The app has no ACCESS_KEY configured. The sync fails with that message.
401 Our signature was rejected: the stored access key does not match.

Health payload

{
  "status": "healthy",
  "components": {
    "database": { "status": "healthy", "latency_ms": 3.1 },
    "redis":    { "status": "not_configured" },
    "celery":   { "status": "ok", "workers_online": 2 }
  },
  "failing": [],
  "summary": { "ok": 3, "healthy": 1 },
  "latency_ms": 12.3,
  "timestamp": "2026-09-30T10:00:00+00:00"
}

Component statuses map onto the portal's semantic levels. not_configured becomes "inactive" and is excluded from the failing-component percentage.

Incident fields the portal mirrors

FieldMeaning
incident_idUnique id, INC-YYYYMMDD-XXXXXXXX
kindexception or slow_response
exception_typeException class, or SlowResponse
affected_methodThe request path (query strings are not stored)
calls_before_closureHow often it fired — escalates the ticket priority
statusopen / closed; closing here closes the ticket