Skip to content

Tauri Backend API Reference

Every Tauri command listed here is a Rust function exposed to the React frontend via invoke(). The frontend sends JSON-serialized parameters over IPC; the backend returns results or errors.

import { invoke } from '@tauri-apps/api/core'
// Basic call
const result = await invoke<string>('command_name', {
param1: 'value',
param2: 123
})
// Error handling
try {
const files = await invoke<FileEntry[]>('read_workspace_files', {
workspacePath: '/path/to/workspace'
})
} catch (error) {
console.error('Command failed:', error) // error is a string
}

Rust uses snake_case parameters. Convert to camelCase when calling from JavaScript:

  • workspace_path becomes workspacePath
  • file_path becomes filePath
  • open_tabs becomes openTabs

Save the last opened workspace path for auto-loading on next launch.

fn save_last_workspace(app: AppHandle, path: String) -> Result<(), String>
ParameterTypeDescription
pathStringAbsolute path to workspace directory

On macOS, creates a security-scoped bookmark for sandbox persistence.

await invoke('save_last_workspace', {
path: '/Users/john/Documents/MyWorkspace'
})

Remove the saved workspace path from settings.

fn clear_last_workspace(app: AppHandle)
await invoke('clear_last_workspace')

Check if a path is a valid Lokus workspace or can become one.

fn validate_workspace_path(app: AppHandle, path: String) -> bool

Returns true if the path exists, is a directory, is readable, and either contains a .lokus folder or has write permissions to create one.

const isValid = await invoke<boolean>('validate_workspace_path', {
path: '/Users/john/NewWorkspace'
})

Check if a workspace path needs re-authorization (macOS sandbox). Returns true when the workspace exists but the security-scoped bookmark is stale (common after app updates).

fn check_workspace_needs_reauth(app: AppHandle, path: String) -> bool
const needsReauth = await invoke<boolean>('check_workspace_needs_reauth', {
path: '/Users/john/MyWorkspace'
})

Get the last saved workspace path, but only if it is still valid. Auto-clears invalid paths from settings.

fn get_validated_workspace_path(app: AppHandle) -> Option<String>
const path = await invoke<string | null>('get_validated_workspace_path')
if (path) {
// Load workspace
} else {
// Show launcher
}

Clear all workspace-related data including session states. Used for development reset.

fn clear_all_workspace_data(app: AppHandle)

Check if the app is running in debug mode.

fn is_development_mode() -> bool

Returns true when compiled with debug_assertions (i.e., npm run tauri dev).

Clear all workspace data and return true. Forces the launcher screen on next start.

fn force_launcher_mode(app: AppHandle) -> bool

Save the current workspace session (open tabs, expanded folders, recent files). State is stored per-workspace using a hashed path as the key.

fn save_session_state(
app: AppHandle,
workspace_path: String,
open_tabs: Vec<String>,
expanded_folders: Vec<String>,
recent_files: Vec<String>
)
await invoke('save_session_state', {
workspacePath: '/path/to/workspace',
openTabs: ['/path/file1.md', '/path/file2.md'],
expandedFolders: ['/path/folder1'],
recentFiles: ['/path/recent.md']
})

Load saved session state for a workspace.

fn load_session_state(app: AppHandle, workspace_path: String) -> Option<SessionState>

SessionState:

interface SessionState {
open_tabs: string[]
expanded_folders: string[]
recent_files: string[]
}

Get list of known workspaces. Currently returns only the last workspace.

fn get_all_workspaces(app: AppHandle) -> Vec<WorkspaceItem>

WorkspaceItem:

interface WorkspaceItem {
path: string
name: string
}
fn open_workspace_window(app: AppHandle, workspace_path: String)
fn open_preferences_window(app: AppHandle)
fn open_launcher_window(app: AppHandle)
fn sync_window_theme(app: AppHandle, payload: ThemePayload)

These create and manage the multi-window layout. sync_window_theme broadcasts theme changes across all open windows.


All file operations use absolute paths. Writes are atomic (write to .tmp file, then rename).

Recursively read the file tree of a workspace.

pub async fn read_workspace_files(workspace_path: String) -> Result<Vec<FileEntry>, String>

FileEntry:

interface FileEntry {
name: string
path: string
is_directory: boolean
size: number
created?: number
modified?: number
children?: FileEntry[]
}

Excludes .lokus, node_modules, .git, and .DS_Store. Max recursion depth: 10. Skips symlinks. Results are sorted with directories first, then alphabetically.

const files = await invoke<FileEntry[]>('read_workspace_files', {
workspacePath: '/path/to/workspace'
})

Read text content from a file.

pub async fn read_file_content(path: String) -> Result<String, String>
const content = await invoke<string>('read_file_content', {
path: '/path/to/file.md'
})

Read binary content from a file.

pub fn read_binary_file(path: String) -> Result<Vec<u8>, String>

Write text content to a file. Uses atomic writes: content is written to a .tmp file, then renamed. A .backup file is created before overwriting existing files for rollback safety.

pub fn write_file_content(path: String, content: String) -> Result<(), String>

Does NOT create version history automatically. Call save_file_version_manual separately if needed.

await invoke('write_file_content', {
path: '/path/to/file.md',
content: '# New Content\n\nHello world!'
})

Save a file version to the version history.

pub fn save_file_version_manual(path: String, content: String) -> Result<(), String>

Versions are stored in .lokus/backups/{filename}/{timestamp}.md.gz.

Create a new file in the workspace.

pub fn create_file_in_workspace(workspace_path: String, name: String) -> Result<String, String>

Returns the full path of the created file. The name can include subdirectories (e.g., notes/meeting.md).

pub fn create_folder_in_workspace(workspace_path: String, name: String) -> Result<(), String>
pub fn rename_file(path: String, new_name: String) -> Result<String, String>

Returns the new full path. Validates that the source exists, the new name is not empty, and the destination does not already exist.

pub fn move_file(source_path: String, destination_dir: String) -> Result<(), String>

Preserves the original filename. Fails if the destination already has a file with the same name.

pub fn delete_file(path: String) -> Result<(), String>

Permanent deletion (no trash/recycle bin). Recursive for directories.

Open the file or folder in the system file manager (Finder, Explorer, or default Linux file manager).

pub fn reveal_in_finder(path: String) -> Result<(), String>

Open a terminal window at the given directory.

pub fn open_terminal(path: String) -> Result<(), String>

Uses Terminal.app on macOS, cmd on Windows, and the default terminal on Linux.

pub fn read_image_file(path: String) -> Result<String, String> // Base64 encoded
pub fn path_exists(path: String) -> Result<bool, String>
pub fn is_directory(path: String) -> Result<bool, String>
pub fn read_directory(path: String) -> Result<Vec<FileEntry>, String>
pub fn write_file(path: String, content: String) -> Result<(), String>
pub fn create_directory(path: String) -> Result<(), String>
pub fn read_all_files(workspace_path: String) -> Result<Vec<FileEntry>, String>
pub fn copy_external_files_to_workspace(files: Vec<String>, workspace_path: String, target_dir: String) -> Result<Vec<String>, String>
pub fn find_workspace_images(workspace_path: String) -> Result<Vec<String>, String>

File versioning with gzip compression and diff support.

pub fn save_version(
workspace_path: String,
file_path: String,
content: String,
action: Option<String>
) -> Result<FileVersion, String>

FileVersion:

interface FileVersion {
timestamp: string
size: number
lines: number
action: string // "auto_save", "manual_save", etc.
preview: string // First few lines
}

Versions are gzip-compressed and stored in .lokus/backups/{filename}/.

pub fn get_file_versions(workspace_path: String, file_path: String) -> Result<Vec<FileVersion>, String>

Returns versions sorted newest first.

pub fn get_version_content(workspace_path: String, file_path: String, timestamp: String) -> Result<String, String>

Decompresses and returns the content of a specific version.

pub fn get_diff(
workspace_path: String,
file_path: String,
old_timestamp: String,
new_timestamp: String
) -> Result<Vec<DiffLine>, String>

DiffLine:

interface DiffLine {
line_number_old?: number
line_number_new?: number
content: string
change_type: 'add' | 'delete' | 'unchanged'
}
pub fn restore_version(workspace_path: String, file_path: String, timestamp: String) -> Result<(), String>

Creates a backup of the current content before restoring the selected version.

pub fn cleanup_old_versions(
workspace_path: String,
file_path: String,
max_versions: Option<usize>, // Default: 50
retention_days: Option<i64> // Default: 30
) -> Result<usize, String>

Returns the number of versions deleted.


Search for text across all files in a workspace.

pub async fn search_in_files(
query: String,
workspace_path: Option<String>,
options: Option<SearchOptions>
) -> Result<Vec<SearchResult>, String>

SearchOptions:

interface SearchOptions {
caseSensitive?: boolean // Default: false
wholeWord?: boolean // Default: false
regex?: boolean // Default: false
fileTypes?: string[] // Default: ['md', 'txt']
maxResults?: number // Default: 100
contextLines?: number // Default: 2
}

SearchResult:

interface SearchResult {
file: string
fileName: string
matches: SearchMatch[]
matchCount: number
}
interface SearchMatch {
line: number
column: number
text: string
match: string
context: ContextLine[]
}
interface ContextLine {
lineNumber: number
text: string
isMatch: boolean
}

Skips target/, node_modules/, .git/, dist/, build/, .cache/. Max traversal depth: 10. Regex patterns are compiled once per search.

const results = await invoke<SearchResult[]>('search_in_files', {
query: 'TODO',
workspacePath: '/path/to/workspace',
options: { caseSensitive: false, fileTypes: ['md', 'txt', 'js'] }
})

Search within a single file.

pub fn search_in_file(file_path: String, query: String, options: Option<SearchOptions>) -> Result<Vec<SearchMatch>, String>

Build a search index for faster searching. (Planned feature.)

pub fn build_search_index(workspace_path: String) -> Result<(), String>

Read file content with line numbers.

pub fn get_file_content_with_lines(file_path: String) -> Result<Vec<String>, String>

Tasks support 7 statuses: todo, in-progress, urgent, needs-info, completed, cancelled, delegated.

Task:

interface Task {
id: string
title: string
description?: string
status: 'todo' | 'in-progress' | 'urgent' | 'needs-info' | 'completed' | 'cancelled' | 'delegated'
priority: number
created_at: number
updated_at: number
note_path?: string
note_position?: number
tags: string[]
kanban_board?: string
kanban_column?: string
kanban_card_id?: string
}
pub fn create_task(
app: AppHandle,
title: String,
description: Option<String>,
note_path: Option<String>,
note_position: Option<i32>,
tags: Vec<String>
) -> Result<Task, String>
const task = await invoke<Task>('create_task', {
title: 'Review documentation',
description: 'Check all API examples',
notePath: '/workspace/project.md',
tags: ['docs', 'review']
})
pub fn get_all_tasks(app: AppHandle) -> Result<Vec<Task>, String>
pub fn get_task(app: AppHandle, task_id: String) -> Result<Task, String>
pub fn update_task(app: AppHandle, task: Task) -> Result<(), String>
pub fn delete_task(app: AppHandle, task_id: String) -> Result<(), String>
pub fn get_tasks_by_status(app: AppHandle, status: TaskStatus) -> Result<Vec<Task>, String>
pub fn get_tasks_by_note(app: AppHandle, note_path: String) -> Result<Vec<Task>, String>
pub fn bulk_update_task_status(app: AppHandle, task_ids: Vec<String>, status: TaskStatus) -> Result<(), String>
await invoke('bulk_update_task_status', {
taskIds: ['id1', 'id2', 'id3'],
status: 'completed'
})

Extract task checkboxes (- [ ] and - [x]) from markdown content.

pub fn extract_tasks_from_content(app: AppHandle, content: String, note_path: String) -> Result<Vec<Task>, String>
pub fn link_task_to_kanban(
app: AppHandle,
task_id: String,
board_path: String,
column_id: String,
card_id: String
) -> Result<(), String>

Kanban boards are stored as .kanban JSON files in the workspace.

Core types:

interface KanbanBoard {
version: string
name: string
columns: Record<string, KanbanColumn>
settings: BoardSettings
metadata: BoardMetadata
}
interface KanbanColumn {
name: string
order: number
cards: KanbanCard[]
}
interface KanbanCard {
id: string
title: string
description?: string
tags: string[]
assignee?: string
priority: string
due_date?: string
linked_notes: string[]
checklist: { text: string; completed: boolean }[]
created: string
modified: string
}
interface BoardInfo {
name: string
path: string
card_count: number
column_count: number
modified: string
}
pub fn list_kanban_boards(workspace_path: String) -> Result<Vec<BoardInfo>, String>
pub fn create_kanban_board(workspace_path: String, name: String, columns: Vec<String>) -> Result<String, String>

Returns the board file path.

const boardPath = await invoke<string>('create_kanban_board', {
workspacePath: '/workspace',
name: 'Project Tasks',
columns: ['To Do', 'In Progress', 'Review', 'Done']
})
pub fn open_kanban_board(board_path: String) -> Result<KanbanBoard, String>
pub fn save_kanban_board(board_path: String, board: KanbanBoard) -> Result<(), String>
pub fn delete_kanban_board(board_path: String) -> Result<(), String>
pub fn rename_kanban_board(board_path: String, new_name: String) -> Result<String, String>

Returns the new board file path.

pub fn add_card_to_board(board_path: String, column_id: String, card: KanbanCard) -> Result<(), String>
pub fn move_card_between_columns(board_path: String, card_id: String, from_column: String, to_column: String) -> Result<(), String>
pub fn update_card_in_board(board_path: String, column_id: String, card: KanbanCard) -> Result<(), String>
pub fn delete_card_from_board(board_path: String, column_id: String, card_id: String) -> Result<(), String>
pub fn initialize_workspace_kanban(workspace_path: String) -> Result<(), String>

Broadcast theme changes to all windows.

pub fn theme_broadcast(app: AppHandle, payload: ThemePayload)

ThemePayload:

interface ThemePayload {
tokens?: Record<string, string> // CSS vars: {"--bg": "15 23 42"}
mode?: 'light' | 'dark' | 'system'
accent?: string // Preset name or "r g b" value
scope?: 'global'
}
pub fn import_theme_file(theme_file_path: String) -> Result<ThemeManifest, String>

ThemeManifest:

interface ThemeManifest {
name: string
tokens: Record<string, string>
author?: string
description?: string
version?: string
}
pub fn validate_theme_file(theme_file_path: String) -> Result<ThemeValidationResult, String>

Required tokens: --bg, --text, --panel, --border, --muted, --accent, --accent-fg.

Recommended tokens: --task-todo, --task-progress, --task-urgent, --task-completed, --task-cancelled, --task-delegated, --danger, --success, --warning, --info, --editor-placeholder.

ThemeValidationResult:

interface ThemeValidationResult {
valid: boolean
errors: string[]
warnings: string[]
manifest?: ThemeManifest
}
pub fn export_theme(theme: ThemeManifest, export_path: String) -> Result<(), String>
pub fn delete_custom_theme(theme_name: String) -> Result<(), String>

Themes are stored in ~/.lokus/themes/.

pub fn list_custom_themes() -> Result<Vec<ThemeManifest>, String>
pub fn get_theme_tokens() -> Result<HashMap<String, String>, String>
pub fn save_theme_tokens(tokens: HashMap<String, String>) -> Result<(), String>

Still exposed (used by the v3 host):

CommandPurpose
list_pluginsScan ~/.lokus/plugins/ and return each folder’s manifest v3 + path
install_pluginInstall from a ZIP/folder/URL (validates manifest, rejects duplicates)
uninstall_pluginRemove the plugin folder and its stored settings/grants
enable_plugin / disable_pluginToggle the enabled list (keyed by manifest id)
get_enabled_pluginsThe enabled list
set_plugin_permission / get_plugin_permissionsStore/read the user-granted capabilities (the Ask Screen result)
set_plugin_setting / get_plugin_settingPer-plugin settings storage
read_plugin_fileRead a file inside a plugin folder (confined to the plugins dir)

Runtime capabilities (ui, editor, notes.*, network, overlay, …) are not IPC commands — they are RPC methods checked per call against the stored grants inside the plugin’s Worker. See Creating Plugins for the manifest and Plugin API Reference for the surface.


Sync is the encrypted Supabase-backed pipeline described in Sync & Privacy. The frontend drives it through src/core/sync/ (SyncEngine, ManifestManager, KeyManager, OfflineQueue); the Rust side provides the file primitives and storage access used by that pipeline. Earlier git-based and Iroh P2P sync prototypes were removed — there are no git_* or iroh_* commands in the current backend.


Credential Storage Commands (Desktop Only)

Section titled “Credential Storage Commands (Desktop Only)”

Credentials are stored in the OS keychain (macOS Keychain, Windows Credential Manager, Linux Secret Service).

pub fn store_git_credentials(workspace_path: String, username: String, token: String) -> Result<(), String>
pub fn retrieve_git_credentials(workspace_path: String) -> Result<Option<GitCredentials>, String>
pub fn delete_git_credentials(workspace_path: String) -> Result<(), String>
pub fn store_iroh_keys(workspace_path: String, keys: String) -> Result<(), String>
pub fn retrieve_iroh_keys(workspace_path: String) -> Result<Option<String>, String>
pub fn delete_iroh_keys(workspace_path: String) -> Result<(), String>

OAuth2 with PKCE for user authentication.

pub async fn initiate_oauth_flow(provider: String, state: State<SharedAuthState>) -> Result<String, String>

Returns an authorization URL. The flow uses PKCE, starts a localhost callback server, and exchanges the auth code for tokens.

pub async fn is_authenticated(provider: String) -> Result<bool, String>
pub async fn get_auth_token(provider: String) -> Result<Option<AuthToken>, String>
interface AuthToken {
access_token: string
refresh_token?: string
expires_at?: number
user_id?: string
token_type: string
}
pub async fn get_user_profile(provider: String) -> Result<UserProfile, String>
interface UserProfile {
id: string
email: string
name: string
avatar_url?: string
}
pub async fn refresh_auth_token(provider: String) -> Result<AuthToken, String>
pub async fn logout(provider: String) -> Result<(), String>
pub async fn open_auth_url(url: String) -> Result<(), String>

pub fn clipboard_write_text(text: String) -> Result<(), String>
pub fn clipboard_read_text() -> Result<String, String>
pub fn clipboard_write_html(html: String) -> Result<(), String>
pub fn clipboard_read_html() -> Result<String, String>
pub fn clipboard_has_text() -> Result<bool, String>
pub fn clipboard_clear() -> Result<(), String>
pub fn clipboard_write_text_enhanced(text: String) -> Result<(), String>
pub fn clipboard_read_text_enhanced() -> Result<String, String>
pub fn clipboard_write_html_enhanced(html: String) -> Result<(), String>
pub fn clipboard_get_content_info() -> Result<ClipboardContentInfo, String>
pub fn clipboard_get_platform_info() -> Result<PlatformClipboardInfo, String>
pub fn clipboard_get_usage_tips() -> Result<Vec<String>, String>
pub fn clipboard_clear_enhanced() -> Result<(), String>

Model Context Protocol server for AI assistant integration.

pub fn mcp_start(manager: State<MCPServerManager>, port: Option<u16>) -> Result<MCPServerStatus, String>

Default port: 3456.

interface MCPServerStatus {
is_running: boolean
port: number
pid?: number
url?: string
last_error?: string
}
pub fn mcp_stop(manager: State<MCPServerManager>) -> Result<MCPServerStatus, String>
pub fn mcp_restart(manager: State<MCPServerManager>, port: Option<u16>) -> Result<MCPServerStatus, String>
pub fn mcp_status(manager: State<MCPServerManager>) -> Result<MCPServerStatus, String>
pub async fn mcp_health_check(manager: State<MCPServerManager>) -> Result<bool, String>
pub async fn setup_mcp_integration() -> Result<(), String>
pub async fn check_mcp_status() -> Result<MCPSetupStatus, String>
pub async fn restart_mcp_server() -> Result<(), String>
pub fn api_set_workspace(workspace_path: String) -> Result<(), String>
pub fn api_clear_workspace() -> Result<(), String>
pub fn api_get_current_workspace() -> Result<Option<String>, String>

pub fn get_system_information() -> PlatformInfo
pub fn check_platform_feature_support(feature: String) -> bool
pub fn get_platform_capabilities() -> PlatformCapabilities
pub fn platform_reveal_in_file_manager(path: String) -> Result<(), String>
pub fn platform_open_terminal(path: String) -> Result<(), String>
pub fn get_platform_information() -> PlatformInfo

All commands return Result<T, String>. Errors are plain strings describing what went wrong:

"File or folder '/path' does not exist"
"Failed to read file: permission denied"
"Task with id abc123 not found"
"Parent directory does not exist: /invalid/path"

Wrap every invoke() call in try/catch to handle errors gracefully.


  • Path validation prevents directory traversal attacks
  • Workspace boundaries restrict file operations to workspace directories
  • Plugin permissions gate access to filesystem, network, and clipboard
  • OS keychain stores tokens and credentials (macOS Keychain, Windows Credential Manager, Linux Secret Service)
  • Atomic writes prevent data corruption during saves