1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
use std::collections::HashMap;

use crate::{
    chaintypes::HeaderId,
    key::EitherEd25519SecretKey,
    testing::data::{AddressData, AddressDataValue},
    tokens::name::TokenName,
    transaction::{Input, Output, TransactionAuthData, Witness},
    value::Value,
};
use chain_addr::{Address, Discrimination};
use chain_crypto::{Ed25519, PublicKey};

#[derive(Clone, Debug)]
pub struct Wallet {
    alias: String,
    account: AddressDataValue,
}

impl Wallet {
    pub fn from_address_data_value_and_alias<S: Into<String>>(
        alias: S,
        account: AddressDataValue,
    ) -> Self {
        Wallet {
            alias: alias.into(),
            account,
        }
    }

    pub fn from_address_data_value(account: AddressDataValue) -> Self {
        Wallet {
            alias: "".to_owned(),
            account,
        }
    }

    pub fn from_value(initial_value: Value) -> Self {
        Wallet::new("", initial_value)
    }

    pub fn new(alias: &str, initial_value: Value) -> Self {
        Wallet {
            alias: alias.to_owned(),
            account: AddressDataValue::account(Discrimination::Test, initial_value),
        }
    }

    pub fn new_with_tokens(
        alias: &str,
        initial_value: Value,
        tokens: HashMap<TokenName, Value>,
    ) -> Self {
        Wallet {
            alias: alias.to_owned(),
            account: AddressDataValue::account_with_tokens(
                Discrimination::Test,
                initial_value,
                tokens,
            ),
        }
    }

    pub fn alias(&self) -> &str {
        &self.alias
    }

    pub fn value(&self) -> Value {
        self.account.value
    }

    pub fn public_key(&self) -> PublicKey<Ed25519> {
        self.account.public_key()
    }

    pub fn private_key(&self) -> EitherEd25519SecretKey {
        self.account.private_key()
    }

    pub fn make_output(&self) -> Output<Address> {
        self.account.make_output()
    }

    pub fn make_output_with_value(&self, value: Value) -> Output<Address> {
        self.account.make_output_with_value(value)
    }

    pub fn make_input_with_value(&self, value: Value) -> Input {
        self.account.make_input_with_value(None, value)
    }

    pub fn as_account(&self) -> AddressDataValue {
        self.account.clone()
    }

    pub fn as_account_data(&self) -> AddressData {
        self.as_account().into()
    }

    pub fn as_address(&self) -> Address {
        self.as_account_data().address
    }

    pub fn confirm_transaction(&mut self) {
        self.confirm_transaction_at_lane(0);
    }

    pub fn confirm_transaction_at_lane(&mut self, lane: usize) {
        self.account.confirm_transaction_at_lane(lane).unwrap();
    }

    pub fn make_witness(
        &mut self,
        block0_hash: &HeaderId,
        tad: TransactionAuthData<'_>,
    ) -> Witness {
        self.make_witness_at_lane(block0_hash, 0, tad)
    }

    pub fn make_witness_at_lane(
        &mut self,
        block0_hash: &HeaderId,
        lane: usize,
        tad: TransactionAuthData<'_>,
    ) -> Witness {
        self.as_account()
            .make_witness_with_lane(block0_hash, lane, tad)
    }
}