Hi 游客

更多精彩,请登录!

比特池塘 区块链技术 正文

EOS纯技术上手学习

罗宾虚汉
168 0 0
EOS.IO 已发布黎明V1.0版本。EOS.IO 黎明V1.0版本是第一个预发布的 EOS.IO SDK(软件开发工具包)。EOS.IO黎明V1.0版本可以让我们体验下EOS一部分区块链特性和简单上手开发、测试。本篇主要是一个快速的review目前EOS黎明V1.0版本的功能上手。/ l' s, B2 P, `9 U! X- j! O, q
主要内容:, m/ u/ O) ?8 d5 r7 A7 k6 `

: _$ c+ W. z( REOS Docker快速部署
/ K& K! i) v& D/ }' U) W. G. F0 I3 O0 r/ A: U+ A$ h$ Z6 j
EOSC使用! X, H6 Y/ a/ T# j' [
0 p. b0 T# o" s7 X) N
创建钱包
, O( c1 }1 X. C2 r+ D. P3 Z
! ^. D5 E( S7 u  G' x4 h3 q将私钥导入钱包* V0 |! r+ p: ^! \3 _$ B

0 T6 h0 @9 a# F3 |5 O9 N+ U锁定和解锁钱包) a- I/ V+ d% w' s6 f: f2 Q
' r/ a, b- e1 s0 H" w
创建账户
( w3 o% D& N1 {; D6 Y( M
4 q& a$ C, X& ~2 m内置转账
* p# N, o2 K1 a1 o7 \! F' t
! [4 b4 X. [) e查询交易历史" W; V1 c. V5 C) C

9 n. f* q! }) j4 r测试合约 - currency" \- s  y2 G  L/ w1 r0 S7 t

5 \0 }$ D7 P5 q; k调用合约2 f9 ]* r) |- i
) v+ J3 C3 \& V8 A; Q7 W$ ?
查询合约
" z6 p0 e" d1 N( _4 K. q' O1 ^
  T2 o, i- s8 g0 e" q链接特定的节点
# M3 O' ], e& A( g4 _! C# B- D; c/ M% I# t$ c) c
链接独立钱包服务( h& \' g" D6 c8 _" a$ a- M, A  t
* {, L: [1 T& n% s
免签名验证
* u' D% h4 H. @9 Y, j% z8 f+ o1 t2 Z
其他RPC调用
9 y4 l, V0 n1 G- l4 C3 A) X9 a
0 A3 K' e1 L, B' Y0 L) n- d( t
# H" D, N% i* c7 }( z1 ]; D- QEOS Docker快速部署- V) H: `+ f0 A- H" U
构建eos镜像
5 I; W* U2 _9 m, X" W: T4 W+ N( fgit clone https://github.com/EOSIO/eos.git --recursive" U( h. t1 p, J0 l
cd eos0 Z6 h/ M, X6 H# m/ n
cp genesis.json Docker 9 l6 p0 `# [+ z9 A% n% G5 k1 J
docker build -t eosio/eos -f Docker/Dockerfile .
2 @- l) d; M* F5 V( C( X: H启动容器- q& o$ x  z9 r+ `7 M8 d% H* o
sudo rm -rf /data/store/eos # options ( r" K: F3 F$ j
sudo mkdir -p /data/store/eos
' I8 B& R- @$ I1 W# B% F, Ddocker-compose -f Docker/docker-compose.yml up1 W6 ^* n5 G' j. u. Q9 d# W
如果 docker-compose 启动有报错, 可能需要给文件存储目录赋予用户读写权限
4 O: M" u( B9 l/ N- W. `  ~3 z1 \sudo chown -R SYSTEM_USER /data/store/eos
' }) r. q2 }9 w3 D4 _验证,查询区块链状态信息/ b- l0 H% b7 }
curl http://127.0.0.1:8888/v1/chain/get_info5 m/ T) a# V2 \4 ^/ w
如果想使用多节点环境,可使用yml文件启动' o* t  D5 ~/ H5 ^( p) p
version: "2"" O- s, L$ ]+ Z% f
services:* v! E2 c: f5 G! P9 R5 W2 o
  node1:
5 E3 K+ a9 s, t/ k2 E    image: eosio/eos 2 C; b3 m' u: y) j
    ports:  j. k+ N, h" j1 A: }' W/ b
    - "8888:8888") c7 W- v8 o. Z% f
    - "9876:9876"
6 L1 q) ]5 V4 h' {    volumes:
: a3 {1 n3 H4 [( c7 _      - ./node1/data:/opt/eos/bin/data-dir" _; k2 I2 n3 ?5 `
  node2:
3 K4 V- q& T7 W3 k; t    image: eosio/eos
+ X; @& O; [4 k  U  N6 R    ports:
$ E& J% {. O6 v3 C" q3 ^" i* e    - "8889:8889"! _+ c. c. J. T( l
    - "9877:9877") K6 @" l6 G" g
    volumes:
2 A) R' O: M3 z9 ^4 v  _      - ./node2/data:/opt/eos/bin/data-dir2 K% T' h" t# V$ Z; R' Z3 `1 g
    depends_on:
& N' v9 G1 a  [2 C      - "node1"
  |9 q# _1 w9 ^  K3 J% ^& Y# ^EOSC使用
; a& h/ s5 t' X' d) aEOSC是EOS的核心进程EOSD对外暴露的RESTAPI命令行工具。EOSC的使用会利用到一些内置插件,插件在EOSD的配置文件config.ini中进行设置,如与链的交互需要使用’plugin = eos::chain_api_plugin’。为了签署交易并发送到区块链上,需要使用‘plugin = eos::wallet_api_plugin’。为了查询交易和历史记录,需要使用’eos::account_history_api_plugin’ 。4 D2 D% R. f' N3 w
# Plugin(s) to enable, may be specified multiple times
' s( c( ?6 c: W2 N# n2 wplugin =
0 V6 `; \4 D+ ~$ g3 G% q9 ^( Weos::producer_plugin
  @. D8 C4 [9 }1 F/ k, `2 l4 kplugin =
5 q% c$ ?! \1 _6 }8 X! W: b+ meos::chain_api_plugin
$ x. e3 v0 i& p. n$ v4 T, L4 S& }  vplugin =% x7 p$ @8 c& u
eos::wallet_api_plugin
* N. _! P0 p+ ]3 Iplugin =
) g: x' h( p7 n% a2 veos::account_history_api_plugin. k) a( ?- K4 R" Y) c3 K
启动eosd后,可以使用EOSC查询当前的区块链状态
/ \3 h% P& `4 A  edocker exec docker_node1_1 eosc get info! v6 ?8 Z. r6 T( ~7 l0 M
{7 L4 ?2 y& `$ |3 e& \9 k( M7 y
  "head_block_num": 23449,
- ]5 L# G1 _3 b  "last_irreversible_block_num": 23432,( q' ?+ M# h: N
  "head_block_id": "00005b996cc85962b28537c3d72696a012d1071638f5e4bad1809cf9afc9abb6",* o5 o% \9 O) d( X$ D& @) H( ]
  "head_block_time": "2017-09-29T01:53:33",5 R$ i, S& M( d2 `3 s: K: h4 x
  "head_block_producer": "initi",# i* [. N0 G6 B; ]' c7 i
  "recent_slots": "1111111111111111111111111111111111111111111111111111111111111111",1 B! N+ i, q# n# E4 W
  "participation_rate": "1.00000000000000000"0 g/ u  s7 `  f) Y  a# R1 j
}( _2 z* I" W# r+ e- q; F8 f% V* w& v, r
创建钱包7 o/ F2 \" q* Z
任何发送到区块链的交易都需要由所有者持有的私钥进行签名。首先,我们需要一个钱包来储存和管理私钥,使用EOSC命令创建一个钱包。
4 N$ R/ f% ?5 Y8 B8 qdocker exec docker_node1_1 eosc wallet create1 v+ e% C8 }& ~' U, J4 n
Creating wallet: default9 b$ {, @; J3 C6 L8 K
Save password to use in the future to unlock this wallet.6 x# w6 x* v- M7 H3 {6 f
Without password imported keys will not be retrievable.7 g* @0 }$ k* M0 n/ l7 K+ M. t# f# v) S
"PW5JXSxkHqNEwRKCpG2JUTLqkR8SNCBXofkAwaFDLwQkNdqaSXwC8"
% h( \' B+ ^: p( J; _命令执行完成,会在eos-walletd中创建一个名为‘default’的钱包,并返回钱包密码。
8 ?1 ^- n) e0 U" I, _6 z这时候可以查看钱包列表* N: S: p, O& T
docker exec docker_node1_1 eosc wallet list
$ G, l9 B; `& {) c8 U" L" KWallets:
9 F5 r; ~% U% f/ Q[( }* `: N: Y; [" P
  "default *"
& v' v) X9 h/ ]0 r0 }4 ]]
! z9 s. z" W1 u  W如果你没有指定钱包名称,默认都操作的是‘default’钱包. Y. e. Z- B5 Q* z5 p
将私钥导入钱包
( c" v" O4 l! Q; Z如果你想授权某个钱包可以由某人来管理和控制,需要导入该授权者的私钥。
9 T) f8 `% A( g4 G0 M# @docker exec docker_node1_1 eosc wallet import 5KQwrPbwdL6PhXujxW37FSSQZ1JiwsST4cqQzDeyXtP79zkvFD39 I6 |% y5 y  ~9 G6 [! i) O9 u
imported private key for:/ n9 Y# ^# B) ~( p9 d
EOS6MRyAjQq8ud7hVNYcfnVPJqcVpscN5So8BhtHuGYqET5GDW5CV' Y1 D! a, d, J0 Z/ d$ u0 P
导入后,可以查询钱包已经导入的私钥和对应的公钥
8 o( w( ]. R1 e$ O" Jdocker exec docker_node1_1 eosc wallet keys& y1 P6 y$ z7 V, D% g
[[/ @2 [; D: T4 O- U- U' ^/ E
"EOS6MRyAjQq8ud7hVNYcfnVPJqcVpscN5So8BhtHuGYqET5GDW5CV",
! J6 [' C/ }% a( i6 I* J"5KQwrPbwdL6PhXujxW37FSSQZ1JiwsST4cqQzDeyXtP79zkvFD3"$ G6 y3 V+ d; Z" \9 L3 p
]! g7 w# |9 \0 J
], w6 X# p7 w  b$ W8 |* D8 q
锁定和解锁钱包
  c. o1 r8 e5 t6 Y8 l3 w日常使用,为了保证私钥安全,可临时锁定钱包,锁定后查看钱包列表是不可见的
; w7 E  K) |9 X' V' F0 X- Idocker exec docker_node1_1 eosc wallet lock
" Y4 w1 Q# Q. e5 WLocked: 'default'3 X; f8 K: T' s7 l* G% N; f
当想要使用时,可以用创建钱包时生成的密码来解锁钱包3 z" P1 ?6 F2 V* M4 x( Y! f
docker exec docker_node1_1 eosc wallet unlock --password PW5KVWrn81Y8PLAb52gr2FyXCanVavcrj9d5TC9C3yKhqq1PJYRPk- \& J' `0 x5 D( x4 |  u
Unlocked: 'default'! e, N, n8 B- w& c8 X
解锁后,可以在列表重新看到default钱包了
) [- N" @. \+ p8 [$ zdocker exec docker_node1_1 eosc wallet list
+ \( ]7 k2 U1 qWallets: 5 I6 x; |" m; J' d
[
0 C" w; @4 \. ?5 ^1 O  "default *"' I* I$ g% \/ ?: x# a- a, Z( i
]
* q0 f- t8 |& v( X创建账户: P+ Q8 K+ {; D' l
创建账户需要有两组密钥:owner和active。EOS使用EOSC工具来创建密钥对
$ h8 [  x0 C  V5 j5 b1)owner key.
+ l/ k2 u) W6 CPrivate key:5JRc8XxvodWey4StZ2zzkUhCQhDaHvGMkABtfHzQR2ie4qaUFJ71 x' ^) S: R2 n! ^; t7 j/ C
Public key: EOS5mFEdAzxvMkHLQXt2v4naUjnBrPGmzMUCikymqhSR6m7QLGSTB5 \0 O6 k  y( W, h0 Z  n1 V
2)active key
7 ]* m+ {, w3 b3 QPrivate key:5KNzFCbToz2a9Hztz9Qen5cyJcM3x5Wpq4GFiTYZgGhzntXdmYo) u, }1 k) ]  a5 w5 _+ ~8 a& U
Public key: EOS5EdsvESpibWLJxupTqod1nswJnbiXQZuUcLiAWEEsqcZskymeB
" i& T- c+ N+ R  i) j) IEOSC不会保存生成的私钥8 ]! |8 y: ^3 r0 ^1 H* K) T% E
因为后续测试智能合约需要,我们创建一个名为currency的账号。目前这个版本,所有的账户都需要用已有账户来创建,所以我们用inita账户的owener key和active key来创建currency。 为了使inita获得发送交易的权限,需要先导入inita的私钥到钱包。(参见私钥导入钱包的步骤)0 T* u# v# F+ t+ W
docker exec docker_node1_1 eosc create account inita currency EOS6NpEqWi177VKQkuJQL9V6Y3LqAAp9C2j" [7 V4 ]  T! M* h/ n
执行成功,会输出一串json的交易信息,打印账户创建相关内容- e' I( K: R" A( ?/ ?$ u
我们可以查询inita可以创建了哪些用户; g3 {; g* ]4 V8 A; E
docker exec docker_node1_1 eosc get servants inita
  m* n$ C- [/ i6 {+ q{8 n0 y+ O& X( R1 H$ w6 E: \
"controlled_accounts": [
- l- c. g: J& I7 [% r"currency"
& l1 k1 ^5 b6 I" G' h# k$ @], n8 Q9 T3 {( C6 L
}
$ k- m, X9 Z: u) j: F内置转账
  S# F. X4 i$ E) |) a5 {创建账户之后,可以查看当前账户的状态,可以看到创建的测试账号没有余额,这样不少功能无法测试,我们需要试着给创建账户添加一些余额+ L. W6 H* t2 S# R4 ~% z" t  |
docker exec docker_node1_1 eosc get account currency* R; E5 ^) E- F" S& ?% v2 [
{( C) S! d$ Q  J, N5 o
  "name": "currency",1 j; \6 o: K! q, K1 s
  "eos_balance": "0.0000 EOS",
) M- u3 y5 _% ^% e9 u. U  "staked_balance": "0.0001 EOS",
/ O5 P9 s. A  j& e2 E1 o  "unstaking_balance": "0.0000 EOS",
+ ^; J+ z& ^# K" y, s  "last_unstaking_time": "1969-12-31T23:59:59",
  D- @+ p! U; b' x# Y  "permissions": [{) B7 e, ^  H8 Q2 B- P" p! O
      "name": "active",! a" [4 z8 D, c9 }% E& ~" y
      "parent": "owner",
3 ?8 K4 ^+ X& W9 X3 Q2 ?      "required_auth": {
. l1 b+ l6 M8 s# R) }7 G        "threshold": 1,
+ E1 B# p# x0 r+ [6 v& A/ F9 B9 A        "keys": [{
& {9 t! H% W3 T" }8 B            "key": "EOS8ff42NMpJUybVj3nwUSnPpc3mMysKxyE4HVJy1E5o3fQv7knWf",& x% f8 H5 G9 N& V- m
            "weight": 1- U/ a* G' M& M& ^, o
          }
* r! [# S1 a& h$ H6 p  i        ],
/ I6 H& K. x; e. |! W        "accounts": []
8 M( _; R: R5 T$ A& [7 V$ N      }: C" i  H0 q. n
    },{
0 F5 s1 r  ~& T1 ~/ r      "name": "owner",. g7 m/ O2 E8 b
      "parent": "owner",
6 e8 V# u1 r  N' Q+ w      "required_auth": {7 u0 _- E, q; R$ l% B, {
        "threshold": 1,
0 B2 K; N0 v9 N; j        "keys": [{( ~3 \8 o5 w/ l. V5 X- @
            "key": "EOS5fQ4saiHV426EQ7AKrGoD2AVMBYe77bnGSq42JjXBUfipv7o3E",
9 ^" I/ h2 _; H            "weight": 17 |" ]* C6 p. z, }/ Z& S
          }! H+ k" L; ~' r7 V6 x& J
        ],
  s$ I' k) C3 z9 v, ^        "accounts": []
. J4 c* D  {1 M7 s2 M- O% v3 C      }) |& l/ t/ e9 f& P) f. k6 A
    }0 l9 Q/ D, A. d5 A
  ]& N* }/ T& G& ]( R
}
8 `, ^3 F1 H: ~/ E保存全网余额的创世账号是eos,查询余额状态
6 s( R3 ?' f* r$ u2 e1 r, V- a( R6 edocker exec docker_node1_1 eosc get account eos
% e/ y1 A, N  M{
; P" }1 V, X' }; g3 D+ Y/ _  "name": "eos",
) S9 a' u3 J3 X1 |+ Y( M, G  "eos_balance": "69000000.0000 EOS",
7 H! {/ o, j5 d/ a+ T2 P( r; t  "staked_balance": "0.0000 EOS",
& w* g. G8 ]2 w/ a  "unstaking_balance": "0.0000 EOS",! x1 f3 A. z8 d4 A& v- g
  "last_unstaking_time": "1969-12-31T23:59:59",8 X0 I" t1 @1 @# a& G
  "permissions": [{
) |( b" u$ t. F/ J" P6 d      "name": "active",* S0 T1 N7 T+ ?" R5 Q
      "parent": "owner",) J' i  y$ }9 a' u+ L* h$ K0 {
      "required_auth": {3 Q  n+ E; z% N
        "threshold": 1,
; P  M& \% A$ p1 @3 `7 y" S6 [        "keys": [],2 G+ M1 w5 V' C2 z3 |/ Z* q' o1 N
        "accounts": []7 e! E; y# b: s( p5 l( s
      }
) p1 b# T; I1 |0 }. [    },{2 b: C1 {' c* O3 _2 O* K0 a
      "name": "owner",
/ q  B8 V% r7 Y, z  h7 g1 s) Y      "parent": "owner",! b6 f0 p' z% p2 ^" i1 S* U$ Q: y
      "required_auth": {
: ], ?" q; \' J8 `2 P        "threshold": 1,* t) e% E; w+ ]
        "keys": [],
  f5 Q0 P. w" |. H! l; C8 |        "accounts": []
+ L/ E3 T0 k1 Z! S- o6 e      }
9 E( _% X: {! R, ]" s& J; c7 O    }
. N2 K) ], S' R  ]. Y/ @9 j4 F  f& r+ n
}
) ~" A; N* Y1 B+ o; O我们可以通过创世块定义的创世账户使用EOSC给当前创建的账户转移余额+ p! u+ f1 N0 F2 j2 q7 R3 p3 r5 ^
docker exec docker_node1_1 eosc transfer inita currency 100000000* b' Z3 i1 j, H; u6 Y  V
{
- H) {4 c/ ~7 G0 W( b/ K2 K% R  "transaction_id": "59575b8caf08eac7c00eb7483c048f12d0e7abf1ede839c3b2ed41dc6c5c7c5f",
6 b' K3 ]/ R/ J1 e  "processed": {
4 p! D6 u* O' C    "refBlockNum": 24199,
& P6 J. R, G9 f& _6 [    "refBlockPrefix": 1485651173,
. V6 i, g+ T7 Y+ n' s; \    "expiration": "2017-09-29T02:31:03",$ Q/ k- O1 x" k' v4 P
    "scope": [
6 w0 o! R& K  i      "currency",
6 c* V" m9 y7 V  r% G      "inita": i, q2 u, N' b
    ],% x1 g8 C% t* j3 C( f+ C0 u
    "signatures": [0 k2 n: N  c, h) T
      "1f14229bdd4bfb927021bf96ff0651c8b0fa5666e9f5cf423a0270a1b91f2d2f690b573e179d8475ce2c6b160f5cd5507d58a44f8f6cf536348584efa8dd62ade0"  L) Q7 C$ G8 P" [* e4 w
    ],4 ]! {$ C+ q3 ]+ g; Y7 T  c" o
    "messages": [{4 r+ B& `+ y9 ^" E) i$ W& w
        "code": "eos",
" w/ J% P+ d$ a  x        "type": "transfer",
1 }! G$ W& e. N+ j* C3 A6 F$ c        "authorization": [{9 H" I/ b; k" F0 ^  m! I0 l
            "account": "inita",
" [2 V; c/ U, `# _            "permission": "active"; h7 f4 K) W5 d* y! p+ [/ K
          }
. e# U' w% J# n, l# V) w. B        ],, v5 _" X) w8 l3 J
        "data": {
+ N5 q6 c9 S) i: O7 i          "from": "inita",7 u# U4 d$ H0 q' X! T, Q* c. m
          "to": "currency",
) g6 C; S3 e! z+ B' ^          "amount": 100000000,  ~6 _2 X+ ^" W5 c
          "memo": ""
. L& b/ b9 A. M+ {9 k1 m  l) O        },
1 ~6 u4 \* K0 ?1 \* b        "hex_data": "000000000093dd740000001e4d75af4600e1f5050000000000"
" x( D; c& ?0 X1 i1 G* g      }! z8 M5 h5 J# k; C
    ],; }! p1 t2 ^" K: ^
    "output": [{+ h% S6 z, {  Z6 M4 T+ d+ j
        "notify": [{6 U6 f5 B' m2 \8 Q. r: I
            "name": "currency",. E# s& l" c  @+ F/ e! S
            "output": {. V1 g3 v# k) D5 p! K3 J( ]8 L& h
              "notify": [],
  U( z+ V9 x1 B! Y; r              "deferred_transactions": []$ m# d- e0 ~) O4 t  \$ W# e
            }
7 F9 E1 R* Z% I1 Z, F          },{
+ Z5 `' C6 I" t  p. W            "name": "inita",, x6 T! C) H" O6 B
            "output": {
$ S6 |& k% G3 I3 l. S  b* O8 m              "notify": [],
- e4 n$ I) N. v( K5 I              "deferred_transactions": []' c, G) n& ~7 s/ m% h, b* J
            }
6 |4 R, L" N  x/ |! l( \, y: o          }
; A* o! f0 p$ o; ~, t        ],
- f! ~8 G" B) W- m1 Z$ l3 j6 j  K        "deferred_transactions": []
: S4 a6 `  @0 u) H( }8 z3 @7 [; A( c. E; {      }. w/ H+ o* M0 ~% r6 X
    ]9 g' X7 n. o0 w) _6 [
  }
) I! O. b5 R3 b9 ~- y( a$ y}5 F, b1 l+ ?) k5 ^
再通过执行get account 命令,验证余额已经成功转移到创建的账户下
, @8 r9 n4 c$ F( s! G0 P6 ], g查询交易历史3 d8 I( H& S5 m; s2 g5 i% j
查询交易历史会使用到插件account_history_api_plugin,我们已经在config.ini中定义
' U' X- H/ C6 k8 X  ?+ n7 qdocker exec docker_node1_1 eosc get transaction / ?  j- ]; N  |! D
如果需要查询一个特定账户最近一次的交易记录" Z: T, k5 C0 r& O1 Y/ Y
docker exec docker_node1_1 eosc get transaction inita
9 P) K8 l* _- Q4 o- N7 W# i% D. ]创建智能合约4 F, S4 H2 c, W( E3 w
官方提供了一个示例合约currency,我们依然使用EOSC来创建并部署智能合约,合约代码位置contracts/currency。
9 h' @7 V# {9 n2 E% O! |" }1)为合约创建一个所有者账户。前文已经创建了currency账户
0 ~5 z  j: s. E: r% L! Y  m2)检查区块链上有无同名合约
* j, ]& p" @9 ]1 j. }docker exec docker_node1_1 eosc get code currency
( ^1 `9 u" X% c/ p1 C( f* ccode hash: 0000000000000000000000000000000000000000000000000000000000000000
) h9 I  B, j$ e' }3)为了获得部署权限(发送交易请求)需要将currency的active key导入到钱包中1 y" {4 k4 T; Q/ o& ~; I
4)部署合约(.wast后缀文件)和他的abi(.abi后缀文件)2 t% F$ K* `, |3 }" K
docker exec docker_node1_1 eosc set contract currency ../../contracts/currency/currency.wast ../../contracts/currency/currency.abi
# _+ W' o) D0 q) f# cReading WAST...8 i( @5 {3 T0 y* J+ Y& h; h4 q
Assembling WASM...6 R) t* q2 s( C; {
Publishing contract...- ~, F) g' b' C; E: b. E; g$ L
屏幕打印部署成功相关的信息,并查询合约hash  L6 T3 Q) g; ~9 G5 q) N
docker exec docker_node1_1 eosc get code currency
; N. F; U$ u* H! b: h( vcode hash: c4023f74b3c7a3321d1641e4111b13584078fa7265c6ab12e1c19ff7ee800faf, U: }( a; O1 }8 m7 \. ^8 z) R
调用合约  m; }0 \% m* j* @3 J  @
在合约部署到区块链上之后,所有的currency余额会分配给我们创建的currency账户。我们可以调用合约测试做一些转账交易。5 Q2 Q/ K+ [0 X" w1 E) x9 @7 `1 ?
为了更好了解区块链合约的调用方式,我们可以通过.abi查看可以执行的操作列表和消息结构。
/ P' m4 t  s  I" G# j+ J- qdocker exec docker_node1_1 eosc get code -a currency.abi currency
- l. Z/ E1 Y; w0 A! W# ?1 I' Icode hash: c4023f74b3c7a3321d1641e4111b13584078fa7265c6ab12e1c19ff7ee800faf
0 b  ?4 j; a, {& rsaving abi to currency.abi% ^. B* O$ O+ u- U$ h8 J& V
cat currency.abi #查看
" v: A: |3 J/ m# c+ x) \+ Q+ z, K{
4 F2 a1 ^3 n5 \6 G$ R0 p0 q* M  "types": [{- q5 |# x$ f. ]: G  h# W
      "newTypeName": "AccountName",+ z( T! n0 w. J) ^2 A) C3 X
      "type": "Name"
5 X$ }7 O. a: @4 n, g- [    }: M5 I; f' E8 [/ V
  ],
+ W" d& Q5 k0 J) `! D( \  "structs": [{" h! h- [4 d( O7 l. {' H4 `( k3 N5 x
      "name": "transfer",
7 }; O! [/ u/ ~# N4 x& ~  d      "base": "",$ G  s1 H( F# f! ?
      "fields": {- E; i& ~( W6 t: G( }
        "from": "AccountName",
! m% o( G) L  U" b' m        "to": "AccountName",
* p! x- s' {" e- y) j        "amount": "UInt64"
. n. I5 U( }) d" G) k6 k      }; u/ {, l5 v9 N% w0 h6 w9 a: _& D
    },{
: l4 D/ m7 `9 y, ~5 h$ r( J, T      "name": "account",' e2 u; x3 r3 d8 f* p7 Q& X
      "base": "",
5 s! x# j5 m2 H5 d6 i5 n6 K. L: v      "fields": {
6 |8 r$ Z6 |* w) N  z: ?        "account": "Name",6 T1 c! K8 t/ ^% N  Y
        "balance": "UInt64"
5 H- G" \& x$ N; M8 I4 d      }
8 l, t; L1 b' F1 F5 B    }* g6 |; c9 X  n: |
  ],# W3 P( j$ u9 m! z
  "actions": [{9 D/ e: W+ ~  ]: ~
      "action": "transfer",
" @1 a$ k+ V% \) u. v  V      "type": "transfer"
8 B) _) g3 `4 L    }6 `  g; T+ M" a0 u9 J; |1 F+ Y
  ],7 H6 w' q, G' [  f4 W
  "tables": [{9 ~+ B8 o1 W5 s9 l
      "table": "account",% t7 @3 U/ T8 b- v9 @
      "type": "account",. ~2 {% v! Z9 i3 g# i) }
      "indextype": "i64",0 s" m0 Z) i+ r) g9 F
      "keynames" : ["account"],! R# r- g0 u- w" @' h
      "keytypes" : ["Name"]
# h7 o- X8 {; R' X# y! s. |    }& b* v- }! ^- H- r- u4 ]( o
  ]
, N% z: `# o$ I6 ?% ?# n3 I}$ C" g9 x. b  B# x" R
通过上面的abi我们可以看到currency合约可以执行transfer操作,消息格式为from,to和amount。我们调用合约从currency账户转移50个余额到inita账户: @& w3 Q9 g& [3 g9 E9 P0 L6 O" [
docker exec docker_node1_1 eosc push message currency transfer '{"from":"currency","to":"inita","amount":50}' --scop+ S; b# Q2 J; ^) f( j" Q  V: L
执行完成,我们查询余额验证结果
1 Y0 Y- {3 Y6 t9 Odocker exec docker_node1_1 eosc get table inita currency account
; [* k* X$ f1 Z) |6 [{: C4 r) F! C+ v
  "rows": [{
' v7 a* C' P9 S! T# V      "account": "account",3 r+ ?! E( Y! N7 N1 z
      "balance": 50 7 }  p# S3 i/ M( Y
       }5 Z( ^5 t. x, b9 O
    ],' R9 W: z) l& I; a
  "more": false$ B- W* Q/ d" ?/ M% h1 @, \
}
! K- |) D9 Y3 ?+ \. Ndocker exec docker_node1_1 eosc get table currency currency account; N( x% ?' ?' K" {8 L# M/ Q
{
$ z4 K' G' p0 H& e4 |0 c' a% G2 {  "rows": [{  ~9 q$ |8 P: \" P7 R, N7 C0 S5 [
      "account": "account",
# h* N/ n( w: W9 ~2 W8 y8 G      "balance": 999999950
; S# e$ T1 m  D' p4 T+ S. u$ l    }4 C, E/ Y- p; N
  ],' ?  l% K. ]% C- p
  "more": false
" ^& Y  h, o# C}
: H! p0 H2 Y$ n3 O2 i4 |9 a余额不足的账户尝试转账,会提示失败( ~. W8 a0 d+ Y1 J8 J5 ?
docker exec docker_node1_1 eosc push message currency transfer '{"from":"tester","to":"inita","amount":50}'-S inita -S tester -p tester@active) U4 h8 d( q8 n
3543610ms thread-0 main.cpp:271 operator() ] Converting argument to binary...
  `! N* @& N2 z$ x* _3543615ms thread-0 main.cpp:311  main ] Failed with error: 10 assert_exception: Assert Exception' }4 K; \- s9 D
status_code == 200: Error : 10 assert_exception: Assert Exception  p( w6 G2 }% ?
test: assertion failed: integer underflow subtracting token balance
3 ^' [: A: p/ b, ?  D4 @" g{"s":"integer underflow subtracting token balance","ptr":176} thread-1 wasm_interface.cpp:248 assertnonei32i32 [...snipped...]
. A' |* Y& ^5 b( S8 [. d( Z查询合约
6 ?* G; g* |- v. O* m! g: \' U如上文验证步骤,在调用完合约后,可以通过查询表来验证每个帐户持有的余额。9 x* S5 C7 z8 q7 r0 G/ ^+ n1 G
docker exec docker_node1_1 eosc get table currency currency account
! \  `& A- D6 F% U( }6 r9 A8 @/ `5 `/ G连接特定节点1 w6 u6 L0 B1 U6 G' ~
默认情况下,EOSC连接本地端口8888的节点。可以通过指定主机地址和端口来连接其他EOSD节点。同样的,钱包服务也可以指定特定的主机地址和端口。  U; M+ L* g. ^- P7 x" t
docker exec docker_node1_1 eosc --host  --port 3 ]) Q+ D! M" g0 S( T5 @
链接独立钱包服务: t  ]- L9 r1 T& A( E
除了使用EOSD内置的钱包服务,也可以独立部署钱包服务
! l5 K# I: D" q( }docker exec docker_node1_1 eos-walletd --http-server-endpoint host:port8 L" S9 L  U  J8 T& J
调用独立钱包服务需要添加如下选项
* ]) R5 V  D$ hdocker exec docker_node1_1 eosc --wallet-host --wallet-port' s; u- J/ v# P, `4 S) i
免签名验证3 T1 u7 i' n% j! X3 C
开发者如果需要快速测试功能,可以跳过节点签名的步骤,这样可以解耦密码学的问题而关注应用功能9 f% u- c3 _# T, A7 Z( o
启动时使用特定参数, O1 d6 ]# x8 c! I. X* D
eosd --skip-transaction-signatures( [1 H5 ^4 q6 z- m/ Q. g7 k. @
EOSC调用时添加-s 选项
# ]7 q6 f' M, F" l  u: v8 n, o0 R- W+ cdocker exec docker_node1_1 eosc   -s
8 h6 G+ q% T/ U) `其他RPC调用# Y. G$ U* z; t
EOSD RPC 包含通过HTTP RPC与eosd和注册其上的插件进行调用的方式.
" x. ]6 j6 s2 U+ T' l1)区块链API 配置
6 E& Q. `& N( }0 T  M1 e想要查询eosd信息需要启用plugin = eos::chain_api_plugin插件并添加至config.ini中$ t! v2 D8 U/ q( F9 H; z7 D0 l+ {
2)get_info接口用于查询区块链的基础信息
9 C0 c+ B3 M8 @8 w9 z' O' Qcurl http://127.0.0.1:8888/v1/chain/get_info
& c& ~6 C( z9 F, q4 ^8 x返回结果如下:
6 m" I; d) e& F' X2 S{"head_block_num":25028,"last_irreversible_block_num":25014,"head_block_id":"000061c443dd3e85932c442a8e5176b7ac822a0f6d09d034298f508e71c5ae6c","head_block_time":"2017-09-29T03:12:30","head_block_producer":"initm","recent_slots":"1111111111111111111111111111111111111111111111111111111111111111","participation_rate":"1.00000000000000000"}
- Q3 @6 w' ^/ {+ Z* W# A$ Fget_block接口用于查询区块相关信息! g/ \2 D6 _- E7 m7 M

1 C# @4 G# ?* U* @6 ]curl  http://localhost:8888/v1/chain/get_block -X POST -d '{"block_num_or_id":5}'! G; g/ q( S0 o1 U* p
curl  http://localhost:8888/v1/chain/get_block -X POST -d '{"block_num_or_id":0000000445a9f27898383fd7de32835d5d6a978cc14ce40d9f327b5329de796b}'4 q/ A; @" ~& j) _& k' J. b
返回结果如下:, K: z4 j4 U" C8 B
{"previous":"000000047aba47492d2143beebfdfba171192970a0f9248f0408a8614ff42dca","timestamp":"2017-09-28T06:21:21","transaction_merkle_root":"0000000000000000000000000000000000000000000000000000000000000000","producer":"initf","producer_changes":[],"producer_signature":"1f25a5b592b7f605ffdbd1cba90497e94b3e1c0e5805b70851de6875e0f33e20dd1f363cd1fcfd2dc8421fb918d694d260e255956cc7f8f554fa0be01d805a84ed","cycles":[],"id":"00000005bf39fd177fc2ea8ba6540d5f31e8b07218f054016123a34b16d0b30e","block_num":5,"refBlockPrefix":2347418239}
2 V" U$ {: f6 H$ u6 D4)push_transaction接口,调用合约交易- P# M9 g8 G0 P
该调用为JSON格式并会将结果更新到区块链上
* P1 H8 a* m1 P3 Q5 V$ O4 N( ~' B执行正确的结果返回: P* U/ ]. M/ }% I) `
返回 HTTP 200 和交易ID号
, j/ e) S9 v* h4 L; g' s{
( T  c9 V" ^4 e% d'transaction_id' : "..."
5 F- P& y% L. O. B}" d  z. z! ]4 ^9 }% _- P& h! F
执行错误的结果返回,一般为400错误(参数错误)或者500错误/ l2 v$ ^) e5 [2 r5 q% W
HTTP/1.1 500 Internal Server Error) E! M3 }9 {% O7 r, a
Content-Length: 14665 f  b) l% i) D# J7 p( T+ y
...error message..
9 K" P& D2 U- \- b% h2 \! t( p, Fpush_transaction 调用方法8 W  r3 |: s8 ~! H6 {- e% ^- ~
curl  http://localhost:8888/v1/chain/push_transaction -X POST -d '{"refBlockNum":"5","refBlockPrefix":"27728114","expiration":"2017-07-18T22:28:49","scope":["initb","initc"],"messages":[{"code":"currency","type":"transfer","recipients":["initb","initc"],"authorization":[{"account":"initb","permission":"active"}],"data":"c9252a0000000000050f14dc29000000d00700000000000008454f530000000000"}],"signatures":[],"authorizations":[]}'
3 C3 F# K; S; Z4 O( y$ i3 F6 P8 V此示例模拟一个转账交易。 refBlockNum和refBlockPrefix使用的前例block查询的结果
BitMere.com 比特池塘系信息发布平台,比特池塘仅提供信息存储空间服务。
声明:该文观点仅代表作者本人,本文不代表比特池塘立场,且不构成建议,请谨慎对待。
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

成为第一个吐槽的人

罗宾虚汉 初中生
  • 粉丝

    3

  • 关注

    0

  • 主题

    16