@ultrasafeai/usf-agents
v1.0.2
Published
A lightweight, streaming-enabled agent orchestration SDK with internal planning, dynamic tool support, and multi-agent capabilities. Built for the USF platform with OpenAI-compatible interfaces.
Maintainers
Readme
usf-agents
A lightweight, streaming-enabled agent orchestration SDK with internal planning, dynamic tool support, and multi-agent capabilities. Built for the USF platform with OpenAI-compatible interfaces.
Homepage: https://us.inc
Features
- 🔧 Dynamic Tool Calling: Accepts tools in pure OpenAI format
- 🧠 Internal Planning: Automatic planning phase before tool execution
- 🌊 Streaming Support: Streams final answers while keeping planning/tool_calls non-streaming
- ⚡ Zero Dependencies: Lightweight and standalone
- 🛡️ Safe Execution: No auto tool executor to prevent infinite loops
- 🔗 Sequential Tool Chains: Handle multiple tool calls in sequence
- 👥 Multi-Agent Orchestration: Coordinate between different AI agents
Installation
npm install @ultrasafeai/usf-agentsUsage
Basic Non-Streaming Example
import { USFAgent } from '@ultrasafeai/usf-agents';
const agent = new USFAgent({
apiKey: 'your-api-key',
endpoint: 'https://api.us.inc/usf/v1', // optional
model: 'usf-mini' // optional
});
const tools = [
{
type: "function",
function: {
name: "web_search",
description: "Search for information on the web",
parameters: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query"
}
},
required: ["query"]
}
}
}
];
// Using a string message
const result = await agent.run("What's the weather like in New York?", { tools });
// Using OpenAI message format for history
const result2 = await agent.run([
{ role: "user", content: "What's the weather like in New York?" }
], { tools });
if (result.type === 'tool_calls') {
console.log('Tools needed:', result.tool_calls);
} else if (result.type === 'final_answer') {
console.log('Answer:', result.content);
}Streaming Example
const agent = new USFAgent({
apiKey: 'your-api-key',
stream: true
});
for await (const chunk of agent.run([
{ role: "user", content: "Write a short story about a robot learning to cook" }
], { tools })) {
if (chunk.type === 'plan') {
console.log('Planning:', chunk.content);
} else if (chunk.type === 'tool_calls') {
console.log('Tools needed:', chunk.tool_calls);
} else if (chunk.type === 'final_answer') {
process.stdout.write(chunk.content); // Stream response to user
}
}Sequential Tool Calls Example
import { USFAgent, executeTools } from '@ultrasafeai/usf-agents';
const agent = new USFAgent({
apiKey: 'your-api-key'
});
// Define multiple tools
const tools = [
{
type: "function",
function: {
name: "web_search",
description: "Search for information on the web",
parameters: {
type: "object",
properties: {
query: { type: "string" }
},
required: ["query"]
}
}
},
{
type: "function",
function: {
name: "calculator",
description: "Perform mathematical calculations",
parameters: {
type: "object",
properties: {
expression: { type: "string" }
},
required: ["expression"]
}
}
}
];
// Initial user message
let messages = [
{ role: "user", content: "What's the population of New York and calculate 10% of it?" }
];
// First planning and tool call
let result = await agent.run(messages, { tools });
// Handle first tool call
if (result.type === 'tool_calls' && result.tool_calls.length > 0) {
console.log('First tool calls:', result.tool_calls);
// Execute first tool calls
const toolResults = await executeTools(result.tool_calls);
// Add tool responses to messages
messages.push({
role: "assistant",
tool_calls: result.tool_calls
});
toolResults.forEach(toolResult => {
messages.push({
role: "tool",
content: toolResult.result,
tool_name: toolResult.tool_name
});
});
// Second planning and response
result = await agent.run(messages, { tools });
if (result.type === 'tool_calls') {
// Handle additional tool calls if needed
console.log('Additional tool calls:', result.tool_calls);
} else if (result.type === 'final_answer') {
console.log('Final answer:', result.content);
}
}Multi-Agent Orchestration Example
import { USFAgent } from '@ultrasafeai/usf-agents';
// Create different specialized agents
const researchAgent = new USFAgent({
apiKey: 'your-api-key',
model: 'usf-research' // specialized research model
});
const creativeAgent = new USFAgent({
apiKey: 'your-api-key',
model: 'usf-creative' // specialized creative writing model
});
const analyzerAgent = new USFAgent({
apiKey: 'your-api-key',
model: 'usf-analyzer' // specialized analysis model
});
// Define research tools
const researchTools = [
{
type: "function",
function: {
name: "web_search",
description: "Search for information on the web",
parameters: {
type: "object",
properties: {
query: { type: "string" }
},
required: ["query"]
}
}
}
];
// Multi-agent workflow
async function multiAgentWorkflow(query) {
// Research phase
const researchResult = await researchAgent.run([
{ role: "user", content: `Research about ${query}` }
], { tools: researchTools });
let messages = [{ role: "user", content: query }];
if (researchResult.type === 'tool_calls') {
// Handle tool calls for research agent
messages.push({
role: "assistant",
tool_calls: researchResult.tool_calls
});
// Add tool responses
const researchData = await executeTools(researchResult.tool_calls);
researchData.forEach(data => {
messages.push({
role: "tool",
content: data.result,
tool_name: data.tool_name
});
});
} else {
messages.push({
role: "assistant",
content: researchResult.content
});
}
// Creative writing phase
const creativeResult = await creativeAgent.run(messages, {
tools: [],
temperature: 0.9,
stop: ["#"]
});
// Analysis phase
messages.push({
role: "user",
content: "Analyze the content above and provide key insights"
});
messages.push({
role: "assistant",
content: creativeResult.content
});
const analysisResult = await analyzerAgent.run(messages, {
tools: [],
temperature: 0.3
});
return analysisResult;
}
// Execute multi-agent workflow
const finalResult = await multiAgentWorkflow("sustainable energy solutions");
console.log(finalResult.content);Optional Tool Executor
For executing tool calls manually:
import { executeTools } from '@ultrasafeai/usf-agents';
const toolResults = await executeTools([
{ name: "web_search", arguments: { query: "latest news" } }
]);📘 Comprehensive Examples
1. Google Search Integration
This example demonstrates how to use external Google Search API with the usf-agents SDK for tool calling workflows.
import { USFAgent } from '@ultrasafeai/usf-agents';
// Mock API key - replace with your actual SerpAPI key
const SERPAPI_KEY = 'your-serpapi-key-here';
// Custom tool executor for Google Search
async function executeGoogleSearch(toolCalls) {
const results = [];
for (const toolCall of toolCalls) {
if (toolCall.name === 'google_search') {
try {
// Mock implementation of Google Search API call
// In a real implementation, you would use:
// const response = await fetch(`https://serpapi.com/search.json?engine=google&q=${encodeURIComponent(toolCall.arguments.query)}&api_key=${SERPAPI_KEY}`);
// const data = await response.json();
// Mock response for demonstration
const mockResults = [
{
title: "Paris - Wikipedia",
snippet: "Paris is the capital and most populous city of France, with an estimated population of 2,175,601 residents as of 2024, in an area of more than 105 square kilometres.",
link: "https://en.wikipedia.org/wiki/Paris"
},
{
title: "Weather in Paris - AccuWeather",
snippet: "Current weather in Paris, France - hourly forecasts, daily forecasts, and severe weather alerts from AccuWeather.",
link: "https://www.accuweather.com/en/fr/paris"
}
];
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify(mockResults)
});
} catch (error) {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Failed to execute Google search: ${error.message}` })
});
}
}
}
return results;
}
// Define tools in OpenAI format
const tools = [
{
type: "function",
function: {
name: "google_search",
description: "Search Google for information",
parameters: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query"
}
},
required: ["query"]
}
}
}
];
// Create agent instance
const agent = new USFAgent({
apiKey: 'your-usf-api-key',
tempMemory: {
enabled: true,
maxLength: 5
}
});
// Example usage
async function runGoogleSearchExample() {
console.log("Running Google Search Example...");
// First query
let result = await agent.run("What's the weather like in Paris?", { tools });
if (result.type === 'tool_calls') {
console.log("Tool calls required:", result.tool_calls);
// Execute tools
const toolResults = await executeGoogleSearch(result.tool_calls);
// Feed results back to agent
for (const toolResult of toolResults) {
console.log(`Tool '${toolResult.tool_name}' executed with arguments:`, toolResult.tool_arguments);
console.log("Result:", toolResult.result);
}
// Continue conversation with tool results
result = await agent.run("Based on the search results, can you provide more details about Paris weather?", { tools });
}
console.log("Final answer:", result.content);
}
// Execute example
runGoogleSearchExample().catch(console.error);2. News Research Workflow
This example demonstrates a multi-step research workflow combining Google Search and Google News APIs.
import { USFAgent } from '@ultrasafeai/usf-agents';
// Mock API keys - replace with your actual keys
const SERPAPI_KEY = 'your-serpapi-key-here';
// Custom tool executor for both Search and News tools
async function executeResearchTools(toolCalls) {
const results = [];
for (const toolCall of toolCalls) {
try {
if (toolCall.name === 'google_search') {
// Mock implementation of Google Search API call
// In a real implementation, you would use:
// const response = await fetch(`https://serpapi.com/search.json?engine=google&q=${encodeURIComponent(toolCall.arguments.query)}&api_key=${SERPAPI_KEY}`);
// const data = await response.json();
// Mock response for demonstration
const mockResults = [
{
title: "Tesla - Wikipedia",
snippet: "Tesla, Inc. is an American multinational automotive and clean energy company headquartered in Austin, Texas. Tesla designs and manufactures electric cars, battery energy storage devices, solar panels and solar roof tiles.",
link: "https://en.wikipedia.org/wiki/Tesla,_Inc."
},
{
title: "Tesla Q2 2025 Financial Results",
snippet: "Tesla reported Q2 2025 financial results with revenue of $24.9 billion and net income of $1.9 billion.",
link: "https://tesla.com/investor"
}
];
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify(mockResults)
});
} else if (toolCall.name === 'google_news') {
// Mock implementation of Google News API call
// In a real implementation, you would use:
// const response = await fetch(`https://serpapi.com/search.json?engine=google_news&q=${encodeURIComponent(toolCall.arguments.query)}&api_key=${SERPAPI_KEY}`);
// const data = await response.json();
// Mock response for demonstration
const mockResults = [
{
title: "Tesla unveils new battery technology",
snippet: "Tesla has announced a breakthrough in battery technology that could increase range by 30% while reducing charging time.",
link: "https://tech-news.com/tesla-battery-breakthrough",
source: "Tech News Daily"
},
{
title: "Electric vehicle market expands in 2025",
snippet: "The global electric vehicle market has grown by 25% year-over-year, with Tesla maintaining its market leadership position.",
link: "https://business-report.com/ev-market-growth",
source: "Business Report"
}
];
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify(mockResults)
});
} else {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Unknown tool: ${toolCall.name}` })
});
}
} catch (error) {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Failed to execute tool '${toolCall.name}': ${error.message}` })
});
}
}
return results;
}
// Define tools in OpenAI format
const tools = [
{
type: "function",
function: {
name: "google_search",
description: "Search Google for general information",
parameters: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query"
}
},
required: ["query"]
}
}
},
{
type: "function",
function: {
name: "google_news",
description: "Search Google News for recent news articles",
parameters: {
type: "object",
properties: {
query: {
type: "string",
description: "News search query"
}
},
required: ["query"]
}
}
}
];
// Create agent instance
const agent = new USFAgent({
apiKey: 'your-usf-api-key',
tempMemory: {
enabled: true,
maxLength: 10
}
});
// Example usage
async function runNewsResearchExample() {
console.log("Running News Research Example...");
// Step 1: Initial research query
let result = await agent.run("Research about Tesla's latest developments in 2025", { tools });
// Step 2: Handle tool calls
if (result.type === 'tool_calls') {
console.log("Tool calls required:", result.tool_calls);
// Execute all required tools
const toolResults = await executeResearchTools(result.tool_calls);
// Feed results back to agent
for (const toolResult of toolResults) {
console.log(`Tool '${toolResult.tool_name}' executed with arguments:`, toolResult.tool_arguments);
console.log("Result:", toolResult.result);
}
// Step 3: Continue with search results
result = await agent.run("Based on the search results, what are Tesla's recent financial performance and news?", { tools });
// Step 4: Handle additional tool calls if needed
if (result.type === 'tool_calls') {
console.log("Additional tool calls required:", result.tool_calls);
const additionalToolResults = await executeResearchTools(result.tool_calls);
// Feed additional results back to agent
for (const toolResult of additionalToolResults) {
console.log(`Tool '${toolResult.tool_name}' executed with arguments:`, toolResult.tool_arguments);
console.log("Result:", toolResult.result);
}
// Step 5: Get final answer
result = await agent.run("Summarize Tesla's position in the 2025 electric vehicle market based on all the information provided.", { tools });
}
}
console.log("Final answer:", result.content);
}
// Execute example
runNewsResearchExample().catch(console.error);3. Multi-Tool Complex Workflow
This example demonstrates a complex workflow that combines research, calculation, and content generation using multiple tools.
import { USFAgent } from '@ultrasafeai/usf-agents';
// Mock API keys - replace with your actual keys
const SERPAPI_KEY = 'your-serpapi-key-here';
// Custom tool executor for multiple tools
async function executeMultiTools(toolCalls) {
const results = [];
for (const toolCall of toolCalls) {
try {
switch (toolCall.name) {
case 'web_search':
// Mock implementation of web search
const searchResults = [
{
title: "Apple Inc. - Wikipedia",
snippet: "Apple Inc. is an American multinational technology company that designs and manufactures consumer electronics, software and online services.",
link: "https://en.wikipedia.org/wiki/Apple_Inc."
},
{
title: "Apple Q3 2025 Earnings Report",
snippet: "Apple reported Q3 2025 revenue of $98.2 billion, up 5% year-over-year. iPhone revenue was $52.3 billion.",
link: "https://investor.apple.com"
}
];
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify(searchResults)
});
break;
case 'calculator':
// Mock implementation of calculator
try {
// In a real implementation, you might use a math library
// For this example, we'll do simple evaluations
const expression = toolCall.arguments.expression;
let result;
// Simple evaluation for demonstration
if (expression === "98.2 - 93.6") {
result = 4.6;
} else if (expression === "4.6 / 93.6 * 100") {
result = 4.9;
} else {
// Mock evaluation
result = eval(expression); // Note: Using eval is not recommended in production
}
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ result: result })
});
} catch (error) {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Calculation failed: ${error.message}` })
});
}
break;
case 'content_generator':
// Mock implementation of content generator
const topic = toolCall.arguments.topic;
const content = `# ${topic}\n\nThis is AI-generated content about ${topic}. In a real implementation, this would be generated using a language model.\n\n## Key Points\n- Point 1 about ${topic}\n- Point 2 about ${topic}\n- Point 3 about ${topic}\n\nThis concludes the generated content.`;
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ content: content })
});
break;
default:
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Unknown tool: ${toolCall.name}` })
});
}
} catch (error) {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: `Failed to execute tool '${toolCall.name}': ${error.message}` })
});
}
}
return results;
}
// Define tools in OpenAI format
const tools = [
{
type: "function",
function: {
name: "web_search",
description: "Search the web for information",
parameters: {
type: "object",
properties: {
query: {
type: "string",
description: "Search query"
}
},
required: ["query"]
}
}
},
{
type: "function",
function: {
name: "calculator",
description: "Perform mathematical calculations",
parameters: {
type: "object",
properties: {
expression: {
type: "string",
description: "Mathematical expression to evaluate"
}
},
required: ["expression"]
}
}
},
{
type: "function",
function: {
name: "content_generator",
description: "Generate structured content on a given topic",
parameters: {
type: "object",
properties: {
topic: {
type: "string",
description: "Topic for content generation"
},
format: {
type: "string",
description: "Desired content format",
enum: ["report", "article", "summary"]
}
},
required: ["topic"]
}
}
}
];
// Create agent instance
const agent = new USFAgent({
apiKey: 'your-usf-api-key',
tempMemory: {
enabled: true,
maxLength: 15
}
});
// Example usage
async function runMultiToolExample() {
console.log("Running Multi-Tool Complex Example...");
// Step 1: Initial complex query
let result = await agent.run("Analyze Apple's Q3 2025 financial performance and create a report", { tools });
// Step 2: Handle tool calls
while (result.type === 'tool_calls') {
console.log("Tool calls required:", result.tool_calls);
// Execute all required tools
const toolResults = await executeMultiTools(result.tool_calls);
// Feed results back to agent
for (const toolResult of toolResults) {
console.log(`Tool '${toolResult.tool_name}' executed`);
}
// Continue with next step
result = await agent.run("Based on these results, calculate the year-over-year growth percentage and generate a comprehensive report", { tools });
}
console.log("Final answer:", result.content);
}
// Execute example
runMultiToolExample().catch(console.error);🛠️ Custom Tool Implementation
Each example demonstrates how to implement custom tool executors:
async function executeTools(toolCalls) {
const results = [];
for (const toolCall of toolCalls) {
// Implement tool-specific logic
if (toolCall.name === 'your_tool_name') {
try {
// Call external API
const response = await fetch('your-api-endpoint', {
method: 'POST',
headers: { 'Authorization': `Bearer ${API_KEY}` },
body: JSON.stringify(toolCall.arguments)
});
const data = await response.json();
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify(data)
});
} catch (error) {
results.push({
tool_name: toolCall.name,
tool_arguments: toolCall.arguments,
result: JSON.stringify({ error: error.message })
});
}
}
}
return results;
}📦 Tool Definition Format
Tools are defined in OpenAI's function calling format:
const tools = [
{
type: "function",
function: {
name: "tool_name",
description: "Tool description",
parameters: {
type: "object",
properties: {
parameter_name: {
type: "string",
description: "Parameter description"
}
},
required: ["parameter_name"]
}
}
}
];🔄 Tool Call Workflow
- Agent Planning: Agent determines which tools to call
- Tool Execution: Custom executor calls external APIs
- Result Feeding: Tool results are fed back to agent
- Continuation: Agent continues with updated context
// Step 1: Agent returns tool calls
const result = await agent.run("Query", { tools });
if (result.type === 'tool_calls') {
// Step 2: Execute tools
const toolResults = await executeTools(result.tool_calls);
// Step 3: Process results
for (const toolResult of toolResults) {
console.log("Tool result:", toolResult.result);
}
// Step 4: Continue conversation
const finalResult = await agent.run("Follow-up query", { tools });
}🚀 Getting Started
Prerequisites
Install the usf-agents package:
npm install @ultrasafeai/usf-agentsObtain API keys for external services:
- SerpAPI for Google Search and News
- Replace placeholder keys in example code
API Reference
USFAgent Constructor
new USFAgent({
apiKey: string, // Required API key
endpoint?: string, // Base URL (default: https://api.us.inc/usf/v1)
model?: string, // Model name (default: usf-mini)
stream?: boolean // Enable streaming (default: false)
})agent.run(messages, options)
messages: Can be either:- A string representing a new query
- An array of message objects in OpenAI format (with role and content)
options.tools: Array of tools in OpenAI formatoptions.temperature: Temperature for final answer generationoptions.stop: Stop sequences for final answer generation
Returns:
- Non-streaming mode: Single result object with
typefield - Streaming mode: Async iterable of chunk objects
Each result includes a plan key showing internal planning steps.
Memory Features
The USFAgent supports temporary memory for context preservation between calls:
const agent = new USFAgent({
apiKey: 'your-api-key',
tempMemory: {
enabled: true, // Enable memory (default: false)
maxLength: 10, // Maximum number of messages to keep (default: 10)
autoTrim: true // Automatically trim old messages (default: true)
}
});
// First call
await agent.run("What's the weather like in New York?");
// Second call - agent remembers previous conversation
await agent.run("What about tomorrow?");
// Memory management methods
agent.getMemory(); // Returns current memory state
agent.setMemory(messages); // Manually set memory
agent.clearMemory(); // Clear memory