commit
d23139c181
@ -0,0 +1,5 @@ |
|||||||
|
/_build |
||||||
|
/cover |
||||||
|
/deps |
||||||
|
erl_crash.dump |
||||||
|
*.ez |
@ -0,0 +1,17 @@ |
|||||||
|
# EXW3 |
||||||
|
|
||||||
|
**TODO: Add description** |
||||||
|
|
||||||
|
## Installation |
||||||
|
|
||||||
|
1. Add exw3 to your list of dependencies in mix.exs: |
||||||
|
|
||||||
|
def deps do |
||||||
|
[{:exw3, "~> 0.0.1"}] |
||||||
|
end |
||||||
|
|
||||||
|
2. Ensure exw3 is started before your application: |
||||||
|
|
||||||
|
def application do |
||||||
|
[applications: [:exw3]] |
||||||
|
end |
@ -0,0 +1,28 @@ |
|||||||
|
# This file is responsible for configuring your application |
||||||
|
# and its dependencies with the aid of the Mix.Config module. |
||||||
|
use Mix.Config |
||||||
|
|
||||||
|
# This configuration is loaded before any dependency and is restricted |
||||||
|
# to this project. If another project depends on this project, this |
||||||
|
# file won't be loaded nor affect the parent project. For this reason, |
||||||
|
# if you want to provide default values for your application for third- |
||||||
|
# party users, it should be done in your mix.exs file. |
||||||
|
|
||||||
|
# Sample configuration: |
||||||
|
# |
||||||
|
# config :logger, |
||||||
|
# level: :info |
||||||
|
# |
||||||
|
# config :logger, :console, |
||||||
|
# format: "$date $time [$level] $metadata$message\n", |
||||||
|
# metadata: [:user_id] |
||||||
|
|
||||||
|
# It is also possible to import configuration files, relative to this |
||||||
|
# directory. For example, you can emulate configuration per environment |
||||||
|
# by uncommenting the line below and defining dev.exs, test.exs and such. |
||||||
|
# Configuration from the imported file will override the ones defined |
||||||
|
# here (which is why it is important to import them last). |
||||||
|
# |
||||||
|
# import_config "#{Mix.env}.exs" |
||||||
|
config :ethereumex, |
||||||
|
url: "http://localhost:8545" |
@ -0,0 +1,44 @@ |
|||||||
|
defmodule EXW3 do |
||||||
|
|
||||||
|
@moduledoc """ |
||||||
|
Documentation for EXW3. |
||||||
|
""" |
||||||
|
|
||||||
|
@doc """ |
||||||
|
Hello world. |
||||||
|
|
||||||
|
## Examples |
||||||
|
|
||||||
|
iex> EXW3.hello |
||||||
|
:world |
||||||
|
|
||||||
|
""" |
||||||
|
def hello do |
||||||
|
:world |
||||||
|
end |
||||||
|
|
||||||
|
def accounts do |
||||||
|
case Ethereumex.HttpClient.eth_accounts do |
||||||
|
{:ok, accounts} -> accounts |
||||||
|
err -> err |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
def reformat_abi abi do |
||||||
|
Map.new Enum.map(abi, fn x -> {x["name"], x} end) |
||||||
|
end |
||||||
|
|
||||||
|
def load_abi file_path do |
||||||
|
file = File.read Path.join(System.cwd, file_path) |
||||||
|
case file do |
||||||
|
{:ok, abi} -> reformat_abi Poison.Parser.parse! abi |
||||||
|
err -> err |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
def encode abi, name, args do |
||||||
|
inputs = Enum.map abi[name]["inputs"], fn x -> x["type"] end |
||||||
|
fn_signature = Enum.join [name, "(", Enum.join(inputs, ","), ")"] |
||||||
|
ABI.encode(fn_signature, args) |
||||||
|
end |
||||||
|
end |
@ -0,0 +1,36 @@ |
|||||||
|
defmodule EXW3.Mixfile do |
||||||
|
use Mix.Project |
||||||
|
|
||||||
|
def project do |
||||||
|
[app: :exw3, |
||||||
|
version: "0.0.1", |
||||||
|
elixir: "~> 1.1-dev", |
||||||
|
build_embedded: Mix.env == :prod, |
||||||
|
start_permanent: Mix.env == :prod, |
||||||
|
deps: deps()] |
||||||
|
end |
||||||
|
|
||||||
|
# Configuration for the OTP application |
||||||
|
# |
||||||
|
# Type `mix help compile.app` for more information |
||||||
|
def application do |
||||||
|
[applications: [:logger, :ethereumex]] |
||||||
|
end |
||||||
|
|
||||||
|
# Dependencies can be Hex packages: |
||||||
|
# |
||||||
|
# {:mydep, "~> 0.3.0"} |
||||||
|
# |
||||||
|
# Or git/path repositories: |
||||||
|
# |
||||||
|
# {:mydep, git: "https://github.com/elixir-lang/mydep.git", tag: "0.1.0"} |
||||||
|
# |
||||||
|
# Type `mix help deps` for more examples and options |
||||||
|
defp deps do |
||||||
|
[ |
||||||
|
{:ethereumex, "~> 0.3.2"}, |
||||||
|
{:abi, "~> 0.1.8"}, |
||||||
|
{:poison, "~> 3.1"} |
||||||
|
] |
||||||
|
end |
||||||
|
end |
@ -0,0 +1,17 @@ |
|||||||
|
%{ |
||||||
|
"abi": {:hex, :abi, "0.1.12", "87ae04cb09e2308db7b3c350584dc3934de0e308f6a056ba82be5756b081a1ca", [:mix], [{:exth_crypto, "~> 0.1.4", [hex: :exth_crypto, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"binary": {:hex, :binary, "0.0.4", "dd077db70c0ded3e85c132b802338e14b80694684a7e2277666bfa4004b7fa66", [:mix], [], "hexpm"}, |
||||||
|
"certifi": {:hex, :certifi, "2.0.0", "a0c0e475107135f76b8c1d5bc7efb33cd3815cb3cf3dea7aefdd174dabead064", [:rebar3], [], "hexpm"}, |
||||||
|
"ethereumex": {:hex, :ethereumex, "0.3.2", "ee01a49c781c9751317b2918f799e84185203c81c8314ebebb1f1e22b754db3e", [:mix], [{:httpoison, "~> 1.0.0", [hex: :httpoison, repo: "hexpm", optional: false]}, {:poison, "~> 3.1.0", [hex: :poison, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"exth_crypto": {:hex, :exth_crypto, "0.1.4", "11f9084dfd70d4f9e96f2710a472f4e6b23044b97530c719550c2b0450ffeb61", [:mix], [{:binary, "~> 0.0.4", [hex: :binary, repo: "hexpm", optional: false]}, {:keccakf1600, "~> 2.0.0", [hex: :keccakf1600_orig, repo: "hexpm", optional: false]}, {:libsecp256k1, "~> 0.1.3", [hex: :libsecp256k1, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"hackney": {:hex, :hackney, "1.11.0", "4951ee019df102492dabba66a09e305f61919a8a183a7860236c0fde586134b6", [:rebar3], [{:certifi, "2.0.0", [hex: :certifi, repo: "hexpm", optional: false]}, {:idna, "5.1.0", [hex: :idna, repo: "hexpm", optional: false]}, {:metrics, "1.0.1", [hex: :metrics, repo: "hexpm", optional: false]}, {:mimerl, "1.0.2", [hex: :mimerl, repo: "hexpm", optional: false]}, {:ssl_verify_fun, "1.1.1", [hex: :ssl_verify_fun, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"httpoison": {:hex, :httpoison, "1.0.0", "1f02f827148d945d40b24f0b0a89afe40bfe037171a6cf70f2486976d86921cd", [:mix], [{:hackney, "~> 1.8", [hex: :hackney, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"idna": {:hex, :idna, "5.1.0", "d72b4effeb324ad5da3cab1767cb16b17939004e789d8c0ad5b70f3cea20c89a", [:rebar3], [{:unicode_util_compat, "0.3.1", [hex: :unicode_util_compat, repo: "hexpm", optional: false]}], "hexpm"}, |
||||||
|
"keccakf1600": {:hex, :keccakf1600_orig, "2.0.0", "0a7217ddb3ee8220d449bbf7575ec39d4e967099f220a91e3dfca4dbaef91963", [:rebar3], [], "hexpm"}, |
||||||
|
"libsecp256k1": {:hex, :libsecp256k1, "0.1.3", "57468b986af7c9633527875f71c7ca08bf4150b07b38a60d5bd48fba299ff6c1", [:rebar3], [], "hexpm"}, |
||||||
|
"metrics": {:hex, :metrics, "1.0.1", "25f094dea2cda98213cecc3aeff09e940299d950904393b2a29d191c346a8486", [:rebar3], [], "hexpm"}, |
||||||
|
"mimerl": {:hex, :mimerl, "1.0.2", "993f9b0e084083405ed8252b99460c4f0563e41729ab42d9074fd5e52439be88", [:rebar3], [], "hexpm"}, |
||||||
|
"poison": {:hex, :poison, "3.1.0", "d9eb636610e096f86f25d9a46f35a9facac35609a7591b3be3326e99a0484665", [:mix], [], "hexpm"}, |
||||||
|
"ssl_verify_fun": {:hex, :ssl_verify_fun, "1.1.1", "28a4d65b7f59893bc2c7de786dec1e1555bd742d336043fe644ae956c3497fbe", [:make, :rebar], [], "hexpm"}, |
||||||
|
"unicode_util_compat": {:hex, :unicode_util_compat, "0.3.1", "a1f612a7b512638634a603c8f401892afbf99b8ce93a45041f8aaca99cadb85e", [:rebar3], [], "hexpm"}, |
||||||
|
} |
@ -0,0 +1,21 @@ |
|||||||
|
require './lib/w3' |
||||||
|
|
||||||
|
url = "http://localhost:8545" |
||||||
|
http_client = W3::Http_Client.new(url) |
||||||
|
|
||||||
|
eth = W3::ETH.new(http_client) |
||||||
|
|
||||||
|
accounts = eth.get_accounts |
||||||
|
pp accounts |
||||||
|
|
||||||
|
puts "Block number: #{eth.get_block_number}" |
||||||
|
|
||||||
|
abi = JSON.parse(File.read(File.join(File.dirname(__FILE__), './build/ArrayTester.abi'))) |
||||||
|
array_tester = W3::Contract.new(eth, abi) |
||||||
|
|
||||||
|
bin = File.read(File.join(File.dirname(__FILE__), './build/ArrayTester.bin')) |
||||||
|
array_tester.at! array_tester.deploy!(bin, {"from" => accounts[0], "gas" => 300000}) |
||||||
|
|
||||||
|
pp array_tester.dynamic_uint([1, 2, 3, 4, 5,]) |
||||||
|
|
||||||
|
#pp array_tester.static_uint([1, 2, 3, 4, 5,]) |
@ -0,0 +1 @@ |
|||||||
|
[{"constant":true,"inputs":[{"name":"ints","type":"uint256[5]"}],"name":"staticUint","outputs":[{"name":"","type":"uint256[5]"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[{"name":"ints","type":"uint256[]"}],"name":"dynamicUint","outputs":[{"name":"","type":"uint256[]"}],"payable":false,"stateMutability":"pure","type":"function"}] |
@ -0,0 +1 @@ |
|||||||
|
6060604052341561000f57600080fd5b61020a8061001e6000396000f30060606040526004361061004c576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff1680635cfd038d146100515780635d4e0342146100d3575b600080fd5b341561005c57600080fd5b6100956004808060a001906005806020026040519081016040528092919082600560200280828437820191505050505091905050610182565b6040518082600560200280838360005b838110156100c05780820151818401526020810190506100a5565b5050505090500191505060405180910390f35b34156100de57600080fd5b61012b600480803590602001908201803590602001908080602002602001604051908101604052809392919081815260200183836020028082843782019150505050505091905050610192565b6040518080602001828103825283818151815260200191508051906020019060200280838360005b8381101561016e578082015181840152602081019050610153565b505050509050019250505060405180910390f35b61018a6101a2565b819050919050565b61019a6101ca565b819050919050565b60a0604051908101604052806005905b60008152602001906001900390816101b25790505090565b6020604051908101604052806000815250905600a165627a7a72305820e41e488a9545e9fa5a98095e6bc74e07ed21def3a9ba0d3867003099fab1eec00029 |
@ -0,0 +1 @@ |
|||||||
|
[{"constant":true,"inputs":[],"name":"getBroAndBroBro","outputs":[{"name":"bro","type":"uint256"},{"name":"broBro","type":"bytes32"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"getBarFoo","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_foobar","type":"bytes32"}],"name":"setFooBar","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"getBoth","outputs":[{"name":"","type":"uint256"},{"name":"","type":"bytes32"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_barFoo","type":"bool"}],"name":"setBarFoo","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"name":"_fooboo","type":"uint256"}],"name":"getFooBoo","outputs":[{"name":"fooBoo","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[],"name":"getFooBar","outputs":[{"name":"","type":"bytes32"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_foo","type":"uint256"}],"name":"setFoo","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"inputs":[{"name":"_foo","type":"uint256"},{"name":"_foobar","type":"bytes32"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"name":"foo","type":"uint256"},{"indexed":false,"name":"person","type":"address"}],"name":"Bar","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"name":"fooboo","type":"bool"},{"indexed":false,"name":"foo","type":"uint256"},{"indexed":false,"name":"foobar","type":"bytes32"}],"name":"FooBar","type":"event"}] |
@ -0,0 +1 @@ |
|||||||
|
6060604052341561000f57600080fd5b6040516040806103128339810160405280805190602001909190805190602001909190505081600081905550806001816000191690555050506102bb806100576000396000f30060606040526004361061008e576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff1680631b85502e1461009357806354fcb8a6146100cb5780637b07059b146100f857806393affe511461011f5780639aa7c12014610157578063b17e413b1461017c578063cfd91f2b146101b3578063dc80035d146101e4575b600080fd5b341561009e57600080fd5b6100a6610207565b6040518083815260200182600019166000191681526020019250505060405180910390f35b34156100d657600080fd5b6100de61021b565b604051808215151515815260200191505060405180910390f35b341561010357600080fd5b61011d600480803560001916906020019091905050610232565b005b341561012a57600080fd5b610132610240565b6040518083815260200182600019166000191681526020019250505060405180910390f35b341561016257600080fd5b61017a60048080351515906020019091905050610251565b005b341561018757600080fd5b61019d600480803590602001909190505061026e565b6040518082815260200191505060405180910390f35b34156101be57600080fd5b6101c661027b565b60405180826000191660001916815260200191505060405180910390f35b34156101ef57600080fd5b6102056004808035906020019091905050610285565b005b600080602a60005401600154915091509091565b6000600260009054906101000a900460ff16905090565b806001816000191690555050565b600080600054600154915091509091565b80600260006101000a81548160ff02191690831515021790555050565b6000602a82019050919050565b6000600154905090565b80600081905550505600a165627a7a72305820fbec4ee932ff7d288a752933ae6cb2b6b01949e15a49b6b854142cc9acb3efa10029 |
@ -0,0 +1 @@ |
|||||||
|
[{"constant":false,"inputs":[{"name":"_data","type":"uint256"}],"name":"set","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"get","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"}] |
@ -0,0 +1 @@ |
|||||||
|
6060604052341561000f57600080fd5b60d38061001d6000396000f3006060604052600436106049576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806360fe47b114604e5780636d4ce63c14606e575b600080fd5b3415605857600080fd5b606c60048080359060200190919050506094565b005b3415607857600080fd5b607e609e565b6040518082815260200191505060405180910390f35b8060008190555050565b600080549050905600a165627a7a723058202d68adcfe82d5e51b80e2a9202eb808515f4ba8f98e4dfcca08a018132d33e530029 |
@ -0,0 +1,25 @@ |
|||||||
|
require './lib/w3' |
||||||
|
|
||||||
|
url = "http://localhost:8545" |
||||||
|
http_client = W3::Http_Client.new(url) |
||||||
|
|
||||||
|
eth = W3::ETH.new(http_client) |
||||||
|
|
||||||
|
accounts = eth.get_accounts |
||||||
|
|
||||||
|
abi = JSON.parse(File.read(File.join(File.dirname(__FILE__), './build/Complex.abi'))) |
||||||
|
complex = W3::Contract.new(eth, abi) |
||||||
|
|
||||||
|
bin = File.read(File.join(File.dirname(__FILE__), './build/Complex.bin')) |
||||||
|
complex.at! complex.deploy!(bin, {"from" => accounts[0], "gas" => 300000}, 6, "foo") |
||||||
|
|
||||||
|
pp complex.address |
||||||
|
|
||||||
|
pp complex.get_both |
||||||
|
|
||||||
|
# complex.set_bar_foo! true, {"from" => accounts[0]} |
||||||
|
# pp complex.get_bar_foo |
||||||
|
|
||||||
|
# pp complex.get_foo_boo 66 |
||||||
|
|
||||||
|
# pp complex.get_bro_and_bro_bro |
@ -0,0 +1,11 @@ |
|||||||
|
pragma solidity ^0.4.18; |
||||||
|
|
||||||
|
contract ArrayTester { |
||||||
|
function dynamicUint(uint[] ints) public pure returns (uint[]) { |
||||||
|
return ints; |
||||||
|
} |
||||||
|
|
||||||
|
function staticUint(uint[5] ints) public pure returns (uint[5]) { |
||||||
|
return ints; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,48 @@ |
|||||||
|
pragma solidity ^0.4.0; |
||||||
|
|
||||||
|
contract Complex { |
||||||
|
|
||||||
|
uint foo; |
||||||
|
bytes32 foobar; |
||||||
|
bool barFoo; |
||||||
|
|
||||||
|
event Bar(uint foo, address person); |
||||||
|
event FooBar(bool fooboo, uint foo, bytes32 foobar); |
||||||
|
|
||||||
|
function Complex(uint _foo, bytes32 _foobar) public { |
||||||
|
foo = _foo; |
||||||
|
foobar = _foobar; |
||||||
|
} |
||||||
|
|
||||||
|
function getBoth() public view returns (uint, bytes32) { |
||||||
|
return (foo, foobar); |
||||||
|
} |
||||||
|
|
||||||
|
function getBarFoo() public view returns (bool) { |
||||||
|
return barFoo; |
||||||
|
} |
||||||
|
|
||||||
|
function getFooBar() public view returns (bytes32) { |
||||||
|
return foobar; |
||||||
|
} |
||||||
|
|
||||||
|
function getFooBoo(uint _fooboo) public pure returns (uint fooBoo) { |
||||||
|
fooBoo = _fooboo + 42; |
||||||
|
} |
||||||
|
|
||||||
|
function getBroAndBroBro() public view returns (uint bro, bytes32 broBro) { |
||||||
|
return (foo + 42, foobar); |
||||||
|
} |
||||||
|
|
||||||
|
function setFoo(uint _foo) public { |
||||||
|
foo = _foo; |
||||||
|
} |
||||||
|
|
||||||
|
function setFooBar(bytes32 _foobar) public { |
||||||
|
foobar = _foobar; |
||||||
|
} |
||||||
|
|
||||||
|
function setBarFoo(bool _barFoo) public { |
||||||
|
barFoo = _barFoo; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,13 @@ |
|||||||
|
pragma solidity ^0.4.0; |
||||||
|
|
||||||
|
contract SimpleStorage { |
||||||
|
uint data; |
||||||
|
|
||||||
|
function set(uint _data) public { |
||||||
|
data = _data; |
||||||
|
} |
||||||
|
|
||||||
|
function get() public view returns (uint) { |
||||||
|
return data; |
||||||
|
} |
||||||
|
} |
@ -0,0 +1,21 @@ |
|||||||
|
require './lib/w3' |
||||||
|
|
||||||
|
url = "http://localhost:8545" |
||||||
|
http_client = W3::Http_Client.new(url) |
||||||
|
|
||||||
|
eth = W3::ETH.new(http_client) |
||||||
|
|
||||||
|
accounts = eth.get_accounts |
||||||
|
pp accounts |
||||||
|
|
||||||
|
puts "Block number: #{eth.get_block_number}" |
||||||
|
|
||||||
|
abi = JSON.parse(File.read(File.join(File.dirname(__FILE__), './build/SimpleStorage.abi'))) |
||||||
|
simple_storage = W3::Contract.new(eth, abi) |
||||||
|
|
||||||
|
bin = File.read(File.join(File.dirname(__FILE__), './build/SimpleStorage.bin')) |
||||||
|
simple_storage.at! simple_storage.deploy!(bin, {"from" => accounts[0], "gas" => 300000}) |
||||||
|
|
||||||
|
pp simple_storage.get |
||||||
|
simple_storage.set!(2, {"from" => accounts[0]}) |
||||||
|
pp simple_storage.get |
@ -0,0 +1,46 @@ |
|||||||
|
defmodule EXW3Test do |
||||||
|
use ExUnit.Case |
||||||
|
doctest EXW3 |
||||||
|
|
||||||
|
setup_all do |
||||||
|
simple_storage_abi = EXW3.load_abi("test/examples/build/SimpleStorage.abi") |
||||||
|
%{simple_storage_abi: simple_storage_abi} |
||||||
|
end |
||||||
|
|
||||||
|
test "loads abi", context do |
||||||
|
assert is_map context[:simple_storage_abi] |
||||||
|
end |
||||||
|
|
||||||
|
test "encodes value and sends it", context do |
||||||
|
tx = %{ |
||||||
|
data: EXW3.encode(context[:simple_storage_abi], "get", []) |
||||||
|
} |
||||||
|
|
||||||
|
tx |
||||||
|
|> Kernel.inspect |
||||||
|
|> IO.puts |
||||||
|
end |
||||||
|
|
||||||
|
test "the truth" do |
||||||
|
assert 1 + 1 == 2 |
||||||
|
end |
||||||
|
|
||||||
|
test "greets the world" do |
||||||
|
assert EXW3.hello() == :world |
||||||
|
end |
||||||
|
|
||||||
|
test "gets accounts" do |
||||||
|
assert EXW3.accounts |> is_list |
||||||
|
end |
||||||
|
|
||||||
|
# test "testing simple storage" do |
||||||
|
# SimpleStorageTester.test_simple_storage "test/examples/build/SimpleStorage.abi" |
||||||
|
# end |
||||||
|
|
||||||
|
# test "get value" do |
||||||
|
# abi = EXW3.load_abi "test/examples/build/SimpleStorage.abi" |
||||||
|
|
||||||
|
# |> Kernel.inspect |
||||||
|
# |> IO.puts |
||||||
|
# end |
||||||
|
end |
@ -0,0 +1 @@ |
|||||||
|
ExUnit.start() |
Loading…
Reference in new issue