use deno_core::error::type_error;
use deno_core::error::AnyError;
use deno_core::include_js_files;
use deno_core::op_async;
use deno_core::op_sync;
use deno_core::serde::Serialize;
use deno_core::serde_json::Value;
use deno_core::Extension;
use deno_core::OpState;
use deno_core::ZeroCopyBuf;
use std::cell::RefCell;
use std::rc::Rc;
use std::{env, thread};
use three_em_arweave::gql_result::GQLTagInterface;
pub struct ArweaveInfo {
port: i32,
host: String,
protocol: String,
}
#[derive(Serialize, Default, Clone)]
pub struct InteractionTx {
pub id: String,
pub owner: String,
pub tags: Vec<GQLTagInterface>,
pub target: String,
pub quantity: String,
pub reward: String,
}
#[derive(Serialize, Default, Clone)]
pub struct InteractionBlock {
pub height: usize,
pub indep_hash: String,
pub timestamp: usize,
}
#[derive(Serialize, Default, Clone)]
pub struct InteractionContext {
pub transaction: InteractionTx,
pub block: InteractionBlock,
}
pub fn init(arweave: (i32, String, String)) -> Extension {
Extension::builder()
.js(include_js_files!(
prefix "3em:smartweave",
"bignumber.js",
"smartweave.js",
"contract-assert.js",
))
.ops(vec![
(
"op_smartweave_wallet_balance",
op_async(op_smartweave_wallet_balance),
),
(
"op_smartweave_wallet_last_tx",
op_async(op_smartweave_wallet_last_tx),
),
("op_smartweave_get_host", op_async(op_smartweave_get_host)),
])
.state(move |state| {
let (port, host, protocol) = arweave.clone();
state.put(ArweaveInfo {
port,
host,
protocol,
});
Ok(())
})
.build()
}
pub async fn op_smartweave_wallet_balance(
_state: Rc<RefCell<OpState>>,
address: String,
_: (),
) -> Result<String, AnyError> {
let s = _state.borrow();
let arweave = s.borrow::<ArweaveInfo>();
let balance =
reqwest::get(format!("{}/wallet/{}/balance", get_host(arweave), address))
.await?
.text()
.await?;
Ok(balance)
}
pub async fn op_smartweave_wallet_last_tx(
_state: Rc<RefCell<OpState>>,
address: String,
_: (),
) -> Result<String, AnyError> {
let s = _state.borrow();
let arweave = s.borrow::<ArweaveInfo>();
let tx =
reqwest::get(format!("{}/wallet/{}/last_tx", get_host(arweave), address))
.await?
.text()
.await?;
Ok(tx)
}
pub fn read_contract_state(id: String) -> Value {
thread::spawn(move || {
println!("Reading contract state for {}", id);
let state: Value = reqwest::blocking::get(format!(
"https://storage.googleapis.com/verto-exchange-contracts/{}/{}_state.json",
id, id,
))
.unwrap()
.json()
.unwrap();
state
})
.join()
.unwrap()
}
pub fn get_host(arweave_info: &ArweaveInfo) -> String {
if arweave_info.port == 80 {
format!("{}://{}", arweave_info.protocol, arweave_info.host)
} else {
format!(
"{}://{}:{}",
arweave_info.protocol, arweave_info.host, arweave_info.port
)
}
}
pub async fn op_smartweave_get_host(
_state: Rc<RefCell<OpState>>,
_parameters: (),
_: (),
) -> Result<String, AnyError> {
let s = _state.borrow();
let arweave = s.borrow::<ArweaveInfo>();
Ok(get_host(arweave))
}