Fix eth_call so it doesn't need the secret of the sender.
This commit is contained in:
parent
aaf04e793d
commit
845fa97da1
@ -905,7 +905,7 @@ mod tests {
|
||||
gas: U256::from(100_000),
|
||||
gas_price: U256::zero(),
|
||||
nonce: U256::zero()
|
||||
}.fake_sign();
|
||||
}.invalid_sign();
|
||||
let mut state_result = get_temp_state();
|
||||
let mut state = state_result.reference_mut();
|
||||
let mut info = EnvInfo::default();
|
||||
|
@ -134,7 +134,7 @@ impl Transaction {
|
||||
|
||||
/// Useful for test incorrectly signed transactions.
|
||||
#[cfg(test)]
|
||||
pub fn fake_sign(self) -> SignedTransaction {
|
||||
pub fn invalid_sign(self) -> SignedTransaction {
|
||||
SignedTransaction {
|
||||
unsigned: self,
|
||||
r: U256::zero(),
|
||||
@ -145,6 +145,18 @@ impl Transaction {
|
||||
}
|
||||
}
|
||||
|
||||
/// Specify the sender; this won't survive the serialize/deserialize process, but can be cloned.
|
||||
pub fn fake_sign(self, from: Address) -> SignedTransaction {
|
||||
SignedTransaction {
|
||||
unsigned: self,
|
||||
r: U256::zero(),
|
||||
s: U256::zero(),
|
||||
v: 0,
|
||||
hash: Cell::new(None),
|
||||
sender: Cell::new(Some(from)),
|
||||
}
|
||||
}
|
||||
|
||||
/// Get the transaction cost in gas for the given params.
|
||||
pub fn gas_required_for(is_create: bool, data: &[u8], schedule: &Schedule) -> u64 {
|
||||
data.iter().fold(
|
||||
@ -342,3 +354,19 @@ fn signing() {
|
||||
}.sign(&key.secret());
|
||||
assert_eq!(Address::from(key.public().sha3()), t.sender().unwrap());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn fake_signing() {
|
||||
let t = Transaction {
|
||||
action: Action::Create,
|
||||
nonce: U256::from(42),
|
||||
gas_price: U256::from(3000),
|
||||
gas: U256::from(50_000),
|
||||
value: U256::from(1),
|
||||
data: b"Hello!".to_vec()
|
||||
}.fake_sign(Address::from(0x69));
|
||||
assert_eq!(Address::from(0x69), t.sender().unwrap());
|
||||
|
||||
let t = t.clone();
|
||||
assert_eq!(Address::from(0x69), t.sender().unwrap());
|
||||
}
|
||||
|
@ -24,7 +24,6 @@ use jsonrpc_core::*;
|
||||
use util::numbers::*;
|
||||
use util::sha3::*;
|
||||
use util::rlp::{encode, UntrustedRlp, View};
|
||||
use util::crypto::KeyPair;
|
||||
use ethcore::client::*;
|
||||
use ethcore::block::IsBlock;
|
||||
use ethcore::views::*;
|
||||
@ -168,33 +167,16 @@ impl<C, S, A, M, EM> EthClient<C, S, A, M, EM>
|
||||
}
|
||||
}
|
||||
|
||||
fn sign_call(client: &Arc<C>, accounts: &Arc<A>, request: CallRequest) -> Option<SignedTransaction> {
|
||||
match request.from {
|
||||
Some(ref from) => {
|
||||
let transaction = EthTransaction {
|
||||
nonce: request.nonce.unwrap_or_else(|| client.nonce(from)),
|
||||
fn sign_call(client: &Arc<C>, request: CallRequest) -> SignedTransaction {
|
||||
let from = request.from.unwrap_or(Address::zero());
|
||||
EthTransaction {
|
||||
nonce: request.nonce.unwrap_or_else(|| client.nonce(&from)),
|
||||
action: request.to.map_or(Action::Create, Action::Call),
|
||||
gas: request.gas.unwrap_or_else(default_gas),
|
||||
gas_price: request.gas_price.unwrap_or_else(default_gas_price),
|
||||
value: request.value.unwrap_or_else(U256::zero),
|
||||
data: request.data.map_or_else(Vec::new, |d| d.to_vec())
|
||||
};
|
||||
|
||||
accounts.account_secret(from).ok().map(|secret| transaction.sign(&secret))
|
||||
},
|
||||
None => {
|
||||
let transaction = EthTransaction {
|
||||
nonce: request.nonce.unwrap_or_else(U256::zero),
|
||||
action: request.to.map_or(Action::Create, Action::Call),
|
||||
gas: request.gas.unwrap_or_else(default_gas),
|
||||
gas_price: request.gas_price.unwrap_or_else(default_gas_price),
|
||||
value: request.value.unwrap_or_else(U256::zero),
|
||||
data: request.data.map_or_else(Vec::new, |d| d.to_vec())
|
||||
};
|
||||
|
||||
KeyPair::create().ok().map(|kp| transaction.sign(kp.secret()))
|
||||
}
|
||||
}
|
||||
}.fake_sign(from)
|
||||
}
|
||||
}
|
||||
|
||||
@ -533,12 +515,10 @@ impl<C, S, A, M, EM> Eth for EthClient<C, S, A, M, EM>
|
||||
fn call(&self, params: Params) -> Result<Value, Error> {
|
||||
from_params_discard_second(params).and_then(|(request, )| {
|
||||
let client = take_weak!(self.client);
|
||||
let accounts = take_weak!(self.accounts);
|
||||
let signed = Self::sign_call(&client, &accounts, request);
|
||||
let output = signed.map(|tx| client.call(&tx)
|
||||
.map(|e| Bytes::new(e.output))
|
||||
.unwrap_or(Bytes::default()));
|
||||
|
||||
let signed = Self::sign_call(&client, request);
|
||||
info!("call: signed={:?}", signed);
|
||||
let output = client.call(&signed).map(|e| Bytes(e.output)).unwrap_or(Bytes::new(vec![]));
|
||||
info!("call: output={:?}", output);
|
||||
to_value(&output)
|
||||
})
|
||||
}
|
||||
@ -546,13 +526,9 @@ impl<C, S, A, M, EM> Eth for EthClient<C, S, A, M, EM>
|
||||
fn estimate_gas(&self, params: Params) -> Result<Value, Error> {
|
||||
from_params_discard_second(params).and_then(|(request, )| {
|
||||
let client = take_weak!(self.client);
|
||||
let accounts = take_weak!(self.accounts);
|
||||
let signed = Self::sign_call(&client, &accounts, request);
|
||||
let output = signed.map(|tx| client.call(&tx)
|
||||
.map(|e| e.gas_used + e.refunded)
|
||||
.unwrap_or(U256::zero()));
|
||||
|
||||
to_value(&output)
|
||||
let signed = Self::sign_call(&client, request);
|
||||
let used = client.call(&signed).map(|res| res.gas_used + res.refunded).unwrap_or(From::from(0));
|
||||
to_value(&used)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@ -345,6 +345,7 @@ fn rpc_eth_call_default_block() {
|
||||
logs: vec![],
|
||||
contracts_created: vec![],
|
||||
output: vec![0x12, 0x34, 0xff],
|
||||
trace: None,
|
||||
});
|
||||
|
||||
let request = r#"{
|
||||
@ -409,6 +410,7 @@ fn rpc_eth_estimate_gas_default_block() {
|
||||
logs: vec![],
|
||||
contracts_created: vec![],
|
||||
output: vec![0x12, 0x34, 0xff],
|
||||
trace: None,
|
||||
});
|
||||
|
||||
let request = r#"{
|
||||
|
Loading…
Reference in New Issue
Block a user