github.com/hyperledger/burrow@v0.34.5-0.20220512172541-77f09336001d/vent/service/consumer_postgres_test.go (about)

     1  // +build integration,!ethereum
     2  
     3  package service_test
     4  
     5  import (
     6  	"encoding/json"
     7  	"testing"
     8  	"time"
     9  
    10  	"github.com/hyperledger/burrow/integration"
    11  	"github.com/hyperledger/burrow/integration/rpctest"
    12  
    13  	"github.com/stretchr/testify/assert"
    14  
    15  	"github.com/hyperledger/burrow/vent/types"
    16  	"github.com/lib/pq"
    17  	"github.com/stretchr/testify/require"
    18  
    19  	"github.com/hyperledger/burrow/vent/test"
    20  )
    21  
    22  func TestPostgresConsumer(t *testing.T) {
    23  	privateAccounts := rpctest.PrivateAccounts
    24  	kern, shutdown := integration.RunNode(t, rpctest.GenesisDoc, privateAccounts)
    25  	defer shutdown()
    26  	inputAddress := privateAccounts[0].GetAddress()
    27  	grpcAddress := kern.GRPCListenAddress().String()
    28  	tcli := test.NewBurrowTransactClient(t, grpcAddress)
    29  
    30  	t.Parallel()
    31  	time.Sleep(2 * time.Second)
    32  
    33  	t.Run("Group", func(t *testing.T) {
    34  		t.Run("PostgresConsumer", func(t *testing.T) {
    35  			testConsumer(t, kern.Blockchain.ChainID(), test.PostgresVentConfig(grpcAddress), tcli, inputAddress)
    36  		})
    37  
    38  		t.Run("PostgresInvalidUTF8", func(t *testing.T) {
    39  			testInvalidUTF8(t, test.PostgresVentConfig(grpcAddress), tcli, inputAddress)
    40  		})
    41  
    42  		t.Run("PostgresDeleteEvent", func(t *testing.T) {
    43  			testDeleteEvent(t, kern.Blockchain.ChainID(), test.PostgresVentConfig(grpcAddress), tcli, inputAddress)
    44  		})
    45  
    46  		t.Run("PostgresResume", func(t *testing.T) {
    47  			testResume(t, test.PostgresVentConfig(grpcAddress))
    48  		})
    49  
    50  		t.Run("PostgresTriggers", func(t *testing.T) {
    51  			tCli := test.NewBurrowTransactClient(t, kern.GRPCListenAddress().String())
    52  			create := test.CreateContract(t, tCli, inputAddress)
    53  
    54  			// generate events
    55  			name := "TestTriggerEvent"
    56  			description := "Trigger it!"
    57  			txe := test.CallAddEvent(t, tCli, inputAddress, create.Receipt.ContractAddress, name, description)
    58  
    59  			cfg := test.PostgresVentConfig(grpcAddress)
    60  			// create test db
    61  			_, closeDB := test.NewTestDB(t, cfg)
    62  			defer closeDB()
    63  
    64  			// Create a postgres notification listener
    65  			listener := pq.NewListener(cfg.DBURL, time.Second, time.Second*20, func(event pq.ListenerEventType, err error) {
    66  				require.NoError(t, err)
    67  			})
    68  
    69  			// These are defined in sqlsol_view.json
    70  			err := listener.Listen("meta")
    71  			require.NoError(t, err)
    72  
    73  			err = listener.Listen("keyed_meta")
    74  			require.NoError(t, err)
    75  
    76  			err = listener.Listen(types.BlockHeightLabel)
    77  			require.NoError(t, err)
    78  
    79  			type payload struct {
    80  				Height uint64 `json:"_height"`
    81  			}
    82  
    83  			heightCh := make(chan uint64)
    84  			notifications := make(map[string]string)
    85  			go func() {
    86  				for n := range listener.Notify {
    87  					notifications[n.Channel] = n.Extra
    88  					if n.Channel == types.BlockHeightLabel {
    89  						pl := new(payload)
    90  						err := json.Unmarshal([]byte(n.Extra), pl)
    91  						if err != nil {
    92  							panic(err)
    93  						}
    94  						if pl.Height >= txe.Height {
    95  							heightCh <- pl.Height
    96  							return
    97  						}
    98  					}
    99  				}
   100  			}()
   101  			resolveSpec(cfg, testViewSpec)
   102  			runConsumer(t, cfg)
   103  
   104  			// Give events a chance
   105  			const timeout = 3 * time.Second
   106  			select {
   107  			case <-time.After(timeout):
   108  				t.Fatalf("timed out after %v waiting for notification", timeout)
   109  			case height := <-heightCh:
   110  				// Assert we get expected returns
   111  				t.Logf("latest height: %d, txe height: %d", height, txe.Height)
   112  				assert.True(t, height >= txe.Height)
   113  			}
   114  			assert.Equal(t, `{"_action" : "INSERT", "testdescription" : "5472696767657220697421000000000000000000000000000000000000000000", "testname" : "TestTriggerEvent"}`,
   115  				notifications["meta"])
   116  			assert.Equal(t, `{"_action" : "INSERT", "testdescription" : "5472696767657220697421000000000000000000000000000000000000000000", "testkey" : "\\x544553545f4556454e5453000000000000000000000000000000000000000000", "testname" : "TestTriggerEvent"}`,
   117  				notifications["keyed_meta"])
   118  		})
   119  	})
   120  }