import { createAgent } from 'clientagentjs';
const agent = createAgent();Include the script in your HTML:
<script src="dist/clientagentjs.global.js"></script>Then access it via the global variable:
const agent = ClientAgent.createAgent();Sends a single request using the active profile and resolves to a response object.
await agent.ask("Summarize this text", {
context: "Optional extra context",
signal: abortController.signal
})prompt: required non-empty stringoptions.context: optional string with extra context injected into the user messageoptions.signal: optionalAbortSignal
{
text: "Assistant response text",
raw: { /* provider response payload */ }
}text: normalized assistant text extracted from the provider responseraw: original provider payload returned by the provider adapter
ask() throws when:
- there is no active profile with the minimum required fields
- the prompt is empty
- the request is aborted
- the provider returns a non-OK HTTP response
- the provider adapter rejects the request
Sends a streaming request using the active profile and returns an AsyncIterable.
for await (const chunk of agent.stream("Write a headline", {
context: "Optional extra context",
signal: abortController.signal
})) {
console.log(chunk.text)
}prompt: required non-empty stringoptions.context: optional string with extra context injected into the user messageoptions.signal: optionalAbortSignal
{
text: "Next visible text delta",
delta: "Next visible text delta",
raw: { /* provider event payload */ }
}text: normalized text emitted for the current chunkdelta: same value astextfor streaming adapters that expose deltasraw: original event payload from the provider adapter
- the iterator yields zero or more chunk objects
- concatenating all
chunk.textvalues produces the full streamed text - provider-specific non-text events may be ignored by the adapter
stream() throws when:
- there is no active profile with the minimum required fields
- the prompt is empty
- the request is aborted
- the provider returns a non-OK HTTP response
- the provider adapter rejects the request
session.ask() and session.stream() follow the same response contracts as agent.ask() and agent.stream(), with conversation history automatically injected from the session memory.
Additional session methods:
session.getHistory()
session.clear()getHistory(): returns the current in-memory conversation as an array of{ role, content }clear(): removes the stored session history
The public local tool methods are:
agent.registerTool(name, handler)
agent.unregisterTool(name)
agent.listTools()
agent.runTool(name, input)name: required non-empty stringhandler: required functioninput: one plain object passed to the tool handler
Tool handlers may return plain JSON-compatible data or strings. When a compatible provider uses the tool through model tool-calling, the return value is serialized and injected back into the conversation.
When createAgent({ onEvent }) is used, the agent may emit:
request:startrequest:endrequest:errortokenstorage:changedprofile:savedprofile:deletedprofile:clearedprofile:activeprofile:importedmcp:savedmcp:deletedmcp:cleared
The event payload depends on the operation, but always follows this outer shape:
{
type: "request:start",
payload: { /* event-specific payload */ }
}The library provides a built-in configuration panel exported from src/ui/profilePanel.js.
Opens the profile management dialog.
agent: the agent instancedialogClass: optional string to add a custom CSS class to the dialog container
Opens the MCP server management dialog.
The UI uses :where() selectors for its default styling, meaning they have zero specificity. You can override any style by simply defining the class in your own CSS:
/* Example: change the look of the profile dialog */
.client-agent-js-profile-dlg {
background: #1e1e1e;
color: white;
border: 1px solid #333;
}Main classes available for customization:
.client-agent-js-profile-overlay.client-agent-js-profile-dlg.caj-field.caj-controls.caj-error.caj-feedback
See license: ClientAgentJS