use anyhow::Context;
use borderless_id_types::{cid_prefix, BlockIdentifier, TxIdentifier, Uuid};
use super::{BlockCtx, Sink, TxCtx};
use crate::common::Participant;
use crate::{
BorderlessId, ContractId,
__private::{
read_field, read_register,
registers::{REGISTER_BLOCK_CTX, REGISTER_TX_CTX, REGISTER_WRITER},
storage_keys::*,
},
common::{Description, Metadata},
};
pub fn is_contract() -> bool {
let id: Uuid = read_field(BASE_KEY_METADATA, META_SUB_KEY_ID).expect("id not in metadata");
cid_prefix(id.as_bytes())
}
pub fn contract_id() -> ContractId {
read_field(BASE_KEY_METADATA, META_SUB_KEY_ID).expect("contract-id not in metadata")
}
pub fn participants() -> Vec<Participant> {
read_field(BASE_KEY_METADATA, META_SUB_KEY_PARTICIPANTS).expect("participants not in metadata")
}
pub fn participant(alias: impl AsRef<str>) -> crate::Result<BorderlessId> {
participants()
.into_iter()
.find(|p| p.alias.eq_ignore_ascii_case(alias.as_ref()))
.map(|p| p.id)
.with_context(|| format!("failed to find participant with alias '{}'", alias.as_ref()))
}
pub fn sinks() -> Vec<Sink> {
read_field(BASE_KEY_METADATA, META_SUB_KEY_SINKS).expect("sinks not in metadata")
}
pub fn sink(alias: impl AsRef<str>) -> crate::Result<Sink> {
sinks()
.into_iter()
.find(|s| s.has_alias(alias.as_ref()))
.with_context(|| format!("failed to find sink with alias '{}'", alias.as_ref()))
}
pub fn sink_id(alias: impl AsRef<str>) -> crate::Result<ContractId> {
sink(alias).map(|s| s.contract_id)
}
pub fn desc() -> Description {
read_field(BASE_KEY_METADATA, META_SUB_KEY_DESC).expect("description not in metadata")
}
pub fn meta() -> Metadata {
read_field(BASE_KEY_METADATA, META_SUB_KEY_META).expect("meta not in metadata")
}
pub fn writer() -> BorderlessId {
let bytes = read_register(REGISTER_WRITER).expect("caller not present");
BorderlessId::from_bytes(bytes.try_into().expect("caller must be a borderless-id"))
}
pub fn writer_roles() -> Vec<String> {
let writer = writer();
let participants = participants();
participants
.into_iter()
.filter(|p| p.id == writer)
.flat_map(|p| p.roles)
.collect()
}
pub fn tx_ctx() -> TxCtx {
let bytes = read_register(REGISTER_TX_CTX).expect("tx-id not present");
TxCtx::from_bytes(&bytes).expect("invalid data-model in tx-id register")
}
pub fn tx_id() -> TxIdentifier {
let bytes = read_register(REGISTER_TX_CTX).expect("tx-id not present");
TxCtx::from_bytes(&bytes)
.expect("invalid data-model in tx-id register")
.tx_id
}
pub fn tx_index() -> u64 {
let bytes = read_register(REGISTER_TX_CTX).expect("tx-id not present");
TxCtx::from_bytes(&bytes)
.expect("invalid data-model in tx-id register")
.index
}
pub fn block_ctx() -> BlockCtx {
let bytes = read_register(REGISTER_BLOCK_CTX).expect("block-id not present");
BlockCtx::from_bytes(&bytes).expect("invalid data-model in block-ctx register")
}
pub fn block_id() -> BlockIdentifier {
let bytes = read_register(REGISTER_BLOCK_CTX).expect("block-id not present");
BlockCtx::from_bytes(&bytes)
.expect("invalid data-model in block-ctx register")
.block_id
}
pub fn block_timestamp() -> u64 {
let bytes = read_register(REGISTER_BLOCK_CTX).expect("block-timestamp not present");
BlockCtx::from_bytes(&bytes)
.expect("invalid data-model in block-ctx register")
.timestamp
}