API Reference¶
- class redel.ReDel(
- *,
- root_engine: BaseEngine | None = None,
- delegate_engine: BaseEngine | None = None,
- root_system_prompt: str | None = DEFAULT_ROOT_PROMPT,
- root_kani_kwargs: dict | None = None,
- delegate_system_prompt: str | None = DEFAULT_DELEGATE_PROMPT,
- delegate_kani_kwargs: dict | None = None,
- delegation_scheme: type | None = DelegateWait,
- max_delegation_depth: int = 8,
- tool_configs: dict[type[_ToolBaseT], ToolConfig] | None = None,
- root_has_tools: bool = False,
- title: str | AutogenerateTitle | None = AUTOGENERATE_TITLE,
- log_dir: Path | None = None,
- clear_existing_log: bool = False,
- session_id: str | None = None,
This class represents a single session of a recursive multi-agent system.
It’s responsible for:
all delegation configuration options
all the spawned kani and their relations within the session
dispatching all events from the session
logging events
All arguments to the constructor are keyword arguments.
- Parameters:
root_engine – The engine to use for the root kani. Requires function calling. (default: gpt-4o) See Engines for a list of available engines and their capabilities.
delegate_engine – The engine to use for each delegate kani. Requires function calling. (default: gpt-4o) See Engines for a list of available engines and their capabilities.
root_system_prompt – The system prompt for the root kani. See
redel.kanisfor default.root_kani_kwargs – Additional keyword args to pass to
kani.Kani.delegate_system_prompt – The system prompt for the each delegate kani. See
redel.kanisfor default.delegate_kani_kwargs – Additional keyword args to pass to
kani.Kani.delegation_scheme – A class that each kani capable of delegation will use to provide the delegation tool. See
redel.delegationfor examples. Can beNoneto disable delegation.max_delegation_depth – The maximum delegation depth. Kanis created at this depth will not inherit from the
delegation_schemeclass.tool_configs – A mapping of tool mixin classes to their configurations (see
ToolConfig).root_has_tools – Whether the root kani should have access to the configured tools (default False).
title – The title of this session. Set to
redel.AUTOGENERATE_TITLEto automatically generate one (default), orNoneto disable title generation.log_dir – A path to a directory to save logs for this session. Defaults to
$REDEL_HOME/instances/{session_id}/(default~/.redel/instances/{session_id}).clear_existing_log – If the log directory has existing events, clear them before writing new events. Otherwise, append to existing events.
session_id – The ID of this session. Generally this should not be set manually; it is used for loading previous states.
- kanis: dict[str, BaseKani]¶
A mapping of ID to BaseKani of all the kanis in the system, regardless of tree depth.
- root_kani: ReDelKani | None¶
A reference to the root node. Guaranteed to exist after
query()orchat_in_terminal()is called; can beNonebefore then.
- get_config(**kwargs)[source]¶
Get a dictionary with arguments suitable for passing to a ReDel constructor to create a new instance with mostly the same configuration.
By default, the title, log_dir, and session_id will not be copied. Explicitly set these as keyword arguments if you want to copy them.
Pass keyword arguments to override existing configuration options (valid arguments are same as constructor).
- async chat_in_terminal()[source]¶
Chat with the defined system in the terminal. Prints function calls and root messages to the terminal.
- async query(query: str) AsyncIterable[BaseEvent][source]¶
Run one round with the given query.
Yields all loggable events from the app (i.e. no stream deltas) during the query. To get only messages from the root, filter for events.RootMessage.
- dispatch(event: BaseEvent)[source]¶
Dispatch an event to all listeners. Technically this just adds it to a queue and then an async background task dispatches it.
- add_listener(callback: Callable[[BaseEvent], Awaitable[Any]])[source]¶
Add a listener which is called for every event dispatched by the system. The listener must be an asynchronous function that takes in an event in a single argument.
- remove_listener(callback)[source]¶
Remove a listener added by
add_listener().
- class redel.ToolConfig[source]¶
A tool’s config should be a dictionary with any of the following keys:
- always_include: bool¶
If true, each delegate kani will always have access to this tool. Defaults to False.
- class redel.ToolBase(app: ReDel, kani: ReDelKani)[source]¶
This class is a base that all tool implementations should inherit from.
It provides an interface to the tools in the group to access the application it’s running in (for emitting events) and the kani it’s bound to (for access to the chat state), as well as common setup/teardown hooks.
- async setup()[source]¶
Called once per bound instance in an async context for each time this tool is bound to a new kani.
Override this method to perform any necessary async setup.
- class redel.DelegationBase(app: ReDel, kani: ReDelKani)[source]¶
This class is a base that all delegation implementations should inherit from.
It extends
ToolBasewith an interface for creating delegate kani instances.- async create_delegate_kani(instructions: str) ReDelKani[source]¶
Call this method to get a fresh
ReDelKaniinstance.This method will handle setting up the new kani in the computation graph as well as its tools, engine, and always included prompt based on the app configuration. It will not launch the kani with the given instructions – this must be done by the calling function.
The calling function is thus responsible for:
Setting the state of the calling kani
Providing the instructions to the delegate kani and calling its
full_round_streammethodBuffering the delegate’s response and returning it to the caller
Calling the appropriate cleanup methods of the delegate
- class redel.state.RunState(value)[source]¶
RunState.STOPPED: This kani is not currently running anything or waiting on a child.RunState.RUNNING: This kani is currently generating text.RunState.WAITING: This kani is waiting for the results of a sub-kani.RunState.ERRORED: This kani has run into a fatal error. Its internal state is indeterminate.
- class redel.state.AIFunctionState(
- *,
- name: str,
- desc: str,
- auto_retry: bool,
- auto_truncate: int | None,
- after: ChatRole,
- json_schema: dict,
Default Events¶
Most events contain an id attribute, which refers to the ID of the kani that the event refers to.
- class redel.BaseEvent(*, type: str, timestamp: float = <factory>)[source]¶
The base event that all other events should inherit from.
- class redel.events.KaniSpawn(*, type: ~typing.Literal['kani_spawn'] = 'kani_spawn', timestamp: float = <factory>, id: str, depth: int, parent: str | None, children: list[str], always_included_messages: list[~kani.models.ChatMessage], chat_history: list[~kani.models.ChatMessage], state: ~redel.state.RunState, name: str, engine_type: str, engine_repr: str = '', functions: list[~redel.state.AIFunctionState])[source]¶
A new kani was spawned. Includes the state of the kani. See
BaseKani.The ID can be the same as an existing ID, in which case this event should overwrite the previous state.
- class redel.events.KaniStateChange(
- *,
- type: ~typing.Literal['kani_state_change'] = 'kani_state_change',
- timestamp: float = <factory>,
- id: str,
- state: ~redel.state.RunState,
A kani’s run state changed.
This is primarily used for rendering the color of a node in the web interface.
- class redel.events.TokensUsed(
- *,
- type: ~typing.Literal['tokens_used'] = 'tokens_used',
- timestamp: float = <factory>,
- id: str,
- prompt_tokens: int,
- completion_tokens: int,
A kani just finished a request to the engine, which used this many tokens.
- class redel.events.KaniMessage(
- *,
- type: ~typing.Literal['kani_message'] = 'kani_message',
- timestamp: float = <factory>,
- id: str,
- msg: ~kani.models.ChatMessage,
A kani added a message to its chat history.
Visualizer¶
- class redel.server.VizServer(
- redel_proto: ReDel | None = None,
- /,
- *,
- save_dirs: Collection[Path] = (DEFAULT_LOG_DIR,),
- redel_factory: Callable[[], Awaitable[ReDel]] | None = None,
- Parameters:
redel_proto – If passed, interactive sessions will use the same configuration as the given prototype. Mutually exclusive with
redel_factory.save_dirs – A list of paths to scan for ReDel saves to make available to load. Defaults to
~/.redel/instances/.redel_factory – An asynchronous function that creates a new
ReDelinstance when called. If this is set,redel_protomust not be set.
Utilities¶
- redel.embeddings.get_embeddings(qs: list[str], model: str) list[EmbeddingResult][source]¶
Get the embeddings for the inputs, caching them.
- class redel.embeddings.EmbeddingResult(idx: int, embedding: numpy.ndarray)[source]¶
Bundled Tools¶
- class redel.tools.browsing.Browsing(*args, long_engine: BaseEngine | None = None, max_webpage_len: int | None = None, **kwargs)[source]¶
A tool that provides tools to search Google and visit webpages.
Renders webpages in Markdown and has basic support for reading PDFs.
- class redel.tools.email.Email(*args, email_from: str, smtp_host: str, smtp_pass: str, **kwargs)[source]¶
A toy tool to send emails via a given SMTP server.
- Parameters:
email_from – the email address to send email from
smtp_host – a string like mailserv.zhu.codes:465
smtp_pass – the password for the email account on the SMTP server
Bundled Delegation Schemes¶
- class redel.delegation.delegate_one.DelegateOne(app: ReDel, kani: ReDelKani)[source]¶
Delegate and immediately wait for the result of the sub-agent. Can be called in parallel to run multiple sub-agents in parallel.
- async delegate(instructions: ~typing.Annotated[str, <kani.ai_function.AIParam object at 0x764b44d87d30>])[source]¶
Ask a capable helper for help looking up a piece of information or performing an action. Do not simply repeat what the user said as instructions. You should use this to break up complex user queries into multiple simpler steps. NOTE: Helpers cannot see previous parts of your conversation.
- class redel.delegation.delegate_and_wait.DelegateWait(*args, **kwargs)[source]¶
Does not immediately wait for a sub-agent after delegating a task; agents must be explicitly waited by using
wait()instead. This lets models without the ability to perform parallel function calling spawn multiple agents in parallel by callingdelegate()multiple times before callingwait().- async delegate(instructions: ~typing.Annotated[str, <kani.ai_function.AIParam object at 0x764b44d87100>], who: ~typing.Annotated[str, <kani.ai_function.AIParam object at 0x764b44d86f20>] | None = None)[source]¶
Ask a capable helper for help looking up a piece of information or performing an action. Use wait() to get a helper’s result. You can call this multiple times to take multiple actions. You should break up user queries into multiple smaller queries if possible. Do not delegate the entire task you were given. If the user’s query can be resolved in parallel, call this multiple times then use wait(“all”).
Internals¶
- class redel.base_kani.BaseKani(
- *args,
- app: ReDel,
- parent: BaseKani = None,
- id: str = None,
- name: str = None,
- dispatch_creation: bool = True,
- **kwargs,
Base class for all kani in the application, regardless of recursive delegation.
Extends
kani.Kani. See the Kani documentation for more details on the internal chat state and LLM interface.- Parameters:
app – The
ReDelinstance this kani is a part of.parent – The parent of this kani, or
Noneif this is the root of a system.id – The internal ID of this kani. If not passed, generates a UUID.
name – The human-readable name of this kani. If not passed, uses the ID.
dispatch_creation – Whether to dispatch a
events.KaniSpawnevent automatically. If false, the caller is responsible for callingapp.on_kani_creation()to dispatch the event.
- state: RunState¶
The run state of this kani.
RunState.STOPPED: This kani is not currently running anything or waiting on a child.RunState.RUNNING: This kani is currently generating text.RunState.WAITING: This kani is waiting for the results of a sub-kani.RunState.ERRORED: This kani has run into a fatal error. Its internal state is indeterminate.
- depth: int¶
How deep in the computation tree this kani is. Will be 0 for the root node, 1 for children of the root, etc.
- children: dict[str, BaseKani]¶
A mapping of kani ids to kanis of all the immediate children of this kani.
- property last_user_message: ChatMessage | None¶
The most recent USER message in this kani’s chat history, if one exists.
- property last_assistant_message: ChatMessage | None¶
The most recent ASSISTANT message in this kani’s chat history, if one exists.
- run_state(state: RunState)[source]¶
Run the body of this statement with a different run state then set it back after.
- class redel.kanis.ReDelKani(*args, **kwargs)[source]¶
Base class for recursive delegation kanis. Extends
BaseKani.This class should not be constructed manually - it is tightly coupled to and managed by the application. You can get a reference to a kani powering an agent in a tool by using
ToolBase.kani.- Parameters:
app – The
ReDelinstance this kani is a part of.parent – The parent of this kani, or
Noneif this is the root of a system.id – The internal ID of this kani. If not passed, generates a UUID.
name – The human-readable name of this kani. If not passed, uses the ID.
dispatch_creation – Whether to dispatch a
events.KaniSpawnevent automatically. If false, the caller is responsible for callingapp.on_kani_creation()to dispatch the event.
- get_tool(cls: type[ToolBase]) ToolBase | None[source]¶
Get the tool from this kani’s list of tools, or None if this kani does not have the given tool class.
- async get_prompt(*args, **kwargs) list[ChatMessage][source]¶
Called each time before asking the LM engine for a completion to generate the chat prompt. Returns a list of messages such that the total token count in the messages is less than
(self.max_context_size - self.desired_response_tokens).Always includes the system prompt plus any always_included_messages at the start of the prompt.
You may override this to get more fine-grained control over what is exposed in the model’s memory at any given call.
- Parameters:
include_functions – Whether to account for the tokens that will be used for function definitions in the context length.
kwargs – Additional arguments that were passed to the model engine from
chat_round()orfull_round()(e.g. decoding arguments).