Skip to content

SDK API

Complete reference for the SDK class.

For detailed ID format documentation, see Models Reference.

sdk = SDK(
chainId=11155111, # ChainId
rpcUrl="https://sepolia.infura.io/v3/YOUR_PROJECT_ID",
signer=None, # Optional[Any] (omit for read-only)
registryOverrides=None, # Optional[Dict[ChainId, Dict[str, Address]]]
indexingStore=None,
embeddings=None,
ipfs=None, # Optional[str]: "node" | "filecoinPin" | "pinata"
ipfsNodeUrl=None,
filecoinPrivateKey=None,
pinataJwt=None,
subgraphOverrides=None, # Optional[Dict[ChainId, str]]
)
import { SDK } from 'agent0-sdk';
const sdk = new SDK({
chainId: 11155111,
rpcUrl: 'https://sepolia.infura.io/v3/YOUR_PROJECT_ID',
// Optional for read-only operations
privateKey: process.env.PRIVATE_KEY,
// Browser alternative (EIP-1193):
// walletProvider,
// registryOverrides?: Record<ChainId, Record<string, Address>>
// subgraphUrl?: string
// subgraphOverrides?: Record<ChainId, string>
});

Note: The chainId parameter sets the SDK’s default chain. When you provide an agentId without a chainId prefix, the SDK uses this default chain.

TypeScript note: signer is still accepted as a backwards-compatible alias for privateKey.

Advanced: direct contract calls (TypeScript)

Section titled “Advanced: direct contract calls (TypeScript)”

The TypeScript SDK no longer exposes legacy registry helpers. If you need direct on-chain access:

  • Use sdk.registries() to get the registry addresses.
  • Use viem directly (recommended) with a minimal ABI for the function(s) you need.
  • Alternatively, you can use the SDK’s exported ViemChainClient if you want a thin wrapper around common read/write operations.

Create a new agent.

agent = sdk.createAgent(
name: str,
description: str,
image: Optional[str] = None
) -> Agent
import { SDK, Agent } from 'agent0-sdk';
const agent: Agent = sdk.createAgent(
name: string,
description: string,
image?: string
);

Load an existing agent by ID.

agent = sdk.loadAgent(agentId: str) -> Agent
import { SDK, Agent } from 'agent0-sdk';
import type { AgentId } from 'agent0-sdk';
const agent: Agent = await sdk.loadAgent(agentId: AgentId);

Search for agents with filters.

results = sdk.searchAgents(
filters: Union[SearchFilters, Dict, None] = None,
options: Union[SearchOptions, Dict, None] = None,
**kwargs
) -> List[AgentSummary]
import { SDK } from 'agent0-sdk';
import type { SearchFilters, SearchOptions, AgentSummary } from 'agent0-sdk';
const results: AgentSummary[] = await sdk.searchAgents(
filters?: SearchFilters,
options?: SearchOptions
);

searchAgents(filters, options) is the unified entrypoint that blends agent discovery + reputation filtering.

Multi-chain note: filters.chains enables multi-chain execution. Results are returned as a flat AgentSummary[] containing agents from all queried chains.

Default chains: if you omit filters.chains, searchAgents() queries chain 1 plus the SDK’s default chainId, de-duplicated (so chain 1 is never queried twice). This applies both with and without filters.keyword.

DateLike = Union[datetime, str, int]
@dataclass
class SearchFilters:
chains: Optional[Union[List[ChainId], Literal["all"]]] = None
agentIds: Optional[List[AgentId]] = None
name: Optional[str] = None
description: Optional[str] = None
owners: Optional[List[Address]] = None
operators: Optional[List[Address]] = None
hasRegistrationFile: Optional[bool] = None
hasWeb: Optional[bool] = None
hasMCP: Optional[bool] = None
hasA2A: Optional[bool] = None
hasOASF: Optional[bool] = None
hasEndpoints: Optional[bool] = None
webContains: Optional[str] = None
mcpContains: Optional[str] = None
a2aContains: Optional[str] = None
ensContains: Optional[str] = None
didContains: Optional[str] = None
walletAddress: Optional[Address] = None
supportedTrust: Optional[List[str]] = None
a2aSkills: Optional[List[str]] = None
mcpTools: Optional[List[str]] = None
mcpPrompts: Optional[List[str]] = None
mcpResources: Optional[List[str]] = None
oasfSkills: Optional[List[str]] = None
oasfDomains: Optional[List[str]] = None
active: Optional[bool] = None
x402support: Optional[bool] = None
registeredAtFrom: Optional[DateLike] = None
registeredAtTo: Optional[DateLike] = None
updatedAtFrom: Optional[DateLike] = None
updatedAtTo: Optional[DateLike] = None
hasMetadataKey: Optional[str] = None
metadataValue: Optional[Dict[str, str]] = None # { key, value }
keyword: Optional[str] = None
feedback: Optional[FeedbackFilters] = None
export interface SearchFilters {
chains?: number[] | 'all';
agentIds?: AgentId[];
name?: string;
description?: string;
owners?: Address[];
operators?: Address[];
hasRegistrationFile?: boolean;
hasWeb?: boolean;
hasMCP?: boolean;
hasA2A?: boolean;
hasOASF?: boolean;
hasEndpoints?: boolean;
webContains?: string;
mcpContains?: string;
a2aContains?: string;
ensContains?: string;
didContains?: string;
walletAddress?: Address;
supportedTrust?: string[];
a2aSkills?: string[];
mcpTools?: string[];
mcpPrompts?: string[];
mcpResources?: string[];
oasfSkills?: string[];
oasfDomains?: string[];
active?: boolean;
x402support?: boolean;
registeredAtFrom?: Date | string | number;
registeredAtTo?: Date | string | number;
updatedAtFrom?: Date | string | number;
updatedAtTo?: Date | string | number;
hasMetadataKey?: string;
metadataValue?: { key: string; value: string };
keyword?: string;
feedback?: FeedbackFilters;
}
FieldSemantics
chainsundefined queries chain 1 + SDK default chainId (de-duplicated); list queries those chains; "all" queries all configured chains
agentIdsOnly these agent IDs ("chainId:agentId")
name / descriptionCase-insensitive substring match
owners / operatorsMatch agent owner or any operator
hasRegistrationFileRequire a registration file
hasWeb / hasMCP / hasA2A / hasOASFRequire that endpoint type is present
hasEndpointsRequire at least one of {web, email, mcp, a2a, oasf}
webContains / mcpContains / a2aContains / ensContains / didContainsCase-insensitive substring match for those endpoint strings
walletAddressExact match for the agent wallet address (if set)
supportedTrustANY-of: agent supports at least one of these trust model strings
a2aSkills / mcpTools / mcpPrompts / mcpResources / oasfSkills / oasfDomainsANY-of: matches at least one listed element
active / x402supportBoolean filters
registeredAtFrom/ToInclusive timestamp range over agent createdAt
updatedAtFrom/ToInclusive timestamp range over agent updatedAt
hasMetadataKeyRequire an on-chain metadata entry with this key (two-phase prefilter)
metadataValueRequire metadata key/value exact match (two-phase prefilter)
keywordSemantic keyword prefilter via external semantic-search endpoint
feedbackUnified reputation filtering (see FeedbackFilters)
@dataclass
class FeedbackFilters:
hasFeedback: Optional[bool] = None
hasNoFeedback: Optional[bool] = None
includeRevoked: Optional[bool] = None
minValue: Optional[float] = None
maxValue: Optional[float] = None
minCount: Optional[int] = None
maxCount: Optional[int] = None
fromReviewers: Optional[List[Address]] = None
endpoint: Optional[str] = None
hasResponse: Optional[bool] = None
tag1: Optional[str] = None
tag2: Optional[str] = None
tag: Optional[str] = None
export interface FeedbackFilters {
hasFeedback?: boolean;
hasNoFeedback?: boolean;
includeRevoked?: boolean;
minValue?: number;
maxValue?: number;
minCount?: number;
maxCount?: number;
fromReviewers?: Address[];
endpoint?: string;
hasResponse?: boolean;
tag1?: string;
tag2?: string;
tag?: string;
}
FieldSemantics
hasFeedback / hasNoFeedbackFilter by whether the agent has any feedback
includeRevokedInclude revoked feedback in the pool used for filtering
minValue / maxValueThreshold on average value over feedback matching the other feedback constraints (inclusive)
minCount / maxCountThreshold on count of feedback matching the other feedback constraints (inclusive)
fromReviewersOnly consider feedback from these reviewer wallets
endpointOnly consider feedback whose endpoint contains this substring
hasResponseOnly consider feedback that has at least one response (if supported)
tag1 / tag2Only consider feedback matching tag1/tag2
tagShorthand: match either tag1 OR tag2
@dataclass
class SearchOptions:
sort: Optional[List[str]] = None
semanticMinScore: Optional[float] = None
semanticTopK: Optional[int] = None
export interface SearchOptions {
sort?: string[];
semanticMinScore?: number;
semanticTopK?: number;
}
FieldSemantics
sortList of sort keys: \"field:asc\" or \"field:desc\"
semanticMinScoreMinimum semantic score cutoff (keyword searches only)
semanticTopKLimits semantic prefilter size (semantic endpoint has no cursor)
  • AgentSummary[]

searchAgents() returns AgentSummary objects. Endpoint fields (mcp, a2a, web, email) are endpoint strings when present (not booleans).

@dataclass
class AgentSummary:
chainId: ChainId
agentId: AgentId
name: str
image: Optional[URI]
description: str
owners: List[Address]
operators: List[Address]
mcp: Optional[str] = None
a2a: Optional[str] = None
web: Optional[str] = None
email: Optional[str] = None
ens: Optional[str]
did: Optional[str]
walletAddress: Optional[Address]
supportedTrusts: List[str]
a2aSkills: List[str]
mcpTools: List[str]
mcpPrompts: List[str]
mcpResources: List[str]
oasfSkills: List[str]
oasfDomains: List[str]
active: bool
x402support: bool
createdAt: Optional[int] = None
updatedAt: Optional[int] = None
lastActivity: Optional[int] = None
agentURI: Optional[str] = None
agentURIType: Optional[str] = None
feedbackCount: Optional[int] = None
averageValue: Optional[float] = None
semanticScore: Optional[float] = None
extras: Dict[str, Any] = field(default_factory=dict)
export interface AgentSummary {
chainId: number;
agentId: AgentId;
name: string;
image?: URI;
description: string;
owners: Address[];
operators: Address[];
mcp?: string;
a2a?: string;
web?: string;
email?: string;
ens?: string;
did?: string;
walletAddress?: Address;
supportedTrusts: string[];
a2aSkills: string[];
mcpTools: string[];
mcpPrompts: string[];
mcpResources: string[];
oasfSkills: string[];
oasfDomains: string[];
active: boolean;
x402support: boolean;
createdAt?: number;
updatedAt?: number;
lastActivity?: number;
agentURI?: string;
agentURIType?: string;
feedbackCount?: number;
averageValue?: number;
semanticScore?: number;
extras: Record<string, any>;
}

Get a single agent summary.

agent = sdk.getAgent(agentId: str) -> AgentSummary
import { SDK } from 'agent0-sdk';
import type { AgentId, AgentSummary } from 'agent0-sdk';
const agent: AgentSummary | null = await sdk.getAgent(agentId: AgentId);

Parameters:

  • agentId (str / AgentId): Agent ID in format "agentId" (uses SDK’s default chain) or "chainId:agentId" (explicit chain, e.g., "11155111:1234") Examples:
# Using default chain
agent = sdk.getAgent("1234") # Uses SDK's default chain
# Explicitly specify chain
agent = sdk.getAgent("11155111:1234") # ETH Sepolia
// Using default chain
const agent = await sdk.getAgent('1234'); // Uses SDK's default chain
// Explicitly specify chain
const agent = await sdk.getAgent('11155111:1234'); // ETH Sepolia

Prepare an off-chain feedback file payload (optional).

feedback_file = sdk.prepareFeedbackFile({
"text": "Optional rich feedback text",
"capability": "tools",
"name": "financial_analyzer",
"skill": "financial_analysis",
"task": "analyze_balance_sheet",
"context": {"userId": "user123"},
"proofOfPayment": {"txHash": "0x...", "amount": "0.01"},
})
import { SDK } from 'agent0-sdk';
import type { FeedbackFileInput } from 'agent0-sdk';
const feedbackFile: FeedbackFileInput = sdk.prepareFeedbackFile({
text: undefined,
capability: 'tools',
name: 'financial_analyzer',
skill: 'financial_analysis',
task: 'analyze_balance_sheet',
context: { userId: 'user123' },
proofOfPayment: { txHash: '0x...', amount: '0.01' },
});

Give feedback on-chain (optionally with an off-chain feedback file).

tx = sdk.giveFeedback(
agentId="11155111:123",
value=85,
tag1="data_analyst",
tag2="finance",
endpoint="https://api.example.com/feedback",
feedbackFile=feedback_file, # optional
) -> TransactionHandle[Feedback]
feedback = tx.wait_confirmed(timeout=180).result
import { SDK } from 'agent0-sdk';
import type { AgentId, Feedback, FeedbackFileInput, TransactionHandle } from 'agent0-sdk';
const tx: TransactionHandle<Feedback> = await sdk.giveFeedback(
agentId,
85,
'data_analyst',
'finance',
'https://api.example.com/feedback',
feedbackFile // optional: FeedbackFileInput
);
const { result: feedback } = await tx.waitConfirmed();

Get single feedback.

feedback = sdk.getFeedback(
agentId="11155111:123",
clientAddress="0xabc...",
feedbackIndex=0
) -> Feedback
import { SDK } from 'agent0-sdk';
import type { AgentId, Address, Feedback } from 'agent0-sdk';
const feedback: Feedback = await sdk.getFeedback(
agentId: AgentId,
clientAddress: Address,
feedbackIndex: number
);

Note: feedbackIndex in the feedback ID is 0-based (first feedback = 0, second = 1, etc.)

Note: Both SDKs take separate parameters instead of a single feedbackId string.

Search feedback with filters.

results = sdk.searchFeedback(
agentId="11155111:123", # optional
agents=None, # optional: search across multiple agents
reviewers=None,
tags=["data_analyst"],
capabilities=["tools"],
skills=["financial_analysis"],
tasks=None,
names=None,
minValue=0,
maxValue=100,
include_revoked=False,
first=100,
skip=0,
) -> List[Feedback]
import { SDK } from 'agent0-sdk';
import type { AgentId, Address, Feedback } from 'agent0-sdk';
const results: Feedback[] = await sdk.searchFeedback(
filters: {
agentId?: AgentId;
agents?: AgentId[];
tags?: string[];
reviewers?: Address[];
capabilities?: string[];
skills?: string[];
tasks?: string[];
names?: string[];
includeRevoked?: boolean;
},
options?: { minValue?: number; maxValue?: number }
);

Parameters:

  • agentId (str / AgentId, optional): Agent ID in format "agentId" (uses SDK’s default chain) or "chainId:agentId" (explicit chain)
  • agents (List[AgentId] / AgentId[], optional): Search across multiple agents (use "chainId:agentId" for cross-chain)
  • reviewers (List[Address] / Address[], optional): Reviewer wallet addresses (enables “all feedback given by a wallet” when used without agentId)

Notes:

  • You must provide at least one filter (agentId/agents/reviewers/tags/etc.). Empty searches are rejected to avoid accidental global queries.
  • Reviewer-only searches require a configured subgraph (no on-chain fallback).

searchAgents (feedback / reputation filters)

Section titled “searchAgents (feedback / reputation filters)”

searchAgentsByReputation was removed. Use searchAgents() with filters.feedback instead.

results = sdk.searchAgents(
filters={
"chains": "all",
"feedback": {
"minValue": 80,
"tag": "enterprise",
"includeRevoked": False,
},
},
)
const results = await sdk.searchAgents(
{
chains: 'all',
feedback: { minValue: 80, tag: 'enterprise', includeRevoked: false },
}
);

Revoke feedback.

result = sdk.revokeFeedback(
agentId: str,
feedbackIndex: int
) -> Feedback
import { SDK } from 'agent0-sdk';
import type { AgentId, TransactionHandle, Feedback } from 'agent0-sdk';
const tx: TransactionHandle<Feedback> = await sdk.revokeFeedback(
agentId: AgentId,
feedbackIndex: number
);
await tx.waitConfirmed();

TypeScript Note: Returns a TransactionHandle<Feedback>.

Append response to feedback.

feedback = sdk.appendResponse(
agentId: str,
clientAddress: str,
feedbackIndex: int,
response: Dict
) -> Feedback
import { SDK } from 'agent0-sdk';
import type { AgentId, Address, URI, TransactionHandle, Feedback } from 'agent0-sdk';
const tx: TransactionHandle<Feedback> = await sdk.appendResponse(
agentId: AgentId,
clientAddress: Address,
feedbackIndex: number,
response: { uri: URI; hash: string }
);
await tx.waitConfirmed();

TypeScript Note: Returns a TransactionHandle<Feedback>. Response parameter is an object with uri and hash properties.

Get reputation summary for an agent.

summary = sdk.getReputationSummary(
agentId: str
) -> Dict
import { SDK } from 'agent0-sdk';
import type { AgentId } from 'agent0-sdk';
const summary: { count: number; averageValue: number } = await sdk.getReputationSummary(
agentId: AgentId,
tag1?: string,
tag2?: string
);

Parameters:

  • agentId (str / AgentId): Agent ID in format "agentId" (uses SDK’s default chain) or "chainId:agentId" (explicit chain)

Transfer agent ownership to a new address.

tx = sdk.transferAgent(
agentId: str,
newOwnerAddress: str
) -> TransactionHandle[Dict[str, Any]]
result = tx.wait_confirmed(timeout=180).result
import { SDK } from 'agent0-sdk';
import type { AgentId, Address, TransactionHandle } from 'agent0-sdk';
const tx: TransactionHandle<{
txHash: string;
from: Address;
to: Address;
agentId: AgentId;
}> = await sdk.transferAgent(
agentId: AgentId,
newOwner: Address
);
const { result } = await tx.waitConfirmed();

Parameters:

  • agentId (str / AgentId): The agent ID to transfer

  • newOwnerAddress / newOwner (str / Address): Ethereum address of the new owner Returns:

  • Python: Dict[str, Any] containing:

  • txHash (str): Transaction hash

  • from (str): Previous owner address

  • to (str): New owner address

  • agentId (str): Agent ID that was transferred

  • TypeScript: Object with typed fields { txHash: string; from: Address; to: Address; agentId: AgentId } Raises/Throws:

  • Python: ValueError: If agent not found or transfer not allowed

  • TypeScript: Error: If agent not found or transfer not allowed Example:

# Transfer agent using SDK method
tx = sdk.transferAgent(
agentId="11155111:123",
newOwnerAddress="0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6"
)
result = tx.wait_confirmed(timeout=180).result
print(f"Transfer successful: {result['txHash']}")
print(f"New owner: {result['to']}")
// Transfer agent using SDK method
const tx = await sdk.transferAgent(
"11155111:123",
"0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6"
);
const { result } = await tx.waitConfirmed();
console.log(`Transfer successful: ${result.txHash}`);
console.log(`New owner: ${result.to}`);

Comparison with Agent.transfer():

  • sdk.transferAgent() is a convenience method that loads the agent first

  • agent.transfer() works directly on an existing agent instance

  • Both methods perform the same validation and transfer logic

  • Use sdk.transferAgent() when you only have the agent ID

  • Use agent.transfer() when you already have an agent instance Important Notes:

  • Only the current owner can transfer the agent

  • Agent URI, metadata, and all other data remain unchanged

  • Transfer is irreversible - ensure the new owner is correct

  • Invalid addresses and self-transfers are automatically rejected

  • Address validation includes checksum format verification

Get the current owner of an agent.

owner = sdk.getAgentOwner(agentId: str) -> str
import { SDK } from 'agent0-sdk';
import type { AgentId, Address } from 'agent0-sdk';
const owner: Address = await sdk.getAgentOwner(agentId: AgentId);

Parameters:

  • agentId (str / AgentId): The agent ID to check Returns:

  • Python: str - The current owner’s Ethereum address

  • TypeScript: Address - The current owner’s Ethereum address Raises/Throws:

  • Python: ValueError: If agent ID is invalid or agent doesn’t exist

  • TypeScript: Error: If agent ID is invalid or agent doesn’t exist Example:

owner = sdk.getAgentOwner("11155111:123")
print(f"Current owner: {owner}")
const owner = await sdk.getAgentOwner("11155111:123");
console.log(`Current owner: ${owner}`);

Check if an address is the owner of an agent.

is_owner = sdk.isAgentOwner(
agentId: str,
address: Optional[str] = None
) -> bool
import { SDK } from 'agent0-sdk';
import type { AgentId, Address } from 'agent0-sdk';
const isOwner: boolean = await sdk.isAgentOwner(
agentId: AgentId,
address: Address
);

Parameters:

  • agentId (str / AgentId): The agent ID to check

  • address (str / Address, optional in Python, required in TypeScript): Address to check (Python defaults to SDK’s signer address) Returns:

  • bool: True if the address is the owner, False otherwise Raises/Throws:

  • Python: ValueError: If agent ID is invalid or agent doesn’t exist

  • TypeScript: Error: If agent ID is invalid or agent doesn’t exist Example:

# Check if current signer is owner
is_owner = sdk.isAgentOwner("11155111:123")
# Check if specific address is owner
is_owner = sdk.isAgentOwner("11155111:123", "0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6")
// Check if specific address is owner (address is required in TypeScript)
const isOwner = await sdk.isAgentOwner(
"11155111:123",
"0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6"
);

Check if an address can transfer an agent (i.e., is the owner).

can_transfer = sdk.canTransferAgent(
agentId: str,
address: Optional[str] = None
) -> bool
// Note: This method is not available in TypeScript SDK
// Use isAgentOwner instead, which serves the same purpose
const canTransfer = await sdk.isAgentOwner(agentId, address);

TypeScript Note: This method is not available in the TypeScript SDK. Use isAgentOwner() instead, which serves the same purpose.

Parameters:

  • agentId (str): The agent ID to check

  • address (str, optional): Address to check (defaults to SDK’s signer address) Returns:

  • bool: True if the address can transfer the agent, False otherwise Example:

# Check if current signer can transfer
can_transfer = sdk.canTransferAgent("11155111:123")
# Check if specific address can transfer
can_transfer = sdk.canTransferAgent("11155111:123", "0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6")
// Use isAgentOwner as equivalent
const canTransfer = await sdk.isAgentOwner(
"11155111:123",
"0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6"
);

Get current chain ID.

chain_id = sdk.chain_id() -> int
import { SDK } from 'agent0-sdk';
import type { ChainId } from 'agent0-sdk';
const chainId: ChainId = await sdk.chainId();

TypeScript Note: Method is async and uses camelCase naming.

Get registry addresses.

registries = sdk.registries() -> Dict[str, str]
import { SDK } from 'agent0-sdk';
import type { Address } from 'agent0-sdk';
const registries: Record = sdk.registries();

Switch to a different chain.

sdk.set_chain(chain_id: int) -> None
// Note: This method is not available in TypeScript SDK
// Create a new SDK instance with the desired chainId instead
const sdk = new SDK({
chainId: newChainId,
rpcUrl: newRpcUrl,
// ... other config
});

TypeScript Note: This method is not available in the TypeScript SDK. Create a new SDK instance with the desired chainId instead.

Check if SDK is in read-only mode.

is_readonly = sdk.isReadOnly -> bool
import { SDK } from 'agent0-sdk';
const isReadOnly: boolean = sdk.isReadOnly;

TypeScript Note: Property access (not a method), uses camelCase naming.