API Troubleshooting and Support Diagnostics
Use this page when an API request fails, a third-party client cannot authenticate, a gateway behaves differently than expected, or Support asks for a safe diagnostic packet.
Quick Triage
- Confirm you are using the right API surface and base URL.
- Confirm the request uses a supported authentication header for that surface.
- Capture the response
X-Request-ID, timestamp, route, HTTP status code, and sanitized error body. - Use the common error table below to check whether the issue is auth, permissions, request shape, rate/credit limits, or a transient failure.
- If you still need help, send Support the evidence packet at the end of this page.
Do not copy raw prompts, API keys, bearer tokens, customer data, private files, or complete response bodies into support tickets unless Support specifically asks for a redacted sample.
Pick The Right API Surface
| Use case | Endpoint or base URL | Notes |
|---|---|---|
| Hatz-native chat, agents, server-side tools, recursive tool calling | https://ai.hatz.ai/v1/chat/completions |
Uses the Hatz harness. Supports Hatz model IDs, auto, and agent-{id} where available. See Chat Completions. |
| OpenAI Responses-compatible clients | https://ai.hatz.ai/v1/openai as the SDK base URL, or POST /v1/openai/responses directly |
Client manages tools. The route mirrors OpenAI Responses-style request and response shapes. See OpenAI Responses. |
| Anthropic Messages-compatible clients | https://ai.hatz.ai/v1/anthropic as the SDK base URL, or POST /v1/anthropic/messages directly |
Client manages tools. The Anthropic SDK appends /v1/messages to the configured base URL. See Anthropic Messages. |
| Workflow runs | POST /v1/workflows/run, then GET /v1/workflows/{job_id} |
Workflow execution is asynchronous. The run endpoint starts the job and returns a job_id; poll for status and outputs. See Workflows. |
| File uploads and processing | /v1/files/upload, /v1/files/upload-url, then GET /v1/files/{file_id}/status |
File processing is asynchronous. Poll until the file is ready before using it in chat, app, workflow, or agent requests. See File Upload. |
| Usage analytics | /v1/usage/* |
Requires the API key owner to have permission for the requested tenant/usage view. See Usage Analytics. |
When the OpenAPI reference shows paths like /chat/completions, prepend the production server base URL shown in the reference: https://ai.hatz.ai/v1.
Authentication Checklist
| Surface | Supported API-key auth | Common failure |
|---|---|---|
| Hatz REST endpoints | X-API-Key: <your-api-key> |
Sending an API key as Authorization: Bearer to a non-compatibility endpoint returns an auth error. |
| OpenAI-compatible endpoint | Authorization: Bearer <your-api-key> or X-API-Key: <your-api-key> |
Using the wrong base URL, such as the Hatz-native /v1 base with an OpenAI client that appends /responses. |
| Anthropic-compatible endpoint | Authorization: Bearer <your-api-key> or X-API-Key: <your-api-key> |
Using the wrong base URL; Anthropic SDK clients should use https://ai.hatz.ai/v1/anthropic. |
Unsupported public API-key auth forms:
- Query-string API keys such as
?api_key=.... - Basic auth.
- Cookie/session auth for external API-key integrations.
- Sending raw API keys in request bodies.
Each API key is tied to a Hatz user. The key inherits that user's tenant, role, package, model, app, workflow, and usage permissions. If a key works for one endpoint but not another, check the key owner's role and tenant access before treating it as an endpoint defect.
Request IDs
Hatz API responses include an X-Request-ID response header. You can also send your own X-Request-ID header on the request; Hatz will use it as the request ID for that request.
If you send your own request ID, use a short opaque value such as support-check-2026-06-27-001. Do not include emails, tenant names, prompts, secrets, customer records, or other sensitive data in the request ID.
Use request IDs when escalating issues to Support:
curl 'https://ai.hatz.ai/v1/chat/models' \
-H "X-API-Key: $HATZ_API_KEY" \
-H "X-Request-ID: support-check-2026-06-27-001" \
-i
Copy the returned X-Request-ID value into your support ticket. If you generated the ID, include both your sent ID and the response header value.
Common Error Classes
| Status | What it usually means | First checks |
|---|---|---|
400 |
Malformed request or unsupported option | Validate JSON, endpoint path, content type, model field, and request shape for the chosen gateway. |
401 |
Missing or invalid authentication | Confirm the auth header type, that the key has not expired, and that the client is pointed at the correct gateway base URL. |
403 |
Authenticated but not allowed | Check user role, tenant access, MSP/customer scope, feature availability, and endpoint permissions. |
404 |
Resource not found or not accessible to this user | Confirm IDs, tenant scope, workflow/app/file ownership, and whether the item is shared with the API key owner. |
422 |
Request shape failed validation | Compare body fields to the Scalar reference and remove fields unsupported by that endpoint. |
429 |
Credit, model, tenant, role, package, concurrency, or provider-side limit | Check usage state, model availability, package/role limits, and whether retries are creating concurrency pressure. |
5xx |
Server, provider, or transient infrastructure failure | Retry once if safe, then send Support the request ID, timestamp, route, sanitized error, and reproduction steps. |
Do not assume every 429 is the same issue. It can reflect credit limits, model availability, provider throttling, or an empty allowed model set. Include the endpoint, model, user/tenant context, and request ID so Support can route it correctly.
For model IDs, token behavior, credit accounting, and rate-limit interpretation, see Model Compatibility.
Email endpoint restrictions
POST /v1/emails/send is a self-preview endpoint. It sends to the authenticated
account's email address with the platform sender. Submitted to_email and
from_email values do not change delivery. Extra recipients (cc/bcc), attachments,
and unsupported form fields return 422. Saved templates must be accessible to
the caller. The email template editor's Send Test Email button follows this
same rule and no longer offers a recipient field.
POST /v1/emails/send/default is reserved for approved platform service API keys.
User sessions and personal API keys return 403, even if the owner is an
administrator. These routes are not a general-purpose outbound email service.
This narrows the previously advertised authentication and recipient contract;
existing integrations that send to other recipients must stop using these routes.
For a suspected platform notification failure, contact Support with the request
ID, route, timestamp and status code; do not send credentials or message content.
Invitation permission refusals
POST /v1/platform/users/invite returns 403 when the invitation service confirms that
the caller cannot manage users or assign a requested role for the organization. The
message is: “You do not have permission to invite users with these roles for this
organization.” No memberships or invitation emails are created by that refused request.
Ask an administrator to check your access to the target organization and the requested
roles before submitting again. This response does not mean an invitation is pending.
LLM Gateway Access and Activation
Where LLM Gateway is available to your MSP, an MSP administrator can open Settings → LLM Gateway, set the MSP monthly budget and default and maximum tenant budgets, review the existing-tenant preview, and accept the billing notice before activation. The page names any setup blockers. If activation fails, retry with the same budgets; the flow preserves the activation attempt across a page reload.
Under an active MSP, tenants enrolled in LLM Gateway use USD billing. Eligible existing tenants shown in the activation preview can continue using legacy credits. Other tenants cannot make compatibility requests until enabled, and a tenant disabled by its MSP is refused even if it previously had access.
For OpenAI Responses and Anthropic Messages requests:
403 permission_errorwith “LLM Gateway is not enabled for your organization” means the tenant has not been enabled for this billing path. Contact your MSP administrator.403 permission_errorwith “LLM Gateway access for your organization has been disabled by your provider” means your MSP has disabled gateway access. Contact your MSP administrator before retrying.- A disabled Connect a client action on the tenant page includes an explanation of the access requirement. Changing API keys does not enable the tenant.
These access refusals happen before model dispatch and do not create a gateway usage charge. Do not retry them automatically as transient failures.
Gateway Caveats
OpenAI-compatible Responses:
- Use
https://ai.hatz.ai/v1/openaias the OpenAI-compatible client base URL. - Use normal Hatz model IDs returned by
/v1/chat/models. - Client-side tools are managed by your client. Hatz does not run the Hatz recursive tool harness on this route.
- Unknown top-level request fields may be ignored for forward compatibility.
previous_response_idandmetadataare currently unsupported on this compatibility route.
Anthropic-compatible Messages:
- Use
https://ai.hatz.ai/v1/anthropicas the Anthropic-compatible client base URL. - The Anthropic SDK appends
/v1/messages; Hatz also accepts that SDK path. - Use Hatz model IDs from
/v1/chat/models, shorthand aliases such assonnet,opus, andhaiku, or supported native Claude-style IDs when mapped to enabled Hatz models. count_tokensis a preflight/limit check. Final billing and usage come from the final model response, not the preflight estimate.
Hatz-native Chat Completions:
- Use
/v1/chat/completionsfor Hatz-native chat, agents, server-side tools, files, and recursive tool calling. - Use
model: "auto"only on the Hatz-native chat route. - Use
model: "agent-{agent_id}"only when calling a listed agent through the Hatz-native chat route.
Support Evidence Packet
For API support, include:
- Endpoint and full base URL used.
- Auth method used, without the secret value.
X-Request-IDresponse header.- Timestamp and timezone.
- Affected tenant, workspace, or organization name or external ID, if safe to share.
- API key owner email or user account, if safe to share.
- Affected user or tenant scope when the issue appears permission-related.
- HTTP status code and sanitized error body.
- SDK, IDE, automation tool, or third-party client name and version when relevant.
- Whether streaming was enabled.
- Model ID or alias sent.
- Whether files, tools, workflows, images, or large context were involved.
- Expected behavior, actual behavior, and whether it reproduces with a minimal sanitized request.
- Business impact, urgency, and workaround.
Never send raw API keys, bearer tokens, private secrets, complete sensitive prompts, customer data, private files, or unredacted logs in a support ticket.