Skip to main content

datex_core/dif/
interface.rs

1use crate::{
2    dif::{
3        reference::DIFReference,
4        r#type::DIFTypeDefinition,
5        update::DIFUpdateData,
6        value::{DIFReferenceNotFoundError, DIFValueContainer},
7    },
8    references::{
9        observers::{ObserveOptions, ObserverError, TransceiverId},
10        reference::{
11            AccessError, AssignmentError, ReferenceCreationError,
12            ReferenceMutability, TypeError,
13        },
14    },
15    runtime::execution::ExecutionError,
16    values::pointer::PointerAddress,
17};
18use core::{fmt::Display, result::Result};
19
20use crate::prelude::*;
21#[derive(Debug)]
22pub enum DIFObserveError {
23    ReferenceNotFound,
24    ObserveError(ObserverError),
25}
26impl From<ObserverError> for DIFObserveError {
27    fn from(err: ObserverError) -> Self {
28        DIFObserveError::ObserveError(err)
29    }
30}
31impl Display for DIFObserveError {
32    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
33        match self {
34            DIFObserveError::ReferenceNotFound => {
35                core::write!(f, "Reference not found")
36            }
37            DIFObserveError::ObserveError(e) => {
38                core::write!(f, "Observe error: {}", e)
39            }
40        }
41    }
42}
43
44#[derive(Debug)]
45pub enum DIFUpdateError {
46    ReferenceNotFound,
47    InvalidUpdate,
48    AccessError(AccessError),
49    AssignmentError(AssignmentError),
50    TypeError(Box<TypeError>),
51}
52
53impl From<DIFReferenceNotFoundError> for DIFUpdateError {
54    fn from(_: DIFReferenceNotFoundError) -> Self {
55        DIFUpdateError::ReferenceNotFound
56    }
57}
58impl From<AccessError> for DIFUpdateError {
59    fn from(err: AccessError) -> Self {
60        DIFUpdateError::AccessError(err)
61    }
62}
63impl From<AssignmentError> for DIFUpdateError {
64    fn from(err: AssignmentError) -> Self {
65        DIFUpdateError::AssignmentError(err)
66    }
67}
68impl From<TypeError> for DIFUpdateError {
69    fn from(err: TypeError) -> Self {
70        DIFUpdateError::TypeError(Box::new(err))
71    }
72}
73
74impl Display for DIFUpdateError {
75    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
76        match self {
77            DIFUpdateError::ReferenceNotFound => {
78                core::write!(f, "Reference not found")
79            }
80            DIFUpdateError::InvalidUpdate => {
81                core::write!(f, "Invalid update operation")
82            }
83            DIFUpdateError::AccessError(e) => {
84                core::write!(f, "Access error: {}", e)
85            }
86            DIFUpdateError::AssignmentError(e) => {
87                core::write!(f, "Assignment error: {}", e)
88            }
89            DIFUpdateError::TypeError(e) => {
90                core::write!(f, "Type error: {}", e)
91            }
92        }
93    }
94}
95
96#[derive(Debug)]
97pub enum DIFApplyError {
98    ExecutionError(ExecutionError),
99    ReferenceNotFound,
100}
101impl Display for DIFApplyError {
102    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
103        match self {
104            DIFApplyError::ExecutionError(e) => {
105                core::write!(f, "Execution error: {}", e)
106            }
107            DIFApplyError::ReferenceNotFound => {
108                core::write!(f, "Reference not found")
109            }
110        }
111    }
112}
113
114#[derive(Debug)]
115pub enum DIFCreatePointerError {
116    ReferenceNotFound,
117    ReferenceCreationError(ReferenceCreationError),
118}
119
120impl From<DIFReferenceNotFoundError> for DIFCreatePointerError {
121    fn from(_: DIFReferenceNotFoundError) -> Self {
122        DIFCreatePointerError::ReferenceNotFound
123    }
124}
125
126impl Display for DIFCreatePointerError {
127    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
128        match self {
129            DIFCreatePointerError::ReferenceNotFound => {
130                core::write!(f, "Reference not found")
131            }
132            DIFCreatePointerError::ReferenceCreationError(e) => {
133                core::write!(f, "Reference from value container error: {}", e)
134            }
135        }
136    }
137}
138
139#[derive(Debug)]
140pub enum DIFResolveReferenceError {
141    ReferenceNotFound,
142}
143impl Display for DIFResolveReferenceError {
144    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
145        match self {
146            DIFResolveReferenceError::ReferenceNotFound => {
147                core::write!(f, "Reference not found")
148            }
149        }
150    }
151}
152
153impl From<ReferenceCreationError> for DIFCreatePointerError {
154    fn from(err: ReferenceCreationError) -> Self {
155        DIFCreatePointerError::ReferenceCreationError(err)
156    }
157}
158
159pub trait DIFInterface {
160    /// Applies a DIF update to the value at the given pointer address.
161    fn update(
162        &self,
163        source_id: TransceiverId,
164        address: PointerAddress,
165        update: &DIFUpdateData,
166    ) -> Result<(), DIFUpdateError>;
167
168    /// Executes an apply operation, applying the `value` to the `callee`.
169    fn apply(
170        &self,
171        callee: DIFValueContainer,
172        value: DIFValueContainer,
173    ) -> Result<DIFValueContainer, DIFApplyError>;
174
175    /// Creates a new pointer and stores it in memory.
176    /// Returns the address of the newly created pointer.
177    fn create_pointer(
178        &self,
179        value: DIFValueContainer,
180        allowed_type: Option<DIFTypeDefinition>,
181        mutability: ReferenceMutability,
182    ) -> Result<PointerAddress, DIFCreatePointerError>;
183
184    /// Resolves a pointer address of a pointer that may not be in memory.
185    /// If the pointer is not in memory, it will be loaded from external storage.
186    fn resolve_pointer_address_external(
187        &self,
188        address: PointerAddress,
189    ) -> impl Future<Output = Result<DIFReference, DIFResolveReferenceError>>;
190
191    /// Resolves a pointer address of a pointer that is currently in memory.
192    /// Returns an error if the pointer is not found in memory.
193    fn resolve_pointer_address_in_memory(
194        &self,
195        address: PointerAddress,
196    ) -> Result<DIFReference, DIFResolveReferenceError>;
197
198    /// Starts observing changes to the pointer at the given address.
199    /// As long as the pointer is observed, it will not be garbage collected.
200    fn observe_pointer(
201        &self,
202        transceiver_id: TransceiverId,
203        address: PointerAddress,
204        options: ObserveOptions,
205        observer: impl Fn(&DIFUpdateData, TransceiverId) + 'static,
206    ) -> Result<u32, DIFObserveError>;
207
208    /// Updates the options for an existing observer on the pointer at the given address.
209    /// If the observer does not exist, an error is returned.
210    fn update_observer_options(
211        &self,
212        address: PointerAddress,
213        observer_id: u32,
214        options: ObserveOptions,
215    ) -> Result<(), DIFObserveError>;
216
217    /// Stops observing changes to the pointer at the given address.
218    /// If no other references to the pointer exist, it may be garbage collected after this call.
219    fn unobserve_pointer(
220        &self,
221        address: PointerAddress,
222        observer_id: u32,
223    ) -> Result<(), DIFObserveError>;
224}