wm-tools 9.1.7

Curated tool implementations for the WhiteMagic MCP server.
Documentation
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
//! Logographic Kernel Execution Pipeline (LKEP) — Proposal 3
//!
//! Ultra-low-latency logographic expression parsing and kernel dispatch for local LLMs.
//! Bridges single-token Sanskrit-Chinese ideograms (`忆`, `索`, `录`, `存`, `读`, `回`,
//! `续`, `契`, `记`, `心`, `律`, `业`, `具`) and arguments (`问`, `数`, `文`, `标`, `界`, `号`)
//! directly into WhiteMagic dispatch and memory kernels without JSON framing overhead.

#![forbid(unsafe_code)]

use async_trait::async_trait;
use serde_json::{Map, Value, json};
use thiserror::Error;
use wm_core::{Context, EffectRow, Gana, Tool, ToolStats};

/// Errors encountered during Logographic Kernel parsing or execution.
#[derive(Debug, Error, PartialEq, Eq)]
pub enum LkepError {
    #[error("Empty logographic expression")]
    EmptyExpression,

    #[error("Unknown route or glyph ideogram: {0}")]
    UnknownRoute(String),

    #[error("Syntax error in logographic expression: {0}")]
    SyntaxError(String),
}

/// Fast route resolver: maps ASCII glyphs ("Ms"), single-character ideograms ("忆"),
/// or canonical route strings ("memory.search") to the canonical route string.
#[must_use]
pub fn resolve_route(code: &str) -> Option<&'static str> {
    let trimmed = code.trim();
    // 1. Check if it's a known code or ideogram in GLYPH_ROUTES
    for &(canonical, route_code) in crate::GLYPH_ROUTES {
        if route_code == trimmed {
            return Some(canonical);
        }
    }
    // 2. Check if it's already a canonical route name
    crate::GLYPH_ROUTES
        .iter()
        .find(|&&(canonical, _)| canonical == trimmed)
        .map(|&(canonical, _)| canonical)
}

/// Fast arg key resolver: maps ASCII arg codes ("q"), single-character ideograms ("问"),
/// or canonical arg names ("query") to the canonical arg name.
#[must_use]
pub fn resolve_arg(code: &str) -> Option<&'static str> {
    let trimmed = code.trim();
    // 1. Check if it's a known code or ideogram in GLYPH_ARGS
    for &(canonical, arg_code) in crate::GLYPH_ARGS {
        if arg_code == trimmed {
            return Some(canonical);
        }
    }
    // 2. Check if it's already a canonical arg name
    crate::GLYPH_ARGS
        .iter()
        .find(|&&(canonical, _)| canonical == trimmed)
        .map(|&(canonical, _)| canonical)
}

/// Returns the primary default argument for a canonical route, used for positional shorthand.
#[must_use]
pub fn primary_arg_for_route(canonical_route: &str) -> &'static str {
    match canonical_route {
        "memory.search" | "memory.hybrid_recall" | "session.continuity" => "query",
        "memory.create" | "session.record" => "content",
        "memory.read" => "id",
        "session.checkpoint" => "title",
        _ => "query",
    }
}

/// Parse a raw scalar or JSON literal string into a `serde_json::Value`.
fn parse_scalar_or_json(raw: &str) -> Value {
    let trimmed = raw.trim();
    if trimmed.is_empty() {
        return Value::Null;
    }

    // Try standard JSON parsing first for numbers, booleans, arrays, objects, and quoted strings
    if let Ok(v) = serde_json::from_str::<Value>(trimmed) {
        return v;
    }

    // Handle single-quoted strings: 'foo' -> "foo"
    if trimmed.len() >= 2 && trimmed.starts_with('\'') && trimmed.ends_with('\'') {
        return Value::String(trimmed[1..trimmed.len() - 1].to_string());
    }

    // Bare word fallback as a string
    Value::String(trimmed.to_string())
}

/// Parse a logographic expression string into a `(canonical_route, args)` tuple.
///
/// Supported formats:
/// 1. Function call syntax: `忆(问="auth failure", 数=5)` or `忆(问: "auth failure")`
/// 2. Positional shorthand: `忆("auth failure")` or `忆(auth failure)`
/// 3. Colon syntax: `忆: "auth failure"` or `忆: auth failure`
/// 4. Bare route: `心()` or `心`
pub fn parse_lkep_expression(expr: &str) -> Result<(String, Value), LkepError> {
    let trimmed = expr.trim();
    if trimmed.is_empty() {
        return Err(LkepError::EmptyExpression);
    }

    // Case 1 & 2: Paren syntax — Route(...)
    if let Some(open_paren) = trimmed.find('(') {
        if !trimmed.ends_with(')') {
            return Err(LkepError::SyntaxError(
                "Missing closing parenthesis ')'".into(),
            ));
        }

        let route_part = trimmed[..open_paren].trim();
        let canonical_route = resolve_route(route_part)
            .ok_or_else(|| LkepError::UnknownRoute(route_part.to_string()))?;

        let inner = trimmed[open_paren + 1..trimmed.len() - 1].trim();
        if inner.is_empty() {
            return Ok((canonical_route.to_string(), json!({})));
        }

        // Check if there are key-value separators (= or :)
        if !inner.contains('=') && !inner.contains(':') {
            // Positional shorthand: single primary argument
            let primary = primary_arg_for_route(canonical_route);
            let val = parse_scalar_or_json(inner);
            let mut map = Map::new();
            map.insert(primary.to_string(), val);
            return Ok((canonical_route.to_string(), Value::Object(map)));
        }

        // Parse key-value arguments separated by commas (respecting quotes and brackets)
        let mut map = Map::new();
        let mut in_quotes = false;
        let mut quote_char = '"';
        let mut bracket_depth = 0;
        let mut current_segment = String::new();

        for ch in inner.chars() {
            match ch {
                '"' | '\'' if !in_quotes => {
                    in_quotes = true;
                    quote_char = ch;
                    current_segment.push(ch);
                }
                c if in_quotes && c == quote_char => {
                    in_quotes = false;
                    current_segment.push(ch);
                }
                '[' | '{' if !in_quotes => {
                    bracket_depth += 1;
                    current_segment.push(ch);
                }
                ']' | '}' if !in_quotes && bracket_depth > 0 => {
                    bracket_depth -= 1;
                    current_segment.push(ch);
                }
                ',' if !in_quotes && bracket_depth == 0 => {
                    parse_arg_pair(&current_segment, &mut map)?;
                    current_segment.clear();
                }
                _ => {
                    current_segment.push(ch);
                }
            }
        }

        if !current_segment.trim().is_empty() {
            parse_arg_pair(&current_segment, &mut map)?;
        }

        return Ok((canonical_route.to_string(), Value::Object(map)));
    }

    // Case 3: Colon syntax — Route: Argument
    if let Some(colon_pos) = trimmed.find(':') {
        let route_part = trimmed[..colon_pos].trim();
        if let Some(canonical_route) = resolve_route(route_part) {
            let inner = trimmed[colon_pos + 1..].trim();
            let primary = primary_arg_for_route(canonical_route);
            let val = parse_scalar_or_json(inner);
            let mut map = Map::new();
            map.insert(primary.to_string(), val);
            return Ok((canonical_route.to_string(), Value::Object(map)));
        }
    }

    // Case 4: Bare route — Route
    if let Some(canonical_route) = resolve_route(trimmed) {
        return Ok((canonical_route.to_string(), json!({})));
    }

    Err(LkepError::UnknownRoute(trimmed.to_string()))
}

/// Helper to parse a single `key=val` or `key:val` argument pair.
fn parse_arg_pair(segment: &str, map: &mut Map<String, Value>) -> Result<(), LkepError> {
    let seg = segment.trim();
    if seg.is_empty() {
        return Ok(());
    }

    let (k_part, v_part) = if let Some(eq_pos) = seg.find('=') {
        (&seg[..eq_pos], &seg[eq_pos + 1..])
    } else if let Some(col_pos) = seg.find(':') {
        (&seg[..col_pos], &seg[col_pos + 1..])
    } else {
        return Err(LkepError::SyntaxError(format!(
            "Expected 'key=value' or 'key:value' in '{seg}'"
        )));
    };

    let k_trimmed = k_part.trim();
    let canonical_key = resolve_arg(k_trimmed).unwrap_or(k_trimmed);
    let val = parse_scalar_or_json(v_part);
    map.insert(canonical_key.to_string(), val);
    Ok(())
}

/// Universal decoder: decodes ANY representation (string expression, glyph JSON,
/// route object, root ideogram map) into `(canonical_route, canonical_args)`.
#[must_use]
pub fn decode_lkep(input: &Value) -> Option<(String, Value)> {
    // 1. String representation: parse as LKEP expression
    if let Some(s) = input.as_str() {
        return parse_lkep_expression(s).ok();
    }

    let obj = input.as_object()?;

    // 2. Standard glyph object: {"r": "忆", "a": {"问": "..."}}
    if let Some(rcode) = obj.get("r").and_then(Value::as_str) {
        let canonical_route = resolve_route(rcode)?;
        let mut decoded_args = Map::new();
        if let Some(aobj) = obj.get("a").and_then(Value::as_object) {
            for (k, v) in aobj {
                let canonical_key = resolve_arg(k).unwrap_or(k);
                decoded_args.insert(canonical_key.to_string(), v.clone());
            }
        }
        return Some((canonical_route.to_string(), Value::Object(decoded_args)));
    }

    // 3. Object with "route" key: {"route": "忆", "args": {...}}
    if let Some(route_str) = obj.get("route").and_then(Value::as_str) {
        let canonical_route = resolve_route(route_str)?;
        let mut decoded_args = Map::new();
        if let Some(aobj) = obj.get("args").and_then(Value::as_object) {
            for (k, v) in aobj {
                let canonical_key = resolve_arg(k).unwrap_or(k);
                decoded_args.insert(canonical_key.to_string(), v.clone());
            }
        }
        return Some((canonical_route.to_string(), Value::Object(decoded_args)));
    }

    // 4. Single-key root ideogram object: {"忆": {"问": "..."}} or {"忆": "query string"}
    if obj.len() == 1 {
        let (k, v) = obj.iter().next()?;
        if let Some(canonical_route) = resolve_route(k) {
            if let Some(inner_obj) = v.as_object() {
                let mut decoded_args = Map::new();
                for (ik, iv) in inner_obj {
                    let canonical_key = resolve_arg(ik).unwrap_or(ik);
                    decoded_args.insert(canonical_key.to_string(), iv.clone());
                }
                return Some((canonical_route.to_string(), Value::Object(decoded_args)));
            }
            // Positional shorthand for single-key root object: {"忆": "auth failure"}
            let primary = primary_arg_for_route(canonical_route);
            let mut map = Map::new();
            map.insert(primary.to_string(), v.clone());
            return Some((canonical_route.to_string(), Value::Object(map)));
        }
    }

    None
}

/// Tool `lkep.exec` — Executes or translates logographic expressions directly.
pub struct LkepExecTool {
    stats: ToolStats,
    effects: EffectRow,
}

impl LkepExecTool {
    #[must_use]
    pub fn new() -> Self {
        Self {
            stats: ToolStats::default(),
            effects: EffectRow::pure(),
        }
    }
}

impl Default for LkepExecTool {
    fn default() -> Self {
        Self::new()
    }
}

#[async_trait]
impl Tool for LkepExecTool {
    fn name(&self) -> &str {
        "lkep.exec"
    }

    fn gana(&self) -> Gana {
        Gana::Horn
    }

    fn effects(&self) -> &EffectRow {
        &self.effects
    }

    fn description(&self) -> &str {
        "Execute or parse a Sanskrit-Chinese logographic expression (e.g. 忆(问=\"auth failure\", 数=5)) directly through the WhiteMagic logographic kernel execution pipeline."
    }

    async fn call(&self, _ctx: &mut Context, args: Value) -> wm_core::Result<Value> {
        let (route, resolved_args) = if let Some((r, a)) = decode_lkep(&args) {
            (r, a)
        } else if let Some(expr) = args.get("expr").and_then(Value::as_str) {
            parse_lkep_expression(expr)
                .map_err(|e| wm_core::CoreError::InvalidArgs(e.to_string()))?
        } else {
            return Err(wm_core::CoreError::InvalidArgs(
                "Expected logographic expression in string format, {expr: \"...\"}, or glyph object".into(),
            ));
        };

        Ok(json!({
            "status": "success",
            "pipeline": "LKEP-v1",
            "route": route,
            "args": resolved_args,
        }))
    }

    fn stats(&self) -> &ToolStats {
        &self.stats
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_resolve_routes_and_args() {
        assert_eq!(resolve_route(""), Some("memory.search"));
        assert_eq!(resolve_route(""), Some("memory.search"));
        assert_eq!(resolve_route("Ms"), Some("memory.search"));
        assert_eq!(resolve_route("memory.search"), Some("memory.search"));
        assert_eq!(resolve_route(""), Some("memory.create"));
        assert_eq!(resolve_route(""), Some("citta.status"));
        assert_eq!(resolve_route("nonexistent"), None);

        assert_eq!(resolve_arg(""), Some("query"));
        assert_eq!(resolve_arg(""), Some("limit"));
        assert_eq!(resolve_arg(""), Some("content"));
        assert_eq!(resolve_arg(""), Some("tags"));
        assert_eq!(resolve_arg("query"), Some("query"));
    }

    #[test]
    fn test_parse_lkep_function_call_named_args() {
        let (route, args) = parse_lkep_expression("忆(问=\"auth failure\", 数=5)").unwrap();
        assert_eq!(route, "memory.search");
        assert_eq!(args["query"], "auth failure");
        assert_eq!(args["limit"], 5);

        let (route2, args2) =
            parse_lkep_expression("录(文=\"daemon restart\", 标=[\"crash\", \"vulkan\"])").unwrap();
        assert_eq!(route2, "memory.create");
        assert_eq!(args2["content"], "daemon restart");
        assert_eq!(args2["tags"][0], "crash");
        assert_eq!(args2["tags"][1], "vulkan");
    }

    #[test]
    fn test_parse_lkep_positional_shorthand() {
        let (route, args) = parse_lkep_expression("忆(\"system deadlock\")").unwrap();
        assert_eq!(route, "memory.search");
        assert_eq!(args["query"], "system deadlock");

        let (route2, args2) = parse_lkep_expression("忆: system deadlock").unwrap();
        assert_eq!(route2, "memory.search");
        assert_eq!(args2["query"], "system deadlock");
    }

    #[test]
    fn test_parse_lkep_bare_route() {
        let (route, args) = parse_lkep_expression("心()").unwrap();
        assert_eq!(route, "citta.status");
        assert_eq!(args, json!({}));

        let (route2, args2) = parse_lkep_expression("").unwrap();
        assert_eq!(route2, "dharma.rules");
        assert_eq!(args2, json!({}));
    }

    #[test]
    fn test_decode_lkep_all_shapes() {
        // Shape 1: String
        let res1 = decode_lkep(&json!("忆(问=\"disk full\", 数=10)")).unwrap();
        assert_eq!(res1.0, "memory.search");
        assert_eq!(res1.1["query"], "disk full");
        assert_eq!(res1.1["limit"], 10);

        // Shape 2: Glyph JSON
        let res2 = decode_lkep(&json!({ "r": "", "a": { "": "timeout" } })).unwrap();
        assert_eq!(res2.0, "memory.search");
        assert_eq!(res2.1["query"], "timeout");

        // Shape 3: Route object
        let res3 =
            decode_lkep(&json!({ "route": "", "args": { "": "snapshot", "": ["auto"] } }))
                .unwrap();
        assert_eq!(res3.0, "memory.create");
        assert_eq!(res3.1["content"], "snapshot");

        // Shape 4: Root ideogram object
        let res4 = decode_lkep(&json!({ "": "uncommitted writes" })).unwrap();
        assert_eq!(res4.0, "memory.search");
        assert_eq!(res4.1["query"], "uncommitted writes");
    }
}