RESTlet, SuiteTalk, or REST Web Services: Which NetSuite Integration Approach Is Right for You
RESTlet, SuiteTalk, or REST Web Services: Which NetSuite Integration Approach Is Right for You
When a new integration requirement lands (connect an ecommerce platform, sync data with a 3PL, expose a fulfilment endpoint for a mobile app), one of the first decisions is which NetSuite API to use. The answer is not obvious, and getting it wrong has consequences: you end up with an authentication approach that doesn't fit your infrastructure, or a SOAP-based integration that a new developer can't maintain, or a custom RESTlet doing something that the native REST API could handle natively.
Here is how to make the right choice.
The Decision at a Glance
| RESTlet | SuiteTalk (SOAP) | REST Web Services | |
|---|---|---|---|
| Protocol | HTTP/JSON (custom) | SOAP/XML | HTTP/JSON (standard) |
| Auth | TBA or OAuth 2.0 | TBA or credentials | OAuth 2.0 |
| Custom logic | Yes, you write it | No | No |
| Standard records | Yes | Yes | Yes |
| Custom records | Yes | Yes | Yes |
| Record coverage | Whatever you build | Near-complete | Growing (but not complete) |
| Development required | Yes (SuiteScript) | No | No |
| Tooling | Custom | WSDL-generated clients | OpenAPI |
| Maturity | Established | Legacy | Actively developed |
| Best for | Custom business logic | Legacy enterprise systems | Modern standardised integrations |
RESTlets: Custom HTTP Endpoints Backed by SuiteScript
A RESTlet is a SuiteScript script deployed as an HTTP endpoint in your NetSuite account. You write the logic; NetSuite handles the routing. An inbound POST request to the RESTlet's URL triggers the post function in your script; a GET request triggers get.
/**
* @NApiVersion 2.1
* @NScriptType Restlet
* @NModuleScope SameAccount
*/
define(['N/record', 'N/search', 'N/log', 'N/error'], (record, search, log, error) => {
const get = (requestParams) => {
const orderId = requestParams.orderId;
if (!orderId) {
throw error.create({ name: 'MISSING_PARAM', message: 'orderId is required' });
}
const fields = search.lookupFields({
type: search.Type.SALES_ORDER,
id: orderId,
columns: ['tranid', 'status', 'entity', 'total']
});
return {
id: orderId,
number: fields.tranid,
status: fields.status[0].text,
customerId: fields.entity[0].value,
total: fields.total
};
};
const post = (requestBody) => {
// Create or update logic here
const rec = record.create({ type: record.Type.SALES_ORDER, isDynamic: false });
rec.setValue({ fieldId: 'entity', value: requestBody.customerId });
// ... set other fields ...
const newId = rec.save();
return { id: newId, success: true };
};
return { get, post };
});The RESTlet URL takes the form: https://{accountId}.restlets.api.netsuite.com/app/site/hosting/restlet.nl?script={scriptId}&deploy={deployId}
Authentication: Two options. Token-Based Authentication (TBA), which is OAuth 1.0a with HMAC-SHA256 signing: every request carries an Authorization header built from a consumer key, consumer secret, token, and token secret. Or OAuth 2.0: the integration record gets the RESTlets scope enabled and calls carry a standard Authorization: Bearer header. Most integration platforms (MuleSoft, Boomi, Zapier, Make) have built-in TBA connectors for NetSuite; for a hand-built caller, OAuth 2.0 is the simpler implementation, and it is the only option for integrations created from 2027.1.
When to use RESTlets:
- When you need custom business logic to run server-side at the point of the API call. Validation that queries other records, conditional field mapping, orchestration across multiple record types.
- When the standard REST Web Services API does not support the record type or operation you need.
- When you are building a mobile app or external portal that needs to call NetSuite logic on demand.
- When you need to expose an operation that doesn't map to a simple CRUD action. "Approve this purchase order", which involves multiple record updates and a workflow trigger, is a good example.
When RESTlets are the wrong choice:
- When you just need standard CRUD on Sales Orders, Customers, or Inventory Items and all the business logic lives in workflows or NetSuite's native processing. Use REST Web Services instead.
- When your integration platform already has a native NetSuite REST connector. Adding a custom RESTlet adds a maintenance burden without adding capability.
SuiteTalk (SOAP): The Legacy Option
SuiteTalk is NetSuite's SOAP API. It has been available since the early 2000s and has the most complete record coverage of any of the three approaches: virtually every NetSuite record type, including obscure ones like BillingSchedule, RevRecTemplate, and ChargeRule, is accessible via SuiteTalk.
It is also on a retirement path. The 2025.2 endpoint is the last planned SOAP endpoint, support narrows to only that endpoint from the 2027.1 release, and SOAP is removed at the 2028.2 release. For the full timeline and a migration plan, see NetSuite SOAP (SuiteTalk) is being retired.
The WSDL is available at https://{accountId}.suitetalk.api.netsuite.com/services/NetSuitePort_2024_1.wsdl (version number changes with each release).
Authentication: SuiteTalk supports both username/password (now strongly discouraged and disabled in many accounts) and Token-Based Authentication. The TBA implementation for SOAP uses the same consumer key/token mechanism as RESTlets, but the request signing is embedded in the SOAP header rather than an HTTP Authorization header.
When SuiteTalk makes sense:
- When you are working with an enterprise integration platform (SAP Integration Suite, IBM App Connect, Oracle Integration Cloud) that has a mature, pre-built NetSuite SOAP connector. The WSDL-generated client handles all the complexity and the connector has been in use for years.
- When you need access to record types that the REST Web Services API doesn't yet cover.
- When you are maintaining an existing SuiteTalk integration that is working correctly and the business case for rewriting it doesn't exist.
When SuiteTalk is the wrong choice:
- For any new integration built today. SOAP is verbose, the XML parsing overhead is significant, and the developer ecosystem has largely moved on. If you are starting fresh, use REST Web Services or RESTlets.
- When your team is modern and JavaScript/REST-native. SOAP's WSDL-generated clients in Java or .NET are manageable; in Python or Node.js they are painful.
REST Web Services: The Native Modern API
REST Web Services is Oracle's first-party REST API for NetSuite, accessible at https://{accountId}.suitetalk.api.netsuite.com/services/rest/record/v1/{recordType}/{id}. It follows standard HTTP conventions: GET to read, POST to create, PATCH to update, DELETE to delete.
Unlike RESTlets, this API is not programmable. You cannot attach custom SuiteScript to it. It exposes the native NetSuite record model: the fields and sublists that exist in the standard platform.
Authentication: OAuth 2.0, either client credentials flow (machine-to-machine, the common choice for background integrations) or authorization code flow (for user-facing applications). OAuth 2.0 is simpler to work with than TBA: you exchange credentials for a bearer token, include the token in requests, refresh it when it expires. The token endpoint is at https://{accountId}.suitetalk.api.netsuite.com/services/rest/auth/oauth2/v1/token.
What it covers:
As of 2026.1, REST Web Services covers all the major transactional and entity record types: Sales Order, Purchase Order, Invoice, Bill, Customer, Vendor, Item, Inventory Item, Assembly Item, Employee, and more. Custom records are fully supported too: CRUD on a custom record works the same way as on a standard record, addressed by its script ID (/record/v1/customrecord_yourrecord/{id}). Coverage has expanded with every release; check the current documentation for the definitive list of supported record types, as it changes.
What it does not cover: some highly specialised record types, sales and purchase custom transactions, and any operation that requires custom server-side logic.
When to use REST Web Services:
- When building a modern integration against standard record types and you do not need custom server-side logic.
- When you want to integrate using standard tooling: Postman collections, OpenAPI specs, HTTP client libraries in any language.
- When you want an integration that benefits from Oracle's ongoing investment without you maintaining custom SuiteScript.
A concrete example: an ecommerce platform syncing orders to NetSuite as Sales Orders. If the order data maps cleanly to NetSuite fields and the business logic (pricing, inventory allocation) is handled natively, REST Web Services is the right approach. A POST to /services/rest/record/v1/salesOrder with a JSON body creates the order. No SuiteScript required, no custom endpoint to maintain.
The Hybrid Approach: When One Is Not Enough
In practice, many real-world integrations combine approaches. The most common hybrid is:
REST Web Services for data, RESTlet for logic.
The REST Web Services API handles the CRUD: creating records, reading record state, updating fields. A RESTlet is used only for operations that require custom business logic: a custom "approve" endpoint that validates approval rules, triggers a workflow, and returns a structured response; or a "bulk-check" endpoint that evaluates 50 records against a custom eligibility rule in one call rather than 50 separate REST requests.
This hybrid gives you the maintenance advantages of the native REST API for standard operations, while keeping custom logic in SuiteScript where it belongs and can be tested independently.
A second common hybrid: REST Web Services for reads, SuiteScript for writes. Reading data from NetSuite via REST Web Services is low risk; it's a GET request against a well-documented API. Writing data, especially to complex record types with field dependencies and workflow triggers, sometimes benefits from a RESTlet that can enforce business rules at the point of entry before the record is created or modified.
The Authentication Decision Matters More Than You Think
A frequently overlooked dimension of this choice is who manages the credentials.
TBA tokens are tied to a user-role pair and carry four credential values that must be stored securely. When that user is deactivated or their role changes, the token is invalidated. When your integration platform stores TBA credentials, rotating them requires updating multiple systems.
OAuth 2.0, supported by both REST Web Services and RESTlets, ties credentials to the integration record. Machine-to-machine tokens expire on a schedule (60 minutes) and are reissued automatically with a signed JWT. This is a more robust model for long-lived background integrations, and it is the only option for integrations created from the 2027.1 release, when new TBA integrations are blocked.
If your organisation is standardising on OAuth 2.0 for all API authentication (which is increasingly common), both REST Web Services and RESTlets satisfy it. The deciding factor goes back to whether you need custom server-side logic.
Summary
Choose REST Web Services for new integrations against standard record types where your requirements are standard CRUD and OAuth 2.0 is available or preferred.
Choose a RESTlet when you need custom server-side logic at the API layer, when you need to expose NetSuite capabilities that aren't in the native REST API, or when you are building a tightly coupled integration that needs to enforce business rules.
Choose SuiteTalk only when you are maintaining an existing SOAP integration that is working, or when you are using an enterprise platform with a mature pre-built SOAP connector and the overhead of building a custom RESTlet isn't justified.
In most greenfield integration projects today, the answer is REST Web Services for the bulk of data exchange, with a RESTlet for any custom operations that require it.
If you are evaluating integration approaches for a new project, or you have an existing integration that has become unmaintainable and you want to understand your options, I can help.
Frequently asked questions
When should I use a RESTlet versus the native REST Web Services API?
Use REST Web Services when your integration needs standard CRUD on NetSuite's built-in record types (Sales Orders, Customers, Items, etc.) and no custom server-side logic is required. Use a RESTlet when you need custom business logic to run inside NetSuite as part of the API call: validation that queries other records, field mapping, or orchestration across record types that doesn't map to a single standard endpoint. If REST Web Services covers your use case, it costs nothing to maintain; a RESTlet is custom code you own forever.
Is SuiteTalk SOAP still a viable option for new NetSuite integrations?
No. Oracle is retiring SuiteTalk: from the 2027.1 release, support narrows to only the 2025.2 SOAP endpoint, and the 2028.2 release removes SOAP entirely. Existing SOAP integrations can continue running until 2028.2, but starting a new one today means planning a migration before that date. Use REST Web Services or RESTlets for anything built now.
Does a RESTlet support OAuth 2.0 authentication from external systems?
Yes. RESTlets accept OAuth 2.0 bearer tokens as well as Token-Based Authentication (OAuth 1.0a). For OAuth 2.0, the integration record needs the RESTlets scope enabled and the role needs the "Log in using OAuth 2.0 Access Tokens" permission; note that roles with the Web Services Only restriction do not work with RESTlets. Standardising on OAuth 2.0 therefore does not rule out RESTlets.
What is the practical difference between a RESTlet and a REST Web Services endpoint?
A RESTlet is custom SuiteScript you write and maintain that runs inside NetSuite on each API call. REST Web Services is Oracle's first-party REST API: no custom code required, no script record to manage, no deployment to configure. REST Web Services follows standard HTTP conventions and uses OAuth 2.0. RESTlets accept TBA or OAuth 2.0 and run whatever logic you put in the script. REST Web Services benefits from Oracle's investment automatically; RESTlet logic stays at the version you last deployed it.
Have a specific problem in mind?
A 30-minute technical review call to understand what's in your codebase and whether this is the right fit.
Book a technical review