Skip to content

Commit aaecfaa

Browse files
committed
Add config saving to payjoin-cli
This Pr adds the ability to save config files for V2 to payjoin-cli . This is introduced via a set-config commandline arg that only works for v2 and when the right set of supporting args is present . Fix msrv issue due to more recent toml version Fix msrv issue due to more recent toml version Fix msrv issue due to more recent toml version Fix msrv issue due to more recent toml version Fix msrv issue due to more recent toml version
1 parent fffcf4d commit aaecfaa

File tree

6 files changed

+85
-0
lines changed

6 files changed

+85
-0
lines changed

Cargo-minimal.lock

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1706,6 +1706,7 @@ dependencies = [
17061706
"tempfile",
17071707
"tokio",
17081708
"tokio-rustls",
1709+
"toml",
17091710
"url",
17101711
]
17111712

Cargo-recent.lock

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1706,6 +1706,7 @@ dependencies = [
17061706
"tempfile",
17071707
"tokio",
17081708
"tokio-rustls",
1709+
"toml",
17091710
"url",
17101711
]
17111712

payjoin-cli/Cargo.toml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,10 +47,13 @@ serde = { version = "1.0.160", features = ["derive"] }
4747
sled = "0.34"
4848
tokio = { version = "1.38.1", features = ["full"] }
4949
tokio-rustls = { version = "0.25", features = ["ring"], default-features = false, optional = true }
50+
toml = "0.5.11"
5051
url = { version = "2.3.1", features = ["serde"] }
5152
dirs = "5.0.1"
5253

5354
[dev-dependencies]
5455
nix = "0.26.4"
5556
payjoin-test-utils = { version = "0.0.1" }
5657
tempfile = "3.20.0"
58+
59+

payjoin-cli/src/app/config.rs

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,77 @@ impl Config {
204204
Ok(config)
205205
}
206206

207+
#[cfg(feature = "v2")]
208+
pub fn save_config(cli: &Cli) -> Result<(), anyhow::Error> {
209+
let version = Self::determine_version(cli)
210+
.map_err(|e| anyhow::anyhow!("Failed to determine version: {e}"))?;
211+
212+
if version != Version::Two {
213+
return Err(anyhow::anyhow!("--set-config is only available for bip77 (v2) mode"));
214+
}
215+
216+
// Ensure all required parameters are present
217+
if cli.rpcuser.is_none()
218+
|| cli.rpcpassword.is_none()
219+
|| cli.rpchost.is_none()
220+
|| cli.pj_directory.is_none()
221+
|| cli.ohttp_relays.is_none()
222+
{
223+
return Err(anyhow::anyhow!(
224+
"--set-config requires ALL of: \
225+
--rpcuser, --rpcpassword, --rpchost, \
226+
--pj-directory, --ohttp-relays"
227+
));
228+
}
229+
230+
// Build the TOML map , this feels a bit hacky but it works
231+
let mut toml_map = toml::map::Map::new();
232+
let mut bitcoind_map = toml::map::Map::new();
233+
234+
bitcoind_map.insert("rpcuser".into(), toml::Value::String(cli.rpcuser.clone().unwrap()));
235+
bitcoind_map
236+
.insert("rpcpassword".into(), toml::Value::String(cli.rpcpassword.clone().unwrap()));
237+
bitcoind_map.insert(
238+
"rpchost".into(),
239+
toml::Value::String(cli.rpchost.clone().unwrap().to_string()),
240+
);
241+
toml_map.insert("bitcoind".into(), toml::Value::Table(bitcoind_map));
242+
243+
let mut v2_map = toml::map::Map::new();
244+
v2_map.insert(
245+
"pj_directory".into(),
246+
toml::Value::String(cli.pj_directory.as_ref().unwrap().to_string()),
247+
);
248+
let relay_list: Vec<toml::Value> = cli
249+
.ohttp_relays
250+
.as_ref()
251+
.unwrap()
252+
.iter()
253+
.map(|url| toml::Value::String(url.to_string()))
254+
.collect();
255+
v2_map.insert("ohttp_relays".into(), toml::Value::Array(relay_list));
256+
toml_map.insert("v2".into(), toml::Value::Table(v2_map));
257+
258+
let toml_content = toml::Value::Table(toml_map);
259+
let toml_str = toml::to_string_pretty(&toml_content)?;
260+
261+
let config_path = std::env::current_dir()?.join("config.toml");
262+
let final_path = if !config_path.exists() {
263+
if let Some(config_dir) = dirs::config_dir() {
264+
let global_dir = config_dir.join(CONFIG_DIR);
265+
std::fs::create_dir_all(&global_dir)?;
266+
global_dir.join("config.toml")
267+
} else {
268+
config_path
269+
}
270+
} else {
271+
config_path
272+
};
273+
274+
std::fs::write(final_path, toml_str)?;
275+
Ok(())
276+
}
277+
207278
#[cfg(feature = "v1")]
208279
pub fn v1(&self) -> Result<&V1Config, anyhow::Error> {
209280
match &self.version {

payjoin-cli/src/cli/mod.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,10 @@ pub struct Cli {
7676
#[arg(long = "pj-directory", help = "The directory to store payjoin requests", value_parser = value_parser!(Url))]
7777
pub pj_directory: Option<Url>,
7878

79+
#[cfg(feature = "v2")]
80+
#[arg(long = "set-config", help = "Save current configuration parameters to config.toml", value_parser = value_parser!(bool))]
81+
pub set_config: bool,
82+
7983
#[cfg(feature = "_danger-local-https")]
8084
#[arg(long = "root-certificate", help = "Specify a TLS certificate to be added as a root", value_parser = value_parser!(PathBuf))]
8185
pub root_certificate: Option<PathBuf>,

payjoin-cli/src/main.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,11 @@ async fn main() -> Result<()> {
1616
env_logger::init();
1717

1818
let cli = Cli::parse();
19+
20+
#[cfg(feature = "v2")]
21+
if cli.set_config {
22+
Config::save_config(&cli)?;
23+
}
1924
let config = Config::new(&cli)?;
2025

2126
#[allow(clippy::if_same_then_else)]

0 commit comments

Comments
 (0)