02 Get your data in /Integrations
n8n
Send records from any of n8n's apps to Dimension Labs with a workflow and the universal API, on n8n Cloud or your own n8n.
- N n8nTickets, chats, calls, reviews
- ⟳ Your jobPull new · map fields · every 15 min
- { } Universal APIPOST /track · /trackhistorical
- Dimension LabsRead in full · enriched daily
n8n connects to thousands of apps (n8n’s integrations page lists 2,000+ as of 2026-10-26). If a tool you use has an n8n trigger, such as a new form response, review, ticket or spreadsheet row, a workflow can send each new record to the universal API. It runs on n8n Cloud or on your own n8n, with nothing else to host.
n8n fits sources where one trigger event is one piece of customer text: a form or survey response, a review, a feedback submission, the first message of a ticket. For full multi-message conversations, or to load history, use the app’s own guide or Any other system, which pull every message in order.
What you need
Section titled “What you need”- An n8n Cloud account or a self-hosted n8n.
- An n8n trigger for your app that returns the customer’s text and a date.
- A Dimension Labs API key for a new Universal API source. See Your API key.
1. Choose the trigger
Section titled “1. Choose the trigger”- In the workflow editor, add the trigger node for your app, for example a new response, new review or new row.
- Run it once and check the output has three things: the customer’s text, an id for the record, and when it was written.
Use one source in Dimension Labs per app, so its data is easy to filter later.
2. Build the message in a Code node
Section titled “2. Build the message in a Code node”n8n’s Code node can’t make HTTP requests (Using the Code node), so the work is split: a Code node builds each message, and an HTTP Request node sends it.
- Add a Code node after the trigger. Set the language to JavaScript and the mode to Run Once for All Items.
- Paste this code, then edit the
picklines so each one reads the right field from your trigger’s output, and setSOURCEto the app’s name.
// n8n Code node (JavaScript, Run Once for All Items).// Builds one Dimension Labs message per input item. The HTTP Request node sends it.const SOURCE = 'jotform'; // the app's name, kept in platformJson
// Edit the right-hand side of each line to match your trigger's fields.const pick = (d) => ({ text: d.text, // the customer's words recordId: d.id, // the record's own id: becomes sessionId customerId: d.customerId, // optional: your internal customer id, never an email or name writtenAt: d.createdAt, // when it was written, ideally with a time zone extra: { rating: d.rating }, // anything else to filter or join on later});
const clean = (s) => String(s).replace(/:/g, '-'); // ids can't contain colonsconst out = [];
for (const item of $input.all()) { const { text, recordId, customerId, writtenAt, extra } = pick(item.json); if (!text || !String(text).trim()) continue; // skip empty text const ts = typeof writtenAt === 'number' ? (writtenAt < 1e12 ? writtenAt * 1000 : writtenAt) : Date.parse(writtenAt); if (Number.isNaN(ts)) throw new Error(`Can't read the date "${writtenAt}". Map a date with a time zone.`); const sessionId = clean(`${SOURCE}-${recordId}`); out.push({ json: { endpoint: Date.now() - ts > 60 * 60 * 1000 ? 'trackhistorical' : 'track', message: { text: String(text), userId: customerId ? clean(customerId) : sessionId, incoming: true, sessionId, conversationId: sessionId, dimensionlabs_timestamp: ts, platformJson: { source: SOURCE, ...extra }, }, }, });}
return out;The code returns one item per record, each with the message and its endpoint: a record written more than an hour ago goes to /trackhistorical, as every guide does. A date given as a number in seconds is turned into milliseconds. Records with empty text are dropped.
3. Send it
Section titled “3. Send it”Add an HTTP Request node after the Code node (HTTP Request node):
- Method:
POST. - URL: switch the field to an expression and enter
https://tracker.dimensionlabs.io/{{ $json.endpoint }} - Authentication: none. The API key goes in the query string.
- Turn on Send Query Parameters, choose Using Fields Below, and add:
| Name | Value |
|---|---|
platform | universal |
v | 11.1.0-rest |
type | incoming |
apiKey | your Dimension Labs API key |
- Turn on Send Body. Set Body Content Type to JSON and Specify Body to Using JSON, and set the JSON field to the expression
{{ JSON.stringify($json.message) }}. n8n sendsContent-Type: application/json.
JSON.stringify escapes quotes and line breaks in the customer’s text, which is why this guide builds the message in code rather than typing the JSON by hand: a review with a quotation mark in it would break hand-typed JSON.
n8n runs the HTTP Request node once per item, so each record is its own POST. Run the node once with a test record. A 200 response means the message reached Dimension Labs.
4. Turn it on
Section titled “4. Turn it on”- Turn the workflow on. Each new record is sent as it arrives, to
/track, and is enriched automatically every day. - If n8n sees a record late (more than an hour after it was written, for example on a polling trigger), the code sends it to
/trackhistorical. Run a backfill from the Backfill tab to enrich those. - History: a trigger only sees new records. Export your history from the app and upload a file (check it with the file checker), then run a backfill.
- Re-runs are safe: if you retry an execution, duplicates are removed automatically.
Personal data. Don’t put email addresses, names or phone numbers into extra: it is sent as platformJson. Redact the text if customers include personal details. See PII redaction.
A record with several messages
Section titled “A record with several messages”If the trigger returns a whole conversation (a ticket with replies, a chat transcript), each message needs its own POST, in order, at least one second apart, with replies from your side marked incoming: false and type=outgoing. That is easier and more reliable in a script: see the app’s guide, or Any other system.
n8n reference
Section titled “n8n reference”- n8n integrations
- HTTP Request node
- Using the Code node
- Code node common issues
- Understand n8n’s data structure
Checked against n8n’s documentation on 2026-10-26.