#403 status code (no body)
1 messages · Page 1 of 1 (latest)
A raw HTTP 403 (often with an empty/HTML body) from “Kimi” usually means the request reached the provider, but the provider is refusing it (auth/plan/quota/endpoint mismatch).
A couple quick triage steps to pin down which case you’re in:
- Which provider are you using in OpenClaw?
moonshot/...(Moonshot API, OpenAI-compatible)kimi-coding/...(Moonshot’s Anthropic-compatible endpoint)openrouter/...(OpenRouter routing to Moonshot)kilocode/...(Kilo gateway)
If you’re not sure, run:
openclaw --version
openclaw models status
(or in chat: /model status) and paste the output with keys redacted. models status will show the resolved provider + (when configured) the baseUrl/api mode, which is the crucial clue.
- If you’re using Moonshot directly (
moonshot/...)
Make sure you configured it exactly like the docs (baseUrl includes/v1, andapiisopenai-completions):
https://docs.openclaw.ai/concepts/model-providers#moonshot-ai-kimi
A very common real-world cause of 403 on Moonshot is account not active / quota exceeded / billing not set up (their API will often say so in the JSON body when you test outside of OpenClaw).
- Check whether OpenClaw is hiding the body or it’s truly empty
Run:
openclaw logs --follow
Then trigger one request and paste the log lines around the failure (again, redact secrets). The logs often contain more detail than the chat surface.
- Sanity test the key/endpoint outside OpenClaw
Ifcurl/a tiny script against the samebaseUrlreturns a JSON error body (quota/billing/etc), then it’s not an OpenClaw bug—it’s provider-side.
If you post:
openclaw --version- the relevant snippet of your
models.providers(or tell me which provider ref you selected, e.g.moonshot/...vsopenrouter/...) - 20–30 lines of logs around the 403
…I can tell you which bucket it’s in and what to change.
2026.2.22-2
Thanks — version looks current enough.
To debug the 403 (no body) we need to confirm which provider path you’re hitting and what OpenClaw thinks the resolved endpoint/auth is.
Can you paste (redact keys):
- What model ref you selected (exact string), e.g.
moonshot/...vskimi-coding/...vsopenrouter/...vskilocode/... - Output of:
openclaw models status
(or in Discord: /model status screenshot/text is fine)
- A log snippet right when it fails:
openclaw logs --follow
(trigger one request, then paste the few lines around the error)
Most common causes for Kimi/Moonshot 403:
- Billing/quota/account not active on the Moonshot side (often 403; sometimes surfaces as “empty body” depending on where it’s caught)
- Endpoint/API mode mismatch (Moonshot “OpenAI-compatible” vs Kimi Coding “Anthropic-compatible”). The config snippets differ — see the exact docs section you should match: https://docs.openclaw.ai/concepts/model-providers#moonshot-ai-kimi
Once you paste /model status + the failing log lines, it’s usually obvious which bucket it is.
openclaw logs --follow cannot see any recent log when calling kimi
nvidia-nim effective=models.json: source=models.json: ~/.openclaw/agents/main/agent/models.json
openclaw logs --follow tails the Gateway’s file logs over RPC (it’s not just “whatever is printing in your terminal”), so if you see nothing new while you trigger a Kimi request, one of these is usually true:
- Your CLI is not connected to the same gateway that’s handling your Discord bot (common when the gateway runs as a service / different user / different machine).
- The gateway isn’t writing file logs (non-default
logging.file, permission issue, etc.). - The interesting events are below your
logging.level(less likely for a 403, but possible).
Can you paste the output of these (redact secrets):
openclaw gateway status
openclaw gateway status --deep
openclaw logs --limit 50
openclaw config get logging
Things to look for in gateway status --deep:
- whether Config (cli) and Config (service) differ (that’s the smoking gun for “I’m tailing the wrong instance”)
- that it shows RPC probe: ok
Also: if your gateway is on a VPS, make sure you’re running openclaw logs --follow against that gateway (either run the CLI on the VPS, or make sure your local CLI is in remote mode pointing at it).
Docs for reference:
- Logs CLI: https://docs.openclaw.ai/cli/logs
- Logging overview (default file path, levels): https://docs.openclaw.ai/logging
That line is an important clue:
nvidia-nim effective=models.json … ~/.openclaw/agents/main/agent/models.json
So you’re not using Moonshot directly (https://api.moonshot.ai/v1) — you’re going through an NVIDIA NIM-style provider defined in models.json.
Two likely outcomes:
1) The 403 is NVIDIA-side “you don’t have access to this model / key not entitled / quota/plan”
NVIDIA’s endpoint will often return a plain 403 (sometimes with an unhelpful/empty body depending on the proxy), if your nvapi-… key isn’t allowed to call that specific model ID.
2) You’re tailing logs from a different gateway than the one handling Discord
If openclaw logs --follow doesn’t change at all when you send a Discord message, you’re very often connected to a different gateway/service instance.
To get unstuck, can you paste (with apiKey redacted):
-
The
nvidia-nimprovider block from:
~/.openclaw/agents/main/agent/models.json
Specifically:baseUrl,api, and the modelidyou’re calling. -
Output of:
openclaw gateway status --deep
openclaw logs --limit 30
That will tell us:
- whether your CLI is talking to the same running gateway (deep status shows config/service mismatches), and
- exactly what URL + API mode OpenClaw is using for the NIM provider.
(For reference on logging behavior + default file location: https://docs.openclaw.ai/logging)
"nvidia-nim": {
"baseUrl": "https://integrate.api.nvidia.com/v1",
"apiKey": "${NVIDIA_API_KEY}",
"api": "openai-completions",
"models": [
{
"id": "moonshotai/kimi-k2.5",
"name": "Kimi K2.5 (NVIDIA NIM)",
"reasoning": false,
"input": [
"text"
],
"cost": {
"input": 0,
"output": 0,
"cacheRead": 0,
"cacheWrite": 0
},
"contextWindow": 200000,
"maxTokens": 8192
}
]
},
Yep — that config means you’re calling Kimi via NVIDIA’s “integrate” OpenAI-compatible gateway, not Moonshot directly.
For a 403 (no body) with that setup, the top two causes are:
1) ${NVIDIA_API_KEY} isn’t actually set in the gateway process
When OpenClaw runs as a service/container, it often doesn’t inherit your shell env, so apiKey: "${NVIDIA_API_KEY}" can end up empty at runtime → provider returns 403/401-ish errors.
Check:
- Run
openclaw models statusand look for thenvidia-nimprovider auth section (it will usually say “Missing auth” or show resolved key sources). - If you’re running as a service/container, easiest fix is to set it in OpenClaw config:
{
env: {
NVIDIA_API_KEY: "nvapi-…"
}
}
Then restart the gateway.
2) The model id NVIDIA expects might be different
Some NVIDIA routes use model ids like nvidia/<vendor>/<model> (varies by catalog/version). If NVIDIA’s gateway doesn’t recognize moonshotai/kimi-k2.5 (or your key isn’t entitled to it), it can come back as a 403.
Quick check: what exact model ref are you selecting in OpenClaw? It should be:
nvidia-nim/moonshotai/kimi-k2.5
If you paste the output of:
openclaw models status
(just the parts that mention nvidia-nim + the resolved primary model; redact secrets)
…I can tell immediately whether the gateway is actually seeing NVIDIA_API_KEY, and what model ref it’s truly using.
nvidia-nim effective=models.json:nvapi-........ | models.json=nvapi-............... | source=models.json: ~/.openclaw/agents/main/agent/models.json
Nice — that effective=models.json:nvapi-… line means OpenClaw is definitely seeing your NVIDIA key, so this is no longer an “env var not set” problem.
At this point, a 403 from https://integrate.api.nvidia.com/v1 is almost always NVIDIA-side authorization/entitlement (key doesn’t have access to that model, or the account/plan can’t use it).
Quick proof with curl (run on the gateway host)
Redact the key if you paste output.
- Can your key even hit the NVIDIA gateway?
curl -i https://integrate.api.nvidia.com/v1/models \
-H "Authorization: Bearer $NVIDIA_API_KEY"
- If this is 403 too → the key/account is the issue (wrong key, disabled, region/account restriction, etc.).
- If this is 200 → key is valid; now check if the model is actually available to you.
- Does
moonshotai/kimi-k2.5work directly?
curl -i https://integrate.api.nvidia.com/v1/chat/completions \
-H "Authorization: Bearer $NVIDIA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}'
- If this is 403 → your key is not entitled to that model ID (you’ll need to pick a model you do have access to, or adjust your NVIDIA plan/settings).
- If this works but OpenClaw still gets 403 → paste the exact OpenClaw error text + bump logging to see the provider error body (set
logging.level: "debug"temporarily, thenopenclaw logs --follow).
If you paste the HTTP status + a couple headers from (1) and (2), we can tell immediately which bucket you’re in.
header from 1 is 200
header from 2 curl -i https://integrate.api.nvidia.com/v1/chat/completions
-H "Authorization: Bearer $NVIDIA_API_KEY"
-H "Content-Type: application/json"
-d '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}'
HTTP/2 500
date: Wed, 25 Feb 2026 12:02:05 GMT
content-type: text/plain; charset=utf-8
content-length: 200
vary: Origin
Missing request extension: Extension of type headers::common::authorization::Authorization<headers::common::authorization::Bearer> was not found. Perhaps you forgot to add it? See `ax
Good — GET /v1/models = 200 confirms the key is valid and reaching NVIDIA.
Next question is: does NVIDIA allow chat for that specific model on your account?
Can you run these two quick checks:
A) Confirm the model is actually in your /v1/models list
curl -sS https://integrate.api.nvidia.com/v1/models \
-H "Authorization: Bearer $NVIDIA_API_KEY" | grep -F "moonshotai/kimi-k2.5"
(If that prints nothing, your key likely doesn’t have hosted access to that model ID.)
B) Try the exact chat call (this is the real test)
curl -i https://integrate.api.nvidia.com/v1/chat/completions \
-H "Authorization: Bearer $NVIDIA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}'
- If (B) returns 403 too: it’s NVIDIA-side entitlement/plan/hosted-access gating (OpenClaw can’t fix that; you’ll need to use a model your key is allowed to run, or enable hosted API access on NVIDIA’s side).
- If (B) works but OpenClaw still gets 403: then it’s an OpenClaw integration mismatch (wrong endpoint, model id being rewritten, etc.). In that case, paste:
- the exact model ref you set as primary (e.g.
nvidia-nim/moonshotai/kimi-k2.5) - and
openclaw models status(redacted) - plus we’ll want to temporarily set
logging.level: "debug"soopenclaw logs --followshows the exact provider/model it’s sending.
- the exact model ref you set as primary (e.g.
That HTTP 500 body is actually pretty telling:
Missing request extension ... Authorization<Bearer> was not found
That’s NVIDIA saying it did not receive an Authorization: Bearer … header on the /v1/chat/completions request (it’s an internal axum error, but the root cause is “no auth header”).
Two common gotchas here:
-
$NVIDIA_API_KEYisn’t set in the shell where you ran curl
OpenClaw seeing the key inmodels.jsondoes not automatically set your terminal’s env var. -
On some systems
/v1/modelsmay still return 200 without auth, so that “step 1 is 200” doesn’t prove the header is being sent.
Quick fix: run curl with the key inline (don’t paste it here)
curl -i https://integrate.api.nvidia.com/v1/chat/completions \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}'
Or: verify your env var is actually set
echo "$NVIDIA_API_KEY" | head -c 8; echo
If curl works with the inline key but OpenClaw still gives 403 (no body), then we’re back to an OpenClaw integration issue and we’ll want:
openclaw models status(redacted)- and temporarily
logging.level: "debug"soopenclaw logs --followshows the exact request/response details (since--verbosedoesn’t raise file log level): https://docs.openclaw.ai/logging
cur with key inline is doing nothing
If curl with the key inline “does nothing”, 90% of the time it’s one of these:
- it’s actually hanging on the request (no output until it finishes), or
- you’re on PowerShell, where
curlis an alias forInvoke-WebRequestand multi-line quoting/escaping behaves differently.
Let’s force it to either succeed or fail quickly and show where it’s stuck.
Try this (Linux/macOS bash/zsh) — with timeouts + verbose
(Don’t paste your key here; just run it locally.)
curl -v --http1.1 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-PASTE_YOUR_KEY_HERE" \
-H "Content-Type: application/json" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":5}' \
https://integrate.api.nvidia.com/v1/chat/completions
- If it times out, the
-voutput will show whether it’s DNS/TLS/connect/server wait. - If it returns a 4xx/5xx, you’ll finally get a real error body.
If you’re on Windows PowerShell
Run curl.exe explicitly (not curl):
curl.exe -v --connect-timeout 10 --max-time 30 `
-H "Authorization: Bearer nvapi-PASTE_YOUR_KEY_HERE" `
-H "Content-Type: application/json" `
--data-binary "{\"model\":\"moonshotai/kimi-k2.5\",\"messages\":[{\"role\":\"user\",\"content\":\"hi\"}],\"max_tokens\":5}" `
https://integrate.api.nvidia.com/v1/chat/completions
If you paste back the -v output with the Authorization line removed, I can tell you exactly what’s happening (and whether the original OpenClaw 403 is NVIDIA entitlement vs. an OpenClaw request-shape issue).
Server certificate:
- subject: CN=integrate.api.nvidia.com
- start date: Jul 1 00:00:00 2025 GMT
- expire date: Jul 30 23:59:59 2026 GMT
- subjectAltName: host "integrate.api.nvidia.com" matched cert's "integrate.api.nvidia.com"
- issuer: C=US; O=Amazon; CN=Amazon RSA 2048 M02
TLS/cert looks fine — you’re past DNS + handshake. The next lines in curl -v are the important ones: we need to see whether it actually sends the request (> POST ...) and what comes back (< HTTP/...).
Can you paste everything from the first line that looks like:
> POST /v1/chat/completions ...- (and the following
< HTTP/...response lines)
…with the Authorization: value redacted?
Also try this exact command (it avoids one common “hang” cause: Expect: 100-continue):
curl -v --http1.1 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
https://integrate.api.nvidia.com/v1/chat/completions
Notes:
GET /v1/models = 200doesn’t necessarily prove auth is working (some deployments return 200 even unauthenticated), but the chat endpoint will tell us the truth.- If this curl returns 200 but OpenClaw still throws 403 (no body), then it’s likely an OpenClaw-side mismatch (e.g. model id being altered). In that case, set
logging.level: "debug"temporarily and grab the log line that showsprovider=... model=...(similar to issue #16010, but that one manifested as 404).
SSL certificate verify ok.
- Certificate level 0: Public key type RSA (2048/112 Bits/secBits), signed using sha256WithRSAEncryption
- Certificate level 1: Public key type RSA (2048/112 Bits/secBits), signed using sha256WithRSAEncryption
- Certificate level 2: Public key type RSA (2048/112 Bits/secBits), signed using sha256WithRSAEncryption
- using HTTP/1.x
POST /v1/chat/completions HTTP/1.1
Host: integrate.api.nvidia.com
User-Agent: curl/8.5.0
Accept: /
Authorization: Bearer nvapi-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Content-Type: application/json
Content-Length: 91
You’re now at the point where the request is definitely being sent (we can see > POST ... and the Authorization: Bearer ... header). What’s missing is the server response (< HTTP/...), so curl is just sitting there waiting.
Re-run the same call but force a timeout so it can’t “do nothing” forever, and paste the output from > POST ... through the end (redact the key):
curl -v --http1.1 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
https://integrate.api.nvidia.com/v1/chat/completions
What we’re trying to learn:
- If you get something like
Operation timed out after 30000 milliseconds→ NVIDIA endpoint is hanging for you (network/proxy/regional issue, or NVIDIA-side). - If you get
< HTTP/1.1 401/403/404/429/500→ we can act on the exact status/body.
- If it returns 200 here but OpenClaw still gets 403 (no body) → then it’s very likely an OpenClaw-side request-shape/model-id bug, and the next step is setting
logging.level: "debug"and capturing theprovider=... model=...line fromopenclaw logs --follow.
Also: you already pasted an Authorization header once—if that key was real, regenerate it to be safe.
not replying
If it’s “not replying” after you see the > POST /v1/chat/completions + Authorization: Bearer ... lines, that means curl is just hanging waiting for the server response.
Two things to do:
- Force a timeout + print timings (so we know if it’s actually stuck)
curl --http2 -sS -v --ipv4 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
Then paste everything from > POST ... down to the end (remove the bearer token value).
- If that times out, try HTTP/1.1 (sometimes HTTP/2 gets weird through certain networks):
curl --http1.1 -sS -v --ipv4 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
Also: if you ever pasted the real nvapi-... token into Discord earlier, rotate/regenerate it.
You just pasted a real nvapi-... key into a public Discord thread. Rotate/revoke it immediately in NVIDIA, and delete/edit that message if you can. Treat that key as burned.
On the curl hang: your output shows the request headers went out, but you never got a < HTTP/... response back yet (so it’s waiting on the server).
Run this to force it to terminate and print the status code + total time (don’t paste the key back here; just paste the result lines and any response body):
curl -sS -v --http2 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
If that still times out, try HTTP/1.1:
curl -sS -v --http1.1 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
What this tells us:
- timeout → NVIDIA endpoint/network path is hanging for you (OpenClaw can’t fix that; you’ll need to resolve NVIDIA-side or network/proxy/region issues).
- 200/4xx/5xx → we can map it directly to entitlement/model-id/auth/request-shape.
Once you have http=... time=... + any body, paste that (with the key redacted) and we’ll connect it back to why OpenClaw shows 403 (no body).
POST /v1/chat/completions HTTP/1.1
Host: integrate.api.nvidia.com
User-Agent: curl/8.5.0
Accept: /
Authorization: Bearer nvapi-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Content-Type: application/json
Content-Length: 92
- TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
You’re still not getting any response back from NVIDIA yet — in curl -v you should eventually see lines starting with < HTTP/.... Since you only see the > POST ... headers, the request is hanging waiting for the server.
Please do two things:
-
Rotate/revoke that
nvapi-...key you pasted (assume it’s compromised), and delete/edit the message if possible. -
Re-run the request with hard timeouts + an explicit “print the HTTP code at the end”, then paste the output from the first
> POSTline through the finalhttp=...line (with the bearer value redacted):
curl -sS -v --ipv4 --http2 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
If you get a timeout (http=000) then this isn’t an OpenClaw config issue — your host/network can reach TLS, but NVIDIA isn’t responding to the chat endpoint (or something in the path is stalling). If you get a real 4xx/5xx, we can map it directly to the fix (entitlement/model id/etc.).
POST /v1/chat/completions HTTP/2
Host: integrate.api.nvidia.com
User-Agent: curl/8.5.0
Accept: /
Authorization: Bearer nvapi-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Content-Type: application/json
Content-Length: 92
- TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
- Operation timed out after 30003 milliseconds with 0 bytes received
- Connection #0 to host integrate.api.nvidia.com left intact
curl: (28) Operation timed out after 30003 milliseconds with 0 bytes received
http=000 time=30.003241
That output means the NVIDIA endpoint isn’t sending any response bytes at all for /v1/chat/completions from where you’re running it:
http=000+0 bytes receivedafter 30s = hang / no HTTP response- so this is not an OpenClaw config nuance at the moment — the upstream call itself is stalling.
Two urgent / next steps:
-
Rotate/revoke your
nvapi-…key right now. You pasted a real key in this thread earlier, so assume it’s compromised. -
Run the same curl from the exact machine/network where the OpenClaw Gateway runs.
This matters a lot: if OpenClaw is running on a VPS but you’re testing curl from your laptop/home network, you can see totally different behavior.
Also try forcing HTTP/1.1 (just in case HTTP/2 is what’s hanging on your path):
curl -sS -v --http1.1 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
If that still times out on the gateway host, then the fix is outside OpenClaw (NVIDIA endpoint issue / routing / account access on the NVIDIA side). Practical workaround is to switch to another provider for Kimi (Moonshot direct / OpenRouter / etc.) until NVIDIA’s integrate endpoint responds reliably.
If it works on the gateway host but not on your local machine, then the earlier OpenClaw 403 is probably a different issue and we should grab openclaw models status + openclaw logs --follow from the gateway host while triggering one request.
im testing on the vps
If you’re testing on the VPS and /v1/chat/completions is timing out with 0 bytes received, then OpenClaw failing is expected — the VPS simply isn’t getting any HTTP response back from NVIDIA’s chat endpoint.
A few focused checks to narrow down whether this is HTTP/2 weirdness, model-specific, or NVIDIA-side / routing:
0) Security: rotate that key
You posted an nvapi-... key in-thread earlier. Rotate/revoke it in NVIDIA first (assume it’s compromised).
1) Force HTTP/1.1 (rules out an h2 path issue)
Run on the VPS:
curl -sS -v --http1.1 --ipv4 --connect-timeout 10 --max-time 30 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":20}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
- If HTTP/1.1 works but HTTP/2 times out → you’ve got an h2/network edge issue; OpenClaw may still fail depending on what its HTTP client negotiates.
2) Test another model id from your own /v1/models output
Since GET /v1/models works for you, pick any other model id listed there and try that same chat request.
If other models respond but only moonshotai/kimi-k2.5 hangs, it’s model-route/entitlement/back-end availability for that specific model on NVIDIA.
3) If chat times out for every model from the VPS
That’s almost certainly NVIDIA integrate endpoint / routing / account hosted access from that VPS IP range. At that point the practical workaround is: don’t use the NVIDIA integrate endpoint from that VPS (switch provider).
OpenClaw-side workaround: configure Kimi via a provider that works reliably for you:
- Moonshot direct (
moonshotprovider) or - OpenRouter, etc.
Moonshot config reference (OpenClaw docs): https://docs.openclaw.ai/concepts/model-providers#moonshot-ai-kimi
If you paste the result of step (1) (just the end: http=... time=... and any < HTTP/... lines, with the token redacted), plus whether any other model works in step (2), I can tell you which bucket you’re in.
Content-Type: application/json
Content-Length: 92
- TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
- Operation timed out after 30003 milliseconds with 0 bytes received
- Closing connection
- TLSv1.3 (OUT), TLS alert, close notify (256):
curl: (28) Operation timed out after 30003 milliseconds with 0 bytes received
If you’re testing on the VPS and you get:
Operation timed out ... with 0 bytes receivedhttp=000
…then the VPS is establishing TLS fine, but NVIDIA’s /v1/chat/completions is not returning any HTTP response at all within 30s. In that situation OpenClaw can’t succeed either (it’ll fail/timeout/possibly surface a weird error).
Two concrete next steps to narrow it down:
1) Try IPv4 vs IPv6 explicitly + give it a bit longer
Run both of these on the VPS (key redacted):
# IPv4
curl -sS -v --ipv4 --http1.1 --connect-timeout 10 --max-time 120 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":5}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
# IPv6
curl -sS -v --ipv6 --http1.1 --connect-timeout 10 --max-time 120 \
-H "Authorization: Bearer nvapi-REDACTED" \
-H "Content-Type: application/json" \
-H "Expect:" \
--data-binary '{"model":"moonshotai/kimi-k2.5","messages":[{"role":"user","content":"hi"}],"max_tokens":5}' \
-w "\n\nhttp=%{http_code} time=%{time_total}\n" \
https://integrate.api.nvidia.com/v1/chat/completions
If one works and the other times out, it’s a network path issue (common on some VPS providers/regions).
2) If both still hang: switch away from NVIDIA Integrate for now
At that point it’s effectively “NVIDIA chat endpoint unreachable from this VPS/region right now”, so the pragmatic fix is using Kimi via another provider (Moonshot direct, OpenRouter, etc.).
Moonshot direct config (official OpenClaw docs):
https://docs.openclaw.ai/concepts/model-providers#moonshot-ai-kimi
Also: you posted an nvapi-... key earlier in this thread — rotate/revoke it immediately and delete/edit the message if you can.
api key revoked thanks