Move the original get_draw_order code into the tree_iter module.
This commit is contained in:
@@ -12,13 +12,16 @@ use crate::database::db_handle::DbHandle;
|
||||
use crate::nix_util::nix_output_stream::NixAction;
|
||||
use crate::nix_util::nix_output_stream::NixOutputStream;
|
||||
use crate::nix_util::output_stream::OutputStream;
|
||||
use crate::nix_util::transparent_iter::TransparentIter;
|
||||
|
||||
use super::activity_tree::ActivityId;
|
||||
use super::activity::Activity;
|
||||
use super::activity_tree::ActivityTree;
|
||||
use super::activity_tree::ActivityTreeEntry;
|
||||
use super::activity_tree_stream::ActivityTreeStream;
|
||||
use super::nix_output_stream::ActivityResultMessage;
|
||||
use super::nix_output_stream::NixMessage;
|
||||
use super::tree_iter::DrawDagEntry;
|
||||
use super::tree_iter::ReverseTreeIter;
|
||||
use super::tree_iter::get_draw_order;
|
||||
|
||||
pub(crate) struct RunningBuild<'db> {
|
||||
db_handle: &'db DbHandle,
|
||||
@@ -159,143 +162,83 @@ impl<'db> RunningBuild<'db> {
|
||||
}
|
||||
|
||||
fn print_current_status(&mut self) -> () {
|
||||
let mut tree = String::new();
|
||||
let draw_order = self.get_draw_order();
|
||||
for dag_entry in draw_order {
|
||||
let leading_bars = {
|
||||
let mut leading_bars = String::with_capacity(3 * dag_entry.depth.len());
|
||||
for leading_bar in dag_entry
|
||||
.depth
|
||||
.iter()
|
||||
.map(|depth| if *depth { " " } else { " " })
|
||||
{
|
||||
leading_bars.push_str(leading_bar);
|
||||
}
|
||||
leading_bars
|
||||
};
|
||||
let branch = if dag_entry.has_later_siblings {
|
||||
""
|
||||
} else {
|
||||
""
|
||||
};
|
||||
let activity = self.activity_tree.get_tree().get(&dag_entry.activity_id);
|
||||
let display_name = activity
|
||||
.get_activity()
|
||||
.display_name()
|
||||
.expect("Currently we always return a display name.");
|
||||
let progress_text = activity.get_activity().get_progress_text();
|
||||
let (progress, progress_sep) = match progress_text {
|
||||
Some(text) => (text, " "),
|
||||
None => (Cow::Borrowed(""), ""),
|
||||
};
|
||||
tree += &format!("{leading_bars}{branch} {progress}{progress_sep}{display_name}\n");
|
||||
}
|
||||
if tree.is_empty() {
|
||||
println!("No active activities.");
|
||||
} else {
|
||||
print!("\n{}\n", tree);
|
||||
}
|
||||
// let draw_order = get_draw_order(self.activity_tree.get_tree());
|
||||
let draw_order = ReverseTreeIter::new(
|
||||
self.activity_tree.get_tree(),
|
||||
None,
|
||||
is_match_predicate,
|
||||
is_transparent_predicate,
|
||||
is_alive_predicate,
|
||||
)
|
||||
.get_draw_order();
|
||||
|
||||
print_dag(self.activity_tree.get_tree(), draw_order);
|
||||
self.last_announce = Some(Instant::now());
|
||||
}
|
||||
|
||||
fn get_draw_order(&self) -> Vec<DrawDagEntry> {
|
||||
let mut draw_order: Vec<DrawDagEntry> = Vec::new();
|
||||
let mut stack: Vec<DrawStackEntry> = self
|
||||
.get_children_in_order(self.activity_tree.get_tree().get_root_id())
|
||||
.filter_map(|child| {
|
||||
if child.get_activity().is_active() {
|
||||
Some(DrawStackEntry::HasNotVisitedChildren(DrawDagEntry {
|
||||
activity_id: child.get_activity_id().clone(),
|
||||
depth: Vec::new(),
|
||||
has_later_siblings: true,
|
||||
}))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.collect();
|
||||
if stack.len() == 0 {
|
||||
return draw_order;
|
||||
}
|
||||
stack
|
||||
.last_mut()
|
||||
.expect("If-statement ensured this is Some()")
|
||||
.set_no_later_siblings();
|
||||
|
||||
while !stack.is_empty() {
|
||||
let current_entry = stack.pop().expect("While-loop ensured this is Some.");
|
||||
match current_entry {
|
||||
DrawStackEntry::HasNotVisitedChildren(draw_dag_entry) => {
|
||||
let current_id = draw_dag_entry.activity_id.clone();
|
||||
let mut current_depth = draw_dag_entry.depth.clone();
|
||||
current_depth.push(draw_dag_entry.has_later_siblings);
|
||||
stack.push(DrawStackEntry::VisitedChildren(draw_dag_entry));
|
||||
let children: Vec<ActivityId> = self
|
||||
.get_children_in_order(current_id)
|
||||
.filter_map(|child| {
|
||||
if child.get_activity().is_active() {
|
||||
Some(child.get_activity_id().clone())
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.collect();
|
||||
let has_children = !children.is_empty();
|
||||
stack.extend(children.into_iter().map(|child_id| {
|
||||
DrawStackEntry::HasNotVisitedChildren(DrawDagEntry {
|
||||
activity_id: child_id,
|
||||
depth: current_depth.clone(),
|
||||
has_later_siblings: true,
|
||||
})
|
||||
}));
|
||||
if has_children {
|
||||
stack
|
||||
.last_mut()
|
||||
.expect("If-statement ensured this is Some()")
|
||||
.set_no_later_siblings();
|
||||
}
|
||||
}
|
||||
DrawStackEntry::VisitedChildren(draw_dag_entry) => {
|
||||
draw_order.push(draw_dag_entry);
|
||||
}
|
||||
};
|
||||
}
|
||||
draw_order
|
||||
}
|
||||
|
||||
fn get_children_in_order(
|
||||
&self,
|
||||
parent_id: ActivityId,
|
||||
) -> impl Iterator<Item = &ActivityTreeEntry> {
|
||||
let parent = self.activity_tree.get_tree().get(&parent_id);
|
||||
parent
|
||||
.get_child_ids()
|
||||
.iter()
|
||||
.map(|child_id| self.activity_tree.get_tree().get(child_id))
|
||||
.flat_map(|child| TransparentIter::new(self.activity_tree.get_tree(), child))
|
||||
}
|
||||
}
|
||||
|
||||
enum DrawStackEntry {
|
||||
HasNotVisitedChildren(DrawDagEntry),
|
||||
VisitedChildren(DrawDagEntry),
|
||||
}
|
||||
|
||||
struct DrawDagEntry {
|
||||
activity_id: ActivityId,
|
||||
depth: Vec<bool>,
|
||||
has_later_siblings: bool,
|
||||
}
|
||||
|
||||
impl DrawStackEntry {
|
||||
fn set_no_later_siblings(&mut self) -> () {
|
||||
match self {
|
||||
DrawStackEntry::HasNotVisitedChildren(draw_dag_entry) => {
|
||||
draw_dag_entry.has_later_siblings = false
|
||||
}
|
||||
DrawStackEntry::VisitedChildren(draw_dag_entry) => {
|
||||
draw_dag_entry.has_later_siblings = false
|
||||
pub(crate) fn print_dag(activity_tree: &ActivityTree, draw_order: Vec<DrawDagEntry>) -> () {
|
||||
let mut tree = String::new();
|
||||
for dag_entry in draw_order {
|
||||
let leading_bars = {
|
||||
let mut leading_bars = String::with_capacity(3 * dag_entry.depth.len());
|
||||
for leading_bar in dag_entry
|
||||
.depth
|
||||
.iter()
|
||||
.map(|depth| if *depth { " " } else { " " })
|
||||
{
|
||||
leading_bars.push_str(leading_bar);
|
||||
}
|
||||
leading_bars
|
||||
};
|
||||
let branch = if dag_entry.has_later_siblings {
|
||||
""
|
||||
} else {
|
||||
""
|
||||
};
|
||||
let activity = activity_tree.get(&dag_entry.activity_id);
|
||||
let display_name = activity
|
||||
.get_activity()
|
||||
.display_name()
|
||||
.expect("Currently we always return a display name.");
|
||||
let progress_text = activity.get_activity().get_progress_text();
|
||||
let (progress, progress_sep) = match progress_text {
|
||||
Some(text) => (text, " "),
|
||||
None => (Cow::Borrowed(""), ""),
|
||||
};
|
||||
tree += &format!("{leading_bars}{branch} {progress}{progress_sep}{display_name}\n");
|
||||
}
|
||||
if tree.is_empty() {
|
||||
println!("No active activities.");
|
||||
} else {
|
||||
print!("\n{}\n", tree);
|
||||
}
|
||||
}
|
||||
|
||||
fn is_match_predicate(_entry: &ActivityTreeEntry) -> bool {
|
||||
true
|
||||
}
|
||||
|
||||
pub(crate) fn is_transparent_predicate(entry: &ActivityTreeEntry) -> bool {
|
||||
match entry.get_activity() {
|
||||
Activity::Root(_activity_root) => true,
|
||||
Activity::Unknown(_activity_unknown) => false,
|
||||
Activity::CopyPath(_activity_copy_path) => false,
|
||||
Activity::FileTransfer(_activity_file_transfer) => false,
|
||||
Activity::Realize(_activity_realize) => true,
|
||||
Activity::CopyPaths(_activity_copy_paths) => true,
|
||||
Activity::Builds(_activity_builds) => true,
|
||||
Activity::Build(_activity_build) => false,
|
||||
Activity::OptimizeStore(_activity_optimize_store) => false,
|
||||
Activity::VerifyPaths(_activity_verify_paths) => false,
|
||||
Activity::Substitute(_activity_substitute) => false,
|
||||
Activity::QueryPathInfo(_activity_query_path_info) => false,
|
||||
Activity::PostBuildHook(_activity_post_build_hook) => false,
|
||||
Activity::BuildWaiting(_activity_build_waiting) => true,
|
||||
Activity::FetchTree(_activity_fetch_tree) => false,
|
||||
}
|
||||
}
|
||||
|
||||
fn is_alive_predicate(entry: &ActivityTreeEntry) -> bool {
|
||||
entry.get_activity().is_active()
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user