Add autostart manager with XDG autostart support

This commit is contained in:
lashman
2026-02-27 23:45:58 +02:00
parent 730452072f
commit 9cf4f1126c
3 changed files with 98 additions and 0 deletions

View File

@@ -1744,6 +1744,16 @@ impl Database {
Ok(self.conn.last_insert_rowid())
}
// --- Autostart ---
pub fn set_autostart(&self, id: i64, enabled: bool) -> SqlResult<()> {
self.conn.execute(
"UPDATE appimages SET autostart = ?2 WHERE id = ?1",
params![id, enabled as i32],
)?;
Ok(())
}
// --- Launch statistics ---
pub fn get_top_launched(&self, limit: i32) -> SqlResult<Vec<(String, u64)>> {

View File

@@ -245,6 +245,61 @@ pub fn integrate_tracked(record: &AppImageRecord, db: &Database) -> Result<Integ
Ok(result)
}
pub fn autostart_dir() -> PathBuf {
dirs::config_dir()
.unwrap_or_else(|| PathBuf::from("/tmp"))
.join("autostart")
}
pub fn enable_autostart(db: &Database, record: &AppImageRecord) -> Result<PathBuf, String> {
let dir = autostart_dir();
fs::create_dir_all(&dir).map_err(|e| format!("Failed to create autostart dir: {}", e))?;
let app_id = record.app_name.as_deref()
.map(|n| make_app_id(n))
.unwrap_or_else(|| format!("appimage-{}", record.id));
let desktop_filename = format!("driftwood-{}.desktop", app_id);
let desktop_path = dir.join(&desktop_filename);
let app_name = record.app_name.as_deref().unwrap_or(&record.filename);
let icon = record.icon_path.as_deref().unwrap_or("application-x-executable");
let content = format!("\
[Desktop Entry]
Type=Application
Name={}
Exec=\"{}\" %U
Icon={}
X-GNOME-Autostart-enabled=true
X-Driftwood-AppImage-ID={}
", app_name, escape_exec_arg(&record.path), icon, record.id);
fs::write(&desktop_path, &content)
.map_err(|e| format!("Failed to write autostart file: {}", e))?;
db.register_modification(record.id, "autostart", &desktop_path.to_string_lossy(), None)
.map_err(|e| format!("Failed to register modification: {}", e))?;
db.set_autostart(record.id, true).ok();
Ok(desktop_path)
}
pub fn disable_autostart(db: &Database, record_id: i64) -> Result<(), String> {
let mods = db.get_modifications(record_id).unwrap_or_default();
for m in &mods {
if m.mod_type == "autostart" {
let path = Path::new(&m.file_path);
if path.exists() {
fs::remove_file(path).ok();
}
db.remove_modification(m.id).ok();
}
}
db.set_autostart(record_id, false).ok();
Ok(())
}
/// Undo all tracked system modifications for an AppImage.
pub fn undo_all_modifications(db: &Database, appimage_id: i64) -> Result<(), String> {
let mods = db.get_modifications(appimage_id)