pub fn rollback(&mut self, blocks: usize) {
        assert!(
            self.height().0 >= blocks as u64,
            "Cannot rollback past genesis block"
        );
        // Each block contain at least two phases:
        // 1. add tx into pool;
        // 2. commit tx from pool into next block.
        self.db_handler.rollback(blocks * 2);
    }
/// Rolls the blockchain back for a certain number of blocks.
///
/// # Examples
///
/// Rollbacks are useful in testing alternative scenarios (e.g., transactions executed
/// in different order and/or in different blocks) that require an expensive setup:
///
/// ```
/// # #[macro_use] extern crate exonum;
/// # #[macro_use] extern crate exonum_testkit;
/// # use exonum::blockchain::{Service, Transaction, TransactionSet, ExecutionResult};
/// # use exonum::messages::RawTransaction;
/// # use exonum::encoding;
/// # use exonum_testkit::{TestKit, TestKitBuilder};
/// #
/// # type FromRawResult = Result<Box<Transaction>, encoding::Error>;
/// # pub struct MyService;
/// # impl Service for MyService {
/// #    fn service_name(&self) -> &str {
/// #        "documentation"
/// #    }
/// #    fn state_hash(&self, _: &exonum::storage::Snapshot) -> Vec<exonum::crypto::Hash> {
/// #        Vec::new()
/// #    }
/// #    fn service_id(&self) -> u16 {
/// #        1
/// #    }
/// #    fn tx_from_raw(&self, raw: RawTransaction) -> FromRawResult {
/// #        let tx = MyServiceTransactions::tx_from_raw(raw)?;
/// #        Ok(tx.into())
/// #    }
/// # }
/// #
/// # transactions! {
/// #     MyServiceTransactions {
/// #         const SERVICE_ID = 1;
/// #
/// #         struct MyTransaction {
/// #             from: &exonum::crypto::PublicKey,
/// #             msg: &str,
/// #         }
/// #     }
/// # }
/// # impl Transaction for MyTransaction {
/// #     fn verify(&self) -> bool { true }
/// #     fn execute(&self, _: &mut exonum::storage::Fork) -> ExecutionResult { Ok(()) }
/// # }
/// #
/// # fn expensive_setup(_: &mut TestKit) {}
/// # fn assert_something_about(_: &TestKit) {}
/// #
/// # fn main() {
/// let mut testkit = TestKitBuilder::validator()
///     .with_service(MyService)
///     .create();
/// expensive_setup(&mut testkit);
/// let (pubkey, key) = exonum::crypto::gen_keypair();
/// let tx_a = MyTransaction::new(&pubkey, "foo", &key);
/// let tx_b = MyTransaction::new(&pubkey, "bar", &key);
/// testkit.create_block_with_transactions(txvec![tx_a.clone(), tx_b.clone()]);
/// assert_something_about(&testkit);
/// testkit.rollback(1);
/// testkit.create_block_with_transactions(txvec![tx_a.clone()]);
/// testkit.create_block_with_transactions(txvec![tx_b.clone()]);
/// assert_something_about(&testkit);
/// testkit.rollback(2);
/// # }
/// ```
Rolls the blockchain back for a certain number of blocks.
Rolls the blockchain back for a certain number of blocks .
pub fn rollback(&mut self, blocks: usize) {
        assert!(
            self.height().0 >= blocks as u64,
            "Cannot rollback past genesis block"
        );
        // Each block contain at least two phases:
        // 1. add tx into pool;
        // 2. commit tx from pool into next block.
        self.db_handler.rollback(blocks * 2);
    }
pub fn rollback ( & mut self , blocks : usize ) { assert ! ( self height ( ) 0 blocks as u64 " " ) ; // Each block contain at least two phases: // 1. add tx into pool; // 2. commit tx from pool into next block. self . db_handler . rollback ( blocks * 2 ) ; }
Rolls the blockchain back for a certain number of blocks.
Rolls the blockchain back for a certain number of blocks .
&mut self
blocks
usize
&mut self
blocks
usize
examples
Rollbacks are useful in testing alternative scenarios  that require an expensive setup.


Rollbacks are useful in testing alternative scenarios that require an expensive setup .
#[macro_use] extern crate exonum;
None
#[macro_use] extern crate exonum_testkit;
None
use exonum::blockchain::{service, transaction, transactionset, executionresult};
None
use exonum::messages::rawtransaction;
None
use exonum::encoding;
None
use exonum_testkit::{testkit, testkitbuilder};
None
type fromrawresult = result<box<transaction>, encoding::error>;
None
pub struct myservice;
None
impl service for myservice {
None
fn service_name(&self) -> &str {
None
"documentation"
None
}
None
fn state_hash(&self, _: &exonum::storage::snapshot) -> vec<exonum::crypto::hash> {
None
vec::new()
None
}
None
fn service_id(&self) -> u16 {
None
1
None
}
None
fn tx_from_raw(&self, raw: rawtransaction) -> fromrawresult {
None
let tx = myservicetransactions::tx_from_raw(raw)?;
None
ok(tx.into())
None
}
None
}
None
transactions! {
None
myservicetransactions {
None
const service_id = 1;
None
struct mytransaction {
None
from: &exonum::crypto::publickey,
None
msg: &str,
None
}
None
}
None
}
None
impl transaction for mytransaction {
None
fn verify(&self) -> bool { true }
None
fn execute(&self, _: &mut exonum::storage::fork) -> executionresult { ok(()) }
None
}
None
fn expensive_setup(_: &mut testkit) {}
None
fn assert_something_about(_: &testkit) {}
None
fn main() {
let mut testkit = TestKitBuilder::validator()
.with_service(MyService)
.create();
expensive_setup(&mut testkit);
let (pubkey, key) = exonum::crypto::gen_keypair();
let tx_a = MyTransaction::new(&pubkey, "foo", &key);
let tx_b = MyTransaction::new(&pubkey, "bar", &key);
testkit.create_block_with_transactions(txvec![tx_a.clone(), tx_b.clone()]);
assert_something_about(&testkit);
testkit.rollback(1);
testkit.create_block_with_transactions(txvec![tx_a.clone()]);
testkit.create_block_with_transactions(txvec![tx_b.clone()]);
assert_something_about(&testkit);
testkit.rollback(2).
let mut testkit = TestKitBuilder :: validator () . with_service ( MyService ) . create () ; expensive_setup ( &mut testkit ) ; let ( pubkey key ) = exonum :: crypto :: gen_keypair () ; let tx_a = MyTransaction :: new ( &pubkey " foo " &key ) ; let tx_b = MyTransaction :: new ( &pubkey " bar " &key ) ; testkit . create_block_with_transactions ( txvec! [ tx_a . clone () tx_b . clone () ] ) ; assert_something_about ( &testkit ) ; testkit . rollback ( 1 ) ; testkit . create_block_with_transactions ( txvec! [ tx_a . clone () ] ) ; testkit . create_block_with_transactions ( txvec! [ tx_b . clone () ] ) ; assert_something_about ( &testkit ) ; testkit . rollback ( 2 ) .
}
None