Skip to content

Commit f780624

Browse files
committed
Merge branch 'master' of github.com:ordinals/ord into index-rune-burns
2 parents 19d971f + 14a9c6f commit f780624

23 files changed

+278
-47
lines changed

crates/mockcore/src/server.rs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -258,17 +258,25 @@ impl Api for Server {
258258
}
259259
}
260260

261+
let Some(tx) = state.transactions.get(&txid) else {
262+
return Ok(None);
263+
};
264+
265+
let script_pubkey = &tx.output[usize::try_from(vout).unwrap()].script_pubkey;
266+
261267
Ok(Some(GetTxOutResult {
262268
bestblock: BlockHash::all_zeros(),
263269
coinbase: false,
264270
confirmations: confirmations.unwrap().try_into().unwrap(),
265271
script_pub_key: GetRawTransactionResultVoutScriptPubKey {
266272
asm: String::new(),
267-
hex: Vec::new(),
273+
hex: script_pubkey.to_bytes(),
268274
req_sigs: None,
269275
type_: None,
270276
addresses: Vec::new(),
271-
address: None,
277+
address: Address::from_script(script_pubkey, state.network)
278+
.ok()
279+
.map(|addr| addr.into_unchecked()),
272280
},
273281
value: *value,
274282
}))

docs/src/guides/api.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1803,6 +1803,7 @@ curl -s -H "Accept: application/json" \
18031803
```json
18041804
{
18051805
"address": "bc1pz4kvfpurqc2hwgrq0nwtfve2lfxvdpfcdpzc6ujchyr3ztj6gd9sfr6ayf",
1806+
"confirmations": 6,
18061807
"indexed": false,
18071808
"inscriptions": [],
18081809
"outpoint": "bc4c30829a9564c0d58e6287195622b53ced54a25711d1b86be7cd3a70ef61ed:0",

justfile

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -49,28 +49,19 @@ deploy-mainnet-charlie branch='master' remote='ordinals/ord': \
4949
deploy-signet branch='master' remote='ordinals/ord': \
5050
(deploy branch remote 'signet' 'signet.ordinals.net')
5151

52-
deploy-testnet branch='master' remote='ordinals/ord': \
53-
(deploy branch remote 'test' 'testnet.ordinals.net')
54-
55-
deploy-testnet4 branch='master' remote='ordinals/ord': \
56-
(deploy branch remote 'testnet4' 'testnet4.ordinals.net')
57-
5852
deploy-all: \
59-
deploy-testnet \
60-
deploy-testnet4 \
6153
deploy-signet \
6254
deploy-mainnet-alpha \
6355
deploy-mainnet-bravo \
6456
deploy-mainnet-charlie
6557

6658
delete-indices: \
6759
(delete-index "signet.ordinals.net") \
68-
(delete-index "testnet.ordinals.net")
6960

7061
delete-index domain:
7162
ssh root@{{domain}} 'systemctl stop ord && rm -f /var/lib/ord/*/index.redb'
7263

73-
servers := 'alpha bravo charlie signet testnet3 testnet4'
64+
servers := 'alpha bravo charlie signet'
7465

7566
initialize-server-keys:
7667
#!/usr/bin/env bash

src/api.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,7 @@ pub struct UtxoRecursive {
169169
#[derive(Debug, PartialEq, Serialize, Deserialize, Clone)]
170170
pub struct Output {
171171
pub address: Option<Address<NetworkUnchecked>>,
172+
pub confirmations: u32,
172173
pub indexed: bool,
173174
pub inscriptions: Option<Vec<InscriptionId>>,
174175
pub outpoint: OutPoint,
@@ -183,6 +184,7 @@ pub struct Output {
183184
impl Output {
184185
pub fn new(
185186
chain: Chain,
187+
confirmations: u32,
186188
inscriptions: Option<Vec<InscriptionId>>,
187189
outpoint: OutPoint,
188190
tx_out: TxOut,
@@ -196,6 +198,7 @@ impl Output {
196198
.address_from_script(&tx_out.script_pubkey)
197199
.ok()
198200
.map(|address| uncheck(&address)),
201+
confirmations,
199202
indexed,
200203
inscriptions,
201204
outpoint,

src/index.rs

Lines changed: 115 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,10 @@ use {
1818
},
1919
bitcoin::block::Header,
2020
bitcoincore_rpc::{
21-
json::{GetBlockHeaderResult, GetBlockStatsResult},
21+
json::{
22+
GetBlockHeaderResult, GetBlockStatsResult, GetRawTransactionResult,
23+
GetRawTransactionResultVout, GetRawTransactionResultVoutScriptPubKey, GetTxOutResult,
24+
},
2225
Client,
2326
},
2427
chrono::SubsecRound,
@@ -1596,6 +1599,87 @@ impl Index {
15961599
Ok(Some(result))
15971600
}
15981601

1602+
pub fn get_unspent_or_unconfirmed_output(
1603+
&self,
1604+
txid: &Txid,
1605+
vout: u32,
1606+
) -> Result<Option<GetTxOutResult>> {
1607+
if txid == &self.genesis_block_coinbase_txid {
1608+
let Some(output) = &self
1609+
.genesis_block_coinbase_transaction
1610+
.output
1611+
.get(vout.into_usize())
1612+
else {
1613+
return Ok(None);
1614+
};
1615+
1616+
return Ok(Some(GetTxOutResult {
1617+
bestblock: self.block_hash(None)?.unwrap(),
1618+
coinbase: true,
1619+
confirmations: self.block_count()?,
1620+
script_pub_key: GetRawTransactionResultVoutScriptPubKey {
1621+
address: None,
1622+
addresses: Vec::new(),
1623+
asm: output.script_pubkey.to_asm_string(),
1624+
hex: output.script_pubkey.to_bytes(),
1625+
req_sigs: Some(1),
1626+
type_: Some(bitcoincore_rpc::json::ScriptPubkeyType::Pubkey),
1627+
},
1628+
value: output.value,
1629+
}));
1630+
}
1631+
1632+
Ok(self.client.get_tx_out(txid, vout, Some(true))?)
1633+
}
1634+
1635+
pub fn get_transaction_info(&self, txid: &Txid) -> Result<Option<GetRawTransactionResult>> {
1636+
if txid == &self.genesis_block_coinbase_txid {
1637+
let tx = &self.genesis_block_coinbase_transaction;
1638+
1639+
let block = bitcoin::blockdata::constants::genesis_block(self.settings.chain().network());
1640+
let time = block.header.time.into_usize();
1641+
1642+
return Ok(Some(GetRawTransactionResult {
1643+
in_active_chain: Some(true),
1644+
hex: consensus::encode::serialize(tx),
1645+
txid: tx.compute_txid(),
1646+
hash: tx.compute_wtxid(),
1647+
size: tx.total_size(),
1648+
vsize: tx.vsize(),
1649+
#[allow(clippy::cast_sign_loss)]
1650+
version: tx.version.0 as u32,
1651+
locktime: 0,
1652+
vin: Vec::new(),
1653+
vout: tx
1654+
.output
1655+
.iter()
1656+
.enumerate()
1657+
.map(|(n, output)| GetRawTransactionResultVout {
1658+
n: n.try_into().unwrap(),
1659+
value: output.value,
1660+
script_pub_key: GetRawTransactionResultVoutScriptPubKey {
1661+
asm: output.script_pubkey.to_asm_string(),
1662+
hex: output.script_pubkey.clone().into(),
1663+
req_sigs: None,
1664+
type_: None,
1665+
addresses: Vec::new(),
1666+
address: None,
1667+
},
1668+
})
1669+
.collect(),
1670+
blockhash: Some(block.block_hash()),
1671+
confirmations: Some(self.block_count()?),
1672+
time: Some(time),
1673+
blocktime: Some(time),
1674+
}));
1675+
}
1676+
1677+
self
1678+
.client
1679+
.get_raw_transaction_info(txid, None)
1680+
.into_option()
1681+
}
1682+
15991683
pub fn get_transaction(&self, txid: Txid) -> Result<Option<Transaction>> {
16001684
if txid == self.genesis_block_coinbase_txid {
16011685
return Ok(Some(self.genesis_block_coinbase_transaction.clone()));
@@ -2404,9 +2488,12 @@ impl Index {
24042488
pub(crate) fn get_output_info(&self, outpoint: OutPoint) -> Result<Option<(api::Output, TxOut)>> {
24052489
let sat_ranges = self.list(outpoint)?;
24062490

2491+
let confirmations;
24072492
let indexed;
2493+
let spent;
2494+
let txout;
24082495

2409-
let txout = if outpoint == OutPoint::null() || outpoint == unbound_outpoint() {
2496+
if outpoint == OutPoint::null() || outpoint == unbound_outpoint() {
24102497
let mut value = 0;
24112498

24122499
if let Some(ranges) = &sat_ranges {
@@ -2415,35 +2502,49 @@ impl Index {
24152502
}
24162503
}
24172504

2505+
confirmations = 0;
24182506
indexed = true;
2419-
2420-
TxOut {
2507+
spent = false;
2508+
txout = TxOut {
24212509
value: Amount::from_sat(value),
24222510
script_pubkey: ScriptBuf::new(),
2423-
}
2511+
};
24242512
} else {
24252513
indexed = self.contains_output(&outpoint)?;
24262514

2427-
let Some(tx) = self.get_transaction(outpoint.txid)? else {
2428-
return Ok(None);
2429-
};
2515+
if let Some(result) = self.get_unspent_or_unconfirmed_output(&outpoint.txid, outpoint.vout)? {
2516+
confirmations = result.confirmations;
2517+
spent = false;
2518+
txout = TxOut {
2519+
value: result.value,
2520+
script_pubkey: ScriptBuf::from_bytes(result.script_pub_key.hex),
2521+
};
2522+
} else {
2523+
let Some(result) = self.get_transaction_info(&outpoint.txid)? else {
2524+
return Ok(None);
2525+
};
24302526

2431-
let Some(txout) = tx.output.into_iter().nth(outpoint.vout as usize) else {
2432-
return Ok(None);
2433-
};
2527+
let Some(output) = result.vout.into_iter().nth(outpoint.vout.into_usize()) else {
2528+
return Ok(None);
2529+
};
24342530

2435-
txout
2531+
confirmations = result.confirmations.unwrap_or_default();
2532+
spent = true;
2533+
txout = TxOut {
2534+
value: output.value,
2535+
script_pubkey: ScriptBuf::from_bytes(output.script_pub_key.hex),
2536+
};
2537+
}
24362538
};
24372539

24382540
let inscriptions = self.get_inscriptions_for_output(outpoint)?;
24392541

24402542
let runes = self.get_rune_balances_for_output(outpoint)?;
24412543

2442-
let spent = self.is_output_spent(outpoint)?;
2443-
24442544
Ok(Some((
24452545
api::Output::new(
24462546
self.settings.chain(),
2547+
confirmations,
24472548
inscriptions,
24482549
outpoint,
24492550
txout.clone(),

0 commit comments

Comments
 (0)