snarkvm_slipstream_plugin_interface/slipstream_plugin_interface.rs
1// Copyright (c) 2019-2026 Provable Inc.
2// This file is part of the snarkVM library.
3
4// Licensed under the Apache License, Version 2.0 (the "License");
5// you may not use this file except in compliance with the License.
6// You may obtain a copy of the License at:
7
8// http://www.apache.org/licenses/LICENSE-2.0
9
10// Unless required by applicable law or agreed to in writing, software
11// distributed under the License is distributed on an "AS IS" BASIS,
12// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13// See the License for the specific language governing permissions and
14// limitations under the License.
15
16use anyhow::Result;
17use std::any::Any;
18
19/// Discriminant-only companion to [`BroadcastEvent`], used by
20/// [`SlipstreamPlugin::subscribed_events`] to declare which event types a plugin
21/// wishes to receive without carrying data payloads.
22#[derive(Copy, Clone, Debug, PartialEq, Eq)]
23pub enum BroadcastEventKind {
24 /// Mapping key-value update during canonical finalize.
25 MappingUpdate,
26 /// Staking reward distribution during canonical finalize.
27 StakingReward,
28}
29
30/// A single event dispatched to plugins via [`SlipstreamPlugin::on_broadcast`].
31///
32/// All `&[u8]` fields carry little-endian byte representations of the
33/// corresponding snarkVM console types (serialized via `ToBytes`).
34///
35/// Derives `Copy` — every field is `Copy` (`&[u8]`, `u32`, `u64`) — so the
36/// same value can be passed to multiple plugins in a dispatch loop without cloning.
37#[derive(Copy, Clone, Debug)]
38pub enum BroadcastEvent<'a> {
39 /// A mapping key-value pair was inserted or updated during canonical finalize.
40 MappingUpdate { program_id: &'a [u8], mapping_name: &'a [u8], key: &'a [u8], value: &'a [u8], block_height: u32 },
41 /// A staking reward was distributed to a staker during canonical finalize.
42 StakingReward { staker: &'a [u8], validator: &'a [u8], reward: u64, new_stake: u64, block_height: u32 },
43}
44
45impl BroadcastEvent<'_> {
46 /// Returns the discriminant of this event.
47 pub fn kind(&self) -> BroadcastEventKind {
48 match self {
49 BroadcastEvent::MappingUpdate { .. } => BroadcastEventKind::MappingUpdate,
50 BroadcastEvent::StakingReward { .. } => BroadcastEventKind::StakingReward,
51 }
52 }
53}
54
55/// The interface for Aleo Slipstream plugins. A plugin must implement
56/// the `SlipstreamPlugin` trait to work with the runtime. In addition,
57/// the dynamic library must export a `C` function `_create_plugin` that
58/// creates the implementation of the plugin.
59pub trait SlipstreamPlugin: Any + Send + Sync + std::fmt::Debug {
60 /// Returns the name of the plugin.
61 fn name(&self) -> &'static str;
62
63 /// The callback called when a plugin is loaded by the system, used for
64 /// doing whatever initialization is required by the plugin. The
65 /// `_config_file` contains the name of the config file (JSON format) with
66 /// a `libpath` field indicating the full path of the shared library.
67 fn on_load(&mut self, _config_file: &str, _is_reload: bool) -> Result<()> {
68 Ok(())
69 }
70
71 /// The callback called right before a plugin is unloaded by the system.
72 /// Used for doing cleanup before unload.
73 fn on_unload(&mut self) {}
74
75 /// Returns the event kinds this plugin subscribes to.
76 ///
77 /// The manager checks this before serializing and dispatching each event,
78 /// so plugins that return an empty slice pay no serialization cost. Defaults
79 /// to no subscriptions.
80 fn subscribed_events(&self) -> &[BroadcastEventKind] {
81 &[]
82 }
83
84 /// Receives a single broadcast event from the plugin manager.
85 ///
86 /// Only invoked when the event's kind appears in [`subscribed_events`].
87 fn on_broadcast(&self, _event: BroadcastEvent<'_>) -> Result<()> {
88 Ok(())
89 }
90}