Skip to main content

telos_agent/agent/prompt/
mod.rs

1//! Prompt system — modular, cache-aware construction of the system prompt.
2//!
3//! The prompt is assembled from independent sections rather than one hardcoded
4//! string. Static sections are rendered once and cached; dynamic sections are
5//! re-rendered every turn. This mirrors the modular prompt architecture:
6//! "prompt is assembled, not hardcoded".
7pub mod assembly;
8pub mod builtins;
9pub mod section;
10
11use std::path::PathBuf;
12use std::sync::Arc;
13
14pub use assembly::{PromptAssembly, PromptSectionStat, PromptStats};
15pub use builtins::{
16    CwdSection, DateSection, GitStatusSection, IdentitySection, McpSection, MemorySection,
17    PathSection, ProfileSection, SafetySection, ShellAwareToolUsageSection, SkillsSection,
18    TaskGuidanceSection, ToneStyleSection, ToolPromptsSection, ToolUsageSection, ToolsSection,
19};
20pub use section::{CacheHint, PromptBlock, PromptSection, PromptStability};
21
22use crate::config::TaskPath;
23use crate::tools::api::ToolRegistry;
24
25#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
26pub enum PromptProfile {
27    #[default]
28    Minimal,
29    Full,
30}
31
32/// Build a standard coding-agent prompt assembly.
33///
34/// This is the recommended default for software-engineering sessions. It
35/// includes the minimum shared guidance needed for software-engineering
36/// sessions: identity, safety rules, task path, the current date, and the
37/// working directory.
38///
39/// Optional sections such as skills, memory, profiles, MCP tools, and git
40/// status can be added afterwards by the caller.
41pub fn default_coding_assembly(
42    tools: Arc<ToolRegistry>,
43    cwd: PathBuf,
44    skills: Option<Arc<crate::knowledge::skills::SkillRegistry>>,
45    path: TaskPath,
46) -> PromptAssembly {
47    default_coding_assembly_for_profile(tools, cwd, skills, path, PromptProfile::Minimal)
48}
49
50pub fn default_coding_assembly_for_profile(
51    tools: Arc<ToolRegistry>,
52    cwd: PathBuf,
53    skills: Option<Arc<crate::knowledge::skills::SkillRegistry>>,
54    path: TaskPath,
55    profile: PromptProfile,
56) -> PromptAssembly {
57    let mut assembly = PromptAssembly::new();
58    assembly.add(IdentitySection::new(None));
59    assembly.add(SafetySection);
60    assembly.add(PathSection::new(path));
61    if profile == PromptProfile::Full {
62        assembly.add(ToneStyleSection);
63        assembly.add(TaskGuidanceSection);
64        assembly.add(ShellAwareToolUsageSection::new(Arc::clone(&tools)));
65        assembly.add(ToolsSection::new(Arc::clone(&tools)));
66        assembly.add(ToolPromptsSection::new(Arc::clone(&tools)));
67        if let Some(skills) = skills {
68            assembly.add(SkillsSection::new(skills));
69        }
70    }
71    assembly.add(DateSection);
72    assembly.add(CwdSection::new(cwd));
73    assembly
74}