oasis_runtime_sdk/event.rs
1//! Event types for runtimes.
2use std::collections::BTreeMap;
3
4use oasis_core_runtime::transaction::tags::{Tag, Tags};
5
6/// An event emitted by the runtime.
7///
8/// This trait can be derived:
9/// ```
10/// # #[cfg(feature = "oasis-runtime-sdk-macros")]
11/// # mod example {
12/// # use oasis_runtime_sdk_macros::Event;
13/// const MODULE_NAME: &str = "my-module";
14/// #[derive(Clone, Debug, cbor::Encode, Event)]
15/// #[cbor(untagged)]
16/// #[sdk_event(autonumber)] // `module_name` meta is required if `MODULE_NAME` isn't in scope
17/// enum MyEvent {
18/// Greeting(String), // autonumbered to 0
19/// #[sdk_event(code = 2)] // manually numbered to 2 (`code` is required if not autonumbering)
20/// DontPanic,
21/// Salutation { // autonumbered to 1
22/// plural: bool,
23/// }
24/// }
25/// # }
26/// ```
27pub trait Event: Sized + cbor::Encode {
28 /// Name of the module that emitted the event.
29 fn module_name() -> &'static str;
30
31 /// Code uniquely identifying the event.
32 fn code(&self) -> u32;
33
34 /// Converts an event into an event tag.
35 ///
36 /// # Key
37 ///
38 /// ```text
39 /// <module (variable size bytes)> <code (big-endian u32)>
40 /// ```
41 ///
42 /// # Value
43 ///
44 /// CBOR-serialized event value.
45 ///
46 fn into_event_tag(self) -> EventTag {
47 etag_for_event(Self::module_name(), self.code(), cbor::to_value(self))
48 }
49}
50
51impl Event for () {
52 fn module_name() -> &'static str {
53 "(none)"
54 }
55
56 fn code(&self) -> u32 {
57 Default::default()
58 }
59}
60
61/// Generate an EventTag corresponding to the passed event triple.
62pub fn etag_for_event(module_name: &str, code: u32, value: cbor::Value) -> EventTag {
63 EventTag {
64 key: [module_name.as_bytes(), &code.to_be_bytes()]
65 .concat()
66 .to_vec(),
67 value,
68 }
69}
70
71/// A key-value pair representing an emitted event that will be emitted as a tag.
72#[derive(Clone, Debug)]
73pub struct EventTag {
74 pub key: Vec<u8>,
75 pub value: cbor::Value,
76}
77
78/// Event tags with values accumulated by key.
79pub type EventTags = BTreeMap<Vec<u8>, Vec<cbor::Value>>;
80
81/// Provides method for converting event tags into events.
82pub trait IntoTags {
83 fn into_tags(self) -> Tags;
84}
85
86impl IntoTags for EventTags {
87 fn into_tags(self) -> Tags {
88 self.into_iter()
89 .map(|(k, v)| Tag::new(k, cbor::to_vec(v)))
90 .collect()
91 }
92}