2 Commits
Author SHA1 Message Date
Lucas RayanandClaude Sonnet 5 21eb4eafae chore(release): bump version to 1.3.4
Release / Create release (push) Successful in 6s
CI / Format and clippy (push) Successful in 22s
CI / Dependency audit (push) Successful in 10s
CI / Check desktop app (Linux) (push) Successful in 1m22s
Release / CLI (linux-x86_64) (push) Successful in 1m45s
CI / Tests (Linux) (push) Successful in 4m7s
Release / CLI (linux-aarch64) (push) Successful in 2m36s
Release / Desktop app (linux-x86_64) (push) Successful in 4m58s
Release / Desktop app (windows) (push) Successful in 3m44s
Release / Desktop app (linux-aarch64) (push) Successful in 8m31s
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VAyr8d7HuAdUGB6aA5xmDD
2026-10-31 08:08:55 -03:00
Lucas RayanandClaude Sonnet 5 5ecf40056f fix(gui): hide the window until elevation is resolved, not after
The window used to be visible from launch, so the unprivileged
instance's normal window would show, flash while pkexec/osascript
asked for the admin password, and only then get replaced by the
elevated relaunch's window once it killed this one ~1.2s later — the
same mechanism Sabiá already uses under the hood, but with Sabiá's
window visible throughout too; Guará's heavier initial UI made the
unprivileged flash far more noticeable.

tauri.conf.json now starts the window with "visible": false. main.rs
shows it explicitly in exactly one of three cases: already elevated
(or non-unix, where the OS-level UAC manifest already elevated the
process before it started), the relaunch failed and the user needs to
see the warning, or this is the already-elevated relaunched instance
itself. Only one window is ever shown to the user now.

Also fixes a latent bug this surfaced: do_relaunch_elevated only
emitted "elevate-failed" from the child-process-exited-nonzero path.
If it fails earlier (pkexec/osascript missing, exe path unresolved,
log file unwritable) it returns Err directly without emitting
anything — with the window now starting hidden, that would have left
it hidden forever with no feedback. The setup() closure now emits the
same event on that early-Err path too.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VAyr8d7HuAdUGB6aA5xmDD
2026-10-31 08:07:57 -03:00
8 changed files with 51 additions and 12 deletions

No files matched your search

+5
View File
@@ -4,6 +4,11 @@
Format based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/); versions follow SemVer.
## [1.3.4] - 2026-10-31
### Fixed
- **Desktop app: only one window on startup.** The main window used to be visible from launch, so the unprivileged instance's normal window would show, flash while the system asked for the administrator password, and only then get replaced by the elevated relaunch's window a moment later. The window now stays hidden until elevation is resolved — either already elevated, elevation failed (the window then shows the warning), or this is the already-elevated relaunched instance — so only one window ever appears, matching Sabiá.
## [1.3.3] - 2026-10-30
Unified updater architecture with Sabiá: migrated from the signed `tauri-plugin-updater` to direct Gitea Releases API checking and self-updating with SHA-256 verification.
+5
View File
@@ -4,6 +4,11 @@
Formato baseado em [Keep a Changelog](https://keepachangelog.com/pt-BR/1.1.0/); versões seguem SemVer.
## [1.3.4] - 2026-10-31
### Corrigido
- **App desktop: só uma janela na abertura.** A janela principal ficava visível desde o lançamento, então a instância sem privilégio mostrava a janela normal, piscava enquanto o sistema pedia a senha de administrador, e só depois era substituída pela janela da instância já elevada. Agora a janela fica escondida até a elevação ser resolvida — já elevada, falhou (a janela aí mostra o aviso), ou é a própria instância já relançada como administrador — então só uma janela aparece, igual ao Sabiá.
## [1.3.3] - 2026-10-30
Arquitetura de atualizador unificada com o Sabiá: migração do `tauri-plugin-updater` assinado para consulta direta à API de Releases do Gitea e autoatualização com verificação de SHA-256.
Generated
+2 -2
View File
@@ -416,7 +416,7 @@ dependencies = [
[[package]]
name = "guara-cli"
version = "1.3.3"
version = "1.3.4"
dependencies = [
"clap",
"ctrlc",
@@ -429,7 +429,7 @@ dependencies = [
[[package]]
name = "guara-core"
version = "1.3.3"
version = "1.3.4"
dependencies = [
"aes",
"argon2",
+1 -1
View File
@@ -3,7 +3,7 @@ resolver = "2"
members = ["crates/guara-core", "crates/guara-cli"]
[workspace.package]
version = "1.3.3"
version = "1.3.4"
edition = "2021"
license = "MIT OR Apache-2.0"
repository = "https://git.lucasrguerra.dev.br/lucasrguerra/guara"
+2 -2
View File
@@ -1342,7 +1342,7 @@ dependencies = [
[[package]]
name = "guara-core"
version = "1.3.3"
version = "1.3.4"
dependencies = [
"aes",
"argon2",
@@ -1373,7 +1373,7 @@ dependencies = [
[[package]]
name = "guara-gui"
version = "1.3.3"
version = "1.3.4"
dependencies = [
"guara-core",
"libc",
+1 -1
View File
@@ -3,7 +3,7 @@
[package]
name = "guara-gui"
description = "Guará: graphical file recovery interface"
version = "1.3.3"
version = "1.3.4"
edition = "2021"
license = "MIT OR Apache-2.0"
authors = ["Guará contributors"]
+32 -4
View File
@@ -247,6 +247,7 @@ fn main() {
std::thread::spawn(move || responder.respond(serve_file(&eng, &request)));
})
.setup(|app| {
use tauri::{Listener, Manager};
// When launched elevated by the unprivileged instance, terminate the old process.
#[cfg(unix)]
if let Some(pid) = std::env::var("GUARA_REPLACE_PID")
@@ -264,15 +265,42 @@ fn main() {
});
}
// Reading raw disks requires root: request elevation as soon as the app launches,
// without waiting for the user to look for a button. If authorization fails,
// the window stays open and the UI displays a warning.
// The window starts hidden (tauri.conf.json: "visible": false) so the
// unprivileged instance never flashes on screen before being replaced.
// Reading raw disks requires root: request elevation as soon as the app
// launches, without waiting for the user to look for a button, and only
// show a window once we know which one it is — the elevated relaunch's,
// or this same one if elevation turned out not to be needed/possible.
#[cfg(any(target_os = "linux", target_os = "macos"))]
{
if unsafe { libc::geteuid() != 0 } && std::env::var("GUARA_REPLACE_PID").is_err() {
use tauri::Emitter;
let handle = app.handle().clone();
let handle_for_failure = app.handle().clone();
std::thread::spawn(move || {
let _ = do_relaunch_elevated(handle);
// do_relaunch_elevated only emits "elevate-failed" itself once the
// child process has actually spawned and later exits non-zero. If it
// fails earlier (pkexec/osascript missing, exe path unresolved, log
// file unwritable), it returns Err directly without emitting anything
// — emit it here too, or the hidden window would never reappear.
if let Err(e) = do_relaunch_elevated(handle) {
let _ = handle_for_failure.emit("elevate-failed", e);
}
});
// Whichever path emits it, make sure the window comes back so the
// user sees the warning instead of a silently stuck, invisible app.
if let Some(win) = app.get_webview_window("main") {
app.handle().listen("elevate-failed", move |_| {
let _ = win.show();
});
}
} else if let Some(win) = app.get_webview_window("main") {
let _ = win.show();
}
}
#[cfg(not(any(target_os = "linux", target_os = "macos")))]
if let Some(win) = app.get_webview_window("main") {
let _ = win.show();
}
Ok(())
})
+3 -2
View File
@@ -1,7 +1,7 @@
{
"$schema": "https://schema.tauri.app/config/2",
"productName": "Guará",
"version": "1.3.3",
"version": "1.3.4",
"identifier": "dev.guara.app",
"build": {
"frontendDist": "../ui"
@@ -15,7 +15,8 @@
"height": 780,
"minWidth": 420,
"minHeight": 560,
"resizable": true
"resizable": true,
"visible": false
}
],
"security": {