Changes for version 0.503 - 2026-10-01
- Distribution
- Langertha-Raider is the merge of the App-Raider distribution with the agent engine extracted from Langertha core. Langertha::Raider, Langertha::Raider::Result and the Langertha::Raid orchestration layer (Raid::Loop, Raid::Parallel, Raid::Sequential) ship here under their own names. Every App::Raider::* module is renamed to Langertha::Raider::*, with the CLI entry point App::Raider becoming Langertha::Raider::CLI; the raider and raider-hall executables keep their names. Requires Langertha 0.503 and Net::Async::MCP 0.004.
- The six App::Raider packages previously indexed on CPAN (App::Raider, App::Raider::FileTools, App::Raider::Plugin::Situation, App::Raider::Plugin::Trace, App::Raider::Skill, App::Raider::WebTools) ship as empty reserved-namespace stubs pointing to their Langertha::Raider replacements.
- Langertha::Raider calls only Langertha's public engine methods (async_request_f, async_loop, langfuse_timestamp, Langertha::Usage->from_raw) and Role::PluginHost's public plugin hooks (plugin_instances, plugin_args, plugin_pipeline_tool_call_f). Langertha::Raider::Result is self-contained.
- IO::Async::SSL is a requirement: every cloud engine and web_search speak https, and without it every request fails.
- Docker builds install from the Dist::Zilla build directory via cpm and the MetaCPAN resolver; no cpanfile.snapshot is shipped. GitHub and Docker release publishing runs from maint/release-after.pl.
- Standalone binary
- Standalone Linux binaries (x86_64, aarch64) are attached to each GitHub release by the release-binaries workflow; the build, verify and runtime-library scripts are in scripts/ and not shipped to CPAN.
- New raider --version: prints raider's and Langertha's version and exits 0.
- The binary's hall runs the binary directly instead of perl <binary>, which died with "Unrecognized character \x7F"; RAIDER_HALL_RAIDER_BIN still overrides it.
- perl_eval, perl_check and perl_cpanm run the perl on PATH inside the binary, whose $^X is no usable interpreter, and return a tool error saying so when there is none. The lib's perl-version marker records the version of the perl that uses the lib, not the packed one.
- CLI and REPL
- bin/raider is a thin wrapper around internal Langertha::Raider::CLI::* classes (Main, REPL, Runner, Commands, PromptBuilder, Output). raider exits 0 on success, 1 when the run failed, 2 on a usage error, 3 on a configuration error and 4 when a session is open in another raider.
- Machine output is versioned: --json, --msgpack and --yaml print one document with "version" (1), "status" (completed or failed) and the run's session; --FORMAT=N selects the version, an unknown one is a usage error. --json encodes UTF-8 once and keeps the live trace off unless --trace is given; the document's elapsed has millisecond resolution.
- New --stream-json, --stream-msgpack and --stream-yaml: run.started, run.state, tool.call, tool.result, message and run.finished events as the run happens, run.finished always last; tool.call and tool.result carry call and status. All six machine flags exclude each other, and so does -i; with any of them --trace goes to stderr and stdout carries only the machine output. Requires Data::MessagePack. raider -i reads piped input to its end.
- A one-shot raider cancels its run on the first SIGINT (Ctrl-C): it writes the cancelled document or run.finished, then dies of SIGINT (exit 130); a second SIGINT, or SIGTERM, interrupts at once, writing the "interrupted" document and dying of the same signal (130/143), also when the signal arrives during startup. Tool commands still running (bash, perl_eval, perl_cpanm) are ended first, and a tool call that ends with an error after a cancel is reported as cancelled.
- The REPL's first Ctrl-C cancels the running turn: tool commands are ended, the model request is abandoned, the session journal records the run as cancelled, and the REPL goes on; a second Ctrl-C within 2s quits, ending tool commands too.
- New Langertha::Raider->cancel stops a raid at its next safe point and is safe in a signal handler; the raid returns a Result of type cancelled (is_cancelled), and a tool call it cut off is reported as cancelled. Langertha::Raid::Parallel passes on a cancelled branch as the raid's result.
- New raider config explain [options] (the options may also come first) and REPL /config: every effective setting with its source (flag, .raider.yml layer, environment, default), the instructions source (-M, .raider.md, default), bare, where each pack comes from, and whether the Perl tools are on and why, and each mounted tool with its source and what it can do (read, write, network, code, message; tools outside the built-in table show as unknown). Information only, nothing is enforced.
- Explicit -m and -k beat model:/api_key: from .raider.yml, and the banner shows the model the engine is actually built with. When neither -m nor a table default is set (e.g. -e minimax), the engine's own default_model applies.
- -o with raider's own keys (perl, packs=a,b, skills=a,b, preferred_lib_target, engine) configures raider like .raider.yml and overrides it; only engine attributes reach the engine.
- raider reads the project config from .raider/config.yml (same keys as .raider.yml). When both files exist only .raider/config.yml is loaded, raider warns on start, and raider config explain names the file in use and the ignored one. /model and saved skills write to the file in use.
- raider reads ~/.raider/config.yml under the project config (default < home < project < command line). Project values replace home ones, skills and no_detect add up, detect: rules are replaced per pack. raider config explain names home values "home" and prints the home file. A broken home file stops raider (exit 3); raider never writes it.
- New raider config migrate [--dry-run] moves .raider.yml to .raider/config.yml and .raider.md to .raider/instructions.md: shows what it does first, writes atomically, keeps the legacy files as .bak, creates .raider/.gitignore, and leaves any api_key out of the shareable .raider/config.yml, reporting where it was. Refuses without writing when a target or backup already exists.
- ~/.raider/config.yml takes project_tools, a map from workspace selector ("*", a path glob, a workspace name) to tool names. raider config explain shows which selectors match the project, which tools they grant and which packs request them; a project file cannot grant. Information only: nothing is mounted from it yet, and workspace names never match yet.
- raider reads the project instructions from .raider/instructions.md, else .raider.md. When both exist only .raider/instructions.md is used, raider warns on start, and raider config explain names the ignored file under instructions:. /prompt writes the file in use (.raider.md when there is none).
- .raider.yml has one reader and writer, Langertha::Raider::Config (internal). Top-level keys apply next to default: and engine sections, so /model or a skills: hash no longer drops packs, perl or engine options; skills: merge across sections and with --claude / --openai / --skills, which all persist; engine: picks the engine. A file that does not parse, or a mapping under one of raider's own keys (packs:, perl:, engine:, ...), stops raider with a one-line error (line, column and reason for a parse error) instead of being ignored. Raider-only keys never reach the engine constructor.
- -M now replaces only the instructions (default persona and .raider.md); skills, packs (configured, flagged or detected) and the tool description still apply. Anyone who used -M to drop everything else needs --bare. /reload and /pack keep a -M mission, and /reload, the banner and the generated raider skill name it as the persona.
- New --bare: isolated context without .raider.md, skills, pack detection, packs: or default packs; --pack NAME and /pack NAME still switch packs on. -M TEXT --bare gives TEXT plus the tool description.
- New --pack NAME for one-shot pack activation.
- REPL: a line !CMD runs CMD with $SHELL -c in the root on the terminal and sends nothing to the model; ?CMD runs it with its output shown and captured, then sends the command, its exit status and its output (head and tail past 20000 characters) to the model as the next prompt, recorded in the session. Ctrl-C ends the command, not raider; a ?CMD ended by Ctrl-C sends nothing. A line that is only ! or ? is a prompt.
- raider --help lists --trace next to --no-trace.
- New raider provider inspect HOST[:PORT]|https://HOST fetches /.well-known/langertha.json (https only, 1 MiB, 10 s, up to 3 same-origin redirects, no credentials sent; internal addresses are refused unless --allow-internal, cloud metadata never), validates it with Langertha::Manifest and shows provider, issuer, endpoints, auth and models, with warnings for unknown dialects, auth types and capabilities. --json, --msgpack and --yaml give one versioned document. Requires Langertha::Manifest from Langertha core.
- New raider --provider HOST[:PORT] runs one invocation on the endpoint a provider manifest declares, mapped to the matching Langertha engine; nothing is stored. -m picks the model (required when the manifest lists several). The key comes only from -k or -o api_key=, never from *_API_KEY in the environment or .raider.yml. The endpoint must be https on the manifest's origin; internal addresses need --allow-internal, as for provider inspect. The engine connects to the endpoint address raider checked (Langertha connect_address) instead of looking the name up again; TLS still verifies the host name. Not combinable with -e, -o engine= or -o url=. The REPL banner shows the -k key as set without printing it.
- Saving skills (--skills, --claude, the /skill writers) no longer writes an empty skills: ~ into an existing default: section of the project config.
- Packs
- Packs are also found in <project>/.raider/packs/<name>/ and ~/.raider/packs/<name>/ (same layout as the shipped packs); for the same name the project beats home, and home beats the shipped pack. A pack directory with an unreadable pack.yml is skipped and reported in raider config explain and /packs instead of stopping the start; one without a SKILL.md loads. The never-used pack keys mcp, add_allowed_commands and engine_options are ignored.
- Packs can activate by workspace detection: declarative must / may / must_not rules on files and their content, from a pack's pack.yml or detect: in .raider.yml; switched off with no_detect:, detect: false, --no-pack NAME or --no-detect. raider config explain and /packs show each pack's source (flag, config, default, detected) and the rule clause that matched; /reload detects packs again.
- New bundled perl pack: in a Perl workspace (cpanfile, dist.ini, Makefile.PL or lib/**/*.pm) the perl_eval / perl_check / perl_cpanm tools are on without --perl; perl: false keeps them off. The bundled git-guru pack drops a pack.yml key the loader never read.
- Tools
- The tool description in the system prompt and the exported how-to-use document (/skill, /skill-claude) are generated from the tool servers mounted for the run (name and parameters from each tool's input schema, optional parameters in brackets), so the Perl and Hall tools are described when mounted and only then. -M and --bare keep it. Switching the perl pack on or off with /pack (or /reload) mounts or unmounts the perl_* tools; the exported Markdown no longer contains POD markup.
- MCP servers are named raider-files, raider-web, raider-perl and raider-hall; the Claude skill export is named raider (.claude/skills/raider/SKILL.md) and points out a leftover app-raider skill.
- Perl tools: --perl unlocks perl_eval / perl_check / perl_cpanm with a private local::lib per raider and auto-recovery on missing modules. perl_eval and perl_check run the current perl in the working root with the private lib; perl_check says BEGIN/use run; real errors are no longer reported as "timeout"; perl_cpanm rejects targets outside the root, uses the local::lib correctly and records only successful installs. The tools kill the child process when it times out, and every timeout (including the retry after an auto-install and cpanm itself) comes back as a result instead of an exception; new install_timeout option. A relative preferred_lib_target resolves against the working root for PERL5LIB and cpanm alike.
- Filesystem confinement rejects symlink escapes for read and write operations.
- A raid, and the web_fetch / web_search tools, fail at once with the module's name when IO::Async::Internals::Connector, or for https IO::Async::SSL (IO::Socket::SSL, Net::SSLeay, libssl), does not load, instead of the first request failing and every later one to that host hanging (a Net::Async::HTTP 0.50 connection-slot leak). web_fetch checks each redirect target too, so an http to https redirect without IO::Async::SSL is a tool error and does not block later fetches from that host. WebTools sync wrappers await IO::Async futures through the loop.
- Plugin self-tools are offered to the model once per raid. A tool name offered by two tool sources (engine mcp_servers, inline MCP, catalog MCPs, self-tools) is sent once: the first source wins and a warning names both. A raider_-prefixed name an MCP source registered is called on that source instead of failing as "Unknown self-tool".
- A tool call whose arguments do not decode (on a reply that did not hit its token limit) is answered with an "arguments are not valid JSON" error result the model can retry, instead of running the tool on {}.
- Raid engine
- Inline MCP tools and raider_wait run on the engine's event loop, so an engine on its own loop no longer hangs a raid. A raider whose engines (engine, compression_engine, engine_catalog, embedding_engine) sit on different event loops fails at the start of raid_f and respond_f, naming the engine, instead of hanging.
- The trace and Langfuse count tokens from Gemini, Ollama and AKI native responses too. Usage follows Langertha's reading: input_tokens wins over prompt_tokens when a response has both, and a count missing from a usage block goes to Langfuse as 0 instead of null.
- Raid tool-loop replies are read via Langertha::Role::Tools tool_loop_response, so a 200 body carrying an error ends the raid loudly instead of silently with "". Gemini thoughts and truncated tool calls are dropped as in core, and an unknown tool returns an error result instead of aborting the raid. compress_history_f reads the summary the same way and croaks instead of producing an empty one.
- Raider compresses its context inside a single long raid, dropping the oldest tool exchanges first, not only between raids. The mission and system prompt carrying activated skill content is never compacted.
- Session-history embeddings no longer block the event loop: each message is embedded in the background through simple_embedding_f, a failed embedding is logged and skipped, and the search tool ranks only what is embedded so far (falling back to text match if the query itself cannot be embedded). no_session_embeddings is no longer needed as a deadlock workaround. An embedding engine without simple_embedding_f gets no embeddings.
- session_history keeps tool_call and tool_result turns as structured blocks, so history replayed into a later raid (and the embedding text derived from it) no longer stringifies or drops them. New clear_session_history empties session_history and its embeddings together.
- The session history renderer (session_history tool, history query) no longer drops or blanks the tool results Langertha sends natively: a Responses function_call_output whose output is an input_text / input_image part array, a Gemini functionResponse with inlineData parts, and an Anthropic tool_result with image blocks keep their text and show each image as [image], never as base64. A Gemini functionResponse carrying the tool's structured content is shown whole, as JSON, instead of as an empty "tool_result:". An Anthropic text document shows its text (and title) instead of a bare <document>, a PDF document shows as [document], and a search_result keeps its title and source URL next to its text. A custom content document (source type content) shows its text chunks instead of a bare [document], and a document's context field is kept on its own [context] line. A tool-result PDF (Responses input_file, Gemini functionResponse inlineData) shows as [document] name.pdf or [document] application/pdf instead of <input_file> or <block>; its base64 payload is never shown.
- A raid paused by an interactive self-tool (raider_ask_user etc.) in the middle of a parallel-tool batch no longer re-runs the calls that completed before it or drops the self-tools queued after it: respond_f resumes with only the calls after the pausing one, so side effects fire once and every tool_use gets exactly one tool_result (strict providers such as Anthropic rejected the duplicates with a 400).
- Tool calls resumed after raider_ask_user or raider_pause go through the same dispatch as any other call: they run plugin_before_tool_call, so they get their tool.call event and plugin gates apply to them.
- The answer to a paused raider_ask_user or raider_pause call and the result of raider_wait go through plugin_after_tool_call, so every tool.call event gets its tool.result. A cancelled raider_wait gets a cancelled tool result like a cut-off MCP call.
- A plugin_before_llm_call that returns a fresh conversation also updates what a paused raid resumes with, so respond_f keeps every assistant and tool_result message from before the pause.
- Langertha::Raider::Result is always true in boolean context, so `if (my $r = $raider->raid(...))` no longer skips question, pause and abort results with empty text. Stringification is unchanged.
- Langertha::Raider checks each tool call's arguments against the tool's inputSchema before running it: a missing required key or a top-level property of the wrong type gets an error result the model can correct, and the tool does not run. The check is lenient: numeric strings, 0/1 booleans and null for an optional property pass. raider_ask_user called without question returns that error instead of dying with a Result type-constraint error.
- Sessions
- Every run is recorded in a session journal, .raider/sessions/<id>.jsonl in the project: the input, every tool call with its whole result, the answer and how the run ended, also when it failed or was interrupted. .raider/.gitignore keeps journals out of git (also written when .raider/lib is created); --no-session switches recording off. A journal that cannot be written mid-run is a warning; the run goes on.
- New raider session list, session show ID [--json], session resume ID, session fork ID and session rm ID (refused while another raider has it open), and --session ID / --continue for one-shot and REPL: the conversation is replayed, nothing recorded is run again, and runs without an end or tool calls without a result are reported. Session ids can be shortened to a unique start or their last four hex digits. /clear in the REPL is recorded and honoured on resume.
- Hall
- raider hall start/spawn/attach/logs/kill no longer treat options as positional arguments (e.g. `start --daemon DIR` ignored DIR). spawn/attach/logs/kill take an optional hall DIR as first argument without it leaking into NAME, MISSION or ID; a name that is a plain directory stays a name. start/stop/status/ps/install fail with "Not a directory" when DIR is not a directory instead of using the current directory.
- Hall raiders run with --stream-json: stdout goes to a file per run, stderr to the slot log, and raider.done carries status and response or error from run.finished; a raider killed before its result is a clear failure. Only the newest 20 events files per slot are kept (logs.keep_events in .raider-hall.yml, 0 keeps all).
- raider hall attach ID prints the run's --stream-json events until the raider exits; raider hall spawn --attach spawns and then attaches (the run ID line goes to stderr, a queued mission is not attached). The spawn reply names events_path, and carries queue_depth for a busy slot.
- The hall ends each run in the slot log with one "[hall] raider ID STATUS: TEXT" line and marks each run's start, so raider hall logs ID shows the answer or error and only that run's part, also after the run has ended; logs --follow prints new output until the raider exits. A slot log over logs.max_log_size (default 1 MiB, 0 off) moves to SLOT.log.1 when the slot's next run starts. Run IDs stay unique (SLOT-TIME.2, .3, ...).
- A plain hall raider name (bjorn) runs its missions in parallel and each run is tracked and reported on its own; numbered names (1bjorn) stay singletons with a queue that survives restarts. Missions a previous hall left waiting run first after a start, and a new mission never overtakes them.
- Hall runs keep their conversation in a session journal under the hall root: a Telegram chat (or topic), a cron job, an ACP session and a numbered slot each continue their own session, a plain-name run gets a fresh one. raider.done, ps and attach name the session; a run whose session is in use outside the hall fails at once with a raider.done saying so. A mission for a binding that is already running waits in that binding's queue, kept across hall restarts. raider hall session reset BINDING and Telegram /new start a binding over in a new session (journals are kept); ACP bindings are forgotten on hall start, and so are the bindings and waiting missions of cron jobs no longer configured.
- A hall cron job with coalesce: true drops an occurrence (cron.coalesced) while its previous run is still running or waiting. Cron scheduling does not block the IO::Async loop.
- A hall raider's persona: X in .raider-hall.yml starts that raider with the pack X as well. The never-used raider keys mcp and isolated are gone (raider hall add-raider --isolated is removed; old configs get a one-time note in the slot log). preferred_lib_target in .raider-hall.yml is read (default .raider/lib): each hall raider installs modules there and gets <target>/lib/perl5 on PERL5LIB.
- Hall raiders without an engine: leave the choice to raider (.raider.yml, then API-key autodetection) instead of anthropic; raider hall init and add-raider write engine: only when --engine is given.
- Hall raiders get telegram_reply, hall_status and hall_spawn tools (keyed on $RAIDER_HALL_SOCKET). Docker-aware systemd install: inside a container the unit is written to .raider-hall/systemd/<name>.service with a cp one-liner printed; --docker uses docker run and publishes the ACP port.
- Hall Telegram access is fail-closed: an empty or missing allowlist rejects every message, allowlist holds sender user ids (from.id), and group chats must also be listed in the new allowed_chats. Rejections emit telegram.rejected; startup warns about empty allowlists and chat ids found in allowlist. telegram.in events carry the sender's first_name and username, also in group chats.
- Telegram replies: a raider spawned for a Telegram message gets its bot and chat id (RAIDER_HALL_TELEGRAM_BOT/_CHAT_ID), and telegram_reply is bound to that chat (and forum topic), needing only text. The Telegram bots stop polling with a warning and a telegram.poll_error event naming the module, and their replies return an error, instead of hanging on the Bot API when a connect module does not load.
- Hall fixes: singleton queue replay, --pack propagation, Telegram future retention, MCP tool result handling, a mission passed as a single argv instead of split on whitespace, no double-reaping of child processes, and the shutdown grace-period timer now fires.
- ACP
- Hall ACP speaks JSON-RPC 2.0 line-framed over TCP (initialize / session/new / session/prompt / session/cancel); configure via acp: { port, host } in .raider-hall.yml or --acp-port N on raider hall start. raider acp ping|prompt|connect HOST:PORT drives any ACP-conforming agent from the same binary.
- A prompt that has to wait is answered when its run ends (end_turn or cancelled) instead of at once, also when the hall had to start that run without its session (hall.session_error names the run); session/cancel ends waiting prompts as cancelled and cancels the running hall raider with SIGINT, so its run ends as cancelled. If it does not end, the hall escalates to SIGTERM, then SIGKILL, each after cancel_grace in .raider-hall.yml (default 5 seconds, 0 never escalates). raider hall kill still stops it with SIGTERM.
- A failed raider run ends session/prompt as a JSON-RPC error (-32000) instead of streaming the error text as an agent_message_chunk with stopReason end_turn; a killed raider is forwarded as that failure rather than raw log text.
- Documentation
- README describes the current CLI, config and Hall/ACP behavior, the standalone binary and a Roadmap for planned features. examples/multi-raider-hall/ walks through a minimal multi-raider village wired for cron and ACP.
- perldoc raider documents every option, the tool set and the environment variables raider reads (API keys, web-search keys, RAIDER_PACK_DIRS, RAIDER_HALL_SOCKET, ...); raider-hall has a manual page of its own; Langertha::Raider::Hall documents RAIDER_HALL_RAIDER_BIN, RAIDER_HALL_ACP_PORT, RAIDER_HALL_ACP_HOST and the environment it gives its raiders; Langertha::Raider::Packs documents the pack.yml keys; Langertha::Raider documents run_f, its raid plugin hooks, automatic context management and the session_history archive. The Hall parts and the raider acp dispatcher are marked internal. engine: is documented as optional for hall raiders, and the hall MCP adapter (.raider-hall.mcp) as not implemented. Broken POD links and empty sections are fixed.
- Tests
- Test suite for packs, Perl tools, Hall, ACP server and client, plus an opt-in live task suite (t/live, RAIDER_LIVE_TASKS=1) that drives bin/raider against a fresh workspace and isolated home and checks the result and session journal; a provider error fails the run. t/42 runs a real OpenAI API session, gated on OPENAI_API_KEY.
Documentation
Autonomous CLI agent with filesystem and bash access
Raider Hall daemon CLI
Modules
Reserved namespace — the CLI entry point moved to Langertha::Raider::CLI
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Reserved namespace — the filesystem MCP tools moved to Langertha::Raider::FileTools
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Reserved namespace — the Situation plugin moved to Langertha::Raider::Plugin::Situation
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Reserved namespace — the Trace plugin moved to Langertha::Raider::Plugin::Trace
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Reserved namespace — the usage-doc generator moved to Langertha::Raider::Skill
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Reserved namespace — the web MCP tools moved to Langertha::Raider::WebTools
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Base class for orchestrating Runnable steps
Looping Raid orchestrator
Parallel Raid orchestrator with branched context isolation
Sequential Raid orchestrator
Autonomous agent with conversation history and MCP tools
Internal dispatcher of the raider acp subcommands (client side)
Minimal synchronous ACP client over TCP
Internal application service that builds and runs a raider for a workspace
Internal approval of one exact tool call, bound to session, run, tool, arguments and policy revision
Internal check whether raider runs as the standalone binary
Autonomous CLI agent that can browse directories, edit files, and run bash commands
Internal slash commands of the raider REPL
Internal writer of the raider CLI's machine output (JSON, MessagePack, YAML)
Internal command-line entry point behind bin/raider
Internal terminal renderer of the raider CLI
Internal prompt-builder sub-agent of the raider CLI (/prompt)
Internal provider commands of the raider CLI: inspect a manifest, activate it for --provider
Internal interactive loop of the raider CLI
Internal runner of one raider CLI prompt, for a human or a machine
Internal session subcommands of the raider CLI: list, show, resume, fork, rm
Internal resolver and writer for the project config file
Internal converter of the legacy project files to .raider/ (raider config migrate)
Internal check that Net::Async::HTTP can open a connection to a URL
Internal evaluator for declarative pack detection rules
Internal choice of engine, model and API key for a raider
MCP::Server factory with local filesystem tools (list/read/write/edit)
Hall daemon — spawns and manages raider processes
POD ERRORS
Hey! The above document had some coding errors, which are explained below:
Around line 3:
Non-ASCII character seen before =encoding in '—'. Assuming CP1252
Internal ACP (Agent Client Protocol) adapter that exposes the hall over TCP
Internal stream shim feeding hall output into an ACP callback
Internal dispatcher of the raider hall subcommands
Internal non-blocking cron scheduler for the raider hall
Internal MCP tool adapter exposing the raider hall
Internal control-socket command handlers for the raider hall
Internal record of a raider process spawned by the hall
Internal multi-bot Telegram long-poll adapter for the raider hall
MCP::Server factory with hall-side tools (telegram_reply, hall_status, hall_spawn)
Internal resolver of the home and project .raider directories
Internal resolver of the project instructions file
Pack discovery, loading, and management for raider personas and power bundles
Set of loaded raider packs with per-session enable state
A single raider pack - persona or power bundle
MCP::Server factory with Perl evaluation, syntax check, and module install
Report a raid's tool calls and results as machine-output events
Inject situational context (current time, timezone, host, user) at the start of the first raid
Live ANSI-colored progress output for a running Langertha::Raider raid
Internal activation of a provider manifest's endpoint as the engine of one raider run
Internal classification of what changed between an accepted and a newly fetched provider manifest
Internal bounded fetch of a provider manifest from /.well-known/langertha.json
Result object for Raider and Raid execution
Internal writer of one session journal, holding its lock
Internal read-only view of one session journal
Internal store of the session journals of one scope
Generate a "how to use raider" documentation file from a live Langertha::Raider::CLI configuration
Internal check of a tool call's arguments against the tool's inputSchema
Internal static table of what each built-in tool can do (effect classes)
MCP::Server factory with web search and fetch tools (Net::Async::WebSearch + Net::Async::HTTP)