2026-04-14 13:22:29 +08:00
|
|
|
pub mod command;
|
|
|
|
|
pub mod common;
|
|
|
|
|
pub mod governance;
|
2026-04-16 22:01:51 +08:00
|
|
|
pub mod kernel;
|
2026-04-15 20:01:12 +08:00
|
|
|
pub mod mindmap;
|
2026-04-14 13:22:29 +08:00
|
|
|
pub mod query;
|
|
|
|
|
pub mod tool;
|
|
|
|
|
|
|
|
|
|
pub use command::{
|
2026-04-15 20:01:12 +08:00
|
|
|
CommandEnvelope, CopyTreeDocumentPages, CreateDocumentPage, CreatePage, CreateWorkspace,
|
|
|
|
|
DeleteBlock, DeleteDocumentPage, DuplicateDocumentPage, EmbedBlock, InsertBlock, MoveBlock,
|
|
|
|
|
MoveDocumentPage, PatchBlock, PatchPageBlock, PutMindmap, ReplaceMediaAssetStorage,
|
|
|
|
|
RestoreDocumentPage, SavePageContent, UpdateBlock, UpdatePageOptions, UpdatePageStats,
|
|
|
|
|
UpdatePageTitle,
|
2026-04-14 13:22:29 +08:00
|
|
|
};
|
|
|
|
|
pub use common::{
|
|
|
|
|
ActorPayload, AffectedObject, ErrorDetail, ErrorPayload, OkPayload, RequestMeta, ResponseMeta,
|
|
|
|
|
SourcePayload, TargetRef,
|
|
|
|
|
};
|
2026-04-16 22:01:51 +08:00
|
|
|
pub use kernel::{
|
|
|
|
|
KernelAttachEdge, KernelAuditStamp, KernelContentPayload, KernelCreateNode,
|
|
|
|
|
KernelDetachEdge, KernelEdge, KernelEdgeListResult, KernelEdgeType, KernelGetNode,
|
|
|
|
|
KernelGetSubtree, KernelGraphDirection, KernelGraphTraversalResult, KernelGraphVisit,
|
|
|
|
|
KernelListChildren, KernelListEdges, KernelMoveSubtree, KernelNode, KernelNodeMetadata,
|
2026-04-18 09:38:16 +08:00
|
|
|
KernelNodeType, KernelProjectionAssetKind, KernelProjectionCapability,
|
|
|
|
|
KernelProjectionFilter, KernelProjectionItem, KernelProjectionKind,
|
|
|
|
|
KernelProjectionRequest, KernelProjectionResourceKind, KernelProjectionResourceMeta,
|
|
|
|
|
KernelProjectionResult, KernelProjectionRowKind, KernelRefsPayload, KernelSubtreeRef,
|
2026-04-16 22:01:51 +08:00
|
|
|
KernelSubtreeResult, KernelTraverseGraph, KernelUpdateNode,
|
|
|
|
|
};
|
2026-04-15 20:01:12 +08:00
|
|
|
pub use mindmap::{
|
|
|
|
|
MindmapNodeData, MindmapNodeInput, MindmapNodeRef, MindmapOp, MindmapTreeNode,
|
|
|
|
|
};
|
2026-04-15 03:06:29 +08:00
|
|
|
pub use query::{
|
2026-04-15 20:01:12 +08:00
|
|
|
GetBlock, GetBridgeCommand, GetBridgeRequest, GetBridgeTrace, GetMindmap, GetPage,
|
|
|
|
|
GetPageContent, GetPageMeta, ListBridgeWorkspaceOverview, ListPageBlocks,
|
|
|
|
|
ListSidebarDataset, QueryEnvelope, SearchBlocks, SearchDocuments, SearchPages, SearchRecent,
|
|
|
|
|
};
|
|
|
|
|
pub use tool::{
|
|
|
|
|
default_tool_registry, invocation_kind_label, tool_effect_label, tool_mode_label,
|
|
|
|
|
InvocationKind, ToolEffect, ToolExecutionMode, ToolInvocation, ToolRegistry, ToolSetSpec,
|
|
|
|
|
ToolSpec, BRIDGE_TOOL_COMMAND_GET, BRIDGE_TOOL_REQUEST_GET, BRIDGE_TOOL_TRACE_GET,
|
2026-04-16 15:24:37 +08:00
|
|
|
DOCS_TOOL_READ, DOCS_TOOL_SEARCH, DOCS_TOOLSET_READ, DOC_TOOL_FIND, DOC_TOOL_GET,
|
|
|
|
|
DOC_TOOL_INSERT_BLOCKS, DOC_TOOL_REPLACE_RANGE, DOC_TOOLSET_READ, DOC_TOOLSET_WRITE,
|
|
|
|
|
INDEX_TOOL_REBUILD, MINDMAP_TOOL_APPLY_OPS,
|
2026-04-15 20:01:12 +08:00
|
|
|
MINDMAP_TOOL_EMPTY_TRASH, MINDMAP_TOOL_EXPAND_NODE, MINDMAP_TOOL_GET,
|
|
|
|
|
MINDMAP_TOOL_GET_SUBTREE,
|
|
|
|
|
MINDMAP_TOOL_OUTLINE_TO_MINDMAP, MINDMAP_TOOL_PUT, MINDMAP_TOOLSET_READ,
|
|
|
|
|
MINDMAP_TOOLSET_WRITE, OBSERVE_TOOLSET_READ, ONLYOFFICE_TOOL_PREPARE_CALLBACK,
|
|
|
|
|
ONLYOFFICE_TOOL_PREPARE_FORCESAVE, ONLYOFFICE_TOOL_PREPARE_PROXY,
|
|
|
|
|
ONLYOFFICE_TOOL_SESSION_RESOLVE, ONLYOFFICE_TOOL_SIGN, ONLYOFFICE_TOOLSET_SERVICE,
|
|
|
|
|
RECOVERY_TOOLSET_JOB, REPLAY_TOOL_EVENTS,
|
2026-04-15 03:06:29 +08:00
|
|
|
};
|
2026-04-14 13:22:29 +08:00
|
|
|
|
|
|
|
|
#[cfg(test)]
|
|
|
|
|
mod tests {
|
|
|
|
|
use super::*;
|
|
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
|
fn command_envelope_keeps_validate_only_flag() {
|
|
|
|
|
let envelope = CommandEnvelope::<CreateWorkspace> {
|
|
|
|
|
name: "create_workspace".into(),
|
|
|
|
|
command_id: "cmd_1".into(),
|
|
|
|
|
idempotency_key: Some("idem_1".into()),
|
|
|
|
|
actor: ActorPayload {
|
|
|
|
|
actor_type: "human".into(),
|
|
|
|
|
actor_id: "user_1".into(),
|
|
|
|
|
session_id: Some("session_1".into()),
|
|
|
|
|
},
|
|
|
|
|
source: SourcePayload {
|
|
|
|
|
channel: "cli".into(),
|
|
|
|
|
client: "mnote-cli".into(),
|
|
|
|
|
},
|
|
|
|
|
target: None,
|
|
|
|
|
payload: CreateWorkspace {
|
|
|
|
|
name: "demo".into(),
|
|
|
|
|
slug: Some("demo".into()),
|
|
|
|
|
},
|
|
|
|
|
reason: Some("初始化工作区".into()),
|
|
|
|
|
refs: vec![],
|
|
|
|
|
dry_run: false,
|
|
|
|
|
validate_only: true,
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
assert!(envelope.validate_only);
|
|
|
|
|
}
|
2026-04-15 20:01:12 +08:00
|
|
|
|
|
|
|
|
#[test]
|
|
|
|
|
fn default_tool_registry_exposes_doc_tools() {
|
|
|
|
|
let registry = default_tool_registry();
|
|
|
|
|
assert_eq!(
|
|
|
|
|
registry.tool_names(),
|
|
|
|
|
vec![
|
|
|
|
|
"search_web",
|
|
|
|
|
"doc_get",
|
|
|
|
|
"doc_find",
|
2026-04-16 15:24:37 +08:00
|
|
|
"docs_search",
|
|
|
|
|
"docs_read",
|
2026-04-15 20:01:12 +08:00
|
|
|
"image_read",
|
|
|
|
|
"doc_insert_blocks",
|
|
|
|
|
"doc_replace_range",
|
|
|
|
|
"slash_run",
|
|
|
|
|
"mindmap_get",
|
|
|
|
|
"mindmap_get_subtree",
|
|
|
|
|
"mindmap_put",
|
|
|
|
|
"mindmap_apply_ops",
|
|
|
|
|
"mindmap_expand_node",
|
|
|
|
|
"mindmap_empty_trash",
|
|
|
|
|
"mindmap_outline_to_mindmap",
|
|
|
|
|
"bridge_request_get",
|
|
|
|
|
"bridge_trace_get",
|
|
|
|
|
"bridge_command_get",
|
|
|
|
|
"event_replay",
|
|
|
|
|
"index_rebuild",
|
|
|
|
|
"onlyoffice_session_resolve",
|
|
|
|
|
"onlyoffice_sign",
|
|
|
|
|
"onlyoffice_prepare_proxy",
|
|
|
|
|
"onlyoffice_prepare_callback",
|
|
|
|
|
"onlyoffice_prepare_forcesave",
|
|
|
|
|
]
|
|
|
|
|
);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
registry
|
|
|
|
|
.tool("search_web")
|
|
|
|
|
.expect("search_web should exist")
|
|
|
|
|
.toolset_id,
|
|
|
|
|
"toolset.readonly"
|
|
|
|
|
);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
registry
|
|
|
|
|
.tool("image_read")
|
|
|
|
|
.expect("image_read should exist")
|
|
|
|
|
.toolset_id,
|
|
|
|
|
"toolset.media_read"
|
|
|
|
|
);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
registry
|
|
|
|
|
.tool("slash_run")
|
|
|
|
|
.expect("slash_run should exist")
|
|
|
|
|
.toolset_id,
|
|
|
|
|
"toolset.slash_write"
|
|
|
|
|
);
|
|
|
|
|
let readonly = registry
|
|
|
|
|
.toolset("toolset.readonly")
|
|
|
|
|
.expect("readonly toolset should exist");
|
|
|
|
|
assert!(!readonly.write_toolset);
|
|
|
|
|
assert_eq!(readonly.tool_names, &["search_web"]);
|
|
|
|
|
let media = registry
|
|
|
|
|
.toolset("toolset.media_read")
|
|
|
|
|
.expect("media toolset should exist");
|
|
|
|
|
assert!(!media.write_toolset);
|
|
|
|
|
assert_eq!(media.tool_names, &["image_read"]);
|
|
|
|
|
let slash = registry
|
|
|
|
|
.toolset("toolset.slash_write")
|
|
|
|
|
.expect("slash toolset should exist");
|
|
|
|
|
assert!(slash.write_toolset);
|
|
|
|
|
assert_eq!(slash.tool_names, &["slash_run"]);
|
2026-04-16 15:24:37 +08:00
|
|
|
let docs_read = registry
|
|
|
|
|
.toolset("toolset.docs_read")
|
|
|
|
|
.expect("docs_read toolset should exist");
|
|
|
|
|
assert!(!docs_read.write_toolset);
|
|
|
|
|
assert_eq!(docs_read.tool_names, &["docs_search", "docs_read"]);
|
2026-04-15 20:01:12 +08:00
|
|
|
let doc_write = registry
|
|
|
|
|
.toolset("toolset.doc_write")
|
|
|
|
|
.expect("doc_write toolset should exist");
|
|
|
|
|
assert!(doc_write.write_toolset);
|
|
|
|
|
assert_eq!(doc_write.tool_names, &["doc_insert_blocks", "doc_replace_range"]);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
registry.tool("doc_get").expect("doc_get should exist").toolset_id,
|
|
|
|
|
"toolset.doc_read"
|
|
|
|
|
);
|
|
|
|
|
let mindmap_write = registry
|
|
|
|
|
.toolset("toolset.mindmap_write")
|
|
|
|
|
.expect("mindmap_write toolset should exist");
|
|
|
|
|
assert!(mindmap_write.write_toolset);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
mindmap_write.tool_names,
|
|
|
|
|
&[
|
|
|
|
|
"mindmap_put",
|
|
|
|
|
"mindmap_apply_ops",
|
|
|
|
|
"mindmap_expand_node",
|
|
|
|
|
"mindmap_empty_trash",
|
|
|
|
|
"mindmap_outline_to_mindmap",
|
|
|
|
|
]
|
|
|
|
|
);
|
|
|
|
|
let onlyoffice_service = registry
|
|
|
|
|
.toolset("toolset.onlyoffice_service")
|
|
|
|
|
.expect("onlyoffice service toolset should exist");
|
|
|
|
|
assert!(onlyoffice_service.write_toolset);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
onlyoffice_service.tool_names,
|
|
|
|
|
&[
|
|
|
|
|
"onlyoffice_session_resolve",
|
|
|
|
|
"onlyoffice_sign",
|
|
|
|
|
"onlyoffice_prepare_proxy",
|
|
|
|
|
"onlyoffice_prepare_callback",
|
|
|
|
|
"onlyoffice_prepare_forcesave",
|
|
|
|
|
]
|
|
|
|
|
);
|
|
|
|
|
let observe = registry
|
|
|
|
|
.toolset("toolset.observe_read")
|
|
|
|
|
.expect("observe toolset should exist");
|
|
|
|
|
assert!(!observe.write_toolset);
|
|
|
|
|
assert_eq!(
|
|
|
|
|
observe.tool_names,
|
|
|
|
|
&["bridge_request_get", "bridge_trace_get", "bridge_command_get"]
|
|
|
|
|
);
|
|
|
|
|
let recovery = registry
|
|
|
|
|
.toolset("toolset.recovery_job")
|
|
|
|
|
.expect("recovery toolset should exist");
|
|
|
|
|
assert!(recovery.write_toolset);
|
|
|
|
|
assert_eq!(recovery.tool_names, &["event_replay", "index_rebuild"]);
|
|
|
|
|
}
|
2026-04-14 13:22:29 +08:00
|
|
|
}
|