Plugin Development Overview
Getting started with Orbis plugin development
What Are Plugins?
Plugins are self-contained modules that extend Orbis functionality. They can:
- Add new pages to the application
- Define custom API routes
- Execute backend logic in WASM
- Store and retrieve data
- Communicate with other plugins
Plugin Types
1. Manifest-Only Plugins
The simplest plugin type. Just a manifest file defining UI pages:
my-plugin/
└── manifest.json Best for:
- Dashboard pages
- Static content
- Simple interactive UIs
- Prototyping
2. WASM Plugins
Full-featured plugins with backend execution:
my-plugin/
├── manifest.json
├── Cargo.toml
├── src/lib.rs
└── target/wasm32-unknown-unknown/release/my_plugin.wasm Best for:
- Complex business logic
- Data processing
- External API integration
- Custom algorithms
Quick Start
Orbis supports two types of plugins:
- Manifest-only plugins - Pure UI with no server logic (simple dashboards, reports)
- WASM plugins - Full-featured with server-side logic using the Orbis SDK
Option 1: Minimal Manifest Plugin
For simple UI-only plugins, create plugins/hello/manifest.json:
{
"name": "hello",
"version": "1.0.0",
"description": "Hello World plugin",
"pages": [
{
"route": "/hello",
"title": "Hello World",
"icon": "Hand",
"sections": [
{
"type": "Container",
"className": "p-6",
"children": [
{
"type": "Heading",
"level": 1,
"text": "Hello, World!"
},
{
"type": "Text",
"content": "This is my first Orbis plugin."
}
]
}
]
}
]
} Option 2: WASM Plugin with SDK
For plugins with server logic, API routes, state management, etc., use the Orbis SDK:
1. Create Project:
cargo new --lib my-plugin
cd my-plugin 2. Add Dependencies (Cargo.toml):
[package]
name = "my-plugin"
version = "1.0.0"
edition = "2021"
[lib]
crate-type = ["cdylib"]
[dependencies]
orbis-plugin-api = { path = "../../crates/orbis-plugin-api" }
serde = { version = "1.0", features = ["derive"] }
serde_json = "1.0"
[profile.release]
opt-level = "s"
lto = true 3. Write Plugin (src/lib.rs):
use orbis_plugin_api::sdk::prelude::*;
use serde_json::json;
orbis_plugin!();
pub fn get_greeting_impl(ctx: Context) -> Result<Response> {
let name = ctx.query_param("name").unwrap_or("World");
Ok(Response::json(&json!({
"message": format!("Hello, {}!", name)
})))
}
wrap_handler!(get_greeting, get_greeting_impl); 4. Create Manifest:
{
"name": "my-plugin",
"version": "1.0.0",
"wasm_entry": "my_plugin.wasm",
"routes": [
{ "path": "/greeting", "handler": "get_greeting" }
],
"pages": [
{
"route": "/my-plugin",
"title": "My Plugin",
"sections": [
{
"type": "Container",
"children": [
{ "type": "Text", "content": "{{state.message}}" }
]
}
]
}
]
} 5. Build:
cargo build --target wasm32-unknown-unknown --release
# Output: target/wasm32-unknown-unknown/release/my_plugin.wasm See the WASM Plugins guide for the complete SDK reference.
That’s it! Place it in the plugins/ directory and restart Orbis.
Plugin File Structure
Recommended Structure
my-plugin/
├── manifest.json # Required: plugin metadata and config
├── README.md # Recommended: documentation
├── CHANGELOG.md # Recommended: version history
│
├── src/ # WASM plugin source (if applicable)
│ └── lib.rs
├── Cargo.toml # WASM plugin dependencies
│
├── assets/ # Static assets (optional)
│ ├── icon.svg
│ └── styles.css
│
└── tests/ # Plugin tests (optional)
└── integration.rs Development Workflow
1. Create Plugin Directory
mkdir -p plugins/my-plugin
cd plugins/my-plugin 2. Write Manifest
Create manifest.json with your plugin configuration.
3. Test Iteratively
Run Orbis in development mode for hot reload:
cd orbis
bun run tauri dev Changes to manifest files are picked up automatically.
4. Add WASM (Optional)
If you need backend logic:
cargo init --lib
# Edit Cargo.toml for WASM target
cargo build --target wasm32-unknown-unknown --release 5. Build for Distribution
Package your plugin:
# As a ZIP
zip -r my-plugin.zip manifest.json my_plugin.wasm
# Or with embedded manifest
python3 add_custom_section.py my_plugin.wasm -s manifest < manifest.json Key Concepts
Pages
Pages are the UI entry points. Each page has:
- A unique route in the application
- Its own state store
- A layout defined by component schemas
See Page Definitions.
State
Each page has reactive state that drives the UI:
{
"state": {
"count": { "type": "number", "default": 0 }
}
} State is accessed via expressions: {{state.count}}
Actions
Actions respond to user events:
{
"events": {
"on_click": [
{ "type": "update_state", "path": "count", "from": "{{state.count + 1}}" }
]
}
} Components
35+ built-in components for building UIs:
- Layout: Container, Flex, Grid
- Typography: Text, Heading
- Forms: Form, Field
- Data: Table, List, Card
- Navigation: Button, Link, Tabs
- And more…
Example Plugins
Counter Plugin
{
"name": "counter",
"version": "1.0.0",
"pages": [
{
"route": "/counter",
"title": "Counter",
"icon": "Hash",
"state": {
"count": { "type": "number", "default": 0 }
},
"sections": [
{
"type": "Flex",
"direction": "column",
"align": "center",
"gap": "1rem",
"className": "p-6",
"children": [
{
"type": "Heading",
"level": 1,
"text": "Count: {{state.count}}"
},
{
"type": "Flex",
"gap": "0.5rem",
"children": [
{
"type": "Button",
"label": "-",
"variant": "outline",
"events": {
"on_click": [
{ "type": "update_state", "path": "count", "from": "{{state.count - 1}}" }
]
}
},
{
"type": "Button",
"label": "+",
"events": {
"on_click": [
{ "type": "update_state", "path": "count", "from": "{{state.count + 1}}" }
]
}
}
]
},
{
"type": "Button",
"label": "Reset",
"variant": "ghost",
"events": {
"on_click": [
{ "type": "update_state", "path": "count", "value": 0 }
]
}
}
]
}
]
}
]
} Todo List Plugin
See the full example in the repository.
Next Steps
- Manifest Reference - Complete manifest documentation
- WASM Plugins - Creating plugins with Rust
- Page Definitions - Defining UI pages
- Building Plugins - Build and distribution
- Best Practices - Guidelines and patterns
On This Page
- What Are Plugins?
- Plugin Types
- 1. Manifest-Only Plugins
- 2. WASM Plugins
- Quick Start
- Option 1: Minimal Manifest Plugin
- Option 2: WASM Plugin with SDK
- Plugin File Structure
- Recommended Structure
- Development Workflow
- 1. Create Plugin Directory
- 2. Write Manifest
- 3. Test Iteratively
- 4. Add WASM (Optional)
- 5. Build for Distribution
- Key Concepts
- Pages
- State
- Actions
- Components
- Example Plugins
- Counter Plugin
- Todo List Plugin
- Next Steps