• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

stacks-network / stacks-core / 23943169302

03 Apr 2026 10:28AM UTC coverage: 77.573% (-8.1%) from 85.712%
23943169302

Pull #7076

github

7f2377
web-flow
Merge bb87ecec2 into c529ad924
Pull Request #7076: feat: sortition side-table copy and validation

3743 of 4318 new or added lines in 19 files covered. (86.68%)

19304 existing lines in 182 files now uncovered.

172097 of 221852 relevant lines covered (77.57%)

7722182.76 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

62.5
/stacks-node/src/burnchains/mod.rs
1
pub mod bitcoin;
2
pub mod bitcoin_regtest_controller;
3
pub mod mocknet_controller;
4
pub mod rpc;
5

6
use std::time::Instant;
7

8
use stacks::burnchains;
9
use stacks::burnchains::{BurnchainStateTransitionOps, Txid};
10
use stacks::chainstate::burn::db::sortdb::SortitionDB;
11
use stacks::chainstate::burn::operations::BlockstackOperationType;
12
use stacks::chainstate::burn::BlockSnapshot;
13
use stacks::core::{EpochList, StacksEpochId};
14
use stacks_common::codec::Error as CodecError;
15

16
pub use self::bitcoin_regtest_controller::{make_bitcoin_indexer, BitcoinRegtestController};
17
pub use self::mocknet_controller::MocknetController;
18
use super::operations::BurnchainOpSigner;
19

20
#[derive(Debug, thiserror::Error)]
21
pub enum Error {
22
    #[error("ChainsCoordinator closed")]
23
    CoordinatorClosed,
24
    #[error("Indexer error: {0}")]
25
    IndexerError(#[from] burnchains::Error),
26
    #[error("Burnchain error")]
27
    BurnchainError,
28
    #[error("Max fee rate exceeded")]
29
    MaxFeeRateExceeded,
30
    #[error("Identical operation, not submitting")]
31
    IdenticalOperation,
32
    #[error("No UTXOs available")]
33
    NoUTXOs,
34
    #[error("Transaction submission failed: {0}")]
35
    TransactionSubmissionFailed(String),
36
    #[error("Serializer error: {0}")]
37
    SerializerError(CodecError),
38
}
39

40
impl PartialEq for Error {
UNCOV
41
    fn eq(&self, other: &Self) -> bool {
×
42
        use Error::*;
UNCOV
43
        match (self, other) {
×
44
            (CoordinatorClosed, CoordinatorClosed)
45
            | (IndexerError(_), IndexerError(_))
46
            | (BurnchainError, BurnchainError)
47
            | (MaxFeeRateExceeded, MaxFeeRateExceeded)
48
            | (IdenticalOperation, IdenticalOperation)
49
            | (NoUTXOs, NoUTXOs)
50
            | (TransactionSubmissionFailed(_), TransactionSubmissionFailed(_))
UNCOV
51
            | (SerializerError(_), SerializerError(_)) => true,
×
52
            _ => false,
×
53
        }
UNCOV
54
    }
×
55
}
56

57
pub trait BurnchainController {
58
    fn start(&mut self, target_block_height_opt: Option<u64>)
59
        -> Result<(BurnchainTip, u64), Error>;
60
    fn submit_operation(
61
        &mut self,
62
        epoch_id: StacksEpochId,
63
        operation: BlockstackOperationType,
64
        op_signer: &mut BurnchainOpSigner,
65
    ) -> Result<Txid, Error>;
66
    fn sync(&mut self, target_block_height_opt: Option<u64>) -> Result<(BurnchainTip, u64), Error>;
67
    fn sortdb_ref(&self) -> &SortitionDB;
68
    fn sortdb_mut(&mut self) -> &mut SortitionDB;
69
    fn get_chain_tip(&self) -> BurnchainTip;
70
    fn get_headers_height(&self) -> u64;
71
    /// Invoke connect() on underlying burnchain and sortition databases, to perform any migration
72
    ///  or instantiation before other callers may use open()
73
    fn connect_dbs(&mut self) -> Result<(), Error>;
74
    fn get_stacks_epochs(&self) -> EpochList;
75

76
    #[cfg(test)]
77
    fn bootstrap_chain(&self, blocks_count: u64);
78
}
79

80
#[derive(Debug, Clone)]
81
pub struct BurnchainTip {
82
    pub block_snapshot: BlockSnapshot,
83
    pub state_transition: BurnchainStateTransitionOps,
84
    pub received_at: Instant,
85
}
86

87
impl BurnchainTip {
88
    pub fn get_winning_tx_index(&self) -> Option<u32> {
35✔
89
        let winning_tx_id = &self.block_snapshot.winning_block_txid;
35✔
90
        let mut winning_tx_vtindex = None;
35✔
91

92
        for op in self.state_transition.accepted_ops.iter() {
35✔
93
            if let BlockstackOperationType::LeaderBlockCommit(op) = op {
35✔
94
                if &op.txid == winning_tx_id {
27✔
95
                    winning_tx_vtindex = Some(op.vtxindex)
27✔
96
                }
×
97
            }
8✔
98
        }
99
        winning_tx_vtindex
35✔
100
    }
35✔
101
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc