- Published on
Upsert by external ID
PUT to eid:<your key> creates the record if the external ID is new, and updates it otherwise. Safe to retry.
upsert.js
export async function upsertByExternalId({ host, token, recordType, externalId, body, replace }) { const qs = replace ? `?replace=${encodeURIComponent(replace)}` : '' const url = `https://${host}.suitetalk.api.netsuite.com/services/rest/record/v1/${recordType}/eid:${encodeURIComponent(externalId)}${qs}`
const res = await fetch(url, { method: 'PUT', headers: { Authorization: `Bearer ${token}`, 'Content-Type': 'application/json' }, body: JSON.stringify(body), }) if (res.status !== 204) throw new Error(`Upsert ${res.status}: ${await res.text()}`)
// NetSuite answers 204 with the record URL in Location return res.headers.get('location')?.split('/').pop()}Usage:
const id = await upsertByExternalId({ host: '1234567-sb1', token, recordType: 'salesOrder', externalId: `SHOPIFY-${order.id}`, replace: 'item', // replace item lines on update instead of appending body: { entity: { id: customerId }, otherRefNum: order.name, item: { items: order.lines.map((l) => ({ item: { id: l.nsItemId }, quantity: l.qty, rate: l.price })) }, },})Use a key from the source system, never one generated at request time. Why this matters: the retry that creates a duplicate order.