Skip to content

Commit

Permalink
f
Browse files Browse the repository at this point in the history
  • Loading branch information
scx1332 committed Feb 27, 2024
1 parent 19bc0cf commit ad6bee4
Show file tree
Hide file tree
Showing 4 changed files with 113 additions and 77 deletions.
11 changes: 10 additions & 1 deletion crates/erc20_payment_lib/src/runtime.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ use crate::transaction::{
create_faucet_mint, create_free_allocation, create_free_allocation_internal,
create_lock_deposit, create_lock_withdraw, create_make_allocation,
create_make_allocation_internal, create_token_transfer, find_receipt_extended,
FindReceiptParseResult,
};
use crate::{err_custom_create, err_from};
use erc20_payment_lib_common::create_sqlite_connection;
Expand Down Expand Up @@ -1531,7 +1532,15 @@ pub async fn verify_transaction(
glm_address: Address,
) -> Result<VerifyTransactionResult, PaymentError> {
let (chain_tx_dao, transfers) =
find_receipt_extended(web3, tx_hash, chain_id, glm_address).await?;
match find_receipt_extended(web3, tx_hash, chain_id, glm_address).await? {
FindReceiptParseResult::Success((chain_tx_dao, transfers)) => (chain_tx_dao, transfers),
FindReceiptParseResult::Failure(str) => {
return Ok(VerifyTransactionResult::Rejected(format!(
"Transaction cannot be parsed {str}"
)))
}
};

if chain_tx_dao.chain_status == 1 {
//one transaction can contain multiple transfers. Search for ours.
for transfer in transfers {
Expand Down
156 changes: 83 additions & 73 deletions crates/erc20_payment_lib/src/service.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ use std::sync::Arc;
use crate::error::{ErrorBag, PaymentError};
use erc20_payment_lib_common::ops::*;

use crate::transaction::find_receipt_extended;
use crate::transaction::{find_receipt_extended, FindReceiptParseResult};
use crate::utils::{ConversionError, U256ConvExt};

use crate::err_from;
Expand Down Expand Up @@ -73,6 +73,7 @@ pub async fn transaction_from_chain_and_into_db(
chain_id: i64,
tx_hash: &str,
glm_address: Address,
get_balances: bool,
) -> Result<Option<ChainTxDbObj>, PaymentError> {
println!("tx_hash: {tx_hash}");
let tx_hash = web3::types::H256::from_str(tx_hash)
Expand All @@ -88,91 +89,100 @@ pub async fn transaction_from_chain_and_into_db(
}

let (mut chain_tx_dao, transfers) =
find_receipt_extended(web3.clone(), tx_hash, chain_id, glm_address).await?;
match find_receipt_extended(web3.clone(), tx_hash, chain_id, glm_address).await? {
FindReceiptParseResult::Success((c, t)) => (c, t),
FindReceiptParseResult::Failure(str) => {
log::warn!("Transaction cannot be parsed: {}", str);
return Ok(None);
}
};

if chain_tx_dao.chain_status != 1 {
return Ok(None);
}

let mut loop_no = 0;
let balance = loop {
loop_no += 1;
match web3
.clone()
.eth_balance(
Address::from_str(&chain_tx_dao.from_addr).unwrap(),
Some(BlockNumber::Number(chain_tx_dao.block_number.into())),
)
.await
{
Ok(v) => break Some(v),
Err(e) => {
log::debug!("Error getting balance: {}", e);
if loop_no > 1000 {
break None;
if get_balances {
let mut loop_no = 0;

let balance = loop {
loop_no += 1;
match web3
.clone()
.eth_balance(
Address::from_str(&chain_tx_dao.from_addr).unwrap(),
Some(BlockNumber::Number(chain_tx_dao.block_number.into())),
)
.await
{
Ok(v) => break Some(v),
Err(e) => {
log::debug!("Error getting balance: {}", e);
if loop_no > 1000 {
break None;
}
}
}
};
tokio::time::sleep(std::time::Duration::from_millis(100)).await;
};
tokio::time::sleep(std::time::Duration::from_millis(100)).await;
};

log::info!(
"Balance: {:.5} for block {}",
balance.unwrap_or_default().to_eth().unwrap(),
chain_tx_dao.block_number
);

loop_no = 0;
let token_balance = loop {
let call_data =
encode_erc20_balance_of(Address::from_str(&chain_tx_dao.from_addr).unwrap())
.map_err(err_from!())?;
match web3
.clone()
.eth_call(
CallRequest {
from: None,
to: Some(glm_address),
gas: None,
gas_price: None,
value: None,
data: Some(web3::types::Bytes::from(call_data)),
transaction_type: None,
access_list: None,
max_fee_per_gas: None,
max_priority_fee_per_gas: None,
},
Some(web3::types::BlockId::Number(BlockNumber::Number(
chain_tx_dao.block_number.into(),
))),
)
.await
{
Ok(v) => {
if v.0.len() == 32 {
break Some(U256::from_big_endian(&v.0));
log::info!(
"Balance: {:.5} for block {}",
balance.unwrap_or_default().to_eth().unwrap(),
chain_tx_dao.block_number
);

loop_no = 0;
let token_balance = loop {
let call_data =
encode_erc20_balance_of(Address::from_str(&chain_tx_dao.from_addr).unwrap())
.map_err(err_from!())?;
match web3
.clone()
.eth_call(
CallRequest {
from: None,
to: Some(glm_address),
gas: None,
gas_price: None,
value: None,
data: Some(web3::types::Bytes::from(call_data)),
transaction_type: None,
access_list: None,
max_fee_per_gas: None,
max_priority_fee_per_gas: None,
},
Some(web3::types::BlockId::Number(BlockNumber::Number(
chain_tx_dao.block_number.into(),
))),
)
.await
{
Ok(v) => {
if v.0.len() == 32 {
break Some(U256::from_big_endian(&v.0));
}
}
Err(e) => {
log::debug!("Error getting token balance: {}", e);
}
};
if loop_no > 1000 {
break None;
}
Err(e) => {
log::debug!("Error getting token balance: {}", e);
}
tokio::time::sleep(std::time::Duration::from_millis(100)).await;
};
if loop_no > 1000 {
break None;
}
tokio::time::sleep(std::time::Duration::from_millis(100)).await;
};

log::info!(
"Token balance: {:.5} for block {}",
token_balance
.map(|v| v.to_eth().unwrap())
.unwrap_or_default(),
chain_tx_dao.block_number
);
log::info!(
"Token balance: {:.5} for block {}",
token_balance
.map(|v| v.to_eth().unwrap())
.unwrap_or_default(),
chain_tx_dao.block_number
);

chain_tx_dao.balance_eth = balance.map(|b| b.to_string());
chain_tx_dao.balance_glm = token_balance.map(|v| v.to_string());
chain_tx_dao.balance_eth = balance.map(|b| b.to_string());
chain_tx_dao.balance_glm = token_balance.map(|v| v.to_string());
}

let mut db_transaction = conn.begin().await.map_err(err_from!())?;

Expand Down
22 changes: 19 additions & 3 deletions crates/erc20_payment_lib/src/transaction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -855,15 +855,21 @@ pub async fn find_receipt(
}
}

#[allow(clippy::large_enum_variant)]
pub enum FindReceiptParseResult {
Success((ChainTxDbObj, Vec<ChainTransferDbObj>)),
Failure(String),
}

pub async fn find_receipt_extended(
web3: Arc<Web3RpcPool>,
tx_hash: H256,
chain_id: i64,
glm_address: Address,
) -> Result<(ChainTxDbObj, Vec<ChainTransferDbObj>), PaymentError> {
) -> Result<FindReceiptParseResult, PaymentError> {
let mut chain_tx_dao = ChainTxDbObj {
id: -1,
tx_hash: tx_hash.to_string(),
tx_hash: format!("{:#x}", tx_hash),
method: "".to_string(),
from_addr: "".to_string(),
to_addr: "".to_string(),
Expand Down Expand Up @@ -1024,6 +1030,11 @@ pub async fn find_receipt_extended(
let from = Address::from_slice(&log.topics[1][12..]);
let to = Address::from_slice(&log.topics[2][12..]);
let amount = U256::from(log.data.0.as_slice());
println!(
"ERC20 transfer from {:#x} to {:#x} amount {:#x}",
from, to, amount
);

if to == tx_to {
if let Some(tcf) = &transfered_to_contract_from {
if from != *tcf {
Expand Down Expand Up @@ -1064,6 +1075,11 @@ pub async fn find_receipt_extended(

if from == tx_to {
if Some(log.address) != transfered_to_contract_token {
if transfered_to_contract_token.is_none() {
return Ok(FindReceiptParseResult::Failure(
"Transfer from contract without contract from".to_string(),
));
}
return Err(err_custom_create!(
"Transfer from contract different token {:#x} != {:#x}",
log.address,
Expand Down Expand Up @@ -1103,7 +1119,7 @@ pub async fn find_receipt_extended(
}
}

Ok((chain_tx_dao, transfers))
Ok(FindReceiptParseResult::Success((chain_tx_dao, transfers)))
}

pub async fn get_erc20_logs(
Expand Down
1 change: 1 addition & 0 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -831,6 +831,7 @@ async fn main_internal() -> Result<(), PaymentError> {
chain_cfg.chain_id,
&format!("{tx:#x}"),
chain_cfg.token.address,
scan_blockchain_options.import_balances,
)
.await
{
Expand Down

0 comments on commit ad6bee4

Please sign in to comment.