Skip to content

Commit

Permalink
Use satpoints instead of ordinals in wallet commands (ordinals#849)
Browse files Browse the repository at this point in the history
  • Loading branch information
raphjaph authored Nov 29, 2022
1 parent 3634e73 commit fd829f2
Show file tree
Hide file tree
Showing 9 changed files with 288 additions and 301 deletions.
2 changes: 1 addition & 1 deletion src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ use {
serde::{Deserialize, Serialize},
std::{
cmp::Ordering,
collections::VecDeque,
collections::{BTreeMap, VecDeque},
env,
fmt::{self, Display, Formatter},
fs, io,
Expand Down
52 changes: 51 additions & 1 deletion src/sat_point.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
use super::*;

#[derive(Debug, PartialEq)]
#[derive(Debug, PartialEq, Copy, Clone)]
pub(crate) struct SatPoint {
pub(crate) outpoint: OutPoint,
pub(crate) offset: u64,
Expand Down Expand Up @@ -29,3 +29,53 @@ impl Decodable for SatPoint {
})
}
}

impl FromStr for SatPoint {
type Err = Error;

fn from_str(s: &str) -> Result<Self, Self::Err> {
let (outpoint, offset) = s
.rsplit_once(':')
.ok_or_else(|| anyhow!("invalid satpoint: {s}"))?;

Ok(SatPoint {
outpoint: outpoint.parse()?,
offset: offset.parse()?,
})
}
}

#[cfg(test)]
mod tests {
use super::*;

#[test]
fn from_str_ok() {
assert_eq!(
"1111111111111111111111111111111111111111111111111111111111111111:1:1"
.parse::<SatPoint>()
.unwrap(),
SatPoint {
outpoint: "1111111111111111111111111111111111111111111111111111111111111111:1"
.parse()
.unwrap(),
offset: 1,
}
);
}

#[test]
fn from_str_err() {
"abc".parse::<SatPoint>().unwrap_err();

"abc:xyz".parse::<SatPoint>().unwrap_err();

"1111111111111111111111111111111111111111111111111111111111111111:1"
.parse::<SatPoint>()
.unwrap_err();

"1111111111111111111111111111111111111111111111111111111111111111:1:foo"
.parse::<SatPoint>()
.unwrap_err();
}
}
17 changes: 17 additions & 0 deletions src/subcommand/wallet.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,23 @@ fn list_unspent(options: &Options, index: &Index) -> Result<Vec<(OutPoint, Vec<(
.collect()
}

fn list_utxos(options: &Options) -> Result<BTreeMap<OutPoint, Amount>> {
let client = options.bitcoin_rpc_client()?;

Ok(
client
.list_unspent(None, None, None, None, None)?
.iter()
.map(|utxo| {
let outpoint = OutPoint::new(utxo.txid, utxo.vout);
let amount = utxo.amount;

(outpoint, amount)
})
.collect(),
)
}

fn get_change_addresses(options: &Options, n: usize) -> Result<Vec<Address>> {
let client = options.bitcoin_rpc_client()?;

Expand Down
31 changes: 19 additions & 12 deletions src/subcommand/wallet/inscribe.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@ use {

#[derive(Debug, Parser)]
pub(crate) struct Inscribe {
#[clap(long, help = "Inscribe <ORDINAL>")]
ordinal: Ordinal,
#[clap(long, help = "Inscribe <SATPOINT>")]
satpoint: SatPoint,
#[clap(long, help = "Inscribe ordinal with contents of <FILE>")]
file: PathBuf,
}
Expand All @@ -36,7 +36,7 @@ impl Inscribe {
let reveal_tx_destination = get_change_addresses(&options, 1)?[0].clone();

let (unsigned_commit_tx, reveal_tx) = Inscribe::create_inscription_transactions(
self.ordinal,
self.satpoint,
inscription,
options.chain.network(),
utxos,
Expand All @@ -62,7 +62,7 @@ impl Inscribe {
}

fn create_inscription_transactions(
ordinal: Ordinal,
satpoint: SatPoint,
inscription: Inscription,
network: bitcoin::Network,
utxos: Vec<(OutPoint, Vec<(u64, u64)>)>,
Expand Down Expand Up @@ -96,8 +96,16 @@ impl Inscribe {
let commit_tx_address = Address::p2tr_tweaked(taproot_spend_info.output_key(), network);

let unsigned_commit_tx = TransactionBuilder::build_transaction(
utxos.into_iter().collect(),
ordinal,
satpoint,
utxos
.into_iter()
.map(|(outpoint, ranges)| {
(
outpoint,
Amount::from_sat(ranges.iter().map(|(start, end)| end - start).sum()),
)
})
.collect(),
commit_tx_address.clone(),
change,
)?;
Expand Down Expand Up @@ -186,12 +194,11 @@ mod tests {
fn reveal_transaction_pays_fee() {
let utxos = vec![(outpoint(1), vec![(10_000, 15_000)])];
let inscription = Inscription::Text("ord".into());
let ordinal = Ordinal(10_000);
let commit_address = change(0);
let reveal_address = recipient();

let (commit_tx, reveal_tx) = Inscribe::create_inscription_transactions(
ordinal,
satpoint(1, 0),
inscription,
bitcoin::Network::Signet,
utxos,
Expand All @@ -211,13 +218,13 @@ mod tests {
#[test]
fn reveal_transaction_value_insufficient_to_pay_fee() {
let utxos = vec![(outpoint(1), vec![(10_000, 11_000)])];
let ordinal = Ordinal(10_000);
let satpoint = satpoint(1, 0);
let inscription = Inscription::Png([1; 10_000].to_vec());
let commit_address = change(0);
let reveal_address = recipient();

assert!(Inscribe::create_inscription_transactions(
ordinal,
satpoint,
inscription,
bitcoin::Network::Signet,
utxos,
Expand All @@ -233,12 +240,12 @@ mod tests {
fn reveal_transaction_would_create_dust() {
let utxos = vec![(outpoint(1), vec![(10_000, 10_600)])];
let inscription = Inscription::Text("ord".into());
let ordinal = Ordinal(10_000);
let satpoint = satpoint(1, 0);
let commit_address = change(0);
let reveal_address = recipient();

let error = Inscribe::create_inscription_transactions(
ordinal,
satpoint,
inscription,
bitcoin::Network::Signet,
utxos,
Expand Down
9 changes: 3 additions & 6 deletions src/subcommand/wallet/send.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use super::*;

#[derive(Debug, Parser)]
pub(crate) struct Send {
ordinal: Ordinal,
satpoint: SatPoint,
address: Address,
}

Expand All @@ -18,15 +18,12 @@ impl Send {
);
}

let index = Index::open(&options)?;
index.update()?;

let utxos = list_unspent(&options, &index)?.into_iter().collect();
let utxos = list_utxos(&options)?;

let change = get_change_addresses(&options, 2)?;

let unsigned_transaction =
TransactionBuilder::build_transaction(utxos, self.ordinal, self.address, change)?;
TransactionBuilder::build_transaction(self.satpoint, utxos, self.address, change)?;

let signed_tx = client
.sign_raw_transaction_with_wallet(&unsigned_transaction, None, None)?
Expand Down
Loading

0 comments on commit fd829f2

Please sign in to comment.