Prepare datadir for multiple wallet support
A new field data_directory is introduced in lianad configuration, it resolves directly to the path of the wallet datadir without the per network reasoning. The previous data_dir field is kept for backward compatibility for already generated configuration file.
This commit is contained in:
parent
1213858489
commit
6ccaa0573b
@ -128,7 +128,7 @@ impl Backup {
|
||||
let mut proprietary = serde_json::Map::new();
|
||||
proprietary.insert(LIANA_VERSION_KEY.to_string(), liana_version().into());
|
||||
|
||||
let config = extract_daemon_config(&ctx);
|
||||
let config = extract_daemon_config(&ctx).map_err(|e| Error::Daemon(e.to_string()))?;
|
||||
if let Ok(config) = serde_json::to_value(config) {
|
||||
proprietary.insert(CONFIG_KEY.to_string(), config);
|
||||
}
|
||||
|
||||
@ -809,22 +809,17 @@ pub async fn import_backup(
|
||||
Vec::new()
|
||||
};
|
||||
|
||||
let datadir = match daemon.config() {
|
||||
Some(c) => match &c.data_dir {
|
||||
Some(dd) => dd,
|
||||
None => {
|
||||
return Err(Error::BackupImport("Failed to get Daemon config".into()));
|
||||
}
|
||||
},
|
||||
None => {
|
||||
return Err(Error::BackupImport("Failed to get Daemon config".into()));
|
||||
}
|
||||
};
|
||||
let lianad_datadir = daemon
|
||||
.config()
|
||||
.and_then(|c| c.data_directory())
|
||||
.ok_or(Error::BackupImport("Failed to get Daemon config".into()))?;
|
||||
|
||||
// check if key aliases can be imported w/o conflict
|
||||
let mut write_aliases = true;
|
||||
let settings = if !account.keys.is_empty() {
|
||||
let settings = match Settings::from_file(datadir.to_path_buf(), network) {
|
||||
// TODO: change lianad_datadir is common to gui datadir only for legacy wallet before
|
||||
// multiple wallet
|
||||
let settings = match Settings::from_file(lianad_datadir.path().to_path_buf(), network) {
|
||||
Ok(s) => s,
|
||||
Err(_) => {
|
||||
return Err(Error::BackupImport("Failed to get App Settings".into()));
|
||||
@ -943,7 +938,10 @@ pub async fn import_backup(
|
||||
|
||||
settings.wallets.get_mut(0).expect("already checked").keys =
|
||||
settings_aliases.clone().into_values().collect();
|
||||
if settings.to_file(datadir.to_path_buf(), network).is_err() {
|
||||
if settings
|
||||
.to_file(lianad_datadir.path().to_path_buf(), network)
|
||||
.is_err()
|
||||
{
|
||||
return Err(Error::BackupImport("Failed to import keys aliases".into()));
|
||||
} else {
|
||||
// Update wallet state
|
||||
|
||||
@ -60,7 +60,7 @@ pub struct Context {
|
||||
pub descriptor: Option<LianaDescriptor>,
|
||||
pub keys: HashMap<bitcoin::bip32::Fingerprint, KeySetting>,
|
||||
pub hws: Vec<(DeviceKind, bitcoin::bip32::Fingerprint, Option<[u8; 32]>)>,
|
||||
pub data_dir: PathBuf,
|
||||
pub root_directory: PathBuf,
|
||||
pub network: bitcoin::Network,
|
||||
pub hw_is_used: bool,
|
||||
// In case a user entered a mnemonic,
|
||||
@ -76,7 +76,7 @@ pub struct Context {
|
||||
impl Context {
|
||||
pub fn new(
|
||||
network: bitcoin::Network,
|
||||
data_dir: PathBuf,
|
||||
root_directory: PathBuf,
|
||||
remote_backend: RemoteBackend,
|
||||
) -> Self {
|
||||
Self {
|
||||
@ -89,7 +89,7 @@ impl Context {
|
||||
keys: HashMap::new(),
|
||||
bitcoin_backend: None,
|
||||
descriptor: None,
|
||||
data_dir,
|
||||
root_directory,
|
||||
network,
|
||||
hw_is_used: false,
|
||||
recovered_signer: None,
|
||||
|
||||
@ -133,7 +133,7 @@ impl Installer {
|
||||
ChooseBackend::new(network).into(),
|
||||
RemoteBackendLogin::new(network).into(),
|
||||
SelectBitcoindTypeStep::new().into(),
|
||||
InternalBitcoindStep::new(&context.data_dir).into(),
|
||||
InternalBitcoindStep::new(&context.root_directory).into(),
|
||||
DefineNode::default().into(),
|
||||
Final::new().into(),
|
||||
],
|
||||
@ -146,7 +146,7 @@ impl Installer {
|
||||
RecoverMnemonic::default().into(),
|
||||
RegisterDescriptor::new_import_wallet().into(),
|
||||
SelectBitcoindTypeStep::new().into(),
|
||||
InternalBitcoindStep::new(&context.data_dir).into(),
|
||||
InternalBitcoindStep::new(&context.root_directory).into(),
|
||||
DefineNode::default().into(),
|
||||
Final::new().into(),
|
||||
],
|
||||
@ -167,7 +167,7 @@ impl Installer {
|
||||
}
|
||||
|
||||
pub fn destination_path(&self) -> PathBuf {
|
||||
self.context.data_dir.clone()
|
||||
self.context.root_directory.clone()
|
||||
}
|
||||
|
||||
pub fn subscription(&self) -> Subscription<Message> {
|
||||
@ -270,21 +270,21 @@ impl Installer {
|
||||
}
|
||||
}
|
||||
Message::Installed(Err(e)) => {
|
||||
let mut data_dir = self.context.data_dir.clone();
|
||||
data_dir.push(self.context.bitcoin_config.network.to_string());
|
||||
let mut network_directory = self.context.root_directory.clone();
|
||||
network_directory.push(self.context.bitcoin_config.network.to_string());
|
||||
// In case of failure during install, block the thread to
|
||||
// deleted the data_dir/network directory in order to start clean again.
|
||||
warn!("Installation failed. Cleaning up the leftover data directory.");
|
||||
if let Err(e) = std::fs::remove_dir_all(&data_dir) {
|
||||
if let Err(e) = std::fs::remove_dir_all(&network_directory) {
|
||||
error!(
|
||||
"Failed to completely delete the data directory (path: '{}'): {}",
|
||||
data_dir.to_string_lossy(),
|
||||
network_directory.to_string_lossy(),
|
||||
e
|
||||
);
|
||||
} else {
|
||||
warn!(
|
||||
"Successfully deleted data directory at '{}'.",
|
||||
data_dir.to_string_lossy()
|
||||
network_directory.to_string_lossy()
|
||||
);
|
||||
};
|
||||
self.steps
|
||||
@ -358,19 +358,13 @@ pub async fn install_local_wallet(
|
||||
ctx: Context,
|
||||
signer: Arc<Mutex<Signer>>,
|
||||
) -> Result<PathBuf, Error> {
|
||||
let mut cfg: lianad::config::Config = extract_daemon_config(&ctx);
|
||||
let data_dir = cfg.data_dir.unwrap();
|
||||
|
||||
let data_dir = data_dir
|
||||
.canonicalize()
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to canonicalize datadir path: {}", e)))?;
|
||||
cfg.data_dir = Some(data_dir.clone());
|
||||
let cfg: lianad::config::Config = extract_daemon_config(&ctx)?;
|
||||
|
||||
daemon_check(cfg.clone())?;
|
||||
|
||||
info!("daemon checked");
|
||||
|
||||
let mut network_datadir_path = data_dir;
|
||||
let mut network_datadir_path = ctx.root_directory.clone();
|
||||
network_datadir_path.push(cfg.bitcoin_config.network.to_string());
|
||||
create_directory(&network_datadir_path)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to create datadir path: {}", e)))?;
|
||||
@ -396,10 +390,7 @@ pub async fn install_local_wallet(
|
||||
signer
|
||||
.lock()
|
||||
.unwrap()
|
||||
.store(
|
||||
&cfg.data_dir().expect("Already checked"),
|
||||
cfg.bitcoin_config.network,
|
||||
)
|
||||
.store(&ctx.root_directory, cfg.bitcoin_config.network)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to store mnemonic: {}", e)))?;
|
||||
|
||||
info!("Hot signer mnemonic stored");
|
||||
@ -407,10 +398,7 @@ pub async fn install_local_wallet(
|
||||
|
||||
if let Some(signer) = &ctx.recovered_signer {
|
||||
signer
|
||||
.store(
|
||||
&cfg.data_dir().expect("Already checked"),
|
||||
cfg.bitcoin_config.network,
|
||||
)
|
||||
.store(&ctx.root_directory, cfg.bitcoin_config.network)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to store mnemonic: {}", e)))?;
|
||||
|
||||
info!("Recovered signer mnemonic stored");
|
||||
@ -450,12 +438,7 @@ pub async fn create_remote_wallet(
|
||||
signer: Arc<Mutex<Signer>>,
|
||||
remote_backend: BackendClient,
|
||||
) -> Result<PathBuf, Error> {
|
||||
let data_dir = ctx
|
||||
.data_dir
|
||||
.canonicalize()
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to canonicalize datadir path: {}", e)))?;
|
||||
|
||||
let mut network_datadir_path = data_dir.clone();
|
||||
let mut network_datadir_path = ctx.root_directory.clone();
|
||||
network_datadir_path.push(ctx.network.to_string());
|
||||
create_directory(&network_datadir_path)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to create datadir path: {}", e)))?;
|
||||
@ -472,7 +455,7 @@ pub async fn create_remote_wallet(
|
||||
signer
|
||||
.lock()
|
||||
.unwrap()
|
||||
.store(&data_dir, ctx.network)
|
||||
.store(&ctx.root_directory, ctx.network)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to store mnemonic: {}", e)))?;
|
||||
|
||||
info!("Hot signer mnemonic stored");
|
||||
@ -480,13 +463,13 @@ pub async fn create_remote_wallet(
|
||||
|
||||
if let Some(signer) = &ctx.recovered_signer {
|
||||
signer
|
||||
.store(&data_dir, ctx.network)
|
||||
.store(&ctx.root_directory, ctx.network)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to store mnemonic: {}", e)))?;
|
||||
|
||||
info!("Recovered signer mnemonic stored");
|
||||
}
|
||||
|
||||
let mut network_datadir_path = data_dir;
|
||||
let mut network_datadir_path = ctx.root_directory.clone();
|
||||
network_datadir_path.push(ctx.network.to_string());
|
||||
|
||||
// create liana GUI configuration file
|
||||
@ -573,20 +556,15 @@ pub async fn import_remote_wallet(
|
||||
) -> Result<PathBuf, Error> {
|
||||
tracing::info!("Importing wallet from remote backend");
|
||||
|
||||
let data_dir = ctx
|
||||
.data_dir
|
||||
.canonicalize()
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to canonicalize datadir path: {}", e)))?;
|
||||
|
||||
if let Some(signer) = &ctx.recovered_signer {
|
||||
signer
|
||||
.store(&data_dir, ctx.network)
|
||||
.store(&ctx.root_directory, ctx.network)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to store mnemonic: {}", e)))?;
|
||||
|
||||
info!("Recovered signer mnemonic stored");
|
||||
}
|
||||
|
||||
let mut network_datadir_path = data_dir;
|
||||
let mut network_datadir_path = ctx.root_directory.clone();
|
||||
network_datadir_path.push(ctx.network.to_string());
|
||||
create_directory(&network_datadir_path)
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to create datadir path: {}", e)))?;
|
||||
@ -700,17 +678,21 @@ pub fn extract_local_gui_settings(ctx: &Context) -> Settings {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extract_daemon_config(ctx: &Context) -> Config {
|
||||
Config {
|
||||
log_level: log::LevelFilter::Info,
|
||||
main_descriptor: ctx
|
||||
.descriptor
|
||||
pub fn extract_daemon_config(ctx: &Context) -> Result<Config, Error> {
|
||||
let mut data_directory = ctx
|
||||
.root_directory
|
||||
.canonicalize()
|
||||
.map_err(|e| Error::Unexpected(format!("Failed to canonicalize datadir path: {}", e)))?;
|
||||
data_directory.push(ctx.bitcoin_config.network.to_string());
|
||||
Ok(Config::new(
|
||||
ctx.bitcoin_config.clone(),
|
||||
ctx.bitcoin_backend.clone(),
|
||||
log::LevelFilter::Info,
|
||||
ctx.descriptor
|
||||
.clone()
|
||||
.expect("Context must have a descriptor at this point"),
|
||||
data_dir: Some(ctx.data_dir.clone()),
|
||||
bitcoin_config: ctx.bitcoin_config.clone(),
|
||||
bitcoin_backend: ctx.bitcoin_backend.clone(),
|
||||
}
|
||||
lianad::datadir::DataDirectory::new(data_directory),
|
||||
))
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
|
||||
@ -531,7 +531,7 @@ impl Step for InternalBitcoindStep {
|
||||
if self.exe_path.is_none() {
|
||||
// Check if current managed bitcoind version is already installed.
|
||||
// For new installations, we ignore any previous managed bitcoind versions that might be installed.
|
||||
let exe_path = bitcoind::internal_bitcoind_exe_path(&ctx.data_dir, VERSION);
|
||||
let exe_path = bitcoind::internal_bitcoind_exe_path(&ctx.root_directory, VERSION);
|
||||
if exe_path.exists() {
|
||||
self.exe_path = Some(exe_path)
|
||||
} else if self.exe_download.is_none() {
|
||||
|
||||
@ -317,6 +317,7 @@ impl GUI {
|
||||
if remove_log {
|
||||
self.logger.remove_install_log_file(i.datadir.clone());
|
||||
}
|
||||
|
||||
let (loader, command) = Loader::new(
|
||||
i.datadir.clone(),
|
||||
cfg,
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
#![cfg(not(target_os = "windows"))]
|
||||
|
||||
use lianad::config::{config_folder_path, Config};
|
||||
use lianad::config::Config;
|
||||
|
||||
use std::{
|
||||
env,
|
||||
@ -89,17 +89,9 @@ fn socket_file(conf_file: Option<PathBuf>) -> PathBuf {
|
||||
process::exit(1);
|
||||
});
|
||||
let data_dir = config
|
||||
.data_dir
|
||||
.unwrap_or_else(|| config_folder_path().unwrap());
|
||||
let data_dir = data_dir.to_str().expect("Datadir is valid unicode");
|
||||
|
||||
[
|
||||
data_dir,
|
||||
config.bitcoin_config.network.to_string().as_str(),
|
||||
"lianad_rpc",
|
||||
]
|
||||
.iter()
|
||||
.collect()
|
||||
.data_directory()
|
||||
.expect("Wallet datadir is not properly defined");
|
||||
data_dir.lianad_rpc_socket_path()
|
||||
}
|
||||
|
||||
fn trimmed(mut vec: Vec<u8>, bytes_read: usize) -> Vec<u8> {
|
||||
|
||||
@ -2,6 +2,7 @@ use liana::descriptors::LianaDescriptor;
|
||||
|
||||
use std::{fmt, net::SocketAddr, path::PathBuf, str::FromStr, time::Duration};
|
||||
|
||||
use crate::datadir::DataDirectory;
|
||||
use miniscript::bitcoin::Network;
|
||||
|
||||
use serde::{de, Deserialize, Deserializer, Serialize, Serializer};
|
||||
@ -146,8 +147,10 @@ pub struct BitcoinConfig {
|
||||
/// Static informations we require to operate
|
||||
#[derive(Debug, Clone, Deserialize, Serialize)]
|
||||
pub struct Config {
|
||||
/// An optional custom data directory
|
||||
pub data_dir: Option<PathBuf>,
|
||||
/// legacy: An optional custom data directory
|
||||
data_dir: Option<PathBuf>,
|
||||
/// Current: A direct point to the current datadir
|
||||
data_directory: Option<PathBuf>,
|
||||
/// What messages to log
|
||||
#[serde(
|
||||
deserialize_with = "deserialize_fromstr",
|
||||
@ -169,8 +172,35 @@ pub struct Config {
|
||||
}
|
||||
|
||||
impl Config {
|
||||
pub fn data_dir(&self) -> Option<PathBuf> {
|
||||
self.data_dir.clone().or_else(config_folder_path)
|
||||
pub fn new(
|
||||
bitcoin_config: BitcoinConfig,
|
||||
bitcoin_backend: Option<BitcoinBackend>,
|
||||
log_level: log::LevelFilter,
|
||||
main_descriptor: LianaDescriptor,
|
||||
data_directory: DataDirectory,
|
||||
) -> Self {
|
||||
Self {
|
||||
bitcoin_config,
|
||||
bitcoin_backend,
|
||||
log_level,
|
||||
main_descriptor,
|
||||
data_directory: Some(data_directory.path().to_path_buf()),
|
||||
data_dir: None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn data_directory(&self) -> Option<DataDirectory> {
|
||||
if self.data_directory.is_some() {
|
||||
self.data_directory.clone().map(DataDirectory::new)
|
||||
} else if let Some(mut dir) = self.data_dir.clone() {
|
||||
dir.push(self.bitcoin_config.network.to_string());
|
||||
Some(DataDirectory::new(dir))
|
||||
} else {
|
||||
config_folder_path().map(|mut dir| {
|
||||
dir.push(self.bitcoin_config.network.to_string());
|
||||
DataDirectory::new(dir)
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
47
lianad/src/datadir.rs
Normal file
47
lianad/src/datadir.rs
Normal file
@ -0,0 +1,47 @@
|
||||
use std::path::{Path, PathBuf};
|
||||
|
||||
pub struct DataDirectory(PathBuf);
|
||||
|
||||
impl DataDirectory {
|
||||
pub fn new(p: PathBuf) -> Self {
|
||||
DataDirectory(p)
|
||||
}
|
||||
}
|
||||
|
||||
impl DataDirectory {
|
||||
pub fn exists(&self) -> bool {
|
||||
self.0.as_path().exists()
|
||||
}
|
||||
pub fn init(&self) -> Result<(), std::io::Error> {
|
||||
#[cfg(unix)]
|
||||
return {
|
||||
use std::fs::DirBuilder;
|
||||
use std::os::unix::fs::DirBuilderExt;
|
||||
|
||||
let mut builder = DirBuilder::new();
|
||||
builder.mode(0o700).recursive(true).create(self.path())
|
||||
};
|
||||
|
||||
// TODO: permissions on Windows..
|
||||
#[cfg(not(unix))]
|
||||
return { std::fs::create_dir_all(self.path()) };
|
||||
}
|
||||
pub fn path(&self) -> &Path {
|
||||
self.0.as_path()
|
||||
}
|
||||
pub fn sqlite_db_file_path(&self) -> PathBuf {
|
||||
let mut dir = self.0.clone();
|
||||
dir.push("lianad.sqlite3");
|
||||
dir
|
||||
}
|
||||
pub fn lianad_watchonly_wallet_path(&self) -> PathBuf {
|
||||
let mut dir = self.0.clone();
|
||||
dir.push("lianad_watchonly_wallet");
|
||||
dir
|
||||
}
|
||||
pub fn lianad_rpc_socket_path(&self) -> PathBuf {
|
||||
let mut dir = self.0.clone();
|
||||
dir.push("lianad_rpc");
|
||||
dir
|
||||
}
|
||||
}
|
||||
@ -2,6 +2,7 @@ mod bitcoin;
|
||||
pub mod commands;
|
||||
pub mod config;
|
||||
mod database;
|
||||
pub mod datadir;
|
||||
mod jsonrpc;
|
||||
#[cfg(test)]
|
||||
mod testutils;
|
||||
@ -9,6 +10,7 @@ mod testutils;
|
||||
pub use bdk_electrum::electrum_client;
|
||||
pub use bip329;
|
||||
use bitcoin::electrum;
|
||||
use datadir::DataDirectory;
|
||||
pub use miniscript;
|
||||
|
||||
pub use crate::bitcoin::{
|
||||
@ -27,7 +29,7 @@ use crate::{
|
||||
};
|
||||
|
||||
use std::{
|
||||
error, fmt, fs, io, path,
|
||||
error, fmt, io, path,
|
||||
sync::{self, mpsc},
|
||||
thread,
|
||||
};
|
||||
@ -166,40 +168,16 @@ impl From<BitcoindError> for StartupError {
|
||||
}
|
||||
}
|
||||
|
||||
fn create_datadir(datadir_path: &path::Path) -> Result<(), StartupError> {
|
||||
#[cfg(unix)]
|
||||
return {
|
||||
use fs::DirBuilder;
|
||||
use std::os::unix::fs::DirBuilderExt;
|
||||
|
||||
let mut builder = DirBuilder::new();
|
||||
builder
|
||||
.mode(0o700)
|
||||
.recursive(true)
|
||||
.create(datadir_path)
|
||||
.map_err(|e| StartupError::DatadirCreation(datadir_path.to_path_buf(), e))
|
||||
};
|
||||
|
||||
// TODO: permissions on Windows..
|
||||
#[cfg(not(unix))]
|
||||
return {
|
||||
fs::create_dir_all(datadir_path)
|
||||
.map_err(|e| StartupError::DatadirCreation(datadir_path.to_path_buf(), e))
|
||||
};
|
||||
}
|
||||
|
||||
// Connect to the SQLite database. Create it if starting fresh, and do some sanity checks.
|
||||
// If all went well, returns the interface to the SQLite database.
|
||||
fn setup_sqlite(
|
||||
config: &Config,
|
||||
data_dir: &path::Path,
|
||||
data_dir: &DataDirectory,
|
||||
fresh_data_dir: bool,
|
||||
secp: &secp256k1::Secp256k1<secp256k1::VerifyOnly>,
|
||||
bitcoind: &Option<BitcoinD>,
|
||||
) -> Result<SqliteDb, StartupError> {
|
||||
let db_path: path::PathBuf = [data_dir, path::Path::new("lianad.sqlite3")]
|
||||
.iter()
|
||||
.collect();
|
||||
let db_path = data_dir.sqlite_db_file_path();
|
||||
let options = if fresh_data_dir {
|
||||
Some(FreshDbOptions::new(
|
||||
config.bitcoin_config.network,
|
||||
@ -242,12 +220,10 @@ fn setup_sqlite(
|
||||
// If all went well, returns the interface to bitcoind.
|
||||
fn setup_bitcoind(
|
||||
config: &Config,
|
||||
data_dir: &path::Path,
|
||||
data_dir: &DataDirectory,
|
||||
fresh_data_dir: bool,
|
||||
) -> Result<BitcoinD, StartupError> {
|
||||
let wo_path: path::PathBuf = [data_dir, path::Path::new("lianad_watchonly_wallet")]
|
||||
.iter()
|
||||
.collect();
|
||||
let wo_path: path::PathBuf = data_dir.lianad_watchonly_wallet_path();
|
||||
let wo_path_str = wo_path.to_str().expect("Must be valid unicode").to_string();
|
||||
// NOTE: On Windows, paths are canonicalized with a "\\?\" prefix to tell Windows to interpret
|
||||
// the string "as is" and to ignore the maximum size of a path. HOWEVER this is not properly
|
||||
@ -426,14 +402,18 @@ impl DaemonHandle {
|
||||
let secp = secp256k1::Secp256k1::verification_only();
|
||||
|
||||
// First, check the data directory
|
||||
let mut data_dir = config
|
||||
.data_dir()
|
||||
let data_dir = config
|
||||
.data_directory()
|
||||
.ok_or(StartupError::DefaultDataDirNotFound)?;
|
||||
data_dir.push(config.bitcoin_config.network.to_string());
|
||||
let fresh_data_dir = !data_dir.as_path().exists();
|
||||
let fresh_data_dir = !data_dir.exists();
|
||||
if fresh_data_dir {
|
||||
create_datadir(&data_dir)?;
|
||||
log::info!("Created a new data directory at '{}'", data_dir.display());
|
||||
data_dir
|
||||
.init()
|
||||
.map_err(|e| StartupError::DatadirCreation(data_dir.path().to_path_buf(), e))?;
|
||||
log::info!(
|
||||
"Created a new data directory at '{}'",
|
||||
data_dir.path().to_string_lossy()
|
||||
);
|
||||
}
|
||||
|
||||
// Set up the connection to bitcoind (if using it) first as we may need it for the database
|
||||
@ -501,9 +481,7 @@ impl DaemonHandle {
|
||||
.spawn({
|
||||
let shutdown = rpcserver_shutdown.clone();
|
||||
move || {
|
||||
let mut rpc_socket = data_dir;
|
||||
rpc_socket.push("lianad_rpc");
|
||||
server::run(&rpc_socket, control, shutdown)?;
|
||||
server::run(&data_dir.lianad_rpc_socket_path(), control, shutdown)?;
|
||||
Ok(())
|
||||
}
|
||||
})
|
||||
@ -776,6 +754,7 @@ mod tests {
|
||||
let data_dir: path::PathBuf = [tmp_dir.as_path(), path::Path::new("datadir")]
|
||||
.iter()
|
||||
.collect();
|
||||
fs::create_dir_all(&data_dir).unwrap();
|
||||
let wo_path: path::PathBuf = [
|
||||
data_dir.as_path(),
|
||||
path::Path::new("bitcoin"),
|
||||
@ -815,13 +794,15 @@ mod tests {
|
||||
let desc = LianaDescriptor::from_str(desc_str).unwrap();
|
||||
let receive_desc = desc.receive_descriptor().clone();
|
||||
let change_desc = desc.change_descriptor().clone();
|
||||
let config = Config {
|
||||
let mut data_directory = data_dir.clone();
|
||||
data_directory.push("bitcoin");
|
||||
let config = Config::new(
|
||||
bitcoin_config,
|
||||
bitcoin_backend: Some(config::BitcoinBackend::Bitcoind(bitcoind_config)),
|
||||
data_dir: Some(data_dir),
|
||||
log_level: log::LevelFilter::Debug,
|
||||
main_descriptor: desc,
|
||||
};
|
||||
Some(config::BitcoinBackend::Bitcoind(bitcoind_config)),
|
||||
log::LevelFilter::Debug,
|
||||
desc,
|
||||
DataDirectory::new(data_directory),
|
||||
);
|
||||
|
||||
// Start the daemon in a new thread so the current one acts as the bitcoind server.
|
||||
let t = thread::spawn({
|
||||
|
||||
@ -4,6 +4,7 @@ use crate::{
|
||||
database::{
|
||||
BlockInfo, Coin, CoinStatus, DatabaseConnection, DatabaseInterface, LabelItem, Wallet,
|
||||
},
|
||||
datadir::DataDirectory,
|
||||
DaemonControl, DaemonHandle,
|
||||
};
|
||||
use liana::descriptors;
|
||||
@ -563,7 +564,11 @@ impl DummyLiana {
|
||||
let tmp_dir = tmp_dir();
|
||||
fs::create_dir_all(&tmp_dir).unwrap();
|
||||
// Use a shorthand for 'datadir', to avoid overflowing SUN_LEN on MacOS.
|
||||
let data_dir: path::PathBuf = [tmp_dir.as_path(), path::Path::new("d")].iter().collect();
|
||||
let root_directory: path::PathBuf =
|
||||
[tmp_dir.as_path(), path::Path::new("d")].iter().collect();
|
||||
fs::create_dir_all(&root_directory).unwrap();
|
||||
let mut data_directory = root_directory.clone();
|
||||
data_directory.push("bitcoin");
|
||||
|
||||
let network = bitcoin::Network::Bitcoin;
|
||||
let bitcoin_config = BitcoinConfig {
|
||||
@ -579,13 +584,13 @@ impl DummyLiana {
|
||||
)
|
||||
.unwrap();
|
||||
let desc = descriptors::LianaDescriptor::new(policy);
|
||||
let config = Config {
|
||||
let config = Config::new(
|
||||
bitcoin_config,
|
||||
bitcoin_backend: None,
|
||||
data_dir: Some(data_dir),
|
||||
log_level: log::LevelFilter::Debug,
|
||||
main_descriptor: desc,
|
||||
};
|
||||
None,
|
||||
log::LevelFilter::Debug,
|
||||
desc,
|
||||
DataDirectory::new(data_directory),
|
||||
);
|
||||
|
||||
let handle =
|
||||
DaemonHandle::start(config, Some(bitcoin_interface), Some(database), rpc_server)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user