Skip to main content

Message

The Message class is the data model that AgentFlow uses to represent every message in a conversation — user inputs, assistant responses, tool calls, and tool results. It is defined in src/message.ts and exported from @10xscale/agentflow-client.


Import

import {
Message,
TextBlock,
ImageBlock,
AudioBlock,
VideoBlock,
DocumentBlock,
DataBlock,
ToolCallBlock,
RemoteToolCallBlock,
ToolResultBlock,
ReasoningBlock,
AnnotationBlock,
ErrorBlock,
MediaRef,
AnnotationRef,
TokenUsages,
} from '@10xscale/agentflow-client';

Message class

class Message {
message_id: string | null;
role: 'user' | 'assistant' | 'system' | 'tool';
content: ContentBlock[];
delta: boolean;
tools_calls?: Record<string, any>[];
timestamp: number;
metadata: Record<string, any>;
usages?: TokenUsages;
raw?: Record<string, any>;

constructor(
role: 'user' | 'assistant' | 'system' | 'tool',
content: ContentBlock[],
message_id?: string | null
);
}

Fields

FieldTypeDescription
message_idstring | nullServer-assigned message ID. Use "0" or null when creating new messages — the server assigns the real ID.
role'user' | 'assistant' | 'system' | 'tool'Who produced this message.
contentContentBlock[]Array of content blocks. A single message can have multiple blocks (e.g. text + image).
deltabooleantrue when this message is a streaming partial update rather than a final message. Set by the server.
tools_callsRecord<string, any>[]Raw tool call array from the underlying LLM response. Populated by the server; do not set this manually.
timestampnumberUnix timestamp in milliseconds when the message was created. Defaults to Date.now() at construction time.
metadataRecord<string, any>Arbitrary key-value metadata you can attach to messages.
usagesTokenUsagesToken usage information returned by the LLM. Only present on assistant messages.
rawRecord<string, any>The raw LLM response object, if the server passes it through. Useful for debugging.

Static factory methods

Message.text_message(content, role?, message_id?)

The most common way to create a message. Creates a Message with a single TextBlock.

const userMsg = Message.text_message('What is the capital of France?');
// role defaults to 'user'

const systemMsg = Message.text_message(
'You are a helpful geography tutor.',
'system'
);

Parameters:

ParameterTypeDefaultDescription
contentstringThe text content.
role'user' | 'assistant' | 'system' | 'tool''user'The role for the message.
message_idstring | nullnullOptional message ID. Use null to let the server assign one.

Message.tool_message(content, message_id?, meta?)

Creates a tool role message containing ToolResultBlock instances. Typically you do not create these manually — when you use remote tools the client creates them for you.

const toolResult = Message.tool_message([
new ToolResultBlock({
call_id: 'call_abc123',
output: { result: 42 },
status: 'completed',
is_error: false,
}),
]);

ContentBlock union type

The content field of a Message is an array of ContentBlock values. Each block has a type discriminant field. The full union is:

type ContentBlock =
| TextBlock
| ImageBlock
| AudioBlock
| VideoBlock
| DocumentBlock
| DataBlock
| ToolCallBlock
| RemoteToolCallBlock
| ToolResultBlock
| ReasoningBlock
| AnnotationBlock
| ErrorBlock;

Block types

TextBlock

Plain text content.

class TextBlock {
type: 'text';
text: string;
annotations: AnnotationRef[];
}
const block = new TextBlock('Hello, world!');
FieldTypeDescription
type'text'Discriminant. Always 'text'.
textstringThe text content.
annotationsAnnotationRef[]Optional citation or note annotations appended to this block.

ImageBlock

An image attached to a message.

class ImageBlock {
type: 'image';
media: MediaRef;
alt_text?: string;
bbox?: number[];
}
const block = new ImageBlock(
new MediaRef('url', 'https://example.com/photo.jpg'),
'A photo of a cat'
);
FieldTypeDescription
type'image'Discriminant.
mediaMediaRefReference to the image data.
alt_textstringAccessible alternative text.
bboxnumber[]Optional bounding box [x, y, w, h] within a parent image.

AudioBlock

An audio clip attached to a message.

class AudioBlock {
type: 'audio';
media: MediaRef;
transcript?: string;
sample_rate?: number;
channels?: number;
}
FieldTypeDescription
mediaMediaRefReference to the audio data.
transcriptstringOptional pre-computed transcript of the audio.
sample_ratenumberSample rate in Hz.
channelsnumberNumber of audio channels (1 = mono, 2 = stereo).

VideoBlock

A video clip attached to a message.

class VideoBlock {
type: 'video';
media: MediaRef;
thumbnail?: MediaRef;
}

DocumentBlock

A document (PDF, DOCX, etc.) attached to a message.

class DocumentBlock {
type: 'document';
media: MediaRef;
pages?: number[];
excerpt?: string;
}
FieldTypeDescription
pagesnumber[]Which pages of the document are relevant (1-indexed).
excerptstringOptional extracted text excerpt from the document.

DataBlock

Raw binary or structured data encoded as base64 or referenced via MediaRef.

class DataBlock {
type: 'data';
mime_type: string;
data_base64?: string;
media?: MediaRef;
}

ToolCallBlock

Represents a tool/function call made by the assistant. Populated by the server; you typically do not create these manually.

class ToolCallBlock {
type: 'tool_call';
id: string;
name: string;
args: Record<string, any>;
tool_type?: string;
}
FieldTypeDescription
idstringUnique ID for this tool call (used to match with ToolResultBlock.call_id).
namestringName of the tool to call.
argsRecord<string, any>Arguments to pass to the tool function.
tool_typestringOptional tool type tag (e.g. 'mcp', 'function').

RemoteToolCallBlock

Like ToolCallBlock but specifically for tools that execute on the client side (browser). When the server needs the client to run a tool, it returns a message containing RemoteToolCallBlock entries. The client's invoke() loop detects these, executes the registered handlers, and sends the results back.

class RemoteToolCallBlock {
type: 'remote_tool_call';
id: string;
name: string;
args: Record<string, any>;
tool_type: string; // always 'remote'
}

You do not create these manually. They arrive from the server inside invoke() responses.


ToolResultBlock

The result of executing a tool call. When using remote tools the client creates these automatically. You only need to construct them manually if you are building custom tool-loop logic.

class ToolResultBlock {
type: 'tool_result';
call_id: string;
output: any;
is_error: boolean;
status?: 'completed' | 'failed';
}

// Constructor takes an object:
new ToolResultBlock({
call_id: 'call_abc123',
output: { temperature: 22.5 },
status: 'completed',
is_error: false,
})
FieldTypeDescription
call_idstringMust match the id of the corresponding ToolCallBlock or RemoteToolCallBlock.
outputanyThe return value of the tool function. Can be any JSON-serialisable value.
is_errorbooleanSet to true when the tool execution failed.
status'completed' | 'failed'Status signal sent back to the server.

ReasoningBlock

Extended-thinking / chain-of-thought reasoning steps emitted by models that support it (e.g. Claude 3+).

class ReasoningBlock {
type: 'reasoning';
summary: string;
details?: string[];
}
FieldTypeDescription
summarystringShort summary of the reasoning step.
detailsstring[]Optional detailed reasoning steps.

AnnotationBlock

Citations or notes appended to message content.

class AnnotationBlock {
type: 'annotation';
kind: 'citation' | 'note';
refs: AnnotationRef[];
spans?: [number, number][];
}
FieldTypeDescription
kind'citation' | 'note'Whether this is a citation to a source or an inline note.
refsAnnotationRef[]List of sources or note references.
spans[number, number][]Character offset spans within TextBlock.text that this annotation covers.

ErrorBlock

Represents an error that occurred during graph execution, embedded in a message.

class ErrorBlock {
type: 'error';
message: string;
code?: string;
data?: Record<string, any>;
}

Helper types

MediaRef

A reference to a media file. Supports three kinds: an external URL, an uploaded file_id, or inline base64 data.

class MediaRef {
kind: 'url' | 'file_id' | 'data';
url?: string; // when kind = 'url'
file_id?: string; // when kind = 'file_id'
data_base64?: string; // when kind = 'data'
mime_type?: string;
size_bytes?: number;
sha256?: string;
filename?: string;
width?: number;
height?: number;
duration_ms?: number;
page?: number;
}

Create a URL reference:

const media = new MediaRef('url', 'https://example.com/image.png');
media.mime_type = 'image/png';

Create a file_id reference (after uploading):

const uploaded = await client.uploadFile(file);
const media = new MediaRef('file_id');
media.file_id = uploaded.data.file_id;
media.mime_type = uploaded.data.mime_type;

AnnotationRef

A reference to a source or note target.

class AnnotationRef {
url?: string;
file_id?: string;
page?: number;
index?: number;
title?: string;
}

TokenUsages

LLM token usage statistics attached to assistant messages.

class TokenUsages {
completion_tokens: number;
prompt_tokens: number;
total_tokens: number;
reasoning_tokens: number;
cache_creation_input_tokens: number;
cache_read_input_tokens: number;
image_tokens?: number;
audio_tokens?: number;
}

Complete example

import {
Message,
TextBlock,
ImageBlock,
MediaRef,
} from '@10xscale/agentflow-client';

// 1. Simple text message
const greeting = Message.text_message('Hello!');

// 2. Message with mixed text and image
const multimodal = new Message('user', [
new TextBlock('What is in this image?'),
new ImageBlock(
new MediaRef('url', 'https://example.com/photo.jpg'),
'A street photo'
),
]);

// 3. System prompt
const system = Message.text_message(
'You are a helpful assistant. Be concise.',
'system'
);

// 4. Send them to the agent
const result = await client.invoke([system, greeting]);
console.log(result.messages);

What you learned

  • Message has four roles: user, assistant, system, and tool.
  • content is always an array of typed ContentBlock objects.
  • Message.text_message() is the easiest way to create a plain text message.
  • RemoteToolCallBlock arrives from the server when a remote tool needs executing — the invoke() loop handles this automatically.
  • Use MediaRef with kind: 'file_id' to reference files you have uploaded via uploadFile().

Next step

See reference/client/invoke to learn how to send messages and receive responses.