A modular, secure plugin system for Tauri applications running on Windows. This system allows dynamic loading and unloading of plugins with a comprehensive permission system, providing a robust foundation for extending your Tauri applications.
- Dynamic Loading: Load and unload plugins at runtime
- Security-First Design: Comprehensive permission system for controlled plugin access
- ZIP Package Format: Simple plugin distribution format with manifest validation
- C ABI Interface: Compatible interface for plugins written in various languages
- UI Integration: Seamless integration with Tauri's UI through commands and events
- Cross-Language Support: Primary support for Rust plugins with potential for other languages
The plugin system consists of five main components:
- Plugin Loader: Handles loading plugin packages, extracting ZIP files, and validating manifests
- Plugin Host: Defines interfaces for plugin execution and lifecycle management
- Permission System: Manages plugin permissions with validation and user prompting
- Plugin Manager: Coordinates plugin lifecycle operations (install, load, enable, disable, uninstall)
- UI Integration: Integrates with Tauri UI via commands and events
Add the plugin system to your Tauri application's dependencies:
[dependencies]
tauri-windows-plugin-system = "0.1.0"use std::sync::Arc;
use std::path::PathBuf;
use tauri::{App, Manager};
use tauri_windows_plugin_system::
permission_system::PermissionSystem,
plugin_manager::PluginManager,
ui_integration;
fn main() {
tauri::Builder::default()
.setup(|app| {
// Setup paths
let app_dir = app.path_resolver().app_data_dir().unwrap();
let plugins_dir = app_dir.join("plugins");
let registry_path = app_dir.join("plugin_registry.json");
let permissions_path = app_dir.join("plugin_permissions.json");
// Create permission system
let permission_system = Arc::new(PermissionSystem::new());
permission_system.load_permissions(&permissions_path)
.unwrap_or_else(|e| eprintln!("Failed to load permissions: {}", e));
// Create plugin manager
let plugin_manager = Arc::new(
PluginManager::new(plugins_dir, registry_path, permission_system.clone())
.expect("Failed to create plugin manager")
);
// Setup UI integration
ui_integration::setup(app, plugin_manager, permission_system)?;
Ok(())
})
.invoke_handler(tauri::generate_handler![
ui_integration::install_plugin_from_file,
ui_integration::install_plugin_from_url,
ui_integration::get_all_plugins,
ui_integration::get_plugin,
ui_integration::enable_plugin,
ui_integration::disable_plugin,
ui_integration::uninstall_plugin,
ui_integration::update_plugin,
ui_integration::trigger_plugin_event,
])
.run(tauri::generate_context!())
.expect("error while running tauri application");
}import { invoke } from '@tauri-apps/api/tauri';
import { listen } from '@tauri-apps/api/event';
// Install a plugin
async function installPlugin(path: string) {
try {
const pluginInfo = await invoke('install_plugin_from_file', { path });
console.log(`Installed plugin: ${pluginInfo.name}`);
return pluginInfo;
} catch (error) {
console.error(`Failed to install plugin: ${error}`);
throw error;
}
}
// Enable a plugin
async function enablePlugin(pluginId: string) {
try {
await invoke('enable_plugin', { pluginId });
console.log(`Enabled plugin: ${pluginId}`);
} catch (error) {
console.error(`Failed to enable plugin: ${error}`);
throw error;
}
}
// Listen for plugin events
function setupPluginEventListeners() {
// Plugin installed
listen('plugin-installed', (event) => {
console.log(`Plugin installed: ${event.payload.plugin.name}`);
});
// Plugin status changed
listen('plugin-status-changed', (event) => {
console.log(`Plugin ${event.payload.plugin_id} status changed to: ${event.payload.status}`);
});
// Plugin uninstalled
listen('plugin-uninstalled', (event) => {
console.log(`Plugin uninstalled: ${event.payload.plugin_id}`);
});
}See the Developer Guide for detailed instructions on creating plugins for the Tauri Windows Plugin System.
A plugin package is a ZIP file with the following structure:
plugin.zip
├── plugin.json # Plugin manifest
├── plugin.dll # Plugin binary
└── resources/ # Optional plugin resources
The plugin.json file contains metadata about the plugin:
{
"name": "my_plugin",
"version": "0.1.0",
"entry": "plugin.dll",
"api_version": "1.0.0",
"permissions": [
{
"type": "file_system",
"read": true,
"write": false,
"paths": ["data/"]
}
],
"description": "My first Tauri plugin",
"author": "Your Name",
"homepage": "https://example.com"
}The permission system ensures that plugins can only access resources they explicitly request and that the user approves. Permissions are categorized into four types:
- File System: Access to read/write files in specific directories
- Network: Access to connect to specific web addresses
- UI: Ability to show notifications or create windows
- System: Access to system information or resources like clipboard
- API Reference: Detailed API documentation
- Developer Guide: Guide for plugin developers
- User Guide: Guide for end users
Check out the examples in the examples/ directory:
demo-app: A sample Tauri application that uses the plugin systemsample-plugin: A simple plugin that demonstrates the basic features
Contributions are welcome! Please feel free to submit a Pull Request.
This project is licensed under the MIT License - see the LICENSE file for details.