Files
firezone/rust/gui-client/src-common/src/errors.rs
Thomas Eizinger fdb7631529 feat(gui-client): gracefully exit GUI on graceful IPC shutdown (#8035)
When the IPC service gets terminated gracefully, the user must have
initiated some kind of action, be it an upgrade or an explicit "Stop the
service". In that case, there is no point in displaying an alert with an
info / error message as the user already knows that they are stopping
Firezone. In order to not fatigue the user with alerts, we exit the GUI
with a toast notification when the IPC service shuts down gracefully.
Toast notifications do not grab the users attention, allowing them to
continue what they are doing while still being notified that their
Firezone client is now disconnected.

Fixes: #6232.
2025-02-10 03:33:24 +00:00

56 lines
1.8 KiB
Rust

use anyhow::Result;
use firezone_headless_client::ipc;
// TODO: Replace with `anyhow` gradually per <https://github.com/firezone/firezone/pull/3546#discussion_r1477114789>
#[derive(Debug, thiserror::Error)]
pub enum Error {
#[error("IPC service not found")]
IpcNotFound,
#[error("IPC closed")]
IpcClosed,
#[error("IPC read failed")]
IpcRead(#[source] anyhow::Error),
#[error(transparent)]
Other(#[from] anyhow::Error),
}
impl From<ipc::Error> for Error {
fn from(value: ipc::Error) -> Self {
match value {
ipc::Error::NotFound(_) => Self::IpcNotFound,
ipc::Error::Other(error) => Self::Other(error),
}
}
}
impl Error {
// Decision to put the error strings here: <https://github.com/firezone/firezone/pull/3464#discussion_r1473608415>
// This message gets shown to users in the GUI and could be localized, unlike
// messages in the log which only need to be used for `git grep`.
pub fn user_friendly_msg(&self) -> String {
match self {
Error::IpcNotFound => {
"Couldn't find Firezone IPC service. Is the service running?".to_string()
}
Error::IpcClosed => "IPC connection closed".to_string(),
Error::IpcRead(_) => "IPC read failure".to_string(),
Error::Other(error) => error.to_string(),
}
}
}
/// Blocks the thread and shows an error dialog
///
/// Doesn't play well with async, only use this if we're bailing out of the
/// entire process.
pub fn show_error_dialog(msg: String) -> Result<()> {
// I tried the Tauri dialogs and for some reason they don't show our
// app icon.
native_dialog::MessageDialog::new()
.set_title("Firezone Error")
.set_text(&msg)
.set_type(native_dialog::MessageType::Error)
.show_alert()?;
Ok(())
}