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.

159 lines
4.2 KiB

  1. package rpctest
  2. import (
  3. "fmt"
  4. "testing"
  5. "time"
  6. "github.com/stretchr/testify/require"
  7. logger "github.com/tendermint/go-logger"
  8. wire "github.com/tendermint/go-wire"
  9. abci "github.com/tendermint/abci/types"
  10. cfg "github.com/tendermint/go-config"
  11. client "github.com/tendermint/go-rpc/client"
  12. "github.com/tendermint/tendermint/config/tendermint_test"
  13. nm "github.com/tendermint/tendermint/node"
  14. "github.com/tendermint/tendermint/proxy"
  15. ctypes "github.com/tendermint/tendermint/rpc/core/types"
  16. core_grpc "github.com/tendermint/tendermint/rpc/grpc"
  17. "github.com/tendermint/tendermint/types"
  18. )
  19. var (
  20. config cfg.Config
  21. node *nm.Node
  22. )
  23. const tmLogLevel = "error"
  24. // GetConfig returns a config for the test cases as a singleton
  25. func GetConfig() cfg.Config {
  26. if config == nil {
  27. config = tendermint_test.ResetConfig("rpc_test_client_test")
  28. // Shut up the logging
  29. logger.SetLogLevel(tmLogLevel)
  30. }
  31. return config
  32. }
  33. func GetNode() *nm.Node {
  34. return node
  35. }
  36. // GetURIClient gets a uri client pointing to the test tendermint rpc
  37. func GetURIClient() *client.ClientURI {
  38. rpcAddr := GetConfig().GetString("rpc_laddr")
  39. return client.NewClientURI(rpcAddr)
  40. }
  41. // GetJSONClient gets a http/json client pointing to the test tendermint rpc
  42. func GetJSONClient() *client.ClientJSONRPC {
  43. rpcAddr := GetConfig().GetString("rpc_laddr")
  44. return client.NewClientJSONRPC(rpcAddr)
  45. }
  46. func GetGRPCClient() core_grpc.BroadcastAPIClient {
  47. grpcAddr := config.GetString("grpc_laddr")
  48. return core_grpc.StartGRPCClient(grpcAddr)
  49. }
  50. func GetWSClient() *client.WSClient {
  51. rpcAddr := GetConfig().GetString("rpc_laddr")
  52. wsc := client.NewWSClient(rpcAddr, "/websocket")
  53. if _, err := wsc.Start(); err != nil {
  54. panic(err)
  55. }
  56. return wsc
  57. }
  58. // StartTendermint starts a test tendermint server in a go routine and returns when it is initialized
  59. // TODO: can one pass an Application in????
  60. func StartTendermint(app abci.Application) *nm.Node {
  61. // start a node
  62. fmt.Println("Starting Tendermint...")
  63. node = NewTendermint(app)
  64. fmt.Println("Tendermint running!")
  65. return node
  66. }
  67. // NewTendermint creates a new tendermint server and sleeps forever
  68. func NewTendermint(app abci.Application) *nm.Node {
  69. // Create & start node
  70. config := GetConfig()
  71. privValidatorFile := config.GetString("priv_validator_file")
  72. privValidator := types.LoadOrGenPrivValidator(privValidatorFile)
  73. papp := proxy.NewLocalClientCreator(app)
  74. node := nm.NewNode(config, privValidator, papp)
  75. // node.Start now does everything including the RPC server
  76. node.Start()
  77. return node
  78. }
  79. //--------------------------------------------------------------------------------
  80. // Utilities for testing the websocket service
  81. // wait for an event; do things that might trigger events, and check them when they are received
  82. // the check function takes an event id and the byte slice read off the ws
  83. func waitForEvent(t *testing.T, wsc *client.WSClient, eventid string, dieOnTimeout bool, f func(), check func(string, interface{}) error) {
  84. // go routine to wait for webscoket msg
  85. goodCh := make(chan interface{})
  86. errCh := make(chan error)
  87. // Read message
  88. go func() {
  89. var err error
  90. LOOP:
  91. for {
  92. select {
  93. case r := <-wsc.ResultsCh:
  94. result := new(ctypes.TMResult)
  95. wire.ReadJSONPtr(result, r, &err)
  96. if err != nil {
  97. errCh <- err
  98. break LOOP
  99. }
  100. event, ok := (*result).(*ctypes.ResultEvent)
  101. if ok && event.Name == eventid {
  102. goodCh <- event.Data
  103. break LOOP
  104. }
  105. case err := <-wsc.ErrorsCh:
  106. errCh <- err
  107. break LOOP
  108. case <-wsc.Quit:
  109. break LOOP
  110. }
  111. }
  112. }()
  113. // do stuff (transactions)
  114. f()
  115. // wait for an event or timeout
  116. timeout := time.NewTimer(10 * time.Second)
  117. select {
  118. case <-timeout.C:
  119. if dieOnTimeout {
  120. wsc.Stop()
  121. require.True(t, false, "%s event was not received in time", eventid)
  122. }
  123. // else that's great, we didn't hear the event
  124. // and we shouldn't have
  125. case eventData := <-goodCh:
  126. if dieOnTimeout {
  127. // message was received and expected
  128. // run the check
  129. require.Nil(t, check(eventid, eventData))
  130. } else {
  131. wsc.Stop()
  132. require.True(t, false, "%s event was not expected", eventid)
  133. }
  134. case err := <-errCh:
  135. panic(err) // Show the stack trace.
  136. }
  137. }
  138. //--------------------------------------------------------------------------------