Packages
Secure BEAM sandbox runtime for LLM code mode and MCP aggregation. Run concurrent LLM/tool clients safely while agents orchestrate approved tools, call upstream MCP/OpenAPI servers, and transform data.
Current section
Files
Jump to
Current section
Files
lib/ptc_runner/sub_agent/namespace.ex
defmodule PtcRunner.SubAgent.Namespace do
@moduledoc """
Renders namespaces for the USER message (REPL with Prelude model).
Coordinates rendering of:
- tool/ : Available tools (from agent config, stable)
- data/ : Input data (from agent config, stable)
- user/ : LLM definitions (prelude, grows each turn)
"""
alias PtcRunner.SubAgent.Namespace.{Data, Tool, User}
@doc """
Render all namespaces as a single string.
## Config keys
- `tools` - Map of tool name to tool struct (for tool/ namespace)
- `data` - Map of input data (for data/ namespace)
- `field_descriptions` - Map of field names to description strings (for data/)
- `context_signature` - Parsed signature for type information (for data/)
- `memory` - Map of LLM definitions (for user/ namespace)
- `has_println` - Boolean, controls sample display in user/ namespace
Always includes the tools section (showing available tools or "No tools available").
## Examples
iex> PtcRunner.SubAgent.Namespace.render(%{})
";; No tools available"
iex> tool = %PtcRunner.Tool{name: "search", signature: "(query :string) -> :string"}
iex> PtcRunner.SubAgent.Namespace.render(%{tools: %{"search" => tool}})
";; === tools ===\\ntool/search(query string) -> string"
iex> PtcRunner.SubAgent.Namespace.render(%{data: %{count: 42}})
";; No tools available\\n\\n;; === data/ ===\\ndata/count ; integer, sample: 42"
iex> PtcRunner.SubAgent.Namespace.render(%{memory: %{total: 100}, has_println: false})
";; No tools available\\n\\n;; === user/ (your prelude) ===\\ntotal ; = integer, sample: 100"
"""
@spec render(map()) :: String.t()
def render(config) do
sample_opts = [
sample_limit: config[:sample_limit] || 3,
sample_printable_limit: config[:sample_printable_limit] || 80
]
data_opts =
[
field_descriptions: config[:field_descriptions],
context_signature: config[:context_signature]
] ++ sample_opts
user_opts = [has_println: config[:has_println] || false] ++ sample_opts
[
Tool.render(config[:tools] || %{}),
Data.render(config[:data] || %{}, data_opts),
User.render(config[:memory] || %{}, user_opts)
]
|> Enum.reject(&is_nil/1)
|> case do
[] -> nil
sections -> Enum.join(sections, "\n\n")
end
end
end