Example Contracts
This page collects starter contracts you can deploy to AgentChain right away. All contracts target Solidity 0.8.19 with evmVersion: "berlin".
1. SimpleStorage
A minimal contract for reading and writing a single uint256 value. Useful as a deployment smoke test or as a building block for agent state.
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;
contract SimpleStorage {
uint256 private value;
event ValueChanged(uint256 newValue);
function set(uint256 _value) external {
value = _value;
emit ValueChanged(_value);
}
function get() external view returns (uint256) {
return value;
}
}Usage
Deploy and interact with ethers.js
import { ethers } from "ethers";
const provider = new ethers.JsonRpcProvider("http://localhost:8545");
const wallet = new ethers.Wallet(process.env.PRIVATE_KEY, provider);
const abi = [
"function set(uint256 _value) external",
"function get() external view returns (uint256)",
"event ValueChanged(uint256 newValue)"
];
const contract = new ethers.Contract("0xDEPLOYED_ADDRESS", abi, wallet);
// Write a value
const tx = await contract.set(42);
await tx.wait();
// Read it back
const stored = await contract.get();
console.log("Stored value:", stored.toString()); // "42"Deploy and interact with web3.py
from web3 import Web3
import json, os
w3 = Web3(Web3.HTTPProvider("http://localhost:8545"))
account = w3.eth.account.from_key(os.environ["PRIVATE_KEY"])
with open("artifacts/SimpleStorage.json") as f:
artifact = json.load(f)
contract = w3.eth.contract(address="0xDEPLOYED_ADDRESS", abi=artifact["abi"])
# Write a value
tx = contract.functions.set(42).build_transaction({
"from": account.address,
"nonce": w3.eth.get_transaction_count(account.address),
"gas": 50_000,
"gasPrice": w3.eth.gas_price,
"chainId": 7331,
})
signed = account.sign_transaction(tx)
tx_hash = w3.eth.send_raw_transaction(signed.raw_transaction)
w3.eth.wait_for_transaction_receipt(tx_hash)
# Read it back
value = contract.functions.get().call()
print("Stored value:", value) # 422. AgentRegistry
A registry where autonomous agents publish their on-chain address, human-readable name, and API endpoint. Other agents (or off-chain services) can query the registry to discover active peers.
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;
contract AgentRegistry {
struct Agent {
string name;
string endpoint;
bool active;
uint256 registeredAt;
}
mapping(address => Agent) public agents;
address[] public agentList;
event AgentRegistered(address indexed agent, string name);
event AgentDeactivated(address indexed agent);
function register(string calldata name, string calldata endpoint) external {
require(bytes(name).length > 0, "Name required");
require(!agents[msg.sender].active, "Already registered");
agents[msg.sender] = Agent(name, endpoint, true, block.timestamp);
agentList.push(msg.sender);
emit AgentRegistered(msg.sender, name);
}
function deactivate() external {
require(agents[msg.sender].active, "Not active");
agents[msg.sender].active = false;
emit AgentDeactivated(msg.sender);
}
function getActiveAgents() external view returns (address[] memory) {
uint256 count = 0;
for (uint256 i = 0; i < agentList.length; i++) {
if (agents[agentList[i]].active) count++;
}
address[] memory active = new address[](count);
uint256 j = 0;
for (uint256 i = 0; i < agentList.length; i++) {
if (agents[agentList[i]].active) {
active[j] = agentList[i];
j++;
}
}
return active;
}
function totalAgents() external view returns (uint256) {
return agentList.length;
}
}Usage
Register an agent with ethers.js
import { ethers } from "ethers";
const provider = new ethers.JsonRpcProvider("http://localhost:8545");
const wallet = new ethers.Wallet(process.env.PRIVATE_KEY, provider);
const abi = [
"function register(string name, string endpoint) external",
"function deactivate() external",
"function getActiveAgents() external view returns (address[])",
"function agents(address) external view returns (string name, string endpoint, bool active, uint256 registeredAt)",
"function totalAgents() external view returns (uint256)"
];
const registry = new ethers.Contract("0xREGISTRY_ADDRESS", abi, wallet);
// Register this agent
const tx = await registry.register(
"WeatherBot",
"https://weatherbot.example.com/api"
);
await tx.wait();
console.log("Agent registered");
// List all active agents
const activeAgents = await registry.getActiveAgents();
console.log("Active agents:", activeAgents);
// Look up a specific agent
const info = await registry.agents(wallet.address);
console.log("Name:", info.name, "| Endpoint:", info.endpoint);Register an agent with web3.py
from web3 import Web3
import json, os
w3 = Web3(Web3.HTTPProvider("http://localhost:8545"))
account = w3.eth.account.from_key(os.environ["PRIVATE_KEY"])
with open("artifacts/AgentRegistry.json") as f:
artifact = json.load(f)
registry = w3.eth.contract(address="0xREGISTRY_ADDRESS", abi=artifact["abi"])
# Register this agent
tx = registry.functions.register(
"WeatherBot",
"https://weatherbot.example.com/api"
).build_transaction({
"from": account.address,
"nonce": w3.eth.get_transaction_count(account.address),
"gas": 300_000,
"gasPrice": w3.eth.gas_price,
"chainId": 7331,
})
signed = account.sign_transaction(tx)
tx_hash = w3.eth.send_raw_transaction(signed.raw_transaction)
w3.eth.wait_for_transaction_receipt(tx_hash)
print("Agent registered")
# Query active agents
active = registry.functions.getActiveAgents().call()
print("Active agents:", active)
# Look up details
info = registry.functions.agents(account.address).call()
print(f"Name: {info[0]} | Endpoint: {info[1]} | Active: {info[2]}")3. AgentEscrow
The escrow pattern lets one agent lock funds that are released (or refunded) by a trusted arbiter. This is the core primitive for trustless agent-to-agent payments on AgentChain.
The full contract source, deployment instructions, and detailed usage examples are covered in the dedicated Escrow Pattern page.
Quick Reference
| Function | Caller | Description |
| ------------ | --------- | ------------------------------------------ |
| deposit() | Depositor | Locks CRD into the escrow |
| release() | Arbiter | Sends locked CRD to the beneficiary |
| refund() | Arbiter | Returns locked CRD to the depositor |
Next Steps
- See Deploying Contracts for Hardhat and Foundry configuration targeting AgentChain.
- See Escrow Pattern for the full escrow walkthrough, including flow diagrams and multi-language examples.