synwire_agent/middleware/
summarisation.rs1use synwire_core::BoxFuture;
4use synwire_core::agents::error::AgentError;
5use synwire_core::agents::middleware::{Middleware, MiddlewareInput, MiddlewareResult};
6
7#[derive(Debug, Clone)]
9pub struct SummarisationThresholds {
10 pub max_messages: Option<usize>,
12 pub max_tokens: Option<usize>,
14 pub max_context_utilisation: Option<f32>,
16}
17
18impl Default for SummarisationThresholds {
19 fn default() -> Self {
20 Self {
21 max_messages: Some(50),
22 max_tokens: Some(80_000),
23 max_context_utilisation: Some(0.8),
24 }
25 }
26}
27
28#[derive(Debug)]
30pub struct SummarisationMiddleware {
31 thresholds: SummarisationThresholds,
32}
33
34impl SummarisationMiddleware {
35 #[must_use]
37 pub const fn new(thresholds: SummarisationThresholds) -> Self {
38 Self { thresholds }
39 }
40}
41
42impl Default for SummarisationMiddleware {
43 fn default() -> Self {
44 Self::new(SummarisationThresholds::default())
45 }
46}
47
48impl Middleware for SummarisationMiddleware {
49 fn name(&self) -> &'static str {
50 "summarisation"
51 }
52
53 fn process(
54 &self,
55 input: MiddlewareInput,
56 ) -> BoxFuture<'_, Result<MiddlewareResult, AgentError>> {
57 Box::pin(async move {
58 let should_summarise = self
59 .thresholds
60 .max_messages
61 .is_some_and(|max| input.messages.len() > max);
62
63 if should_summarise {
64 tracing::debug!(
65 messages = input.messages.len(),
66 "Summarisation threshold exceeded"
67 );
68 let mut ctx = input.context.clone();
71 if let Some(obj) = ctx.as_object_mut() {
72 let _ =
73 obj.insert("summarisation_pending".to_string(), serde_json::json!(true));
74 }
75 return Ok(MiddlewareResult::Continue(MiddlewareInput {
76 messages: input.messages,
77 context: ctx,
78 }));
79 }
80
81 Ok(MiddlewareResult::Continue(input))
82 })
83 }
84}