1
//! Error types for Minion bindings.
2

            
3
use crate::ffi;
4
use thiserror::Error;
5

            
6
/// A wrapper over all errors thrown by `minion_rs`.
7
///
8
/// `Error` allows functions involving Minion to return a single error type. All error types in
9
/// `minion_rs` are able to be converted into this type using into / from.
10
#[derive(Debug, Error)]
11
pub enum MinionError {
12
    #[error("runtime error: `{0}.to_string()`")]
13
    RuntimeError(#[from] RuntimeError),
14
    #[error("not implemented: {0}")]
15
    NotImplemented(String),
16
    #[error(transparent)]
17
    Other(#[from] anyhow::Error), // source and Display delegate to anyhow::Error
18
}
19

            
20
/// RuntimeErrors are thrown by Minion during execution.
21
///
22
/// These represent internal Minion C++ exceptions translated into Rust.
23
///
24
/// Invalid usage of this library should throw an error before Minion is even run. Therefore, these
25
/// should be quite rare. Consider creating an issue on
26
/// [Github](https://github.com/conjure-cp/conjure-oxide) if these occur regularly!
27
#[derive(Debug, Error)]
28
pub enum RuntimeError {
29
    // These closely follow the ReturnCodes found in Minion's libwrapper.cpp.
30
    /// The model given to Minion is invalid.
31
    #[error("the given instance is invalid")]
32
    InvalidInstance,
33

            
34
    /// An unknown error has occurred.
35
    #[error("an unknown error has occurred while running minion")]
36
    UnknownError,
37
}
38

            
39
// Minion's ReturnCodes are passed over FFI as ints.
40
// Convert them to their appropriate error.
41
impl From<u32> for RuntimeError {
42
    fn from(return_code: u32) -> Self {
43
        match return_code {
44
            #[allow(non_upper_case_globals)]
45
            ffi::ReturnCodes_INVALID_INSTANCE => RuntimeError::InvalidInstance,
46
            _ => RuntimeError::UnknownError,
47
        }
48
    }
49
}