Skip to content

Hot-Reload of OpenClaw Plugins #4

Description

@joshuajbouw

Context

Follows from #2. During plugin development, the edit → compile → reload cycle is tedious. A file watcher can auto-detect source changes, recompile, and hot-reload plugins without daemon restart.

Design

Watch Directories

  1. .astralis/plugins/src/ — workspace-level source directory
  2. ~/.config/astralis/plugins/src/ — user-level source directory (if exists)
  3. Any directories specified in config

Watch Flow

Source file change detected (FSEvents/inotify)
  → Debounce (500ms — avoid recompiling on every keystroke)
  → Compute blake3 hash of source
  → Check compilation cache (#22)
    → Cache hit: skip compilation
    → Cache miss: compile via openclaw-bridge pipeline
  → On success:
    → Copy compiled output to plugin directory
    → Unload old plugin from registry
    → Load new plugin
    → Emit event (for CLI/frontend to show)
  → On failure:
    → Log compilation errors
    → Emit error event
    → Keep old version loaded

Implementation Options

Library Pros Cons
notify (crate) Pure Rust, well-maintained, cross-platform Extra dependency
Raw FSEvents/inotify No extra deps Platform-specific code

Recommendation: Use notify crate. It's the standard choice and handles debouncing, recursive watching, and cross-platform differences.

Integration with Daemon

The watcher runs as a background task inside the daemon process:

pub struct PluginWatcher {
    watcher: notify::RecommendedWatcher,
    cache: CompilationCache,
    registry: Arc<Mutex<PluginRegistry>>,
}

Dev Mode

Only active when the daemon is running with --dev or --watch-plugins flag. Production deployments should not auto-recompile.

Security Note

The file watcher only operates on designated source directories. It does NOT watch arbitrary paths. Compiled WASM still goes through the full security pipeline (hash verification, capability check, sandbox).

Steelman: When NOT to Build This

Recommendation: Phase 2 priority. Nice-to-have for developer experience but not critical path.

Dependencies

  • notify crate

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions