Slipstream Plugin Integration/Interface#3190
Conversation
0341a32 to
b77006b
Compare
There was a problem hiding this comment.
Pull request overview
Adds a Slipstream plugin system to stream canonical mapping updates and staking rewards to external services via dynamically loaded plugins, avoiding RPC-based polling.
Changes:
- Introduces new plugin interface + plugin manager crates (dynamic loading via
libloading, JSON5 config parsing). - Wires canonical-finalize lifecycle signaling into the VM + finalize store so storage writes can fan out events to plugins.
- Extends
ledger/storefeature flags to include the plugin manager dependency forhistoryandhistory-staking-rewards.
Reviewed changes
Copilot reviewed 13 out of 14 changed files in this pull request and generated 16 comments.
Show a summary per file
| File | Description |
|---|---|
| utilities/src/bytes.rs | Minor refactor using is_multiple_of(8) for clarity. |
| synthesizer/src/vm/finalize.rs | Sets/reset canonical-finalize mode flag; emits staking reward notifications; some whitespace-only edits. |
| ledger/store/src/program/finalize.rs | Adds finalize-mode flag + plugin manager installation; notifies plugins on mapping updates and staking rewards. |
| ledger/store/Cargo.toml | history* features now pull in slipstream plugin manager. |
| plugins/slipstream_plugin_interface/src/slipstream_plugin_interface.rs | Defines the SlipstreamPlugin trait and callback surface. |
| plugins/slipstream_plugin_interface/src/lib.rs | Exposes the interface module. |
| plugins/slipstream_plugin_interface/README.md | Documents plugin config and library export convention. |
| plugins/slipstream_plugin_interface/Cargo.toml | New crate manifest for the interface. |
| plugins/slipstream_plugin_manager/src/slipstream_manager.rs | Implements plugin loading/unloading + fan-out notification logic + tests. |
| plugins/slipstream_plugin_manager/src/slipstream_service.rs | Adds a small service wrapper around the manager. |
| plugins/slipstream_plugin_manager/src/lib.rs | Module exports for manager/service. |
| plugins/slipstream_plugin_manager/Cargo.toml | New crate manifest for the manager. |
| Cargo.toml | Adds the new plugin crates to the workspace and workspace dependencies. |
| Cargo.lock | Adds transitive deps (e.g., json5, pest*) and the new crates. |
adf0c33 to
77faa25
Compare
7fb6b76 to
933fbf9
Compare
vicsn
left a comment
There was a problem hiding this comment.
Mostly LGTM! Few questions
iamalwaysuncomfortable
left a comment
There was a problem hiding this comment.
One question and one change requested
Question: Serialization Formats
If we use to_bytes_le() that ensures all consumers must have SnarkVM onboard to deserialize it downstream anywhere which ensures indexers can only work in JS or Rust. Most chain indexing services who might be interested in Aleo data will prefer gRPC or JSON. If we make this current choice we should be lucid that we'll have to serve this transformed data formats from slipstream consumers to most other 3rd parties (unless they decide they want to use SnarkVM, but most people won't want to do this).
That makes it such that for most external parties the flow will be:
SnarkVM --> Slipstream Plugin --> gRPC/JSON --> 3rd party consumer
Most people won't do this:
SnarkVM --> 3rd party slipstream impl
This is fine, but let's make sure we're confidently making this choice.
Changes
The slipstream interface trait shouldn't have a method per datastream, the data should be encapsulated with an enum and just publish that. Trait implementors can then handle that enum at their own callsite.
deb96c7 to
afd430a
Compare
|
@dgrkotsonis are all comments addressed? Can you request new reviews via github if they are? Or if there's too much back and forth organize a videocall with reviewers so we don't let this grow stale. I'll merge once they approve |
…gation to slipstream plugin manager
03b9871 to
8c526ce
Compare
Overview
Introduces a plugin framework for streaming canonical finalize events out of snarkVM to external consumers via dynamically loaded shared libraries. This enables downstream services (e.g., explorer backends) to receive real-time mapping updates and staking rewards at block finalization time.
Related PRs/Repos:
New Crates
plugins/slipstream_plugin_interfaceDefines:
SlipstreamPlugintrait — trait all plugins must implement. Contains on_load(), on_unload(), subscribed_events(), on_broadcast() (see below)BroadcastEventenum — MappingUpdate and StakingReward variants carrying little-endian serialized byte slicesBroadcastEventKind— used for subscription opt-in checkson_load/on_unloadon_broadcastsubscribed_eventsplugins/slipstream_plugin_managerManages loaded plugins and their backing
libloading::Libraryhandles.LoadedSlipstreamPlugin— wrapper holding a boxed plugin + its name; implementsDeref/DerefMutSlipstreamPluginManagerfrom_config_files()- takes a vec of paths to plugin config files (JSON5) and loads them into the manager via libloadingunload()— fireson_unload()on each plugin then drops the librarieshas_subscribers()— aggregate opt-in checksbroadcast()— fan-out broadcast to all interested pluginslist_plugins()- return the names of all loaded pluginsCore runtime integration (gated behind --features slipstream-plugins)
ledger/store/src/program/finalize.rs FinalizeStore now has three Arc-wrapped fields shared across all store clones:
update_key_value()andreplace_mapping()serialize their arguments before the storage call and fan-outMappingUpdateevents to subscribed plugins after each successful write. Serialization is skipped entirely when is_finalize_mode is false or has_subscribers() returns false.notify_staking_reward()broadcastsStakingRewardevents with the same finalize-mode guard.synthesizer/src/vm/finalize.rs
Design notes
Plugin Config File (JSON5)
Each plugin requires a config file:
Plugin Library Convention
The shared library (
.so/.dylib/.dll) must export a C function:Startup
SlipstreamPluginManager::from_config_files()takes a slice of config file paths and returns a manager object: