github.com/ethersphere/bee/v2@v2.2.0/pkg/pingpong/pingpong_test.go (about)

     1  // Copyright 2020 The Swarm Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package pingpong_test
     6  
     7  import (
     8  	"bytes"
     9  	"context"
    10  	"fmt"
    11  	"runtime"
    12  	"testing"
    13  	"time"
    14  
    15  	"github.com/ethersphere/bee/v2/pkg/swarm"
    16  
    17  	"github.com/ethersphere/bee/v2/pkg/log"
    18  	"github.com/ethersphere/bee/v2/pkg/p2p"
    19  	"github.com/ethersphere/bee/v2/pkg/p2p/protobuf"
    20  	"github.com/ethersphere/bee/v2/pkg/p2p/streamtest"
    21  	"github.com/ethersphere/bee/v2/pkg/pingpong"
    22  	"github.com/ethersphere/bee/v2/pkg/pingpong/pb"
    23  )
    24  
    25  func TestPing(t *testing.T) {
    26  	t.Parallel()
    27  
    28  	logger := log.Noop
    29  
    30  	// create a pingpong server that handles the incoming stream
    31  	server := pingpong.New(nil, logger, nil)
    32  
    33  	// setup the stream recorder to record stream data
    34  	recorder := streamtest.New(
    35  		streamtest.WithProtocols(server.Protocol()),
    36  		streamtest.WithMiddlewares(func(f p2p.HandlerFunc) p2p.HandlerFunc {
    37  			if runtime.GOOS == "windows" {
    38  				// windows has a bit lower time resolution
    39  				// so, slow down the handler with a middleware
    40  				// not to get 0s for rtt value
    41  				time.Sleep(100 * time.Millisecond)
    42  			}
    43  			return f
    44  		}),
    45  	)
    46  
    47  	// create a pingpong client that will do pinging
    48  	client := pingpong.New(recorder, logger, nil)
    49  
    50  	// ping
    51  	addr := swarm.MustParseHexAddress("ca1e9f3938cc1425c6061b96ad9eb93e134dfe8734ad490164ef20af9d1cf59c")
    52  	greetings := []string{"hey", "there", "fella"}
    53  	rtt, err := client.Ping(context.Background(), addr, greetings...)
    54  	if err != nil {
    55  		t.Fatal(err)
    56  	}
    57  
    58  	// check that RTT is a sane value
    59  	if rtt <= 0 {
    60  		t.Errorf("invalid RTT value %v", rtt)
    61  	}
    62  
    63  	// get a record for this stream
    64  	records, err := recorder.Records(addr, "pingpong", "1.0.0", "pingpong")
    65  	if err != nil {
    66  		t.Fatal(err)
    67  	}
    68  	if l := len(records); l != 1 {
    69  		t.Fatalf("got %v records, want %v", l, 1)
    70  	}
    71  	record := records[0]
    72  
    73  	// validate received ping greetings from the client
    74  	wantGreetings := greetings
    75  	messages, err := protobuf.ReadMessages(
    76  		bytes.NewReader(record.In()),
    77  		func() protobuf.Message { return new(pb.Ping) },
    78  	)
    79  	if err != nil {
    80  		t.Fatal(err)
    81  	}
    82  	gotGreetings := make([]string, 0, len(messages))
    83  	for _, m := range messages {
    84  		gotGreetings = append(gotGreetings, m.(*pb.Ping).Greeting)
    85  	}
    86  	if fmt.Sprint(gotGreetings) != fmt.Sprint(wantGreetings) {
    87  		t.Errorf("got greetings %v, want %v", gotGreetings, wantGreetings)
    88  	}
    89  
    90  	// validate sent pong responses by handler
    91  	wantResponses := make([]string, 0, len(greetings))
    92  	for _, g := range greetings {
    93  		wantResponses = append(wantResponses, "{"+g+"}")
    94  	}
    95  	messages, err = protobuf.ReadMessages(
    96  		bytes.NewReader(record.Out()),
    97  		func() protobuf.Message { return new(pb.Pong) },
    98  	)
    99  	if err != nil {
   100  		t.Fatal(err)
   101  	}
   102  	gotResponses := make([]string, 0, len(messages))
   103  	for _, m := range messages {
   104  		gotResponses = append(gotResponses, m.(*pb.Pong).Response)
   105  	}
   106  	if fmt.Sprint(gotResponses) != fmt.Sprint(wantResponses) {
   107  		t.Errorf("got responses %v, want %v", gotResponses, wantResponses)
   108  	}
   109  
   110  	if err := record.Err(); err != nil {
   111  		t.Fatal(err)
   112  	}
   113  }