icepick.toml: make derivation prefix and derivation algorithm optional

This commit is contained in:
Ryan Heywood 2024-12-23 15:35:35 -05:00
parent a2fc02f65a
commit 3d8aec844d
Signed by: ryan
GPG Key ID: 8E401478A3FBEF72
2 changed files with 40 additions and 10 deletions

View File

@ -49,13 +49,25 @@ pub fn derive_keys(
#[derive(Serialize, Deserialize, Debug)]
struct ModuleConfig {
/// The name of the module.
name: String,
/// The name of the command used to invoke the module. If not given, the default would be
/// `format!("icepick-{name}")`, using the name of the module.
command_name: Option<String>,
algorithm: keyfork_derive_util::request::DerivationAlgorithm,
/// The bip32 derivation algorithm. This is currently used for deriving keys from Keyfork, but
/// may be passed to modules within the workflow to provide additional context, such as the
/// algorithm for a generic signer.
algorithm: Option<DerivationAlgorithm>,
/// The bip44 derivation prefix. This is currently used for deriving keys from Keyfork directly
/// within Icepick, but may be passed to modules within the workflow to provide additional
/// context, such as a module for deriving keys.
#[serde(with = "serde_derivation")]
derivation_prefix: keyfork_derive_util::DerivationPath,
derivation_prefix: Option<DerivationPath>,
/// All workflows for a module.
#[serde(rename = "workflow", default)]
workflows: Vec<workflow::Workflow>,
}
@ -65,21 +77,28 @@ mod serde_derivation {
use serde::{Deserialize, Deserializer, Serializer};
use std::str::FromStr;
pub fn serialize<S>(p: &DerivationPath, serializer: S) -> Result<S::Ok, S::Error>
pub fn serialize<S>(p: &Option<DerivationPath>, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
let path = p.to_string();
serializer.serialize_str(&path)
if let Some(p) = p {
let path = p.to_string();
serializer.serialize_str(&path)
} else {
serializer.serialize_none()
}
}
pub fn deserialize<'de, D>(deserializer: D) -> Result<DerivationPath, D::Error>
pub fn deserialize<'de, D>(deserializer: D) -> Result<Option<DerivationPath>, D::Error>
where
D: Deserializer<'de>,
{
use serde::de::Error;
String::deserialize(deserializer)
.and_then(|string| DerivationPath::from_str(&string).map_err(Error::custom))
let opt_string = Option::<String>::deserialize(deserializer)?;
opt_string
.map(|string| DerivationPath::from_str(&string).map_err(Error::custom))
.transpose()
}
}
@ -249,7 +268,11 @@ pub fn do_cli_thing() {
let accounts: Vec<keyfork_derive_util::DerivationIndex> =
serde_json::from_value(accounts.clone())
.expect("valid derivation_accounts");
derived_keys.extend(derive_keys(&algo, &path, &accounts));
derived_keys.extend(derive_keys(
&algo.expect("a module requested keys but didn't provide algorithm"),
&path.expect("a module requested keys but didn't provide prefix"),
&accounts,
));
}
let json = serde_json::json!({

View File

@ -198,7 +198,14 @@ impl Workflow {
.expect("could not find module config");
let algo = &config.algorithm;
let path_prefix = &config.derivation_prefix;
derived_keys.extend(derive_keys(algo, path_prefix, &derivation_accounts));
derived_keys.extend(derive_keys(
algo.as_ref()
.expect("a module requested keys but didn't provide algorithm"),
path_prefix
.as_ref()
.expect("a module requested keys but didn't provide prefix"),
&derivation_accounts,
));
derivation_accounts.clear();
// Prepare all inputs for the operation invocation