feat: 收口 Rust Web 3000 主链

This commit is contained in:
lix-2026
2026-05-11 13:16:34 +08:00
parent 7f3f7d4e2f
commit 17c003976b
61 changed files with 2090 additions and 2256 deletions
@@ -99,9 +99,13 @@ fn render_filetree_row(
create_action_html = create_action_html,
title = escape_html(&row.title),
));
if row.expandable && row.expanded {
if row.expandable {
if let Some(children) = children_by_parent.get(&Some(row.node_id.clone())) {
html.push_str(r#"<ul class="tree-children">"#);
html.push_str(if row.expanded {
r#"<ul class="tree-children">"#
} else {
r#"<ul class="tree-children tree-children--collapsed">"#
});
for child in children {
render_filetree_row(html, child, children_by_parent);
}
@@ -9,6 +9,7 @@ pub struct PageTreeRenderRow {
pub depth: u32,
pub expandable: bool,
pub expanded: bool,
pub openable: bool,
}
#[derive(Debug, Clone, PartialEq, Eq)]
@@ -21,6 +22,7 @@ pub struct PageTreeDomRow {
pub depth: u32,
pub title: String,
pub expandable: bool,
pub openable: bool,
}
#[derive(Debug, Clone, PartialEq, Eq)]
@@ -41,6 +43,7 @@ pub fn build_page_tree_dom_rows(rows: &[PageTreeRenderRow]) -> Vec<PageTreeDomRo
depth: row.depth,
title: row.title.clone(),
expandable: row.expandable,
openable: row.openable,
})
.collect()
}
@@ -121,7 +124,7 @@ fn render_page_row(
.unwrap_or_default();
let render_depth = render_depth_for_node(&input.rows, &row.node_id, row.depth);
html.push_str(&format!(
r#"<li class="tree-node" data-node-id="{node_id}"><div class="tree-row" role="treeitem" aria-level="{aria_level}" aria-expanded="{expanded_attr}" data-rust-rendered-row="page" data-testid="wolai-sidebar-row" data-tree-testid="{test_id}" data-node-id="{node_id}"{parent_attr} data-depth="{depth}" data-shell-mode="page" data-active="{active}" aria-selected="{selected}"{current_attr} data-focused="{focused}" data-draggable="true" draggable="true" tabindex="{tab_index}">{toggle_html}<button type="button" class="tree-link" data-testid="tree-node-open" data-rust-action="open" data-node-id="{node_id}"><span class="tree-link-title">{title}</span></button><div class="tree-actions"><button type="button" class="tree-action" data-testid="tree-action-menu" data-rust-action="menu" data-node-id="{node_id}" aria-label="更多操作">…</button><button type="button" class="tree-action" data-testid="tree-action-create" data-rust-action="create" data-node-id="{node_id}" aria-label="新建子页面">+</button></div></div>"#,
r#"<li class="tree-node" data-node-id="{node_id}"><div class="tree-row" role="treeitem" aria-level="{aria_level}" aria-expanded="{expanded_attr}" data-rust-rendered-row="page" data-testid="wolai-sidebar-row" data-tree-testid="{test_id}" data-node-id="{node_id}"{parent_attr} data-depth="{depth}" data-shell-mode="page" data-active="{active}" aria-selected="{selected}"{current_attr} data-focused="{focused}" data-page-openable="{openable}" data-draggable="true" draggable="true" tabindex="{tab_index}">{toggle_html}<button type="button" class="tree-link" data-testid="tree-node-open" data-rust-action="open" data-node-id="{node_id}" data-page-openable="{openable}"><span class="tree-link-title">{title}</span></button><div class="tree-actions"><button type="button" class="tree-action" data-testid="tree-action-menu" data-rust-action="menu" data-node-id="{node_id}" aria-label="更多操作">…</button><button type="button" class="tree-action" data-testid="tree-action-create" data-rust-action="create" data-node-id="{node_id}" aria-label="新建子页面">+</button></div></div>"#,
node_id = escape_html(&row.node_id),
aria_level = render_depth + 1,
expanded_attr = if row.expandable && expanded { "true" } else { "false" },
@@ -132,13 +135,18 @@ fn render_page_row(
selected = active,
current_attr = if active { r#" aria-current="page""# } else { "" },
focused = focused,
openable = row.openable,
tab_index = if focused { "0" } else { "-1" },
toggle_html = toggle_html,
title = escape_html(&row.title),
));
if row.expandable && expanded {
if row.expandable {
if let Some(children) = children_by_parent.get(&Some(row.node_id.clone())) {
html.push_str(r#"<ul class="tree-children">"#);
html.push_str(if expanded {
r#"<ul class="tree-children">"#
} else {
r#"<ul class="tree-children tree-children--collapsed">"#
});
for child in children {
render_page_row(html, child, children_by_parent, input);
}
@@ -204,6 +212,7 @@ mod tests {
depth: 0,
expandable: true,
expanded: false,
openable: true,
},
PageTreeRenderRow {
node_id: "page_child".into(),
@@ -212,6 +221,7 @@ mod tests {
depth: 1,
expandable: false,
expanded: false,
openable: true,
},
]);
@@ -234,6 +244,7 @@ mod tests {
depth: 0,
expandable: true,
expanded: true,
openable: true,
},
PageTreeRenderRow {
node_id: "page_child".into(),
@@ -242,6 +253,7 @@ mod tests {
depth: 1,
expandable: false,
expanded: false,
openable: true,
},
],
active_node_id: Some("page_root".into()),