AkurAI Build
Menu

Public repository / 2d36cd6c72fc6a63a7edb87bb54a4020e50f2f8a

AkurAI-Drive / desktop/README.md

Latest change 2d36cd6c72fc6a63a7edb87bb54a4020e50f2f8a - desktop: Tauri v2 tray + Google-Drive-style file browser app by olibuijr

# AkurAI Drive — desktop app

A KDE-tray, Google-Drive-style desktop file browser for **AkurAI Drive** storage,
built with **Tauri v2**. It reuses the existing native sync client
(`../client`, crate `akurai-drive-sync`) as a library — same auth, same API
client, same bidirectional sync engine — and wraps it in a single dark-themed
window plus a system-tray icon.

Target: Linux / KDE Plasma 6 (EndeavourOS/Arch), `webkit2gtk-4.1`.

## What it does

- **Tray-first.** The window starts hidden and lives in the system tray. Closing
  the window hides it back to the tray (it does not quit). Left-click the tray
  toggles the window; the tray menu has **Open AkurAI Drive · Sync now · Open
  folder · Status: <idle/syncing/error> · Quit**.
- **Sign in with AkurAI.** Uses the client's device-token loopback flow (opens
  the system browser to `<api>/auth/device`, captures `?token=`, stores it via
  the shared config at `~/.config/akurai-drive/config.toml`).
- **Browse, upload, download, organise.** Folders-first file browser per prefix
  (synthesised from S3 key prefixes), drag-and-drop upload anywhere on the
  window, an Upload button (native picker), New folder, rename, delete, grid/list
  views, sort, and per-folder search.
- **Background sync.** Once a folder + bucket + token are set, a background task
  runs the same debounced (2 s) + polled (30 s) bidirectional sync as the CLI
  daemon, pushing `sync-status` events to the UI and updating the tray.
- **Single instance.** Launching a second copy focuses the existing window.

## Layout

```
desktop/
├── ui/                      # static, no-build frontend (vanilla HTML/CSS/JS)
│   ├── index.html
│   ├── app.css
│   └── app.js
├── src-tauri/
│   ├── Cargo.toml
│   ├── build.rs
│   ├── tauri.conf.json      # frontendDist = ../ui, empty before* commands, tray window
│   ├── capabilities/default.json
│   ├── icons/               # brand hexagon mark (SVG + rasterised PNG/ICO + tray.png)
│   └── src/
│       ├── main.rs          # builder, plugins, tray, window-hide, background loop
│       ├── commands.rs      # Tauri commands (wrap the lib)
│       ├── sync.rs          # SyncManager + background sync loop
│       ├── tray.rs          # tray icon, menu, window show/hide
│       └── logging.rs       # tracing → stdout + log file
├── akurai-drive.desktop
├── install.sh
└── README.md
```

The app depends on the sync client via `akurai-drive-sync = { path = "../../client" }`.

## Build

```sh
cd src-tauri
cargo build            # debug — must compile cleanly
cargo build --release  # optimised binary
```

System deps (already present on the target): `webkit2gtk-4.1`, `libsoup-3.0`,
`javascriptcoregtk-4.1`. The tray uses libappindicator at runtime (dlopened).

Override the backend with `AKURAI_DRIVE_API` (default
`https://akurai-drive.olibuijr.com`).

## Install (per-user)

```sh
./install.sh
```

Builds release, copies the binary to `~/.local/bin/akurai-drive`, installs the
`.desktop` launcher + icons, and adds an autostart entry so it launches to the
tray on login.

> If app/taskbar grouping looks off on your DE, check the window class with
> `xprop WM_CLASS` on the running window and set `StartupWMClass` in
> `akurai-drive.desktop` to match.

## Logs (screenshot-free diagnosis)

Everything is logged to **stdout and a file**:

```
${XDG_STATE_HOME:-~/.local/state}/akurai-drive/desktop.log
```

Verbosity comes from `RUST_LOG` (default `info,akurai_drive=debug`). Logged:
app startup + resolved config (api/folder/bucket, logged-in y/n), every command
invocation (name + args, never the token), every backend call
(`METHOD path → status + duration`), every presigned S3 PUT/GET (key → status),
every sync action (`↑ ↓ ⊘` key), tray events, window show/hide, and every error
with full context. The webview mirrors its console (and `window.onerror` /
`unhandledrejection`) into the same file via the `log_frontend` command — so a
report like "the file list is blank" is fully diagnosable from `desktop.log`.