aboutsummaryrefslogtreecommitdiffstats
path: root/crates/client/src/command
diff options
context:
space:
mode:
authorBenedikt Peetz <benedikt.peetz@b-peetz.de>2026-07-20 14:18:36 +0200
committerBenedikt Peetz <benedikt.peetz@b-peetz.de>2026-07-20 14:18:36 +0200
commit63a0ec3901a863fb07d18f4b814a98a813644382 (patch)
treec94b7b501601b5df05cf654e9f9c9b5bc66a239e /crates/client/src/command
parentchore: Commit (diff)
downloadatuin-63a0ec3901a863fb07d18f4b814a98a813644382.zip
chore: Commit
Diffstat (limited to 'crates/client/src/command')
-rw-r--r--crates/client/src/command/client/history.rs105
1 files changed, 105 insertions, 0 deletions
diff --git a/crates/client/src/command/client/history.rs b/crates/client/src/command/client/history.rs
index 9f383a08..4d633b7d 100644
--- a/crates/client/src/command/client/history.rs
+++ b/crates/client/src/command/client/history.rs
@@ -262,6 +262,111 @@ pub(crate) fn print_list(
}
}
+async fn connect_client(settings: &Settings) -> Result<HistoryClient> {
+ HistoryClient::new(
+ #[cfg(unix)]
+ settings.daemon.socket_path.clone(),
+ )
+ .await
+}
+
+async fn probe(settings: &Settings) -> Probe {
+ let mut client = match connect_client(settings).await {
+ Ok(client) => client,
+ Err(err) => return Probe::Unreachable(err),
+ };
+
+ match client.status().await {
+ Ok(status) => {
+ if daemon_matches_expected(&status.version, status.protocol) {
+ Probe::Ready(client)
+ } else {
+ Probe::NeedsRestart(daemon_mismatch_message(&status.version, status.protocol))
+ }
+ }
+ Err(err) => Probe::Unreachable(err),
+ }
+}
+
+pub(crate) async fn start_history(settings: &Settings, history: History) -> Result<String> {
+ match async {
+ connect_client(settings)
+ .await?
+ .start_history(history.clone())
+ .await
+ }
+ .await
+ {
+ Ok(resp) => {
+ if daemon_matches_expected(&resp.version, resp.protocol) {
+ return Ok(resp.id);
+ }
+
+ Err(eyre!(
+ "{}. Restart the daemon manually",
+ daemon_mismatch_message(&resp.version, resp.protocol)
+ ))
+ }
+ Err(err) => Err(err),
+ }
+}
+
+pub(crate) async fn end_history(
+ settings: &Settings,
+ id: String,
+ duration: u64,
+ exit: i64,
+) -> Result<()> {
+ match async {
+ connect_client(settings)
+ .await?
+ .end_history(id.clone(), duration, exit)
+ .await
+ }
+ .await
+ {
+ Ok(resp) => {
+ if daemon_matches_expected(&resp.version, resp.protocol) {
+ return Ok(());
+ }
+
+ Err(eyre!(
+ "{}. Restart the daemon manually",
+ daemon_mismatch_message(&resp.version, resp.protocol)
+ ))
+ }
+ Err(err) => Err(err),
+ }
+}
+
+/// Emit a daemon event.
+pub(crate) async fn emit_event(settings: &Settings, event: DaemonEvent) {
+ // Try to connect and send
+ match ControlClient::from_settings(settings).await {
+ Ok(mut client) => {
+ if let Err(e) = client.send_event(event).await {
+ tracing::debug!(?e, "failed to send event to daemon");
+ }
+ }
+ Err(e) => {
+ tracing::debug!(?e, "daemon not available, skipping event emission");
+ }
+ }
+}
+
+pub(crate) async fn tail_client(settings: &Settings) -> Result<HistoryClient> {
+ match probe(settings).await {
+ Probe::Ready(client) => Ok(client),
+ Probe::NeedsRestart(reason) => {
+ bail!("{reason}. Restart the daemon manually");
+ }
+ Probe::Unreachable(err) if is_legacy_daemon_error(&err) => {
+ Err(err.wrap_err(LEGACY_DAEMON_RESTART_MESSAGE))
+ }
+ Probe::Unreachable(err) => Err(err),
+ }
+}
+
fn check_for_write_errors(write: Result<(), io::Error>) {
if let Err(err) = write {
// Ignore broken pipe (issue #626)