Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 31 additions & 1 deletion src/rust/workunit_store/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,21 @@ use tokio::task_local;

mod metrics;

/// Formats a duration for display in workunit completion logs.
///
/// For durations under 60 seconds, returns " (X.XXs)".
/// For durations of 60 seconds or more, returns " (Xm Y.Ys)".
pub(crate) fn format_workunit_duration(duration: Duration) -> String {
let total_secs = duration.as_secs_f64();
if total_secs >= 60.0 {
let mins = (total_secs / 60.0).floor() as u64;
let secs = total_secs % 60.0;
format!(" ({mins}m {secs:.1}s)")
} else {
format!(" ({total_secs:.2}s)")
}
}

///
/// A unique id for a single run or `--loop` iteration of Pants within a single Scheduler.
///
Expand Down Expand Up @@ -254,6 +269,17 @@ impl Workunit {
(WorkunitState::Completed { .. }, _) => "Completed:",
};

let duration_str: Option<String> = match &self.state {
WorkunitState::Completed { time_span } => {
Some(format_workunit_duration(std::time::Duration::from(time_span.duration)))
}
WorkunitState::Started { start_time, .. } if canceled => {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So you only show the elapsed time if the work was canceled? Why? Wouldn't the opposite make more sense? Or just always show it?

let elapsed = start_time.elapsed().unwrap_or_default();
Some(format_workunit_duration(elapsed))
}
_ => None,
};

let identifier = if let Some(ref s) = metadata.desc {
s.as_str()
} else {
Expand Down Expand Up @@ -281,7 +307,11 @@ impl Workunit {
"".to_string()
};

log!(self.level, "{state} {effective_identifier}{message}");
log!(
self.level,
"{state} {effective_identifier}{}{message}",
duration_str.as_deref().unwrap_or("")
);
}
}

Expand Down
51 changes: 50 additions & 1 deletion src/rust/workunit_store/src/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use std::time::Duration;

use internment::Intern;

use crate::{Level, ParentIds, SpanId, WorkunitMetadata, WorkunitState, WorkunitStore};
use crate::{Level, ParentIds, SpanId, WorkunitMetadata, WorkunitState, WorkunitStore, format_workunit_duration};

#[test]
fn heavy_hitters_basic() {
Expand Down Expand Up @@ -224,3 +224,52 @@ fn wu_level(span_id: u64, parent_id: Option<u64>, level: Level) -> AnonymousWork
metadata.desc = Some(format!("{span_id}"));
(level, SpanId(span_id), parent_id.map(SpanId), metadata)
}

#[test]
fn format_duration_sub_second() {
let duration = Duration::from_millis(123);
assert_eq!(format_workunit_duration(duration), " (0.12s)");
}

#[test]
fn format_duration_seconds() {
let duration = Duration::from_secs_f64(12.345);
assert_eq!(format_workunit_duration(duration), " (12.35s)");
}

#[test]
fn format_duration_just_under_minute() {
let duration = Duration::from_secs_f64(59.99);
assert_eq!(format_workunit_duration(duration), " (59.99s)");
}

#[test]
fn format_duration_exactly_one_minute() {
let duration = Duration::from_secs(60);
assert_eq!(format_workunit_duration(duration), " (1m 0.0s)");
}

#[test]
fn format_duration_minutes_and_seconds() {
let duration = Duration::from_secs_f64(90.5);
assert_eq!(format_workunit_duration(duration), " (1m 30.5s)");
}

#[test]
fn format_duration_multiple_minutes() {
let duration = Duration::from_secs_f64(185.7);
assert_eq!(format_workunit_duration(duration), " (3m 5.7s)");
}

#[test]
fn format_duration_zero() {
let duration = Duration::from_secs(0);
assert_eq!(format_workunit_duration(duration), " (0.00s)");
}

#[test]
fn format_duration_over_one_hour() {
// 1 hour 30 minutes 45.5 seconds = 5445.5 seconds
let duration = Duration::from_secs_f64(5445.5);
assert_eq!(format_workunit_duration(duration), " (90m 45.5s)");
}
Loading