handshake_test.go 20.9 KB
Newer Older
1 2 3
// Copyright 2020 The Swarm Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
4

5
package handshake_test
6 7 8

import (
	"bytes"
9
	"context"
10 11
	"errors"
	"fmt"
12 13
	"io/ioutil"
	"testing"
14

15
	"github.com/ethereum/go-ethereum/common"
16
	"github.com/ethersphere/bee/pkg/bzz"
17
	"github.com/ethersphere/bee/pkg/crypto"
18
	"github.com/ethersphere/bee/pkg/logging"
19
	"github.com/ethersphere/bee/pkg/p2p/libp2p/internal/handshake"
20
	"github.com/ethersphere/bee/pkg/p2p/libp2p/internal/handshake/mock"
21
	"github.com/ethersphere/bee/pkg/p2p/libp2p/internal/handshake/pb"
22
	"github.com/ethersphere/bee/pkg/p2p/protobuf"
23
	"github.com/ethersphere/bee/pkg/swarm"
24

25
	libp2ppeer "github.com/libp2p/go-libp2p-core/peer"
26
	ma "github.com/multiformats/go-multiaddr"
27 28 29
)

func TestHandshake(t *testing.T) {
30 31 32 33
	const (
		testWelcomeMessage = "HelloWorld"
	)

34
	logger := logging.New(ioutil.Discard, 0)
35
	networkID := uint64(3)
36

37
	node1ma, err := ma.NewMultiaddr("/ip4/127.0.0.1/tcp/1634/p2p/16Uiu2HAkx8ULY8cTXhdVAcMmLcH9AsTKz6uBQ7DPLKRjMLgBVYkA")
38 39 40
	if err != nil {
		t.Fatal(err)
	}
41
	node2ma, err := ma.NewMultiaddr("/ip4/127.0.0.1/tcp/1634/p2p/16Uiu2HAkx8ULY8cTXhdVAcMmLcH9AsTKz6uBQ7DPLKRjMLgBVYkS")
42 43 44
	if err != nil {
		t.Fatal(err)
	}
45 46 47 48 49 50 51 52
	node1maBinary, err := node1ma.MarshalBinary()
	if err != nil {
		t.Fatal(err)
	}
	node2maBinary, err := node2ma.MarshalBinary()
	if err != nil {
		t.Fatal(err)
	}
53
	node2AddrInfo, err := libp2ppeer.AddrInfoFromP2pAddr(node2ma)
54 55 56 57
	if err != nil {
		t.Fatal(err)
	}

58 59 60 61 62
	privateKey1, err := crypto.GenerateSecp256k1Key()
	if err != nil {
		t.Fatal(err)
	}
	privateKey2, err := crypto.GenerateSecp256k1Key()
63 64 65 66
	if err != nil {
		t.Fatal(err)
	}

67 68 69
	trxHash := common.HexToHash("0x1").Bytes()
	blockhash := common.HexToHash("0x2").Bytes()

70 71
	signer1 := crypto.NewDefaultSigner(privateKey1)
	signer2 := crypto.NewDefaultSigner(privateKey2)
72
	addr, err := crypto.NewOverlayAddress(privateKey1.PublicKey, networkID, blockhash)
73 74 75
	if err != nil {
		t.Fatal(err)
	}
76
	node1BzzAddress, err := bzz.NewAddress(signer1, node1ma, addr, networkID, trxHash)
77 78 79
	if err != nil {
		t.Fatal(err)
	}
80
	addr2, err := crypto.NewOverlayAddress(privateKey2.PublicKey, networkID, blockhash)
81 82 83
	if err != nil {
		t.Fatal(err)
	}
84
	node2BzzAddress, err := bzz.NewAddress(signer2, node2ma, addr2, networkID, trxHash)
85 86 87 88
	if err != nil {
		t.Fatal(err)
	}

89 90
	node1Info := handshake.Info{
		BzzAddress: node1BzzAddress,
91
		FullNode:   true,
92
	}
93 94
	node2Info := handshake.Info{
		BzzAddress: node2BzzAddress,
95
		FullNode:   true,
96
	}
97

98 99
	aaddresser := &AdvertisableAddresserMock{}

100 101 102
	senderMatcher := &MockSenderMatcher{v: true, blockHash: blockhash}

	handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, trxHash, testWelcomeMessage, logger)
103 104 105 106
	if err != nil {
		t.Fatal(err)
	}

107
	t.Run("Handshake - OK", func(t *testing.T) {
108 109
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
110 111
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)
112

Petar Radovic's avatar
Petar Radovic committed
113
		w, r := protobuf.NewWriterAndReader(stream2)
114
		if err := w.WriteMsg(&pb.SynAck{
115
			Syn: &pb.Syn{
116 117 118
				ObservedUnderlay: node1maBinary,
			},
			Ack: &pb.Ack{
119 120 121 122 123
				Address: &pb.BzzAddress{
					Underlay:  node2maBinary,
					Overlay:   node2BzzAddress.Overlay.Bytes(),
					Signature: node2BzzAddress.Signature,
				},
124
				NetworkID:      networkID,
125
				FullNode:       true,
126
				Transaction:    trxHash,
127
				WelcomeMessage: testWelcomeMessage,
Petar Radovic's avatar
Petar Radovic committed
128
			},
129 130 131 132
		}); err != nil {
			t.Fatal(err)
		}

133
		res, err := handshakeService.Handshake(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
134 135 136 137
		if err != nil {
			t.Fatal(err)
		}

138
		testInfo(t, *res, node2Info)
139 140 141

		var syn pb.Syn
		if err := r.ReadMsg(&syn); err != nil {
Petar Radovic's avatar
Petar Radovic committed
142 143
			t.Fatal(err)
		}
144 145 146 147 148 149 150 151 152 153 154 155 156 157

		if !bytes.Equal(syn.ObservedUnderlay, node2maBinary) {
			t.Fatal("bad syn")
		}

		var ack pb.Ack
		if err := r.ReadMsg(&ack); err != nil {
			t.Fatal(err)
		}

		if !bytes.Equal(ack.Address.Overlay, node1BzzAddress.Overlay.Bytes()) ||
			!bytes.Equal(ack.Address.Underlay, node1maBinary) ||
			!bytes.Equal(ack.Address.Signature, node1BzzAddress.Signature) ||
			ack.NetworkID != networkID ||
158
			ack.FullNode != true {
159 160
			t.Fatal("bad ack")
		}
161 162 163 164 165 166 167 168 169 170

		if ack.WelcomeMessage != testWelcomeMessage {
			t.Fatalf("Bad ack welcome message: want %s, got %s", testWelcomeMessage, ack.WelcomeMessage)
		}
	})

	t.Run("Handshake - welcome message too long", func(t *testing.T) {
		const LongMessage = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi consectetur urna ut lorem sollicitudin posuere. Donec sagittis laoreet sapien."

		expectedErr := handshake.ErrWelcomeMessageLength
171
		_, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, LongMessage, logger)
172 173 174
		if err == nil || err.Error() != expectedErr.Error() {
			t.Fatal("expected:", expectedErr, "got:", err)
		}
175
	})
176

177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199
	t.Run("Handshake - dynamic welcome message too long", func(t *testing.T) {
		const LongMessage = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi consectetur urna ut lorem sollicitudin posuere. Donec sagittis laoreet sapien."

		expectedErr := handshake.ErrWelcomeMessageLength
		err := handshakeService.SetWelcomeMessage(LongMessage)
		if err == nil || err.Error() != expectedErr.Error() {
			t.Fatal("expected:", expectedErr, "got:", err)
		}
	})

	t.Run("Handshake - set welcome message", func(t *testing.T) {
		const TestMessage = "Hi im the new test message"

		err := handshakeService.SetWelcomeMessage(TestMessage)
		if err != nil {
			t.Fatal("Got error:", err)
		}
		got := handshakeService.GetWelcomeMessage()
		if got != TestMessage {
			t.Fatal("expected:", TestMessage, ", got:", got)
		}
	})

200
	t.Run("Handshake - Syn write error", func(t *testing.T) {
201
		testErr := errors.New("test error")
202
		expectedErr := fmt.Errorf("write syn message: %w", testErr)
203
		stream := &mock.Stream{}
204
		stream.SetWriteErr(testErr, 0)
205
		res, err := handshakeService.Handshake(context.Background(), stream, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
206
		if err == nil || err.Error() != expectedErr.Error() {
207 208 209 210 211 212 213 214
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handshake returned non-nil res")
		}
	})

215
	t.Run("Handshake - Syn read error", func(t *testing.T) {
216
		testErr := errors.New("test error")
217
		expectedErr := fmt.Errorf("read synack message: %w", testErr)
218 219
		stream := mock.NewStream(nil, &bytes.Buffer{})
		stream.SetReadErr(testErr, 0)
220
		res, err := handshakeService.Handshake(context.Background(), stream, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
221
		if err == nil || err.Error() != expectedErr.Error() {
222 223 224 225 226 227 228
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handshake returned non-nil res")
		}
	})
Petar Radovic's avatar
Petar Radovic committed
229

230
	t.Run("Handshake - ack write error", func(t *testing.T) {
Petar Radovic's avatar
Petar Radovic committed
231
		testErr := errors.New("test error")
232
		expectedErr := fmt.Errorf("write ack message: %w", testErr)
Petar Radovic's avatar
Petar Radovic committed
233 234
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
235 236 237
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream1.SetWriteErr(testErr, 1)
		stream2 := mock.NewStream(&buffer2, &buffer1)
Petar Radovic's avatar
Petar Radovic committed
238

239
		w := protobuf.NewWriter(stream2)
240
		if err := w.WriteMsg(&pb.SynAck{
241
			Syn: &pb.Syn{
242 243 244
				ObservedUnderlay: node1maBinary,
			},
			Ack: &pb.Ack{
245 246 247 248 249
				Address: &pb.BzzAddress{
					Underlay:  node2maBinary,
					Overlay:   node2BzzAddress.Overlay.Bytes(),
					Signature: node2BzzAddress.Signature,
				},
250
				NetworkID: networkID,
251
				FullNode:  true,
Petar Radovic's avatar
Petar Radovic committed
252
			},
253 254
		},
		); err != nil {
Petar Radovic's avatar
Petar Radovic committed
255 256 257
			t.Fatal(err)
		}

258
		res, err := handshakeService.Handshake(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
Petar Radovic's avatar
Petar Radovic committed
259 260 261 262 263 264 265 266
		if err == nil || err.Error() != expectedErr.Error() {
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handshake returned non-nil res")
		}
	})
267

268
	t.Run("Handshake - networkID mismatch", func(t *testing.T) {
269 270 271 272 273 274 275 276
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		w := protobuf.NewWriter(stream2)
		if err := w.WriteMsg(&pb.SynAck{
			Syn: &pb.Syn{
277 278 279
				ObservedUnderlay: node1maBinary,
			},
			Ack: &pb.Ack{
280 281 282 283 284
				Address: &pb.BzzAddress{
					Underlay:  node2maBinary,
					Overlay:   node2BzzAddress.Overlay.Bytes(),
					Signature: node2BzzAddress.Signature,
				},
285
				NetworkID: 5,
286
				FullNode:  true,
287 288 289 290 291
			},
		}); err != nil {
			t.Fatal(err)
		}

292
		res, err := handshakeService.Handshake(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
293 294 295 296 297 298 299 300 301
		if res != nil {
			t.Fatal("res should be nil")
		}

		if err != handshake.ErrNetworkIDIncompatible {
			t.Fatalf("expected %s, got %s", handshake.ErrNetworkIDIncompatible, err)
		}
	})

302
	t.Run("Handshake - invalid ack", func(t *testing.T) {
303 304 305 306 307 308 309 310
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		w := protobuf.NewWriter(stream2)
		if err := w.WriteMsg(&pb.SynAck{
			Syn: &pb.Syn{
311
				ObservedUnderlay: node1maBinary,
312
			},
313
			Ack: &pb.Ack{
314 315 316 317 318
				Address: &pb.BzzAddress{
					Underlay:  node2maBinary,
					Overlay:   node2BzzAddress.Overlay.Bytes(),
					Signature: node1BzzAddress.Signature,
				},
319
				NetworkID: networkID,
320
				FullNode:  true,
321 322 323 324 325
			},
		}); err != nil {
			t.Fatal(err)
		}

326
		res, err := handshakeService.Handshake(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
327 328 329 330
		if res != nil {
			t.Fatal("res should be nil")
		}

331 332
		if err != handshake.ErrInvalidAck {
			t.Fatalf("expected %s, got %s", handshake.ErrInvalidAck, err)
333 334
		}
	})
335

336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359
	t.Run("Handshake - error advertisable address", func(t *testing.T) {
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		testError := errors.New("test error")
		aaddresser.err = testError
		defer func() {
			aaddresser.err = nil
		}()

		w, _ := protobuf.NewWriterAndReader(stream2)
		if err := w.WriteMsg(&pb.SynAck{
			Syn: &pb.Syn{
				ObservedUnderlay: node1maBinary,
			},
			Ack: &pb.Ack{
				Address: &pb.BzzAddress{
					Underlay:  node2maBinary,
					Overlay:   node2BzzAddress.Overlay.Bytes(),
					Signature: node2BzzAddress.Signature,
				},
				NetworkID: networkID,
360
				FullNode:  true,
361 362 363 364 365
			},
		}); err != nil {
			t.Fatal(err)
		}

366
		res, err := handshakeService.Handshake(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
367 368 369 370 371 372 373 374 375 376 377
		if err != testError {
			t.Fatalf("expected error %v got %v", testError, err)

		}

		if res != nil {
			t.Fatal("expected nil res")
		}

	})

378
	t.Run("Handle - OK", func(t *testing.T) {
379
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, trxHash, "", logger)
380 381
		if err != nil {
			t.Fatal(err)
382
		}
383 384
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
385 386
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)
387

388
		w := protobuf.NewWriter(stream2)
389
		if err := w.WriteMsg(&pb.Syn{
390
			ObservedUnderlay: node1maBinary,
391 392 393
		}); err != nil {
			t.Fatal(err)
		}
394

395
		if err := w.WriteMsg(&pb.Ack{
396 397 398 399 400
			Address: &pb.BzzAddress{
				Underlay:  node2maBinary,
				Overlay:   node2BzzAddress.Overlay.Bytes(),
				Signature: node2BzzAddress.Signature,
			},
401 402 403
			NetworkID:   networkID,
			Transaction: trxHash,
			FullNode:    true,
404
		}); err != nil {
Petar Radovic's avatar
Petar Radovic committed
405 406 407
			t.Fatal(err)
		}

408
		res, err := handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
409 410 411 412
		if err != nil {
			t.Fatal(err)
		}

413
		testInfo(t, *res, node2Info)
414 415

		_, r := protobuf.NewWriterAndReader(stream2)
416
		var got pb.SynAck
417 418 419 420
		if err := r.ReadMsg(&got); err != nil {
			t.Fatal(err)
		}

421 422 423 424
		if !bytes.Equal(got.Syn.ObservedUnderlay, node2maBinary) {
			t.Fatalf("got bad syn")
		}

425
		bzzAddress, err := bzz.ParseAddress(got.Ack.Address.Underlay, got.Ack.Address.Overlay, got.Ack.Address.Signature, got.Ack.Transaction, blockhash, got.Ack.NetworkID)
426 427 428 429
		if err != nil {
			t.Fatal(err)
		}

430
		testInfo(t, node1Info, handshake.Info{
431
			BzzAddress: bzzAddress,
432
			FullNode:   got.Ack.FullNode,
433
		})
434
	})
435

436
	t.Run("Handle - read error ", func(t *testing.T) {
437
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
438 439 440
		if err != nil {
			t.Fatal(err)
		}
441
		testErr := errors.New("test error")
442
		expectedErr := fmt.Errorf("read syn message: %w", testErr)
443
		stream := &mock.Stream{}
444
		stream.SetReadErr(testErr, 0)
445
		res, err := handshakeService.Handle(context.Background(), stream, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
446
		if err == nil || err.Error() != expectedErr.Error() {
447 448 449 450 451 452 453 454
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handle returned non-nil res")
		}
	})

455
	t.Run("Handle - write error ", func(t *testing.T) {
456
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
457 458 459
		if err != nil {
			t.Fatal(err)
		}
460
		testErr := errors.New("test error")
461
		expectedErr := fmt.Errorf("write synack message: %w", testErr)
462
		var buffer bytes.Buffer
463 464
		stream := mock.NewStream(&buffer, &buffer)
		stream.SetWriteErr(testErr, 1)
465
		w := protobuf.NewWriter(stream)
466
		if err := w.WriteMsg(&pb.Syn{
467
			ObservedUnderlay: node1maBinary,
468 469 470 471
		}); err != nil {
			t.Fatal(err)
		}

472
		res, err := handshakeService.Handle(context.Background(), stream, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
473
		if err == nil || err.Error() != expectedErr.Error() {
474 475 476 477 478 479 480
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handshake returned non-nil res")
		}
	})
Petar Radovic's avatar
Petar Radovic committed
481

482
	t.Run("Handle - ack read error ", func(t *testing.T) {
483
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
484 485
		if err != nil {
			t.Fatal(err)
Petar Radovic's avatar
Petar Radovic committed
486
		}
487 488
		testErr := errors.New("test error")
		expectedErr := fmt.Errorf("read ack message: %w", testErr)
Petar Radovic's avatar
Petar Radovic committed
489 490
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
491 492 493
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)
		stream1.SetReadErr(testErr, 1)
494
		w := protobuf.NewWriter(stream2)
495
		if err := w.WriteMsg(&pb.Syn{
496
			ObservedUnderlay: node1maBinary,
Petar Radovic's avatar
Petar Radovic committed
497 498 499 500
		}); err != nil {
			t.Fatal(err)
		}

501
		res, err := handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
Petar Radovic's avatar
Petar Radovic committed
502 503 504 505 506 507 508 509
		if err == nil || err.Error() != expectedErr.Error() {
			t.Fatal("expected:", expectedErr, "got:", err)
		}

		if res != nil {
			t.Fatal("handshake returned non-nil res")
		}
	})
510

511
	t.Run("Handle - networkID mismatch ", func(t *testing.T) {
512
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
513 514
		if err != nil {
			t.Fatal(err)
515 516 517 518 519 520
		}
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

521
		w := protobuf.NewWriter(stream2)
522
		if err := w.WriteMsg(&pb.Syn{
523 524 525 526 527 528
			ObservedUnderlay: node1maBinary,
		}); err != nil {
			t.Fatal(err)
		}

		if err := w.WriteMsg(&pb.Ack{
529 530 531 532 533
			Address: &pb.BzzAddress{
				Underlay:  node2maBinary,
				Overlay:   node2BzzAddress.Overlay.Bytes(),
				Signature: node2BzzAddress.Signature,
			},
534
			NetworkID: 5,
535
			FullNode:  true,
536 537 538 539
		}); err != nil {
			t.Fatal(err)
		}

540
		res, err := handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
541 542 543 544
		if res != nil {
			t.Fatal("res should be nil")
		}

545 546
		if err != handshake.ErrNetworkIDIncompatible {
			t.Fatalf("expected %s, got %s", handshake.ErrNetworkIDIncompatible, err)
547 548
		}
	})
549

550
	t.Run("Handle - duplicate handshake", func(t *testing.T) {
551
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, trxHash, "", logger)
552 553
		if err != nil {
			t.Fatal(err)
554 555 556 557 558 559
		}
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

560
		w := protobuf.NewWriter(stream2)
561
		if err := w.WriteMsg(&pb.Syn{
562
			ObservedUnderlay: node1maBinary,
563 564 565 566
		}); err != nil {
			t.Fatal(err)
		}

567
		if err := w.WriteMsg(&pb.Ack{
568 569 570 571 572
			Address: &pb.BzzAddress{
				Underlay:  node2maBinary,
				Overlay:   node2BzzAddress.Overlay.Bytes(),
				Signature: node2BzzAddress.Signature,
			},
573 574 575
			NetworkID:   networkID,
			Transaction: trxHash,
			FullNode:    true,
576
		}); err != nil {
577 578 579
			t.Fatal(err)
		}

580
		res, err := handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
581 582
		if err != nil {
			t.Fatal(err)
583 584
		}

585 586 587 588 589 590 591 592
		testInfo(t, *res, node2Info)

		_, r := protobuf.NewWriterAndReader(stream2)
		var got pb.SynAck
		if err := r.ReadMsg(&got); err != nil {
			t.Fatal(err)
		}

593 594 595
		if !bytes.Equal(got.Syn.ObservedUnderlay, node2maBinary) {
			t.Fatalf("got bad syn")
		}
596
		bzzAddress, err := bzz.ParseAddress(got.Ack.Address.Underlay, got.Ack.Address.Overlay, got.Ack.Address.Signature, got.Ack.Transaction, blockhash, got.Ack.NetworkID)
597 598 599 600
		if err != nil {
			t.Fatal(err)
		}

601
		testInfo(t, node1Info, handshake.Info{
602
			BzzAddress: bzzAddress,
603
			FullNode:   got.Ack.FullNode,
604 605
		})

606
		_, err = handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
607 608 609 610 611
		if err != handshake.ErrHandshakeDuplicate {
			t.Fatalf("expected %s, got %s", handshake.ErrHandshakeDuplicate, err)
		}
	})

612
	t.Run("Handle - invalid ack", func(t *testing.T) {
613
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
614 615 616 617 618 619 620 621 622 623
		if err != nil {
			t.Fatal(err)
		}
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		w := protobuf.NewWriter(stream2)
		if err := w.WriteMsg(&pb.Syn{
624
			ObservedUnderlay: node1maBinary,
625 626 627 628
		}); err != nil {
			t.Fatal(err)
		}

629
		if err := w.WriteMsg(&pb.Ack{
630 631 632 633 634
			Address: &pb.BzzAddress{
				Underlay:  node2maBinary,
				Overlay:   node2BzzAddress.Overlay.Bytes(),
				Signature: node1BzzAddress.Signature,
			},
635
			NetworkID: networkID,
636
			FullNode:  true,
637 638 639 640
		}); err != nil {
			t.Fatal(err)
		}

641
		_, err = handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
642
		if err != handshake.ErrInvalidAck {
643
			t.Fatalf("expected %s, got %v", handshake.ErrInvalidAck, err)
644 645
		}
	})
646

647
	t.Run("Handle - transaction is not on the blockchain", func(t *testing.T) {
648
		sbMock := &MockSenderMatcher{v: false, blockHash: blockhash}
649

650
		handshakeService, err := handshake.New(signer1, aaddresser, sbMock, node1Info.BzzAddress.Overlay, networkID, true, trxHash, "", logger)
651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671
		if err != nil {
			t.Fatal(err)
		}
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		w := protobuf.NewWriter(stream2)
		if err := w.WriteMsg(&pb.Syn{
			ObservedUnderlay: node1maBinary,
		}); err != nil {
			t.Fatal(err)
		}

		if err := w.WriteMsg(&pb.Ack{
			Address: &pb.BzzAddress{
				Underlay:  node2maBinary,
				Overlay:   node2BzzAddress.Overlay.Bytes(),
				Signature: node2BzzAddress.Signature,
			},
672 673 674
			NetworkID:   networkID,
			FullNode:    true,
			Transaction: trxHash,
675 676 677 678 679
		}); err != nil {
			t.Fatal(err)
		}

		_, err = handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
680 681
		if err == nil {
			t.Fatalf("expected error, got nil")
682 683 684
		}
	})

685
	t.Run("Handle - advertisable error", func(t *testing.T) {
686
		handshakeService, err := handshake.New(signer1, aaddresser, senderMatcher, node1Info.BzzAddress.Overlay, networkID, true, nil, "", logger)
687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707
		if err != nil {
			t.Fatal(err)
		}
		var buffer1 bytes.Buffer
		var buffer2 bytes.Buffer
		stream1 := mock.NewStream(&buffer1, &buffer2)
		stream2 := mock.NewStream(&buffer2, &buffer1)

		testError := errors.New("test error")
		aaddresser.err = testError
		defer func() {
			aaddresser.err = nil
		}()

		w := protobuf.NewWriter(stream2)
		if err := w.WriteMsg(&pb.Syn{
			ObservedUnderlay: node1maBinary,
		}); err != nil {
			t.Fatal(err)
		}

708
		res, err := handshakeService.Handle(context.Background(), stream1, node2AddrInfo.Addrs[0], node2AddrInfo.ID)
709 710 711 712 713 714 715 716
		if err != testError {
			t.Fatal("expected error")
		}

		if res != nil {
			t.Fatal("expected nil res")
		}
	})
717
}
718 719

// testInfo validates if two Info instances are equal.
720
func testInfo(t *testing.T, got, want handshake.Info) {
721
	t.Helper()
722
	if !got.BzzAddress.Equal(want.BzzAddress) || got.FullNode != want.FullNode {
723 724 725
		t.Fatalf("got info %+v, want %+v", got, want)
	}
}
726 727 728 729 730 731

type AdvertisableAddresserMock struct {
	advertisableAddress ma.Multiaddr
	err                 error
}

chuwt's avatar
chuwt committed
732
func (a *AdvertisableAddresserMock) Resolve(observedAddress ma.Multiaddr) (ma.Multiaddr, error) {
733 734 735 736 737 738 739 740
	if a.err != nil {
		return nil, a.err
	}

	if a.advertisableAddress != nil {
		return a.advertisableAddress, nil
	}

chuwt's avatar
chuwt committed
741
	return observedAddress, nil
742
}
743 744

type MockSenderMatcher struct {
745 746
	v         bool
	blockHash []byte
747 748
}

749 750 751 752 753 754 755
func (m MockSenderMatcher) Matches(context.Context, []byte, uint64, swarm.Address) ([]byte, error) {

	if m.v {
		return m.blockHash, nil
	}

	return nil, errors.New("")
756
}