Salesforce Headless 360 Agent API Invoked by Node.js Applications: Building Intelligent Connected Experiences
The real power of Salesforce Headless 360 is the Agent API which now exposes the Salesforce Agent and any third party application can invoke the Agent and consume the Agent responses. The salesforce system now becomes the platform and any application can bypass the manual salesforce login to interact with the Agents.

Invoking Salesforce Agent from Node.JS
Salesforce Headless 360 makes every Salesforce resource available as an API, Model Context Protocol(MCP) tool, or CLI command. Salesforce Headless 360 represents a new approach where Salesforce capabilities can be consumed through APIs, developer tools, automation frameworks, and intelligent agents. Instead of forcing users and developers to work only within traditional Salesforce interfaces, businesses can expose Salesforce-powered processes and data wherever customers, employees, or AI systems need them.
In a traditional Salesforce implementation, users typically interact through Salesforce applications such as Sales Cloud, Service Cloud, Experience Cloud, or custom-built Lightning components. While these solutions provide powerful functionality, businesses increasingly require more freedom to design unique digital experiences.
A headless approach separates:
Backend capabilities — customer data, workflows, automation, security, business rules, and Salesforce services
from
Frontend experiences — websites, mobile applications, AI assistants, chat interfaces, portals, and external platforms
This separation allows companies to reuse Salesforce functionality across many different experiences without rebuilding business logic.
Understanding Salesforce Headless 360 Agent API
Salesforce Headless 360 Agent API acts as a communication layer between external applications and Salesforce-powered intelligent agents. Instead of users directly interacting with Salesforce screens, an external application can send requests to an agent, allowing it to understand intent, access relevant information, and execute defined actions.
The agent acts as an intelligent layer capable of:
Understanding user requests
Accessing Salesforce data securely
Executing business processes
Calling configured Salesforce actions
Returning meaningful responses
This creates a new model where Salesforce becomes an intelligent service platform that can support any application experience.
High-Level Architecture
A typical implementation follows this flow:
User / Application
|
|
v
Node.js Application
|
|
v
Salesforce Headless 360 Agent API
|
|
v
Salesforce Agent
|
|
+----------------+
| Salesforce Data |
| Workflows |
| Actions |
+----------------+The Node.js layer acts as an orchestration service, controlling communication between the customer experience layer and Salesforce intelligence.
Invoking Salesforce Agent API from Node.js
A Node.js application generally performs the following activities:
Authentication
The application first establishes secure access to Salesforce services using authentication mechanisms such as OAuth-based flows.
The authentication process ensures that:
Only authorized applications can access Salesforce
User permissions are respected
import jsforce from 'jsforce';
import { v4 as uuidv4 } from 'uuid';
async function testSalesforceConnection(){
const conn = new jsforce.Connection({
oauth2: {
clientId: SF_CLIENT_ID,
clientSecret: SF_CLIENT_SECRET,
redirectUri: 'http://localhost:3000/oauth2/callback' // Must match Connected App setting
},
instanceUrl: SF_INSTANCE_URL,
accessToken: SF_ACCESS_TOKEN
});
const sessionId=conn.accessToken;
}Connection Variables
const SF_CLIENT_ID=
const SF_CLIENT_SECRET=
const tokenEndpoint=
const ApiEndPoint =
const SF_INSTANCE_URL =
const AGENT_ID =
const RANDOM_UUID = uuidv4();
const agentSessionUrl = 'https://api.salesforce.com//einstein/ai-agent/v1/agents/AgentID/sessions';
const agentSessionUrl1='https://api.salesforce.com/einstein/ai-agent/v1/sessions/'Fetching the Session ID
try {
const response = await conn.request({
method: 'POST',
url: agentSessionUrl,
headers: {
'Content-Type': 'application/json',
'Authorization': SF_ACCESS_TOKEN
},
body: JSON.stringify({
externalSessionKey: RANDOM_UUID,
instanceConfig: { "endpoint": SF_INSTANCE_URL},
tz: "America/Los_Angeles",
variables: [
{
"name": "$Context.EndUserLanguage",
"type": "Text",
"value": "en_US"
}
],
featureSupport: "Streaming",
// streamingCapabilities: {"chunkTypes":["text"]},
bypassUser: true // true uses the Agent User; false uses the token User
})
});
console.log('Session Created Successfully!');
console.log('Agent Session Details:', response);
const sessionId1=response.sessionId;
console.log(sessionId1);Passing the Synchronous Message or the Agent Prompt
const timestamp = new Date().toISOString().split('T')[0];
const timestamp1=timestamp.replace(/[-,\s]/g, '');
console.log('timestamp'+timestamp);
const response1= await conn.request({
method: 'POST',
url: agentSessionUrl1+sessionId1+'/messages',
headers: {
'Content-Type': 'application/json',
'Authorization': SF_ACCESS_TOKEN
},
body: JSON.stringify({
message : {sequenceId: timestamp1,
"type": "Text",
"text": "Find recommend Books similar to Dracula, language English and Genre Horror"}
})
});
console.log('Book recommendation:', response1);
return response;
} catch (error) {
console.error('Error starting agent session:', error);
}
}Summary
In our earlier example we created a Agent in our Master Org and provide a Agent force Data Library for the Agent response context. We are invoking this Agent from a Node JS application which is hosted on localhost. The callback URL has to be updated wit the below URL http://localhost:3000/oauth2/callback' in the connected app in the master org.
In the Example we are trying to recommend books basis on the prompt
Prompt - Find recommend Books similar to Dracula, language English and Genre Horror
Response - (Example)- "Here are some book recommendations similar to "Dracula" in the horror genre and English language. 1. Midnight Shadows - Horror - English 2. Vampire’s Promise - Horror - English 3. Dark Echoes - Horror - English Let me know if you'd like more suggestions!"



Comments