The /agent endpoint is a new feature of the Brian API designed to build chat-like apps or integrate chat features within existing apps.
The /agent endpoint has the capabilities of /transaction and /knowledge, which means that you can ask for both transactions (/transaction) and web3 info (/knowledge).
Have a look at /transation to understand the transaction flow from prompt request to execution.
Understanding /agent
The existing /transaction and /knowledge endpoints allow users to send a single prompt and get a response (either a transaction or textual information). However, these endpoints do not maintain chat history context â each prompt is handled independently, without awareness of previous requests.
The new /agent endpoint introduces session-based context, allowing developers to maintain a conversation history between the user and Brian within the same session. This means that previous messages and responses generated by Brian can be "remembered", for more dynamic and powerful interactions.
Why message history matters
Being able to have a message history significantly improves the capabilities of the Brian API by combining the functionalities of /transaction and /knowledge. With this, developers can build more powerful chat-like use cases, such as:
user: âi want to swap 100 usdc on Baseâ
brian: âok, what is the token to buy for the swap operation?â
user: âethâ
brian: generates the executable transaction for swapping 100 usdc to eth on base
or:
user: âwhen vitalik.eth expires on ethereum?â
brian: âoctober 20 2040âĻâ
user: âgot it, renew it for another 4 years on ethereumâ
brian: generates the executable transaction for renewing vitalik.eth for 4 years on ethereum
or users can ask both questions and transactions using the same /agent endpoint:
user: âwhat is uniswap v4 hooks?â
brian: âuniswap v4 is âĻâĻ..â
user: âok now bridge 1 eth from arbitrum to zk syncâ
brian: generates the executable transaction for bridging 1 eth from arbitrum to zk sync
Chain ID of the user. Can be specified here or in the messages parameter.
messages
array object[]
messages exchanged between the user and Brian (conversation history). It represents the chat history.
*mandatory parameters
If you don't pass the chainId in the body, the source chain will be deducted from the chat history, if available. Otherwise, it will throw an error.
Request Example
fetch('<https://api.brianknows.org/api/v0/agent>', { method:'POST', headers: {'X-Brian-Api-Key':'API_KEY','Content-Type':'application/json' }, body:JSON.stringify({ prompt:'ethereum', address:'vitalik.eth', messages: [ { sender:'user', content:'when vitalik.eth expires?' }, { sender:'brian', content:'The ENS domain vitalik.eth.eth (0xd8dA...6045) expiration is Thu Nov 29 2040 08:36:18 GMT+0100 (Central European Standard Time).' }, { sender:'user', content:'ok, renew it' }, { sender:'brian', content:'What is the chain you would like to perform this operation on?' } ] })})
Response example
{"result": [ {"solver":"Brian","action":"ENS Renewal","type":"write","data": {"description":"You are about to renew the ENS domain \\"vitalik.eth\\" for 12 months. The ENS \\"vitalik.eth\\" renewal cost for 12 months is 0.0021 ETH ($5.006591677699126).","steps": [ {"chainId":1,"blockNumber":20734848,"from":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","to":"0x253553366Da8546fC250F225fe3d25d0C782303b","value":"2347997171390886","data":"0xacf1a84100000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000001e133800000000000000000000000000000000000000000000000000000000000000007766974616c696b00000000000000000000000000000000000000000000000000","gasLimit":"200000" } ],"fromChainId":1,"fromAmount":"2347997171390886","fromToken": {"address":"0x0000000000000000000000000000000000000000","chainId":1,"symbol":"ETH","decimals":18,"name":"ETH","coinKey":"ETH","logoURI":"<https://raw.githubusercontent.com/trustwallet/assets/master/blockchains/ethereum/assets/0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2/logo.png>","priceUSD":"2345.51" },"fromAddress":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","toChainId":1,"finalEnsPriceString":"2347997171390886","toAmountMin":"2347997171390886","toToken": {"address":"0x0000000000000000000000000000000000000000","chainId":1,"symbol":"ETH","decimals":18,"name":"ETH","coinKey":"ETH","logoURI":"<https://raw.githubusercontent.com/trustwallet/assets/master/blockchains/ethereum/assets/0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2/logo.png>","priceUSD":"2345.51" },"toAddress":"0x253553366Da8546fC250F225fe3d25d0C782303b" }"extractedParams": {"action":"ensrenewal","address":"vitalik.eth","duration":"365","chain":"ethereum" },"conversationHistory": [ {"sender":"user","content":"when vitalik.eth expires?" }, {"sender":"brian","content":"The ENS domain vitalik.eth.eth (0xd8dA...6045) expiration is Thu Nov 29 2040 08:36:18 GMT+0100 (Central European Standard Time)." }, {"sender":"user","content":"ok, renew it" }, {"sender":"brian","content":"What is the chain you would like to perform this operation on?" }, {"sender":"user","content":"ethereum" }, {"sender":"brian","content":"You are about to renew the ENS domain \"vitalik.eth\" for 12 months. The ENS \"vitalik.eth\" renewal cost for 12 months is 0.0020 ETH ($5.010546811623313)." } ] } ]}
Integrating /agent
Body request
As shown in the example above, the body parameters are:
prompt: the last user prompt request.
address: the address (EOA/smart contract) requesting a transaction.
chainId: optional chainId. If you don't provide it, the source chain will be deducted from the chat history, if available.
messages: chat history between the user and Brian.
Handle body requests in the session
First message of the session: In the first request, the prompt field should be populated with the user's input, while the messages[] array should be empty. This marks the beginning of the session, so there are no prior messages to include.
Example of how the session request should be built on the first message:
{"prompt":"I want to swap 100 USDC on Base","address":"0xYourAddressOrEns","messages": []}
Subsequent messages in the session: From the second message onwards, the messages[] array should contain the conversation history between the user and Brian. In these cases, the prompt field will hold the new user request, while messages[] will include the previous exchanges between Brian and the user.
Example of how the session request should be built from the second message onwards:
{"prompt":"ETH","address":"0xYourAddressOrEns","messages": [ {"sender":"user","content":"I want to swap 100 USDC on Base" }, {"sender":"brian","content":"OK, what is the token for the swap operation?" } ]}
Storing messages
When integrating the /agent endpoint, developers have the flexibility to decide how to store the conversation history (messages[]) of a user session. Possible approaches include:
In-memory storage: Store the messages in temporary memory (e.g., a JavaScript array) and reset them when the session ends.
Database storage: Store messages in a database for long-term persistence and reset them when the session ends.
Key-value storage: Store messages in a key-value store (eg. Redis), which can handle quick access to active sessions and reset them when the session ends.
Other solutions: for example, when integrating /agent within an XMTP bot (try brian-agent.eth on Converse client), the messages are already stored as part of the XMTP chat history. In such a scenario, there's no need for additional storage, as the XMTP SDK can retrieve the messages at runtime.
For the moment, we suggest to often clean the message history sent to the API for better performance or at least after a couple of sucesfull response from the API.
Step-by-step procedure on how to create body requests during the session
This paragraph explains step-by-step how to construct body requests for API calls to /agent during a chat session from a developer's point of view.
It is fundamental to understand that the /agent endpoint returns:
200: only when a transaction or info request can be generated from the prompt + messages (chat history).
400: when a transaction or info request cannot be generated from the prompt + messages because certain parameters are missing. Consequently, the developer during the session must take the error message returned by Brian and add it to the messages array parameters for the next request
The /agent response is a 400 with the following error:
{"error":"Hey there! I see you're looking to make a swap. Could you let me know which token you'd like to buy? That way, I can help you out better. Thanks!","extractedParams": [ {"action":"swap","chain":"","token1":"usdc","token2":"","address":"","amount":"100" } ],"conversationHistory": [ {"sender":"user","content":"swap 100 usdc" } ]}
2) The user writes "to ETH".
The request should contain the new prompt along with the previous error message:
fetch('<https://api.brianknows.org/api/v0/agent>', { method:'POST', headers: {'X-Brian-Api-Key':'API_KEY','Content-Type':'application/json' }, body:JSON.stringify({ prompt:'to ETH', address:'limone.eth', messages: [ {"sender":"user","content":"I want to swap 100 usdc" }, {"sender":"brian","content":"Hey there! I see you're looking to make a swap. Could you let me know which token you'd like to buy? That way, I can help you out better. Thanks!" } ] })})
The /agent response is a 400 with the following error:
{"error":"What is the chain you would like to perform this operation on?","extractedParams": [ {"action":"swap","chain":"","token1":"usdc","token2":"eth","address":"","amount":"100" } ],"conversationHistory": [ {"sender":"user","content":"I want to swap 100 usdc" }, {"sender":"brian","content":"Hey there! I see you're looking to make a swap. Could you let me know which token you'd like to buy? That way, I can help you out better. Thanks!" }, {"sender":"user","content":"to ETH" }, {"sender":"brian","content":"What is the chain you would like to perform this operation on?" } ]}
3) The user writes "on Base".
The request should contain the new prompt along with the previous error messages:
fetch('<https://api.brianknows.org/api/v0/agent>', { method:'POST', headers: {'X-Brian-Api-Key':'API_KEY','Content-Type':'application/json' }, body:JSON.stringify({ prompt:'on Base', address:'limone.eth', messages: [ {"sender":"user","content":"I want to swap 100 usdc" }, {"sender":"brian","content":"Hey there! I see you're looking to make a swap. Could you let me know which token you'd like to buy? That way, I can help you out better. Thanks!" }, {"sender":"user","content":"to ETH" }, {"sender":"brian","content":"What is the chain you would like to perform this operation on?" } ] })})
At this point, the /agent response is a 200 providing the requested swap transaction:
{"result": [ {"solver":"Enso","action":"swap","type":"write","data": {"description":"You are about to swap 100.0 USDC ($100.1) for 0.040 ETH ($99.9) on Base using Enso solver. The address receiver is 0x1358155a15930f89eBc787a34Eb4ccfd9720bC62.","steps": [ {"chainId":8453,"blockNumber":21625399,"from":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","to":"0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913","gasLimit":"80000","data":"0x095ea7b300000000000000000000000080eba3855878739f4710233a8a19d89bdd2ffb8e0000000000000000000000000000000000000000000000000000000005f5e100","value":"0" }, {"chainId":8453,"blockNumber":21625399,"from":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","to":"0x80EbA3855878739F4710233A8a19d89Bdd2ffB8E","gasLimit":"345347", "data": "0xb35d7e73000000000000000000000000833589fcd6edb6e08f4c7c32d4f71b54bda029130000000000000000000000000000000000000000000000000000000005f5e100000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000001a00000000000000000000000000000000000000000000000000000000000000008a9059cbb010001ffffffffff833589fcd6edb6e08f4c7c32d4f71b54bda02913095ea7b3010203ffffffffff833589fcd6edb6e08f4c7c32d4f71b54bda0291319198595a30485ffffffff85111111125421ca6dc452d289314280a0f8842a659bd3b227018504ffffffff056675a323dedb77822fcf39eaa9d682f6abe72555ddcd52200105ffffffffff057e7d64d987cab6eed08a191c4c2459daf2f8ed0b19198595a30586ffffffffff1358155a15930f89ebc787a34eb4ccfd9720bc626e7a43a3010507ffffffff057e7d64d987cab6eed08a191c4c2459daf2f8ed0b241c59120105ffffffffffff7e7d64d987cab6eed08a191c4c2459daf2f8ed0b000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000140000000000000000000000000000000000000000000000000000000000000018000000000000000000000000000000000000000000000000000000000000001c000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000240000000000000000000000000000000000000000000000000000000000000084000000000000000000000000000000000000000000000000000000000000008600000000000000000000000000000000000000000000000000000000000000020000000000000000000000000129b480ad625bcd1a5c3a1c10d708114726fa467000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000186a00000000000000000000000000000000000000000000000000000000000000020000000000000000000000000111111125421ca6dc452d289314280a0f8842a6500000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000005f45a600000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000005c807ed2379000000000000000000000000e37e799d5077682fa0a244d46e5649f71457bd09000000000000000000000000833589fcd6edb6e08f4c7c32d4f71b54bda02913000000000000000000000000eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee000000000000000000000000e37e799d5077682fa0a244d46e5649f71457bd090000000000000000000000007d585b0e27bbb3d981b7757115ec11f47c4769940000000000000000000000000000000000000000000000000000000005f45a60000000000000000000000000000000000000000000000000008a43f6539a353e00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000120000000000000000000000000000000000000000000000000000000000000046e00000000000000000000000000000000000000000000045000043a0003f0512003c01acae3d0173a93d819efdc832c7c4f153b06833589fcd6edb6e08f4c7c32d4f71b54bda02913016452bbbe2900000000000000000000000000000000000000000000000000000000000000e0000000000000000000000000e37e799d5077682fa0a244d46e5649f71457bd090000000000000000000000000000000000000000000000000000000000000000000000000000000000000000e37e799d5077682fa0a244d46e5649f71457bd090000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000671e517cdef66c6c178087fd931514e99b04479e4d3d956c0002000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000833589fcd6edb6e08f4c7c32d4f71b54bda0291300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000005f45a6000000000000000000000000000000000000000000000000000000000000000c0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000180000000000000000000000000000000000000000000000000000625745d692b2400000000000000000000000000000000000000000000000000000000671e517c00000000000000000000000000000000000000000000000000000000000000e00000000000000000000000007d585b0e27bbb3d981b7757115ec11f47c47699400000000000000000000000000000000000000000000000000005af3107a40000000000000000086fb9011e2ff8b85700000000000000005784141ea082380000000000000001fa72a814595da483000000000000000000281967d8eade9f05f00000000000000000000000000000000000000000004a963b280a64b330bc48200000000000000004563918244f400000000000000000000006a94d74f430000000000000000000000000000671e51540000000000000000000044364c5bb000000000000000000000000000000000000000000000000000000000000000004128a9125558dbd81d9a74af9f04d915a7505757a7263f5f0f0ad350c2c24b117b612244009379d2ab449a8dd5bb815320719455db5b19a04408aae5bc0599534a1b0000000000000000000000000000000000000000000000000000000000000000a0f2fa6b66eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee0000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000723184cdcc4fbc061111111125421ca6dc452d289314280a0f8842a6500000000000000000000000000000000000097864b9100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000008a3f4713a61b82",
"value":"0" } ],"gasCostUSD":"","fromChainId":8453,"fromAmountUSD":"100.1201441730076","fromAmount":"100000000","fromToken": {"address":"0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913","chainId":8453,"symbol":"USDC","decimals":6,"name":"USD Coin","coinKey":"USDC","logoURI":"https://raw.githubusercontent.com/trustwallet/assets/master/blockchains/ethereum/assets/0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48/logo.png","priceUSD":"1.001201441730076" },"fromAddress":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","toChainId":8453,"toAmountUSD":"99.85106923258168","toAmount":"40116619887578922","toAmountMin":"40116619887578922","toToken": {"address":"0x0000000000000000000000000000000000000000","chainId":8453,"symbol":"ETH","decimals":18,"name":"ETH","coinKey":"ETH","logoURI":"https://raw.githubusercontent.com/trustwallet/assets/master/blockchains/ethereum/assets/0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2/logo.png","priceUSD":"2489.02" },"toAddress":"0x80EbA3855878739F4710233A8a19d89Bdd2ffB8E","receiver":"0x1358155a15930f89eBc787a34Eb4ccfd9720bC62","protocol": {"key":"enso","name":"enso","logoURI":"" } },"extractedParams": {"action":"swap","chain":"Base","token1":"usdc","token2":"eth","address":"","amount":"100" },"conversationHistory": [ {"sender":"user","content":"I want to swap 100 usdc" }, {"sender":"brian","content":"Hey there! I see you're looking to make a swap. Could you let me know which token you'd like to buy? That way, I can help you out better. Thanks!" }, {"sender":"user","content":"to ETH" }, {"sender":"brian","content":"What is the chain you would like to perform this operation on?" }, {"sender":"user","content":"on Base" }, {"sender":"brian","content":"You are about to swap 100.0 USDC ($100.1) for 0.040 ETH ($99.9) on Base using Enso solver. The address receiver is 0x1358155a15930f89eBc787a34Eb4ccfd9720bC62." } ] } ]}