How do I create and manage a custom agent?

Prev Next

Custom agents enable you to build specialist assistants tailored to your needs in LUSID. Beyond Candela’s built-in system agents, you can define an agent with:

  • A focused purpose

  • A curated set of tools

  • A prompt that reflects how your organisation works

This article explains how to create, update, and delete custom agents via the Candela API.

Defining the scope of your agent

Before creating the agent, plan the following:

Purpose: What is the agent for?

Define one clear purpose for your agent - Candela uses this to decide when to route a user to your agent. For example:

"Help users analyse equity holdings and retrieve valuation data."

"Allow operations staff to trigger and monitor reconciliation jobs."

"Answer questions about fixed income instruments held across all portfolios."

Tool set: Which tools does the agent need?

Agents with a tightly scoped set of tools perform better and produce more predictable results than agents with broad access. Decide on 5-10 focused tools your agent needs.

For example, an equity research agent might include the following tools:

  • ListEquities: Finds equity instruments

  • ListHoldingsInLusid: Finds equity instruments

  • RunBasicValuation: Values a portfolio

  • GetPortfolioProperties: Finds custom properties on portfolios

  • SearchKnowledgeBase: Answers questions about LUSID

To retrieve the available tools for your domain, ask Candela "What tools do you have access to?". See how to create a new tool.

Note

If you want your agent to be able to search LUSID documentation, you must explicitly include the SearchKnowledgeBase tool.

Prompt: What instructions should govern the agent’s behaviour?

The agent prompt defines how your agent behaves, what it assumes, and how it presents results. Prompts are the most important factor in the quality of an agent; follow these guidelines:

  • Provide sensible defaults: Pre-populate common parameter values so users do not have to specify everything every time.

    Default parameters:
    - Scope: Finbourne-Examples
    - Recipe: Finbourne-Examples/marketValue
    - If the user does not specify a date, use today's date.
  • Specify output format: Tell the agent how to present results.

    When returning results, use a markdown table with columns: Instrument, Units, Market Value, Currency.
    Exclude cash balances. Sort by Market Value descending.
  • Handle no-results: Tell the agent what to do when a tool returns empty data.

    If a tool returns no results, tell the user what you searched for and suggest alternative parameters they can try.

Combining all of the above, a prompt for an equity research agent might look like this:

You are an equity research assistant. Your goal is to help users analyse 
equity holdings and retrieve valuation data using LUSID.

Default parameters:
- Scope: acme
- Recipe: acme/marketValue
- If the user does not specify a date, use today's date.

When returning results:
- Use a markdown table with columns: Instrument, ISIN, Units, Market Value, Currency
- Sort by Market Value descending
- Exclude cash balances

If a tool returns no results, tell the user what you searched for and 
suggest alternative scopes or portfolios they can try.

Do not attempt to use tools outside your allowed set.

Creating the agent

All agents share the following fields:

Field

Description

code

A unique identifier for the agent within your domain.

name

A friendly title to show for agent transitions in conversations.

description

A specific, purpose-oriented description for the AI to use to decide when to route to the agent.

prompt

Instructions defining the agent’s behaviour. See prompt section above.

examplePrompts

A set of example prompts to show users in conversations with the agent.

toolNames

The tools this agent can call. See tool names section above. Note the name must match the tool names exactly.

isEnabled

Set to false to hide the agent from users without deleting it.

To create your agent, call the AddAgent API, specifying a scope for the agent in the URL and the required fields in the request body, for example:

curl -X POST 'https://<your-domain>.lusid.com/candela/api/agents/Finbourne-Examples'
  -H 'Accept: application/json' 
  -H 'Authorization: Bearer <your-API-access-token>'
  -H 'Content-Type: application/json-patch+json' 
  -d '{
  "code": "equity-research-agent",
  "name": "EquityResearchAgent",
  "description": "Agent for equity research queries - instrument lookups, holdings analysis, and equity valuation data",
  "prompt": "You are an equity research assistant. Help users find equity instruments, analyse holdings, and retrieve valuation data.\n\nDefault parameters:\n- If the user does not specify a scope, ask them which scope to use.\n\nWhen listing results, use markdown tables.\nIf a tool returns no results, tell the user and suggest what they can try next.",
  "examplePrompts": [
    "Show me all GBP equities",
    "What are the holdings in portfolio UK_Equity in scope Finbourne-Examples?",
    "Run a valuation on my equity portfolio"
  ],
  "toolNames": [
    "ListEquities",
    "ListHoldingsInLusid",
    "ListPortfolioScopes",
    "ListPortfolioCodesInScope",
    "RunBasicValuation",
    "GetPortfolioProperties",
    "SearchKnowledgeBase"
  ],
  "isEnabled": true
}'

Note

The scope you pass into the URL defines who can access the agent. You must assign a suitable access policy to users you want to allow to see and use the agent.

Checking an agent is available

To verify your agent is available, simply ask Candela “What agents are available?“

Alternatively, you can retrieve agents programmatically by calling the ListAgents API:

curl -X GET 'https://<your-domain>.lusid.com/candela/api/agents/Finbourne-Examples'
  -H 'Accept: application/json' 
  -H 'Authorization: Bearer <your-API-access-token>'

Updating an agent

To update an agent, use the same AddAgent API call with your new values. Each update creates a new version of the agent while retaining the previous versions.

Note

You can retrieve previous versions of an agent via the GetAgent API.

Deleting an agent

You have the option to:

  • Disable an agent by setting the isEnabled field to false when updating

  • Delete an agent outright by calling the DeleteAgent API, passing in the scope, code and version of the agent you need to delete