Expand description
Config-file driven plugin loader for cordis-rs.
This crate is the assembly half of porting upstream Cordis’ loader: it
connects cordis-include’s entry trees to cordis fibers. Everything a
config-driven cordis application needs is re-exported here — depend on
cordis-loader alone.
§How it works
- Static registry (
PluginRegistry) replaces upstream’s dynamicimport(name): register plugins at startup, entries resolve by name. Thegroupbuiltin is pre-registered. - Startup:
Loader::openreads the entry file (writinginitialwhen missing), builds theEntryTree, and starts every enabled entry — group entries ascordis_group::Groupfibers, children beneath their parent group’s context, so disposing a group cascades. - Config: entries carry a
cordis_include::Nodeconfig (never()); loader plugins read it viaconfig.downcast::<Node>().${{ env.X }}templates expand at hand-off time; the file keeps the raw text. - Reload (
Loader::reload, wired to thewatchfeature): re-read the file, diff the tree, and reconcile fibers — created entries start, removed subtrees stop, moved entries restart under their new parent, config-only changes patch in place viaFiber::update_value. - Inject: an entry’s
injectlist is merged into the plugin’s own declaration, so the core fiber machinery reconciles entries when services come and go — “hot-swapped service restarts its dependents” for free. - Self-kill vs. removal: a fiber that reaches
Disposedoutside loader operation was killed by its own plugin; the loader persistsdisabled: truefor that entry. Removing an entry from the file just stops it. - Write-back:
Loader::update_configis the runtime entry point — it updates the fiber and persists the config. Reloads never echo back (file-level suspend).
§Example
use cordis_loader::{Loader, LoaderConfig, PluginRegistry};
let root = cordis::Context::new();
let mut registry = PluginRegistry::new();
// registry.register_plugin(my_plugin); // your plugins, by name
let config = LoaderConfig::new("cordis.yml").with_registry(registry);
let loader = Loader::open(&root, config)?;Register the plugins first (the group builtin is pre-registered), then
open; plugins registered later via Loader::register_plugin are picked
up by the next Loader::reload.
§Not in scope yet
The import entry kind (mounting a sub-file), isolate/service
migration, the loader/entry-init-style event family, and debounced
merged writes are future work.
Re-exports§
pub use error::LoaderError;pub use error::Result;pub use loader::Loader;pub use loader::LoaderConfig;pub use loader::LoaderHandle;pub use registry::PluginRegistry;
Modules§
- error
- Error type combining core and include failures.
- loader
- The loader: entry tree ⇄ fiber lifecycle, file reloads, write-back.
- registry
- Static plugin registry — the Rust replacement for upstream’s dynamic
import(name).
Structs§
- Document
- The parsed content of one config file: the entry list plus any unknown top-level keys, which are preserved on write-back.
- Entry
- A live entry in an
crate::EntryTree. - Entry
Options - One entry in a config file: a plugin instance plus its group position.
- Entry
Tree - An in-memory tree of
Entrys mirroring one config file. - Group
- Nesting marker plugin for group entries.
- Loader
File - A handle to one config file on disk.
Enums§
- Node
- A dynamically typed value that round-trips through YAML and JSON while preserving object key order.