Project Management & Workspaces
Relevant source files
The following files were used as context for generating this wiki page:
The Project Management and Workspace system in Keynobi provides a robust registry for Android/Gradle projects, enabling developers to manage multiple codebases efficiently. Rather than serving as a full IDE, Keynobi acts as a companion that maintains a multi-project registry, allowing users to switch between workspaces while preserving build variants and device selections for each.
The system handles project discovery, Gradle root detection, and session restoration. It persists project metadata in a local registry, allowing for features like project pinning, custom naming, and quick access via a dedicated sidebar or a welcome panel for recent projects.
Sources: README.md:14-16, src/components/projects/WelcomePanel.tsx:10-14
Architecture and Data Flow
The project management system follows a client-server architecture using Tauri's IPC mechanism. The Rust backend handles filesystem operations and persistent storage in settings.json, while the SolidJS frontend manages the reactive UI state and user interactions.
Project Registry Lifecycle
When a user opens a folder, the backend validates the directory, detects the Gradle root, and generates a unique deterministic ID based on the path. This project is then "upserted" into the recent projects list, which is capped at 50 entries by default, evicting the oldest non-pinned entries as needed.
The diagram shows the flow of opening a new project and persisting it within the system registry.
Sources: src-tauri/src/commands/file_system.rs:72-132, src/lib/tauri-api.ts:16-24
Core Components
Project Sidebar
The ProjectSidebar serves as the primary navigation hub. It supports two states: expanded (showing project names, avatars, and shortened paths) and collapsed (showing only avatars). It allows users to:
- Switch active projects.
- Rename projects for display purposes (without altering the disk folder).
- Remove projects from the registry.
- Add new projects via a filesystem dialog.
Sources: src/components/projects/ProjectSidebar.tsx:10-24, src/components/projects/ProjectSidebar.tsx:300-350
Welcome Panel
Shown when no project is active, the WelcomePanel provides a central "Open Project Folder" action and a list of up to 8 recent projects for quick restoration.
Sources: src/components/projects/WelcomePanel.tsx:55-100
Project Info Editor
A specialized modal for viewing and modifying Android-specific metadata. It interacts directly with the project's build.gradle or build.gradle.kts files to read and update:
applicationId(Read-only)versionNameversionCode
Sources: src/components/projects/ProjectInfoEditor.tsx:32-60, src-tauri/src/commands/file_system.rs:242-265
Backend Services and Persistence
The backend maintains the ProjectEntry structure, which tracks the project's state across sessions.
Data Structures
| Field | Type | Description |
|---|---|---|
id | String | Deterministic hex ID generated from the absolute path. |
path | String | Absolute path to the project directory. |
name | String | Display name of the project. |
gradle_root | Option<String> | Path where gradlew was detected. |
last_opened | String | RFC3339 timestamp of the last access. |
pinned | Boolean | If true, prevents automatic eviction from the registry. |
last_build_variant | Option<String> | The last selected Gradle build variant. |
last_device | Option<String> | The last targeted device serial. |
Sources: src-tauri/src/commands/file_system.rs:21-41, src/lib/tauri-api.ts:40-48
Gradle Root Detection
Keynobi differentiates between the "Workspace Root" (the folder opened by the user) and the "Gradle Root" (where the build system resides). The fs_manager scans the directory structure to find gradlew. If found, it is used for all subsequent Gradle tasks; otherwise, the workspace root is treated as the project root.
Sequence diagram depicting the detection of Gradle roots and canonicalization of paths.
Sources: src-tauri/src/commands/file_system.rs:92-115, src/lib/tauri-api.ts:25-30
Project Information Management
Keynobi implements atomic writes for updating project files. When a user updates the versionName or versionCode via the ProjectInfoEditor, the backend:
- Reads the current
build.gradle(.kts)content. - Uses regex to find and replace values.
- Writes the updated content to a temporary file (
.gradle.tmp). - Renames the temporary file to the original path to ensure atomicity.
Sources: src-tauri/src/commands/file_system.rs:282-307, src-tauri/src/commands/file_system.rs:312-340
Keyboard Shortcuts for Project Management
| Shortcut | Action | Description |
|---|---|---|
Cmd + O | Open Folder | Opens the system dialog to add/open a project. |
Cmd + B | Toggle Project Sidebar | Shows or hides the left-hand project registry. |
Cmd + Shift + P | Command Palette | Access "Project App Info" and other project actions. |
Sources: src/App.tsx:94-100, src/App.tsx:165-175, README.md:270-285
Conclusion
The Project Management and Workspace system in Keynobi provides a lightweight yet powerful way to organize Android development environments. By decoupling the display name from the physical directory and providing features like pinning and deterministic IDs, it ensures a stable and customizable workflow that persists across application restarts.
Sources: src/components/projects/ProjectSidebar.tsx:10-15, src-tauri/src/commands/file_system.rs:188-200