feat: continue tree rust family cutover
- add rust renderer/state-family scaffolds and inline compat host thinning for page tree, file tree, and picker - route tree/filetree preflight, file projection, resource artifact, and stream delta contracts through rust plans - preserve canonical move-order validation, file-tree search projection, and related frontend/runtime regression coverage
This commit is contained in:
@@ -20,6 +20,8 @@ pub struct KernelProjectionQuery {
|
||||
pub workspace_id: Option<String>,
|
||||
pub root_node_id: Option<String>,
|
||||
pub depth: Option<u32>,
|
||||
pub query: Option<String>,
|
||||
pub max_results: Option<usize>,
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
@@ -73,6 +75,8 @@ async fn project_projection(
|
||||
workspace_id: &effective_workspace_id,
|
||||
root_node_id: query.root_node_id.as_deref(),
|
||||
depth: query.depth,
|
||||
query: query.query.as_deref(),
|
||||
max_results: query.max_results,
|
||||
projection,
|
||||
},
|
||||
)
|
||||
@@ -388,4 +392,64 @@ mod tests {
|
||||
.iter()
|
||||
.any(|value| value == "expand"));
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn file_tree_projection_query_returns_matches_and_ancestors() {
|
||||
let response = app()
|
||||
.oneshot(
|
||||
Request::builder()
|
||||
.uri("/api/tree/projections/file?workspaceId=ws_demo&rootNodeId=page_root&query=%E9%A2%84%E7%AE%97")
|
||||
.body(Body::empty())
|
||||
.expect("request"),
|
||||
)
|
||||
.await
|
||||
.expect("response");
|
||||
|
||||
assert_eq!(response.status(), StatusCode::OK);
|
||||
let body = to_bytes(response.into_body(), usize::MAX)
|
||||
.await
|
||||
.expect("body");
|
||||
let payload: Value = serde_json::from_slice(&body).expect("json");
|
||||
let items = payload["result"]["items"].as_array().expect("items");
|
||||
let row_ids = items
|
||||
.iter()
|
||||
.filter_map(|item| item["rowId"].as_str())
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
assert_eq!(row_ids, vec!["doc:page_root", "asset:table_1"]);
|
||||
assert_eq!(items[0]["expandedByDefault"], true);
|
||||
assert_eq!(items[1]["resourceMeta"]["resourceKind"], "table");
|
||||
let edges = payload["result"]["edges"].as_array().expect("edges");
|
||||
assert_eq!(edges.len(), 1);
|
||||
assert_eq!(edges[0]["fromNodeId"], "page_root");
|
||||
assert_eq!(edges[0]["toNodeId"], "asset:table_1");
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn file_tree_projection_query_honors_max_results_and_keeps_ancestors() {
|
||||
let response = app()
|
||||
.oneshot(
|
||||
Request::builder()
|
||||
.uri("/api/tree/projections/file?workspaceId=ws_demo&rootNodeId=page_root&query=png&maxResults=1")
|
||||
.body(Body::empty())
|
||||
.expect("request"),
|
||||
)
|
||||
.await
|
||||
.expect("response");
|
||||
|
||||
assert_eq!(response.status(), StatusCode::OK);
|
||||
let body = to_bytes(response.into_body(), usize::MAX)
|
||||
.await
|
||||
.expect("body");
|
||||
let payload: Value = serde_json::from_slice(&body).expect("json");
|
||||
let items = payload["result"]["items"].as_array().expect("items");
|
||||
let row_ids = items
|
||||
.iter()
|
||||
.filter_map(|item| item["rowId"].as_str())
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
assert_eq!(row_ids, vec!["doc:page_root", "asset:asset_file_1"]);
|
||||
assert_eq!(items[0]["expandedByDefault"], true);
|
||||
assert_eq!(items[1]["resourceMeta"]["assetKind"], "image");
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user