Hi 游客

更多精彩,请登录!

比特池塘 区块链技术 正文

EOS纯技术上手学习

罗宾虚汉
115 0 0
EOS.IO 已发布黎明V1.0版本。EOS.IO 黎明V1.0版本是第一个预发布的 EOS.IO SDK(软件开发工具包)。EOS.IO黎明V1.0版本可以让我们体验下EOS一部分区块链特性和简单上手开发、测试。本篇主要是一个快速的review目前EOS黎明V1.0版本的功能上手。
1 U* E% L/ |. g3 x主要内容:: n/ A) j- U" O1 S# j

4 q5 r. w3 D, m4 m/ `8 X, HEOS Docker快速部署
: d9 f- n% g! h* t
. Q& \+ C9 ]+ L$ a0 E/ H7 c- YEOSC使用/ g) @& S5 J/ |! D/ r/ P* T  }
) V# {7 g9 m* M
创建钱包
& P, G& Q: p" p' u9 P/ X9 u+ i, p* `5 Z2 `1 T5 b- E9 J
将私钥导入钱包) t; D) n; l+ L$ i+ e% ?/ `

, \/ ^* f4 I! l# j9 f' B9 i, s% m8 u锁定和解锁钱包
9 D: H9 U1 g' f9 C; {+ h
) M. X8 r) x- Y# {7 i1 g2 x2 x创建账户8 S& F: e7 z, b- _) J' k

& @# e- S; k% _  _( d; I: U内置转账
6 K& Y: ]) j$ |
! b0 f# F# D: r) n' m0 x查询交易历史
' s: U. M( n4 W- E# K" }0 A! t, {( U$ J, X7 a, c
测试合约 - currency  r( V2 ?2 {% M/ T  z3 y
/ C; S. k5 Z/ K# F6 _! V
调用合约6 M# o1 m  v4 W3 ?& g" i
  u3 S3 x) u7 f. u3 k) j! L% N
查询合约$ N7 s5 i+ F8 m/ m
4 ?( I0 `7 m, ]$ [: L
链接特定的节点
+ }* g$ P- `/ W& t& n" M4 V/ W) J# m" N5 F' f/ X
链接独立钱包服务
* U" y0 e2 l, u7 W+ s! b4 S
8 y$ y* s  ]+ M免签名验证% M9 {+ Z' E# R5 O  {3 k
4 g0 D" |' @! m0 p& b
其他RPC调用# o/ W# X2 ?/ K. \' x" G2 ]' `
6 I8 ?0 `  F$ O6 x& m. X; @

! T9 Z3 f- z) \' L/ t2 CEOS Docker快速部署  I2 b/ }" a+ U# n
构建eos镜像
& K' P6 F1 v/ M* ^git clone https://github.com/EOSIO/eos.git --recursive" W/ t; V2 C, z, A8 Q3 l
cd eos% Y" ^3 {( L: Q
cp genesis.json Docker 7 i5 m' F  N! c' `% |% u" s
docker build -t eosio/eos -f Docker/Dockerfile .
9 A$ V  i4 b" v" a0 A4 g' N启动容器* T6 }! l4 c# W; H* a' _6 m5 z
sudo rm -rf /data/store/eos # options
, b8 `9 V& e2 w: c2 ?sudo mkdir -p /data/store/eos4 ?- B& r2 H0 m" [, L# P
docker-compose -f Docker/docker-compose.yml up# p2 ?+ G$ _$ f4 [1 K/ T- M8 q
如果 docker-compose 启动有报错, 可能需要给文件存储目录赋予用户读写权限
2 A2 e6 H0 f4 m* r! ^sudo chown -R SYSTEM_USER /data/store/eos# z' m5 B% w! y7 j9 t: R4 x
验证,查询区块链状态信息
3 y7 R7 F! @. b7 q! F4 s; F) x6 Ccurl http://127.0.0.1:8888/v1/chain/get_info
/ W) V" O' \+ P3 t9 J如果想使用多节点环境,可使用yml文件启动5 k/ [( r, G8 H8 Y3 T
version: "2"
# n  i& b6 z, Wservices:$ P$ a9 ]  K' m
  node1:+ [3 n, K1 B, b  v
    image: eosio/eos
* z& D3 I7 ?4 I) ^- q    ports:
1 Q9 e, O9 S, a" C( n3 ]9 B: E! d    - "8888:8888"  q2 `$ b; \  v! y0 w% t
    - "9876:9876"% k$ x! i: u8 c5 X1 b- r
    volumes:
; B% n2 T: }4 M: z5 m$ |/ U* `) v      - ./node1/data:/opt/eos/bin/data-dir( ^  J0 i0 y6 p
  node2:
) K+ U; g1 B, E- ~  x    image: eosio/eos
( J& K7 F) `. i' ~8 x+ ]3 n( i, ~: b    ports:
1 Z0 F; P' K' g    - "8889:8889": j3 K" ^0 z- V* D( E
    - "9877:9877"
0 A5 t& E, c) G' ~9 r& p/ i$ b; k    volumes:, j% z/ ~/ @2 v
      - ./node2/data:/opt/eos/bin/data-dir* P4 R+ b; H, M3 t
    depends_on:
* N/ h. I. P6 d" h- l( o4 _" L5 e      - "node1"' s: s3 r& [+ g1 N! _, {* x4 O7 k
EOSC使用% |# Q& @) E8 N5 _' p% G. V
EOSC是EOS的核心进程EOSD对外暴露的RESTAPI命令行工具。EOSC的使用会利用到一些内置插件,插件在EOSD的配置文件config.ini中进行设置,如与链的交互需要使用’plugin = eos::chain_api_plugin’。为了签署交易并发送到区块链上,需要使用‘plugin = eos::wallet_api_plugin’。为了查询交易和历史记录,需要使用’eos::account_history_api_plugin’ 。  r1 R: w2 C7 [$ b4 {
# Plugin(s) to enable, may be specified multiple times( j1 P6 f$ `. y
plugin =
; y5 c4 y) F6 L+ G3 W: ?, neos::producer_plugin) u% D% H; ?  l4 A; M
plugin =
% Y: S* O( g- S7 b+ r* O3 @# Weos::chain_api_plugin
1 K/ A' ]: l, ?2 R+ w- t6 _plugin =
( D4 b' J. c! A* jeos::wallet_api_plugin
. q" a' m6 Y' m, z& T3 Dplugin =* s0 ^/ u; t5 z- p* I
eos::account_history_api_plugin) s& Y3 r& @! a! ^" u& K5 i" _
启动eosd后,可以使用EOSC查询当前的区块链状态
0 K) V0 P. v+ [* f# {4 h/ R* ]docker exec docker_node1_1 eosc get info8 w- Y. z. B! ^! u9 |/ e  Q$ k6 g
{
$ c/ G. ~7 K: }0 T; U, ?  "head_block_num": 23449,
& _" e2 C' O* \' j  "last_irreversible_block_num": 23432,, T9 ~5 I+ W) {- _8 |8 S* ~% `
  "head_block_id": "00005b996cc85962b28537c3d72696a012d1071638f5e4bad1809cf9afc9abb6",
# @% S) V3 l( U) O3 A7 J1 p8 Z( C  "head_block_time": "2017-09-29T01:53:33",1 W- w6 ]4 [7 W, J4 c: D2 u' x! Z6 A
  "head_block_producer": "initi",
0 E; g% M& J; J* @% w; z  "recent_slots": "1111111111111111111111111111111111111111111111111111111111111111",' N4 K( D* P7 ]3 X
  "participation_rate": "1.00000000000000000"# ?5 z& a! Z' d) }
}1 p% S$ L7 f5 R0 }% N
创建钱包
# c* r- D2 G9 Q# B  r$ `任何发送到区块链的交易都需要由所有者持有的私钥进行签名。首先,我们需要一个钱包来储存和管理私钥,使用EOSC命令创建一个钱包。
0 T% \% k  N: Y9 Sdocker exec docker_node1_1 eosc wallet create* J1 V1 E# S! N; x1 N5 }
Creating wallet: default
0 T7 h3 j# c# o  k$ x" ?1 |Save password to use in the future to unlock this wallet.
, T0 Z/ C8 Y# a7 [! J- ^) YWithout password imported keys will not be retrievable.4 k0 f" ~9 D* a4 {1 X
"PW5JXSxkHqNEwRKCpG2JUTLqkR8SNCBXofkAwaFDLwQkNdqaSXwC8"
; Q( u% y1 F$ X, a( a9 |) k命令执行完成,会在eos-walletd中创建一个名为‘default’的钱包,并返回钱包密码。, m4 z, H# X* q
这时候可以查看钱包列表
( q# Y4 t3 [4 n' z5 x/ K* S) ~docker exec docker_node1_1 eosc wallet list2 E! p: I& f% [
Wallets: " P8 q0 Z! Q( M5 g
[  i* Y& A4 v/ t
  "default *"+ z) Q2 s& }# t" g4 i% G' N) A" v
]& k! W; b" `) L' P
如果你没有指定钱包名称,默认都操作的是‘default’钱包
) w6 O" v! J- ^+ b将私钥导入钱包  y9 K# x, j& f; F# k
如果你想授权某个钱包可以由某人来管理和控制,需要导入该授权者的私钥。6 |8 G; X5 ?, q6 }
docker exec docker_node1_1 eosc wallet import 5KQwrPbwdL6PhXujxW37FSSQZ1JiwsST4cqQzDeyXtP79zkvFD3
/ c+ c. ?" j2 E& Jimported private key for:4 q/ A/ a$ H" ^$ |$ x" E0 m' V
EOS6MRyAjQq8ud7hVNYcfnVPJqcVpscN5So8BhtHuGYqET5GDW5CV
# E( @: N2 {( N5 B) z导入后,可以查询钱包已经导入的私钥和对应的公钥
: h  ?" ?4 N3 Edocker exec docker_node1_1 eosc wallet keys4 y& ]3 f2 {# C6 J* X- M$ T# w
[[
' `+ l: [- c  o: ^"EOS6MRyAjQq8ud7hVNYcfnVPJqcVpscN5So8BhtHuGYqET5GDW5CV",
1 I( k& q/ y' j6 ^"5KQwrPbwdL6PhXujxW37FSSQZ1JiwsST4cqQzDeyXtP79zkvFD3"2 H3 A% ~& r6 h0 E$ ~6 c* i
]2 }0 F' o, G+ p5 K& ]3 ]$ Q% a# E. P
]/ F' Q  q, ~  D! y
锁定和解锁钱包* L- n) Z, t! k2 t
日常使用,为了保证私钥安全,可临时锁定钱包,锁定后查看钱包列表是不可见的
/ [* E! }2 Z4 j2 ]& z% H4 K1 G& Wdocker exec docker_node1_1 eosc wallet lock
& k4 [7 E% H6 zLocked: 'default'
! P) I1 q4 ]; ]8 \# Y# {5 f* N当想要使用时,可以用创建钱包时生成的密码来解锁钱包
: l! e/ Q( ]  d% y+ w' W$ A2 F8 ndocker exec docker_node1_1 eosc wallet unlock --password PW5KVWrn81Y8PLAb52gr2FyXCanVavcrj9d5TC9C3yKhqq1PJYRPk
2 c' X5 ?$ K1 sUnlocked: 'default'
3 W7 e0 [% N  m* X解锁后,可以在列表重新看到default钱包了3 O; o0 c$ f: W3 i# V
docker exec docker_node1_1 eosc wallet list
1 o" h( X+ z8 _! aWallets: . _* I( a7 p2 `' [5 X0 p
[5 U5 O$ C( Y$ E' M& t
  "default *"8 w6 r0 ~4 V+ U% B7 ?
]2 ^- ~, G$ q4 v0 |; y5 N7 @  p, U
创建账户' a: {! i4 K2 H# ~9 e7 Z
创建账户需要有两组密钥:owner和active。EOS使用EOSC工具来创建密钥对
, C+ X' m7 d5 t1)owner key.
6 V9 `; L/ B" P8 {: u! S3 yPrivate key:5JRc8XxvodWey4StZ2zzkUhCQhDaHvGMkABtfHzQR2ie4qaUFJ76 E6 j7 ]4 p. ~. e2 L! L
Public key: EOS5mFEdAzxvMkHLQXt2v4naUjnBrPGmzMUCikymqhSR6m7QLGSTB8 l8 u! R" P' q- V( T' o" y
2)active key* E+ f! k, Q2 R1 v
Private key:5KNzFCbToz2a9Hztz9Qen5cyJcM3x5Wpq4GFiTYZgGhzntXdmYo6 U+ Y$ c" z* Y8 ?0 J
Public key: EOS5EdsvESpibWLJxupTqod1nswJnbiXQZuUcLiAWEEsqcZskymeB
# y% a1 `) j: D4 q* O; xEOSC不会保存生成的私钥
* T1 G7 }' A6 Z! a因为后续测试智能合约需要,我们创建一个名为currency的账号。目前这个版本,所有的账户都需要用已有账户来创建,所以我们用inita账户的owener key和active key来创建currency。 为了使inita获得发送交易的权限,需要先导入inita的私钥到钱包。(参见私钥导入钱包的步骤)6 N! E9 J, b, o9 {1 g* H
docker exec docker_node1_1 eosc create account inita currency EOS6NpEqWi177VKQkuJQL9V6Y3LqAAp9C2j
. g+ v" C$ C( ^& g! r+ A执行成功,会输出一串json的交易信息,打印账户创建相关内容7 V4 K( i* S7 i! l4 q! u# h+ j. E
我们可以查询inita可以创建了哪些用户& a0 {+ m0 r) ]
docker exec docker_node1_1 eosc get servants inita
7 B9 y9 J9 [: u% v+ e! P{" a8 I$ b  B. }& D) @& b( J
"controlled_accounts": [) L1 h. M! D0 v# T0 R
"currency"
2 M4 d; ]+ j  h* A7 K  d: Z]
# j3 W3 V( X1 a- `+ i}4 B0 i6 T( V) i" {* T3 M
内置转账
) E. ^* h+ B/ N2 ?0 O) L创建账户之后,可以查看当前账户的状态,可以看到创建的测试账号没有余额,这样不少功能无法测试,我们需要试着给创建账户添加一些余额, }- s4 e) Q( U/ D) j
docker exec docker_node1_1 eosc get account currency
3 D' o7 i( c/ A: ~, ^+ X{- t% j2 N+ L! j, r  l  w
  "name": "currency",
( i3 s8 O3 i% e" _* P/ m  "eos_balance": "0.0000 EOS",; x( }6 y4 D3 k
  "staked_balance": "0.0001 EOS",2 g2 M5 l- C% _% Y
  "unstaking_balance": "0.0000 EOS",
' N7 O; \# ]. L( u5 e5 O4 o' n6 v  "last_unstaking_time": "1969-12-31T23:59:59",/ J* M2 z5 n) t/ ~9 a+ H; q
  "permissions": [{- `- g% m1 t5 U3 R6 z/ n
      "name": "active",
* W7 B0 O  {! x; p: z2 b      "parent": "owner",4 U* o) ?3 a; N* E; Q
      "required_auth": {5 e3 V& x9 c9 f2 [
        "threshold": 1,6 w8 Q5 o9 Z+ d  \
        "keys": [{
7 W* J% C7 ~2 X! W2 R            "key": "EOS8ff42NMpJUybVj3nwUSnPpc3mMysKxyE4HVJy1E5o3fQv7knWf",% d, N4 j1 f! U+ h
            "weight": 1
- x1 A4 k" e9 H; Q2 S          }
! ?) L/ p6 O/ O0 @* V6 b" e        ],
  \4 V8 O2 P" e! E6 @  ~        "accounts": []* y- O. \- Z" c3 s3 _
      }
% G& x# J( P0 m8 w' X    },{
2 C0 v- `$ t8 u0 j  b      "name": "owner",
* t) Z6 @5 }0 z' |' M4 o1 k      "parent": "owner",
, I& [: M; _7 F* m      "required_auth": {
# p. a2 H; V: k- o1 F7 p) k        "threshold": 1,
( O! o- X- Q* g; d" }/ \; w        "keys": [{
  Y* x. W& Y1 J" r# O; d            "key": "EOS5fQ4saiHV426EQ7AKrGoD2AVMBYe77bnGSq42JjXBUfipv7o3E",
+ F( U& B, z* Y! J  Z- \            "weight": 1
# h% v# u2 j, N, `. M4 Q: |- I          }% v% v/ O% G3 N. C+ Q" I
        ],- R0 D/ A" ~7 o; y' _
        "accounts": []. G" D9 u1 ]: x
      }
" h4 h7 \6 s$ A9 }5 w    }
0 P% q- m% i1 q: N. O$ T" b  ]7 u$ u- A, I: Z7 @* ?
}; p+ ~* \0 Q0 J7 E
保存全网余额的创世账号是eos,查询余额状态
% S0 @) Y  X- wdocker exec docker_node1_1 eosc get account eos
& o0 y$ @% k2 k' K7 x{% F# G* g9 |, s
  "name": "eos"," h% C! J8 }7 p4 X) m$ s$ X
  "eos_balance": "69000000.0000 EOS",
6 b. P* @( E  H  "staked_balance": "0.0000 EOS",( I1 d3 C1 f) w4 a" j) ?0 l
  "unstaking_balance": "0.0000 EOS",
" t- H# Y/ L, N& |) s4 _- E  "last_unstaking_time": "1969-12-31T23:59:59",
0 o3 g  r) o1 v; s& @  "permissions": [{, ~( M, j, r) I7 S
      "name": "active",- w2 j3 e3 W& I  h- w5 h
      "parent": "owner",0 K' r- S4 C! e! p
      "required_auth": {/ ?( L' u6 ?1 ^! E: w6 M
        "threshold": 1,, Q! k2 f- u% C* Z( p# }
        "keys": [],
1 A. d- x7 @2 X+ E8 L/ X+ X1 j8 {        "accounts": []4 G+ \, G( g- ]$ e3 d9 ^
      }* E9 \# J3 [6 S$ o8 W0 `- O0 n) P2 R& x
    },{: s6 V2 T) i9 Y* M- V2 H* c2 D+ _3 y
      "name": "owner",
9 M4 c/ g- u; F6 e( t! q5 n7 F      "parent": "owner",+ l' a& B- P+ U; _$ Z7 u  N
      "required_auth": {
8 w# E3 m& P  y( A: n7 Q* U        "threshold": 1,
6 q- W( x! P  p' u- I& {/ C8 b        "keys": [],
/ {: a3 \8 k" K# S$ ]6 [! L7 X0 c        "accounts": []
+ x' E# \! y" k: {) P      }, p# \* w  W/ t+ F5 `- r
    }
1 c' f/ y: f- v9 R- w  ]8 F& ?* c/ }$ m0 o
}7 v9 D0 E# Y% U# D! R* D
我们可以通过创世块定义的创世账户使用EOSC给当前创建的账户转移余额
# w& V& Z+ y' Y; C, ^+ Ndocker exec docker_node1_1 eosc transfer inita currency 100000000/ }1 @" q2 R  g' a! R. [
{' F* X8 M, q( Z- e! I9 o- r6 Y
  "transaction_id": "59575b8caf08eac7c00eb7483c048f12d0e7abf1ede839c3b2ed41dc6c5c7c5f",
7 u/ i8 y: \. U7 [* Y  "processed": {
( p% d+ R# h2 Q    "refBlockNum": 24199,: y9 L% u5 U# T4 Y& i+ @0 B
    "refBlockPrefix": 1485651173,; c# `; W7 M/ C# }$ L* ~
    "expiration": "2017-09-29T02:31:03",. I% O6 r( N* f) y  G: [$ _
    "scope": [3 Q* p4 H7 @' V% x# V
      "currency",
3 s, B+ ?1 m  n$ T      "inita". p9 ~; n/ H" M; V  e9 m
    ],# y8 Z8 M1 E2 E  ^9 |' Q
    "signatures": [6 f6 C3 q7 s% u4 ?1 J
      "1f14229bdd4bfb927021bf96ff0651c8b0fa5666e9f5cf423a0270a1b91f2d2f690b573e179d8475ce2c6b160f5cd5507d58a44f8f6cf536348584efa8dd62ade0"
! d+ A/ f) ~# T0 Y7 X/ h8 A2 R* C    ]," ~# m2 U+ f1 s  H* p+ |; E
    "messages": [{5 i5 ~$ G$ \# e3 e, L
        "code": "eos",
+ j3 p# [4 R# D' t        "type": "transfer",$ o7 C- ^+ p+ ~" I6 ?" ~4 b
        "authorization": [{
, c% o  C3 i" W8 A# i  x& |            "account": "inita",8 {+ v! {6 [7 `# ^# J! V2 g1 T5 q# k6 f
            "permission": "active"
: L3 A  K) ^9 O- i' d# p2 [          }
5 i9 {& U8 z: t8 W$ h$ M+ k/ f        ],8 \- X( b) J. j8 x8 ~; j
        "data": {
5 A" Q  K' }1 C' V$ w/ n          "from": "inita",
% {2 @0 [: i4 h2 C          "to": "currency",7 K  i1 T2 G" i; h6 J
          "amount": 100000000,- }# b: e4 h3 h2 w9 X( [4 k5 y- o
          "memo": ""
: f7 ]+ _' _) G2 [* W        },2 _( H1 W3 j* R0 F# A
        "hex_data": "000000000093dd740000001e4d75af4600e1f5050000000000"
& e% ]. [4 w$ f  C. u1 S0 g      }
* C+ K% F  h6 g7 N0 g. f# l    ],
( @7 u) l7 s/ z2 m" r8 Y- C* W    "output": [{
2 x* I" v' t3 @/ f        "notify": [{
3 }5 F( D' `' p3 I9 S( K            "name": "currency",
9 ^* V/ ]3 C" X; b            "output": {
+ ]9 x4 m( N# W/ w" h              "notify": [],
' U; a6 B/ M7 E, W9 @              "deferred_transactions": []" f' m7 i" A1 L8 Z7 L
            }6 c1 ~" d2 h; g( |$ u
          },{& @) h3 R5 Z" S5 S
            "name": "inita",3 S, f( P4 l" {4 ~; `
            "output": {6 `( z% ~& e( m7 i7 X) F# W
              "notify": [],
1 e8 e& ?3 p6 ^+ S9 z: e              "deferred_transactions": []" M5 R6 r7 d/ }+ |7 d+ V, n5 r
            }9 e8 o# ?6 \7 L+ \
          }2 Y# L# f' |9 B% b+ d& U
        ],
) ]2 b% t$ L& B# }, z+ u        "deferred_transactions": []
5 _* x, ]6 E1 v7 r5 ~0 w& h      }
; J! A" R* J6 t( O    ]. i" {5 p4 Z4 j
  }. w' V& Z5 a+ t6 k) l
}
6 l+ B* _+ x: A再通过执行get account 命令,验证余额已经成功转移到创建的账户下
! A- C! k2 w; {3 r. D+ q/ c3 w查询交易历史
; [' x9 S. f" A. Z/ Q2 p% w6 T查询交易历史会使用到插件account_history_api_plugin,我们已经在config.ini中定义
" }: k- K) @) P3 `& R- J6 }docker exec docker_node1_1 eosc get transaction
4 |7 W! w% Z! e/ K) {" \" u. F如果需要查询一个特定账户最近一次的交易记录2 H" T* S2 U9 ]' b
docker exec docker_node1_1 eosc get transaction inita5 M" C1 j$ [6 Y4 Z" o( s6 S
创建智能合约
* }% T3 E; _$ y! _: n7 x! \官方提供了一个示例合约currency,我们依然使用EOSC来创建并部署智能合约,合约代码位置contracts/currency。
! b( u/ o% P; r& W1)为合约创建一个所有者账户。前文已经创建了currency账户; A$ n  j" A; |% R& E, g
2)检查区块链上有无同名合约9 S2 e+ q4 _, h" X
docker exec docker_node1_1 eosc get code currency * S) s3 N/ B( s/ s0 P9 e
code hash: 0000000000000000000000000000000000000000000000000000000000000000
; q/ q* G# v' s$ w( ~+ B) W3)为了获得部署权限(发送交易请求)需要将currency的active key导入到钱包中
& O0 K8 n# I9 X" w4)部署合约(.wast后缀文件)和他的abi(.abi后缀文件)
' V- R1 g/ |  f* Kdocker exec docker_node1_1 eosc set contract currency ../../contracts/currency/currency.wast ../../contracts/currency/currency.abi
# G- X; w$ H1 C9 c+ D1 l% `- I% Q' QReading WAST...) U4 c! j! [2 {8 ]
Assembling WASM...
( l' S  K+ J( f8 [8 x  U" U( bPublishing contract...( s0 R, @. T7 l1 Q- _
屏幕打印部署成功相关的信息,并查询合约hash5 @4 u8 i: P; J3 j; @. ?
docker exec docker_node1_1 eosc get code currency
" D$ |0 t& E. B1 y- dcode hash: c4023f74b3c7a3321d1641e4111b13584078fa7265c6ab12e1c19ff7ee800faf$ K  p1 b1 s* p/ a0 z0 i. S9 [
调用合约5 M! V; J  _$ A/ S5 G7 K3 {9 L* e
在合约部署到区块链上之后,所有的currency余额会分配给我们创建的currency账户。我们可以调用合约测试做一些转账交易。+ i8 ~8 b0 `3 U7 b4 A2 [6 ^
为了更好了解区块链合约的调用方式,我们可以通过.abi查看可以执行的操作列表和消息结构。
  M6 t* V9 N- Ddocker exec docker_node1_1 eosc get code -a currency.abi currency: g- A( V- S* t( j
code hash: c4023f74b3c7a3321d1641e4111b13584078fa7265c6ab12e1c19ff7ee800faf- P: ^4 f9 k% Z0 S& m/ d5 O- e
saving abi to currency.abi
; p% N( G6 r5 R2 d) m  b2 e2 r- r" Bcat currency.abi #查看) a& \6 {* g2 w# Q6 A9 q1 {
{7 h; s, p: r2 N" v7 v1 t1 N) v
  "types": [{) m7 z, Q: t" E0 R8 u  K
      "newTypeName": "AccountName",
0 s$ n& Z/ x' Y/ `      "type": "Name"
" t, w4 j7 }& w5 V' n* l    }
. {* N4 u7 s+ x& b  ],) w; T) [! i6 z9 f) r3 T
  "structs": [{
; H8 m7 i! ]) f1 t4 P' D  f      "name": "transfer",2 Q* p) L$ g% _# W! ]9 u  _
      "base": "",
4 v, W# G, Q' U      "fields": {& w! _+ }( K  J5 s, I* v6 {( W! {
        "from": "AccountName",, O. k9 f) o3 t! I  A( y
        "to": "AccountName",
! A9 C$ m  `. y! U7 @5 y        "amount": "UInt64"# ^* u% W; t' F8 i4 g, X% G
      }
/ Y5 x; L/ c7 D3 z  D0 j# e    },{2 y, [9 u3 s- {) {; l& u/ O  e7 n
      "name": "account",
- `' e5 V4 H* a7 R) K      "base": "",
" ?8 n6 P, t7 H      "fields": {
/ c7 K+ r, M1 ^2 _$ \/ `) D        "account": "Name",; L; W" E& k2 s: ?& M, X! A1 m8 @9 H
        "balance": "UInt64") x; T8 c" ?' e. g. g. O& b
      }( s. [* Z5 E, s& ~: e. H4 S8 A
    }
6 v2 j) [' [9 ~, u1 p  ],
: q1 a2 S: ]3 n6 ~  "actions": [{! x. H' N. [0 q% ~" j2 c4 G2 h8 n
      "action": "transfer",
7 w8 G/ u0 S& G* C3 R      "type": "transfer"' e3 j+ E9 @$ t/ ^- T  s
    }* n; ]. O! `, ~' m7 L& X2 @
  ],
' r& u6 v& @7 P: v9 U  "tables": [{& a) I  N% w4 J& j
      "table": "account",
! D  a2 R! S- t0 Q/ i3 \      "type": "account",7 G( D/ m( W% l3 s$ p: w$ S
      "indextype": "i64",
' R! c2 ^$ |' x      "keynames" : ["account"],
: T) }( o; F/ b      "keytypes" : ["Name"]
% }; w9 w$ c. X- c5 @1 v# j    }, k9 e/ m. Z) s  W$ T
  ]
1 {5 A, [' w- _* Z7 {! A+ w3 ]/ D}! S  q" Y5 z: W5 I
通过上面的abi我们可以看到currency合约可以执行transfer操作,消息格式为from,to和amount。我们调用合约从currency账户转移50个余额到inita账户
, q4 b+ b$ N6 s1 x+ H  @% t* c7 z7 Vdocker exec docker_node1_1 eosc push message currency transfer '{"from":"currency","to":"inita","amount":50}' --scop
1 v% J, ], `7 F7 L执行完成,我们查询余额验证结果
0 k% F- Z, `: x* i. k' v* Pdocker exec docker_node1_1 eosc get table inita currency account
% s+ d( F$ b& O" a0 v{2 E3 Q4 ]6 J/ R9 `) Z
  "rows": [{
/ r* E- P0 R* c* h8 k: N/ k4 e5 k      "account": "account",
) E8 Z% f2 j, E0 ?8 Y7 y! z      "balance": 50 + E" X" ~0 ?- b/ v, e
       }
9 d/ k, ]" B- J: O- {% H' g. n    ],' A- l+ K& l4 C  [. S& S" z$ ?8 Z( N
  "more": false: F" @/ w7 K9 M
}
. m8 ]& d5 s9 E1 Fdocker exec docker_node1_1 eosc get table currency currency account- `) n  O, Z* n2 N: \1 v1 V
{. B2 b- f% X* ^+ Z/ ^' J4 C$ ?
  "rows": [{0 h# x( ~% h% G# p  p
      "account": "account",* ?' Q/ K; g+ T$ R
      "balance": 9999999505 y; y8 _" m. j" |5 e4 ~3 p7 F9 |
    }
3 l2 Q* B4 b: L! }8 g( n/ U  ],+ V$ u+ m7 n. q8 w/ c
  "more": false, _& {, h1 [4 y0 E9 k9 u
}
9 X2 a# |1 W! g0 g" T+ j& R余额不足的账户尝试转账,会提示失败
7 J. \' ]/ M! r1 |8 w+ ]$ L0 ]docker exec docker_node1_1 eosc push message currency transfer '{"from":"tester","to":"inita","amount":50}'-S inita -S tester -p tester@active) U9 A; x3 y2 r: c7 u% N
3543610ms thread-0 main.cpp:271 operator() ] Converting argument to binary...( W# ?2 o' y6 s6 }& t5 u* \' U
3543615ms thread-0 main.cpp:311  main ] Failed with error: 10 assert_exception: Assert Exception' `  V5 `" M2 [* z3 d
status_code == 200: Error : 10 assert_exception: Assert Exception( b) T6 h) o# K5 O
test: assertion failed: integer underflow subtracting token balance# O9 _# \  x% M
{"s":"integer underflow subtracting token balance","ptr":176} thread-1 wasm_interface.cpp:248 assertnonei32i32 [...snipped...]
! H7 x5 v' n: I$ I查询合约1 ?- }( \3 J( c. D: s
如上文验证步骤,在调用完合约后,可以通过查询表来验证每个帐户持有的余额。
8 a  v$ @0 A, Kdocker exec docker_node1_1 eosc get table currency currency account
* D' V* G: g6 y( S6 f9 g- ~1 q! q# \% A连接特定节点& V8 i$ B6 d+ H5 N; N
默认情况下,EOSC连接本地端口8888的节点。可以通过指定主机地址和端口来连接其他EOSD节点。同样的,钱包服务也可以指定特定的主机地址和端口。
$ h: e& Z( A, e- u3 n+ s& ~1 @docker exec docker_node1_1 eosc --host  --port
, A' n  y$ K* q$ B: D链接独立钱包服务) t5 J4 m1 i- B/ s
除了使用EOSD内置的钱包服务,也可以独立部署钱包服务
5 ?  n# A+ x9 U! W& d( E' B/ v; @docker exec docker_node1_1 eos-walletd --http-server-endpoint host:port
5 o& G5 {+ E, V0 h- @3 t调用独立钱包服务需要添加如下选项
! R/ Y* M- Y6 Y8 v9 K  z3 xdocker exec docker_node1_1 eosc --wallet-host --wallet-port7 P6 ^6 P' Q( d& K
免签名验证
+ G  I2 M# W" }* f开发者如果需要快速测试功能,可以跳过节点签名的步骤,这样可以解耦密码学的问题而关注应用功能# W9 t1 z% e' ~" Q9 O
启动时使用特定参数
* y! i9 p5 x+ w- ^0 p4 xeosd --skip-transaction-signatures
* R8 b) r3 S! pEOSC调用时添加-s 选项9 r$ P, S3 B# l1 s3 i* f$ R" S4 m( S5 r
docker exec docker_node1_1 eosc   -s
6 F5 _, F2 Q% z' k2 p, v其他RPC调用
  C5 g( S# ], ^5 k- lEOSD RPC 包含通过HTTP RPC与eosd和注册其上的插件进行调用的方式.; t- G8 d1 k7 E: ]2 ^7 `% n1 F
1)区块链API 配置
' G1 S2 M# t* T  ?/ t* C2 b, \想要查询eosd信息需要启用plugin = eos::chain_api_plugin插件并添加至config.ini中$ z. i  W/ A9 }" e; @
2)get_info接口用于查询区块链的基础信息
7 H- j7 w3 @+ A+ M6 O! ]curl http://127.0.0.1:8888/v1/chain/get_info 0 x) S' M5 N8 y7 ]& G2 M1 z$ ]- C
返回结果如下:
: W& N( g# v8 O) E* c  y{"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"}
6 B" `5 P  T; K: M- _) F3 r* I) m' eget_block接口用于查询区块相关信息
/ q# s* c6 }9 Q, w
# X% P1 |8 C3 d5 W' H5 S  E) A; \curl  http://localhost:8888/v1/chain/get_block -X POST -d '{"block_num_or_id":5}'$ x1 H1 S1 P% ?1 O7 W; n* d
curl  http://localhost:8888/v1/chain/get_block -X POST -d '{"block_num_or_id":0000000445a9f27898383fd7de32835d5d6a978cc14ce40d9f327b5329de796b}'
0 `' T6 Q! G% \" E) Y6 g返回结果如下:. b4 y: G+ Z/ {, Z
{"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}! c5 y" g. x9 Z" }! ^
4)push_transaction接口,调用合约交易
: a' m9 I) c) o# y2 Y& ~$ N该调用为JSON格式并会将结果更新到区块链上* T" h6 {' A7 _: N' G
执行正确的结果返回! B3 g  {# s: k# E- Z- R: ^
返回 HTTP 200 和交易ID号
5 A$ ?. @+ v6 H{
* l  `5 g( J6 T6 G! y'transaction_id' : "..." 0 g5 ~3 ~7 |. B/ V  z$ w
}' c' W  `" P# R; ^
执行错误的结果返回,一般为400错误(参数错误)或者500错误
% v, j6 n6 U7 V0 x2 {5 L. [+ uHTTP/1.1 500 Internal Server Error
4 u& m: F. {* V" v" ]; ^, uContent-Length: 1466, @# y1 F7 ^# D) X; N8 {! a
...error message.., Z, }1 O  {- G" S+ |+ Q' ?9 Q" _
push_transaction 调用方法: F  q  e. f4 V2 u' m
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":[]}'
: u. v1 Y2 q5 i1 \# h4 k$ |8 y$ a  Z此示例模拟一个转账交易。 refBlockNum和refBlockPrefix使用的前例block查询的结果
BitMere.com 比特池塘系信息发布平台,比特池塘仅提供信息存储空间服务。
声明:该文观点仅代表作者本人,本文不代表比特池塘立场,且不构成建议,请谨慎对待。
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

成为第一个吐槽的人

罗宾虚汉 初中生
  • 粉丝

    3

  • 关注

    0

  • 主题

    16