Skip to content

Commit

Permalink
Finish trireme client docs
Browse files Browse the repository at this point in the history
  • Loading branch information
MitchTurner committed Oct 15, 2023
1 parent 4cbe21f commit 522caf6
Show file tree
Hide file tree
Showing 10 changed files with 83 additions and 0 deletions.
1 change: 1 addition & 0 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,4 +28,5 @@ pub mod transaction;

/// Types and helpers for working with the Trireme CLI
pub mod trireme_ledger_client;
/// Values module
pub mod values;
13 changes: 13 additions & 0 deletions src/trireme_ledger_client.rs
Original file line number Diff line number Diff line change
Expand Up @@ -441,7 +441,9 @@ impl ClientConfig {

/// Variants of Secret Phrase [`Keys`] impl
pub enum SecretPhraseKeys {
/// Raw secret phrase
RawSecretPhraseKeys(RawSecretPhraseKeys),
/// Password-protected secret phrase
PasswordProtectedPhraseKeys(PasswordProtectedPhraseKeys<TerminalPasswordUpfront>),
}

Expand All @@ -462,6 +464,7 @@ impl Keys for SecretPhraseKeys {
}
}

/// Client for interacting with the Ledger via Trireme
enum InnerClient<Datum, Redeemer>
where
Datum: PlutusDataInterop
Expand All @@ -473,8 +476,11 @@ where
+ TryFrom<PlutusData>,
Redeemer: PlutusDataInterop,
{
/// BlockFrost client
BlockFrost(CMLLedgerCLient<BlockFrostLedger, SecretPhraseKeys, Datum, Redeemer>),
/// Ogmios + Scrolls client
OgmiosScrolls(CMLLedgerCLient<OgmiosScrollsLedger, SecretPhraseKeys, Datum, Redeemer>),
/// Test client
Mocked(TestLedgerClient<Datum, Redeemer, LocalPersistedStorage<PathBuf, Datum>>),
}

Expand Down Expand Up @@ -506,6 +512,7 @@ where
+ TryFrom<PlutusData>,
Redeemer: PlutusDataInterop,
{
/// Get current time within context of current ledger
pub async fn current_time(&self) -> LedgerClientResult<i64> {
match &self.inner_client {
InnerClient::BlockFrost(_cml_client) => Err(LedgerClientError::CurrentTime(Box::new(
Expand All @@ -518,6 +525,9 @@ where
}
}

/// Advance time for current context.
///
/// **NOTE:** This is only implemented for the test client.
pub async fn advance_blocks(&self, count: i64) -> LedgerClientResult<()> {
match &self.inner_client {
InnerClient::BlockFrost(_cml_client) => Err(LedgerClientError::CurrentTime(Box::new(
Expand Down Expand Up @@ -621,12 +631,14 @@ where
}
}

#[allow(missing_docs)]
#[derive(Debug, Error)]
pub enum TomlError {
#[error("No config directory for raw phrase file: {0:?}")]
NoParentDir(String),
}

/// Write a TOML-serializable struct to a file
pub async fn write_toml_struct_to_file<Toml: ser::Serialize>(
file_path: &PathBuf,
toml_struct: &Toml,
Expand All @@ -652,6 +664,7 @@ pub async fn write_toml_struct_to_file<Toml: ser::Serialize>(
Ok(())
}

/// Read a TOML-serializable struct from a TOML file
pub async fn read_toml_struct_from_file<Toml: DeserializeOwned>(
file_path: &PathBuf,
) -> Result<Option<Toml>> {
Expand Down
30 changes: 30 additions & 0 deletions src/trireme_ledger_client/cml_client.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ pub mod plutus_data_interop;
mod tests;

// TODO: Add minimum ADA https://github.com/MitchTurner/naumachia/issues/41
/// Basic implementation of the [`LedgerClient`] that uses `cardano-multiplatform-lib` under the hood
pub struct CMLLedgerCLient<L, K, Datum, Redeemer>
where
L: Ledger,
Expand All @@ -72,9 +73,12 @@ where
_redeemer: PhantomData<Redeemer>,
}

/// Interface for providing keys to the [`CMLLedgerCLient`]
#[async_trait]
pub trait Keys {
/// Get the base address for signer
async fn base_addr(&self) -> Result<BaseAddress>;
/// Get the private key for signer
async fn private_key(&self) -> Result<PrivateKey>;
}

Expand All @@ -84,6 +88,7 @@ fn addr_from_bech_32(addr: &str) -> Result<CMLAddress> {
Ok(cml_address)
}

/// Local representation of a UTxO
#[derive(Debug)]
pub struct UTxO {
tx_hash: TransactionHash,
Expand All @@ -93,6 +98,7 @@ pub struct UTxO {
}

impl UTxO {
/// Constructor for the [`UTxO`]
pub fn new(
tx_hash: TransactionHash,
output_index: BigNum,
Expand All @@ -107,39 +113,50 @@ impl UTxO {
}
}

/// Get the transaction hash
pub fn tx_hash(&self) -> &TransactionHash {
&self.tx_hash
}

/// Get the output index
pub fn output_index(&self) -> BigNum {
self.output_index
}

/// Get the amount
pub fn amount(&self) -> &CMLValue {
&self.amount
}

/// Get the datum attached to the `UTxO`
pub fn datum(&self) -> &Option<PlutusData> {
&self.datum
}
}

/// Cost of execution for a transaction
#[derive(Debug)]
pub struct ExecutionCost {
execution_type: ExecutionType,
memory: u64,
steps: u64,
}

/// Type of execution
#[derive(Clone, Debug)]
pub enum ExecutionType {
/// Spending a script UTxO
Spend,
/// Minting new tokens
Mint,
///
Certificate,
/// Withdrawing from stake pool
Withdrawal,
}

impl ExecutionCost {
/// Constructor for the [`ExecutionCost`] with `Spend` type
pub fn new_spend(memory: u64, steps: u64) -> Self {
let execution_type = ExecutionType::Spend;
ExecutionCost {
Expand All @@ -149,6 +166,7 @@ impl ExecutionCost {
}
}

/// Constructor for the [`ExecutionCost`] with `Mint` type
pub fn new_mint(memory: u64, steps: u64) -> Self {
let execution_type = ExecutionType::Mint;
ExecutionCost {
Expand All @@ -158,6 +176,7 @@ impl ExecutionCost {
}
}

/// Constructor for the [`ExecutionCost`] with `Certificate` type
pub fn new_certificate(memory: u64, steps: u64) -> Self {
let execution_type = ExecutionType::Certificate;
ExecutionCost {
Expand All @@ -167,6 +186,7 @@ impl ExecutionCost {
}
}

/// Constructor for the [`ExecutionCost`] with `Withdrawal` type
pub fn new_withdrawal(memory: u64, steps: u64) -> Self {
let execution_type = ExecutionType::Withdrawal;
ExecutionCost {
Expand All @@ -176,24 +196,33 @@ impl ExecutionCost {
}
}

/// Getter for the execution type
pub fn execution_type(&self) -> ExecutionType {
self.execution_type.clone()
}

/// Getter for the memory cost
pub fn memory(&self) -> u64 {
self.memory
}
/// Getter for the step cost
pub fn steps(&self) -> u64 {
self.steps
}
}

/// Interface for providing a ledger to the [`CMLLedgerCLient`]
#[async_trait]
pub trait Ledger {
/// Get the last block time in seconds
async fn last_block_time_secs(&self) -> Result<i64>;
/// Get the UTxOs for an address
async fn get_utxos_for_addr(&self, addr: &CMLAddress, count: usize) -> Result<Vec<UTxO>>;
/// Get all the UTxOs for an address
async fn get_all_utxos_for_addr(&self, addr: &CMLAddress) -> Result<Vec<UTxO>>;
/// Calculate the execution units for a transaction
async fn calculate_ex_units(&self, tx: &CMLTransaction) -> Result<HashMap<u64, ExecutionCost>>;
/// Submit a transaction
async fn submit_transaction(&self, tx: &CMLTransaction) -> Result<String>;
}

Expand All @@ -204,6 +233,7 @@ where
D: PlutusDataInterop,
R: PlutusDataInterop,
{
/// Constructor for the [`CMLLedgerCLient`] struct
pub fn new(ledger: L, keys: K, network_settings: NetworkSettings) -> Self {
CMLLedgerCLient {
ledger,
Expand Down
4 changes: 4 additions & 0 deletions src/trireme_ledger_client/cml_client/key_manager.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,14 @@ use cardano_multiplatform_lib::{
use std::{fs, path::Path};
use thiserror::Error;

/// Standard implementation of the [`Keys`] trait
pub struct KeyManager {
config_path: String,
network: u8,
}

impl KeyManager {
/// Constructor for the [`KeyManager`] struct
pub fn new(config_path: String, network: u8) -> Self {
KeyManager {
config_path,
Expand All @@ -22,6 +24,7 @@ impl KeyManager {
}
}

#[allow(missing_docs)]
#[derive(Debug, Error)]
pub enum KeyManagerError {
#[error("Some non-StdError 🤮 error from Bip32 lib: {0:?}")]
Expand Down Expand Up @@ -69,6 +72,7 @@ impl KeyManager {
}
}

/// Loads the phrase from the config file
pub fn load_phrase_from_file(config_path: &str) -> String {
let path = Path::new(config_path);
let text = fs::read_to_string(path).unwrap();
Expand Down
8 changes: 8 additions & 0 deletions src/trireme_ledger_client/cml_client/network_settings.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use crate::trireme_ledger_client::Network;

/// Network Settings
#[derive(Debug, Clone, Copy)]
pub struct NetworkSettings {
network: u8,
Expand All @@ -9,6 +10,7 @@ pub struct NetworkSettings {
}

impl NetworkSettings {
/// Constructor for the [`NetworkSettings`] struct
pub fn new(
network: u8,
slot_length: i64,
Expand All @@ -23,28 +25,34 @@ impl NetworkSettings {
}
}

/// Getter for the network
pub fn network(&self) -> u8 {
self.network
}

/// Getter for the slot length
pub fn slot_length(&self) -> i64 {
self.slot_length
}

/// Getter for the starting slot time
pub fn starting_slot_time(&self) -> i64 {
self.starting_slot_time
}

/// Getter for the starting slot number
pub fn starting_slot_number(&self) -> u64 {
self.starting_slot_number
}

/// Converts a POSIX timestamp to a slot number
pub fn slot_from_posix(&self, posix: i64) -> Option<u64> {
let time_s = posix.checked_sub(self.starting_slot_time())?;
let abs_slot = (time_s / self.slot_length()) as u64 + self.starting_slot_number();
Some(abs_slot)
}

/// Converts a slot number to a POSIX timestamp
pub fn posix_from_slot(&self, slot: u64) -> i64 {
let slot = slot;
let time_s = (slot - self.starting_slot_number()) as i64 * self.slot_length();
Expand Down
3 changes: 3 additions & 0 deletions src/trireme_ledger_client/cml_client/ogmios_scrolls_ledger.rs
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ fn plutus_data_from_scroll_datum(datum: &str) -> Result<Option<PlutusData>> {
Ok(PlutusData::from_bytes(bytes).ok())
}

/// Implementation of the [`Ledger`] trait for the Ogmios + Scrolls client
pub struct OgmiosScrollsLedger {
scrolls_client: ScrollsClient,
ogmios_client: OgmiosClient,
Expand All @@ -80,6 +81,7 @@ pub struct OgmiosScrollsLedger {
}

impl OgmiosScrollsLedger {
/// Constructor for the [`OgmiosScrollsLedger`] struct
pub fn new(
scrolls_client: ScrollsClient,
ogmios_client: OgmiosClient,
Expand All @@ -92,6 +94,7 @@ impl OgmiosScrollsLedger {
}
}

/// Get the UTxOs for an address
pub async fn get_utxos(&self, addr: &CMLAddress) -> Result<Vec<UTxO>> {
let address_str = addr
.to_bech32(None)
Expand Down
6 changes: 6 additions & 0 deletions src/trireme_ledger_client/cml_client/plutus_data_interop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,21 @@ use cardano_multiplatform_lib::{
};
use std::collections::BTreeMap;

#[allow(missing_docs)]
pub enum PlutusDataInteropError {
CannotDeserializeFromPlutusData(PlutusData),
}

#[allow(missing_docs)]
pub type Result<T, E = PlutusDataInteropError> = std::result::Result<T, E>;

/// Trait for converting between [`PlutusData`] and the `CMLPlutusData`
pub trait PlutusDataInterop: Sized {
/// The error type
type Error;
/// Convert into a `CMLPlutusData`
fn to_plutus_data(&self) -> CMLPlutusData;
/// Convert from a `CMLPlutusData`
fn from_plutus_data(plutus_data: &CMLPlutusData) -> Result<Self, Self::Error>;
}

Expand Down
Loading

0 comments on commit 522caf6

Please sign in to comment.