You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

323 lines
8.5 KiB

10 years ago
10 years ago
10 years ago
10 years ago
  1. package rpctest
  2. import (
  3. "bytes"
  4. "encoding/json"
  5. "fmt"
  6. "net/http"
  7. "testing"
  8. "time"
  9. "github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/gorilla/websocket"
  10. _ "github.com/tendermint/tendermint/config/tendermint_test"
  11. "github.com/tendermint/tendermint/rpc/types"
  12. "github.com/tendermint/tendermint/types"
  13. "github.com/tendermint/tendermint/wire"
  14. )
  15. //--------------------------------------------------------------------------------
  16. // Utilities for testing the websocket service
  17. // create a new connection
  18. func newWSCon(t *testing.T) *websocket.Conn {
  19. dialer := websocket.DefaultDialer
  20. rHeader := http.Header{}
  21. con, r, err := dialer.Dial(websocketAddr, rHeader)
  22. fmt.Println("response", r)
  23. if err != nil {
  24. t.Fatal(err)
  25. }
  26. return con
  27. }
  28. // subscribe to an event
  29. func subscribe(t *testing.T, con *websocket.Conn, eventid string) {
  30. err := con.WriteJSON(rpctypes.RPCRequest{
  31. JSONRPC: "2.0",
  32. Id: "",
  33. Method: "subscribe",
  34. Params: []interface{}{eventid},
  35. })
  36. if err != nil {
  37. t.Fatal(err)
  38. }
  39. }
  40. // unsubscribe from an event
  41. func unsubscribe(t *testing.T, con *websocket.Conn, eventid string) {
  42. err := con.WriteJSON(rpctypes.RPCRequest{
  43. JSONRPC: "2.0",
  44. Id: "",
  45. Method: "unsubscribe",
  46. Params: []interface{}{eventid},
  47. })
  48. if err != nil {
  49. t.Fatal(err)
  50. }
  51. }
  52. // wait for an event; do things that might trigger events, and check them when they are received
  53. // the check function takes an event id and the byte slice read off the ws
  54. func waitForEvent(t *testing.T, con *websocket.Conn, eventid string, dieOnTimeout bool, f func(), check func(string, []byte) error) {
  55. // go routine to wait for webscoket msg
  56. goodCh := make(chan []byte)
  57. errCh := make(chan error)
  58. quitCh := make(chan struct{})
  59. defer close(quitCh)
  60. /*
  61. // TODO delete: we moved pinging to the server.
  62. // Write pings repeatedly
  63. go func() {
  64. pingTicker := time.NewTicker((time.Second * rpcserver.WSReadTimeoutSeconds) / 2)
  65. for {
  66. select {
  67. case <-quitCh:
  68. pingTicker.Stop()
  69. return
  70. case <-pingTicker.C:
  71. con.WriteControl(websocket.PingMessage, []byte("whatevs"), time.Now().Add(time.Second))
  72. }
  73. }
  74. }()
  75. */
  76. // Read message
  77. go func() {
  78. for {
  79. _, p, err := con.ReadMessage()
  80. if err != nil {
  81. errCh <- err
  82. break
  83. } else {
  84. // if the event id isnt what we're waiting on
  85. // ignore it
  86. var response struct {
  87. Result rpctypes.RPCEventResult `json:"result"`
  88. }
  89. if err := json.Unmarshal(p, &response); err != nil {
  90. errCh <- err
  91. break
  92. }
  93. if response.Result.Event == eventid {
  94. goodCh <- p
  95. break
  96. }
  97. }
  98. }
  99. }()
  100. // do stuff (transactions)
  101. f()
  102. // wait for an event or timeout
  103. timeout := time.NewTimer(10 * time.Second)
  104. select {
  105. case <-timeout.C:
  106. if dieOnTimeout {
  107. con.Close()
  108. t.Fatalf("%s event was not received in time", eventid)
  109. }
  110. // else that's great, we didn't hear the event
  111. // and we shouldn't have
  112. case p := <-goodCh:
  113. if dieOnTimeout {
  114. // message was received and expected
  115. // run the check
  116. err := check(eventid, p)
  117. if err != nil {
  118. t.Fatal(err)
  119. }
  120. } else {
  121. con.Close()
  122. t.Fatalf("%s event was not expected", eventid)
  123. }
  124. case err := <-errCh:
  125. t.Fatal(err)
  126. }
  127. }
  128. //--------------------------------------------------------------------------------
  129. func unmarshalResponseNewBlock(b []byte) (*types.Block, error) {
  130. // unmarshall and assert somethings
  131. var response struct {
  132. JSONRPC string `json:"jsonrpc"`
  133. Id string `json:"id"`
  134. Result struct {
  135. Event string `json:"event"`
  136. Data *types.Block `json:"data"`
  137. } `json:"result"`
  138. Error string `json:"error"`
  139. }
  140. var err error
  141. wire.ReadJSON(&response, b, &err)
  142. if err != nil {
  143. return nil, err
  144. }
  145. if response.Error != "" {
  146. return nil, fmt.Errorf(response.Error)
  147. }
  148. block := response.Result.Data
  149. return block, nil
  150. }
  151. func unmarshalResponseNameReg(b []byte) (*types.NameTx, error) {
  152. // unmarshall and assert somethings
  153. var response struct {
  154. JSONRPC string `json:"jsonrpc"`
  155. Id string `json:"id"`
  156. Result struct {
  157. Event string `json:"event"`
  158. Data *types.NameTx `json:"data"`
  159. } `json:"result"`
  160. Error string `json:"error"`
  161. }
  162. var err error
  163. wire.ReadJSON(&response, b, &err)
  164. if err != nil {
  165. return nil, err
  166. }
  167. if response.Error != "" {
  168. return nil, fmt.Errorf(response.Error)
  169. }
  170. tx := response.Result.Data
  171. return tx, nil
  172. }
  173. func unmarshalValidateBlockchain(t *testing.T, con *websocket.Conn, eid string) {
  174. var initBlockN int
  175. for i := 0; i < 2; i++ {
  176. waitForEvent(t, con, eid, true, func() {}, func(eid string, b []byte) error {
  177. block, err := unmarshalResponseNewBlock(b)
  178. if err != nil {
  179. return err
  180. }
  181. if i == 0 {
  182. initBlockN = block.Header.Height
  183. } else {
  184. if block.Header.Height != initBlockN+i {
  185. return fmt.Errorf("Expected block %d, got block %d", i, block.Header.Height)
  186. }
  187. }
  188. return nil
  189. })
  190. }
  191. }
  192. func unmarshalValidateSend(amt int64, toAddr []byte) func(string, []byte) error {
  193. return func(eid string, b []byte) error {
  194. // unmarshal and assert correctness
  195. var response struct {
  196. JSONRPC string `json:"jsonrpc"`
  197. Id string `json:"id"`
  198. Result struct {
  199. Event string `json:"event"`
  200. Data types.EventMsgTx `json:"data"`
  201. } `json:"result"`
  202. Error string `json:"error"`
  203. }
  204. var err error
  205. wire.ReadJSON(&response, b, &err)
  206. if err != nil {
  207. return err
  208. }
  209. if response.Error != "" {
  210. return fmt.Errorf(response.Error)
  211. }
  212. if eid != response.Result.Event {
  213. return fmt.Errorf("Eventid is not correct. Got %s, expected %s", response.Result.Event, eid)
  214. }
  215. tx := response.Result.Data.Tx.(*types.SendTx)
  216. if bytes.Compare(tx.Inputs[0].Address, user[0].Address) != 0 {
  217. return fmt.Errorf("Senders do not match up! Got %x, expected %x", tx.Inputs[0].Address, user[0].Address)
  218. }
  219. if tx.Inputs[0].Amount != amt {
  220. return fmt.Errorf("Amt does not match up! Got %d, expected %d", tx.Inputs[0].Amount, amt)
  221. }
  222. if bytes.Compare(tx.Outputs[0].Address, toAddr) != 0 {
  223. return fmt.Errorf("Receivers do not match up! Got %x, expected %x", tx.Outputs[0].Address, user[0].Address)
  224. }
  225. return nil
  226. }
  227. }
  228. func unmarshalValidateCall(amt int64, returnCode []byte) func(string, []byte) error {
  229. return func(eid string, b []byte) error {
  230. // unmarshall and assert somethings
  231. var response struct {
  232. JSONRPC string `json:"jsonrpc"`
  233. Id string `json:"id"`
  234. Result struct {
  235. Event string `json:"event"`
  236. Data struct {
  237. Tx types.CallTx `json:"tx"`
  238. Return []byte `json:"return"`
  239. Exception string `json:"exception"`
  240. } `json:"data"`
  241. } `json:"result"`
  242. Error string `json:"error"`
  243. }
  244. var err error
  245. wire.ReadJSON(&response, b, &err)
  246. if err != nil {
  247. return err
  248. }
  249. if response.Error != "" {
  250. return fmt.Errorf(response.Error)
  251. }
  252. if response.Result.Data.Exception != "" {
  253. return fmt.Errorf(response.Result.Data.Exception)
  254. }
  255. tx := response.Result.Data.Tx
  256. if bytes.Compare(tx.Input.Address, user[0].Address) != 0 {
  257. return fmt.Errorf("Senders do not match up! Got %x, expected %x", tx.Input.Address, user[0].Address)
  258. }
  259. if tx.Input.Amount != amt {
  260. return fmt.Errorf("Amt does not match up! Got %d, expected %d", tx.Input.Amount, amt)
  261. }
  262. ret := response.Result.Data.Return
  263. if bytes.Compare(ret, returnCode) != 0 {
  264. return fmt.Errorf("Call did not return correctly. Got %x, expected %x", ret, returnCode)
  265. }
  266. return nil
  267. }
  268. }
  269. func unmarshalValidateCallCall(origin, returnCode []byte, txid *[]byte) func(string, []byte) error {
  270. return func(eid string, b []byte) error {
  271. // unmarshall and assert somethings
  272. var response struct {
  273. JSONRPC string `json:"jsonrpc"`
  274. Id string `json:"id"`
  275. Result struct {
  276. Event string `json:"event"`
  277. Data types.EventMsgCall `json:"data"`
  278. } `json:"result"`
  279. Error string `json:"error"`
  280. }
  281. var err error
  282. wire.ReadJSON(&response, b, &err)
  283. if err != nil {
  284. return err
  285. }
  286. if response.Error != "" {
  287. return fmt.Errorf(response.Error)
  288. }
  289. if response.Result.Data.Exception != "" {
  290. return fmt.Errorf(response.Result.Data.Exception)
  291. }
  292. if bytes.Compare(response.Result.Data.Origin, origin) != 0 {
  293. return fmt.Errorf("Origin does not match up! Got %x, expected %x", response.Result.Data.Origin, origin)
  294. }
  295. ret := response.Result.Data.Return
  296. if bytes.Compare(ret, returnCode) != 0 {
  297. return fmt.Errorf("Call did not return correctly. Got %x, expected %x", ret, returnCode)
  298. }
  299. if bytes.Compare(response.Result.Data.TxID, *txid) != 0 {
  300. return fmt.Errorf("TxIDs do not match up! Got %x, expected %x", response.Result.Data.TxID, *txid)
  301. }
  302. return nil
  303. }
  304. }