Calling an API
HTTP Request (Net → HttpRequest) is how a flow talks to anything with an HTTP interface — a REST API, a webhook receiver, a legacy endpoint that only speaks XML.
A GET request

Four things happen: a Function node puts the URL on the message, HTTP Request calls it, a Switch checks the status code, and only then does the flow use the response.
That Switch is not decoration — see status codes below.
The fields it uses
The node reads and writes ordinary message fields, and the defaults are worth learning because most examples use them unchanged:
| Direction | Property | Default field |
|---|---|---|
| In | Request body | msg.req |
| In | Headers | msg.reqHeaders |
| In | Cookies | msg.reqCookies |
| Out | Response | msg.resp |
| Out | Headers | msg.respHeaders |
| Out | Cookies | msg.respCookies |
| Out | Status Code | msg.respStatus |
So after a call, msg.resp holds the body and msg.respStatus holds the number.
Method and URL
Method is GET, POST, PUT, DELETE or PATCH. URL takes a literal, a message field or a JS expression.
http://, not https://If the URL does not start with http, the node prefixes http://. Type
api.example.com/v1 and you make a plaintext request. Always include https://.
Status codes do not fail the node
The single most important thing on this page.
A 404, a 500, a 401 — none of them make the node throw. The request succeeded; the server simply answered with a number you may not like. The node only errors when the request could not be made: DNS failure, connection refused, TLS failure, timeout.
So this is a bug:
HTTP Request → Function that reads msg.resp.items
If the API returned 401, msg.resp holds an error object and your Function throws something
confusing several nodes away from the cause.
Check the status first:
| Approach | |
|---|---|
Switch on msg.respStatus | Best when different codes need different handling — retry a 429, alert on a 500 |
| Function that throws on failure | Best when anything non-2xx should just stop the flow, and a Catch deals with it |
POST with a body

Put the payload on msg.req — an object, and the node serialises it — then set the method to
POST.
Content types
The Content-Type header decides how the body is encoded, and the node handles four cases:
| Content-Type | Body should be | What happens |
|---|---|---|
application/json | Object | Serialised as JSON. This is the default header on a new node |
application/x-www-form-urlencoded | Object of strings | URL-encoded form |
multipart/form-data | Object of strings | Multipart form — and see the file trick below |
| anything else | String | Sent as-is |
With multipart/form-data, a value beginning with @ is treated as a path to a file on
the robot, and the file is uploaded as that field:
msg.req = {
description: "Signed contract",
document: "@C:/invoices/contract.pdf"
};
description is sent as a normal field; document is sent as the file's contents. The file
must exist on the robot, not on your machine.
When the response is parsed, and when it is not
Also subtle, also a common surprise. The node parses the body to JSON only when:
- the response has no
Content-Typeheader, or - the
Content-Typeisapplication/json
Anything else — text/html, application/xml, text/plain — arrives as a string.
That is deliberate, so you can fetch a web page or an XML feed and get the raw text. But it
means an API that returns JSON under the wrong content type gives you a string that looks like
JSON, and msg.resp.field is undefined. If that happens, JSON.parse it in a Function node.
Encode as Base64 overrides all of this and gives you the body base64-encoded — which is what you want for images, PDFs and other binary responses.
Authentication
Authentication offers No Authentication or Basic Authentication. Basic takes a Login item from a vault — the username and password come from there, never from a node property.
It must be a Login item specifically. Point it at an API Key item and the node fails with a wrong-credential-type error.
For everything else — bearer tokens, API keys, custom schemes — use a Custom Header instead:
| Name | Value |
|---|---|
Authorization | Bearer <token> |
X-API-Key | <key> |
Read it from a vault item with Get Item and pass it on the message. A token typed into a node property is a token committed to your flow's git history.
Timeout
Timeout (seconds) defaults to 30. Raise it for a slow report endpoint; lower it for something in a loop, so one hanging call does not stall a batch.
A timeout is a node error, so a Catch sees it — unlike a 500.
Sessions and cookies
For an API that logs in and then expects a session, use the cookie store: connect the
response's cookie store output to the next request's cookie store input, and the jar carries
session cookies between calls automatically. That saves parsing Set-Cookie by hand.
Streaming responses
Enable Streaming changes the node's behaviour completely: instead of one message when the
response is complete, it emits a message per line as it arrives, each carrying a
msg.stream_index. The final message has an empty body and marks the end.
This is how you consume a streaming LLM API or a server-sent-events feed and show progress while it happens, rather than waiting for the whole answer.
Proxies
| Setting | |
|---|---|
| No Proxy | Direct. The default |
| Manual Proxy | Your own proxy, host:port, with optional basic auth from a vault |
| Robomotion Proxy | Routes through Robomotion's proxy service, billed to your credits |
Robomotion Proxy is the one to know about: it exists for requests that get blocked when they come from your own address — scraping, geo-restricted endpoints — and takes extra parameters to control its behaviour. Note that it also disables TLS verification, because the proxy terminates the connection.
Debugging a request
Enable Debugging prints the full request and response — method, URL, every header, the body — to the robot's console. When an API works in Postman and not in your flow, turn this on and compare the two requests; the difference is almost always a header.
Insecure Skip Verify turns off TLS certificate checking. It makes self-signed certificates work, and it makes you vulnerable to interception — use it against an internal host you trust, never against the public internet.
See also
- HTTP Request node reference — every property
- Webhooks — receiving requests instead of making them
- Exceptions — handling timeouts and connection errors
- Vaults — where credentials belong