Started work on event loop and callback structure

This commit is contained in:
PMunch 2019-01-07 17:59:57 +01:00
parent 0c82c97369
commit c3d4029a9c
3 changed files with 54 additions and 11 deletions

View File

@ -15,7 +15,7 @@ proc eth_mining(): bool
proc eth_hashrate(): int
proc eth_gasPrice(): int64
proc eth_accounts(): seq[array[20, byte]]
proc eth_blockNumber(): int
proc eth_blockNumber(): string
proc eth_getBalance(data: array[20, byte], quantityTag: string): int
proc eth_getStorageAt(data: array[20, byte], quantity: int, quantityTag: string): seq[byte]
proc eth_getTransactionCount(data: array[20, byte], quantityTag: string)

View File

@ -102,10 +102,10 @@ type
# TODO: I don't think this will work as input, need only one value that is either UInt256 or seq[UInt256]
FilterOptions* = object
fromBlock*: string # (optional, default: "latest") integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions.
toBlock*: string # (optional, default: "latest") integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions.
address*: seq[array[20, byte]] # (optional) contract address or a list of addresses from which logs should originate.
topics*: seq[FilterData] # (optional) list of DATA topics. Topics are order-dependent. Each topic can also be a list of DATA with "or" options.
fromBlock*: Option[string] # (optional, default: "latest") integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions.
toBlock*: Option[string] # (optional, default: "latest") integer block number, or "latest" for the last mined block or "pending", "earliest" for not yet mined transactions.
address*: Option[string] # (optional) contract address or a list of addresses from which logs should originate.
topics*: Option[seq[string]]#Option[seq[FilterData]] # (optional) list of DATA topics. Topics are order-dependent. Each topic can also be a list of DATA with "or" options.
LogObject* = object
#removed*: bool # true when the log was removed, due to a chain reorganization. false if its a valid log.
@ -189,3 +189,17 @@ proc `%`*(x: EthCall): JsonNode =
result["value"] = %x.value.unsafeGet
if x.data.isSome:
result["data"] = %x.data.unsafeGet
proc `%`*(x: byte): JsonNode =
%x.int
proc `%`*(x: FilterOptions): JsonNode =
result = newJobject()
if x.fromBlock.isSome:
result["fromBlock"] = %x.fromBlock.unsafeGet
if x.toBlock.isSome:
result["toBlock"] = %x.toBlock.unsafeGet
if x.address.isSome:
result["address"] = %x.address.unsafeGet
if x.topics.isSome:
result["topics"] = %x.topics.unsafeGet

View File

@ -1,5 +1,5 @@
import macros, strutils, options, math, json
from os import getCurrentDir, DirSep
from os import getCurrentDir, DirSep, sleep
import
nimcrypto, stint, httputils, chronicles, asyncdispatch2, json_rpc/rpcclient
import ethtypes, ethprocs, stintjson, ethhexstrings
@ -286,9 +286,16 @@ proc parseContract(body: NimNode): seq[InterfaceObject] =
macro contract(cname: untyped, body: untyped): untyped =
var objects = parseContract(body)
result = newStmtList()
let address = ident "address"
result.add quote do:
type
`cname` = distinct Contract
#`cname` = distinct Contract
`cname` = ref object
`address`: array[20, byte]
#callbacks: tuple[
# Transfer: seq[proc (fromAddr: Address, toAddr: Address, value: Uint256)]
#]
for obj in objects:
if obj.kind == function:
echo obj.functionObject.outputs
@ -328,7 +335,8 @@ macro contract(cname: untyped, body: untyped): untyped =
procDef[6].add quote do:
var cc: EthCall
cc.source = some(`senderName`.address)
cc.to = `senderName`.contract.Contract.address
#cc.to = `senderName`.contract.Contract.address
cc.to = `senderName`.contract.address
cc.data = some("0x" & ($keccak_256.digest(`signature`))[0..<8].toLower & `encodedParams`)
let response = waitFor `client`.eth_call(cc, "latest")
return response
@ -336,7 +344,8 @@ macro contract(cname: untyped, body: untyped): untyped =
procDef[6].add quote do:
var cc: EthSend
cc.source = `senderName`.address
cc.to = some(`senderName`.contract.Contract.address)
#cc.to = some(`senderName`.contract.Contract.address)
cc.to = some(`senderName`.contract.address)
cc.data = "0x" & ($keccak_256.digest(`signature`))[0..<8].toLower & `encodedParams`
let response = waitFor `client`.eth_sendTransaction(cc)
return response
@ -393,7 +402,26 @@ macro toAddress(input: string): untyped =
ident "byte"
)
var x = Contract(address: "254dffcd3277C0b1660F6d42EFbB754edaBAbC2B".toAddress).TestContract
proc eventListen(callback: proc(receipt: LogObject)) =
var client = newRpcHttpClient()
client.httpMethod(MethodPost)
waitFor client.connect("127.0.0.1", Port(8545))
var lastBlock = "0x" & (parseHexInt((waitFor client.eth_blockNumber())[2..^1]) + 1).toHex[^2..^1]
while true:
waitFor client.connect("127.0.0.1", Port(8545))
let response = waitFor client.eth_getLogs(FilterOptions(fromBlock: some(lastBlock), toBlock: none(string), address: some("0x254dffcd3277C0b1660F6d42EFbB754edaBAbC2B".toLower), topics: none(seq[string])))
if response.len > 0:
lastBlock = "0x" & (parseHexInt(response[^1].blockNumber[2..^1]) + 1).toHex[^2..^1]
for receipt in response:
callback(receipt)
sleep(1000)
var thr: Thread[proc(receipt: LogObject)]
createThread(thr, eventListen, proc(receipt: LogObject) =
echo receipt
)
var x = TestContract(address: "254dffcd3277C0b1660F6d42EFbB754edaBAbC2B".toAddress)#.TestContract
echo x.sender("127.0.0.1", 8545, "90f8bf6a479f320ead074411a4b0e7944ea8c9c1".toAddress).getBalance(
fromHex(Stuint[256], "ffcf8fdee72ac11b5c542428b35eef5769c409f0")
@ -401,10 +429,11 @@ echo x.sender("127.0.0.1", 8545, "90f8bf6a479f320ead074411a4b0e7944ea8c9c1".toAd
echo toHex(x.sender("127.0.0.1", 8545, "90f8bf6a479f320ead074411a4b0e7944ea8c9c1".toAddress).sendCoin(
fromHex(Stuint[256], "ffcf8fdee72ac11b5c542428b35eef5769c409f0"),
100000.to(Stuint[256])
256.to(Stuint[256])
))
echo x.sender("127.0.0.1", 8545, "90f8bf6a479f320ead074411a4b0e7944ea8c9c1".toAddress).getBalance(
fromHex(Stuint[256], "ffcf8fdee72ac11b5c542428b35eef5769c409f0")
)
#echo "0x" & $keccak_256.digest("Transfer(address,address,uint256)")
joinThreads([thr])