github.com/klaytn/klaytn@v1.12.1/networks/p2p/discover/discover_api_test.go (about)

     1  // Copyright 2019 The klaytn Authors
     2  // This file is part of the klaytn library.
     3  //
     4  // The klaytn library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The klaytn library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the klaytn library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package discover
    18  
    19  import (
    20  	"testing"
    21  
    22  	"github.com/klaytn/klaytn/common"
    23  	"github.com/klaytn/klaytn/log"
    24  )
    25  
    26  var rawUrls = []string{
    27  	"kni://a3fd567e0e1bb9f7d7a20385b797563883ebb9d45ff6f05a588b56256f46bd649b7ecc8e3e17cc50df4599c1809463e66ad964f7a3fb6cf4c768c25d647f2c02@0.0.0.1:3000",
    28  	"kni://bf0d5b99945d5b94bc8430af9ec8019dd3535be586809d04422aa1bacf16b9161cc868c63d11423e30525d8ea41407c28854b1e12058297f8e0ef3c357c8d6c0@0.0.0.2:4000?discport=0",
    29  	"kni://418211f65eb3c14ddab49f690ed291f7681bff08742889a518ca58d2176b4afaa8fdaff1cd45957d7a7c14965d1ffd811bd677e70dc2e309cf8baacf73eb2bdc@0.0.0.3:5000?discport=32323",
    30  	"kni://7ea7fae31c0d1a0a3208607f948b7b8d2eb5c410fb07d27bbcad8359fef1e78ec10e3f9132feaa69b0438ac70d5a3a13af041e47089bc43d90f68ba5fc72a23c@0.0.0.4:6000",
    31  	"kni://e92f2fcd87ad42b9f6e55aebc2e35c73e5443fc3128a82dc11cc84acf445a14beee202140c5004d73c981d8bf423cb05714e9f7b1cabfd2720e34ed22e819dc3@0.0.0.5:7000",
    32  	"kni://01a63da798a08b6322ae59d398628addebd87eb582a801976d7d1b2a1143574a15adc4a8ae08d1286e8cb36ef6d904e25ae932d3cb4e695944b48afb58981550@0.0.0.6:8000?discport=0",
    33  }
    34  
    35  type mockDiscoveryStorage struct {
    36  	data []*Node
    37  }
    38  
    39  func (mds *mockDiscoveryStorage) name() string                        { return "mockDiscoveryStorage" }
    40  func (mds *mockDiscoveryStorage) setTable(t *Table)                   {}
    41  func (mds *mockDiscoveryStorage) setTargetNodeType(tType NodeType)    {}
    42  func (mds *mockDiscoveryStorage) init()                               {}
    43  func (mds *mockDiscoveryStorage) add(n *Node)                         { mds.data = append(mds.data, n) }
    44  func (mds *mockDiscoveryStorage) delete(n *Node)                      { mds.data = deleteNode(mds.data, n) }
    45  func (mds *mockDiscoveryStorage) len() (n int)                        { return 0 }
    46  func (mds *mockDiscoveryStorage) nodeAll() []*Node                    { return mds.data }
    47  func (mds *mockDiscoveryStorage) readRandomNodes(buf []*Node) (n int) { return 0 }
    48  func (mds *mockDiscoveryStorage) closest(target common.Hash, nresults int) *nodesByDistance {
    49  	return nil
    50  }
    51  func (mds *mockDiscoveryStorage) stuff(nodes []*Node) {}
    52  func (mds *mockDiscoveryStorage) copyBondedNodes()    {}
    53  func (mds *mockDiscoveryStorage) lookup(targetID NodeID, refreshIfEmpty bool, targetType NodeType) []*Node {
    54  	return nil
    55  }
    56  func (mds *mockDiscoveryStorage) getNodes(max int) []*Node { return nil }
    57  func (mds *mockDiscoveryStorage) doRevalidate()            {}
    58  func (mds *mockDiscoveryStorage) doRefresh()               {}
    59  
    60  func (mds *mockDiscoveryStorage) isAuthorized(id NodeID) bool    { return true }
    61  func (mds *mockDiscoveryStorage) getBucketEntries() []*Node      { return mds.data }
    62  func (mds *mockDiscoveryStorage) getAuthorizedNodes() []*Node    { return nil }
    63  func (mds *mockDiscoveryStorage) putAuthorizedNode(node *Node)   {}
    64  func (mds *mockDiscoveryStorage) deleteAuthorizedNode(id NodeID) {}
    65  
    66  func createTestData() *mockDiscoveryStorage {
    67  	var d []*Node
    68  	for _, url := range rawUrls {
    69  		node, _ := ParseNode(url)
    70  		d = append(d, node)
    71  	}
    72  	mds := &mockDiscoveryStorage{
    73  		data: d,
    74  	}
    75  	return mds
    76  }
    77  
    78  func createTestTable() (*Table, error) {
    79  	id := MustHexID("904afadc3587310adad21971c28a9213d03b04c4bd5ec73f7609861eb57b60b26809a52e72cbc6af9dfdd780a6d6629898ef197149f840e03f237660bc0dbb48")
    80  	tmpDB, _ := newNodeDB("", Version, id)
    81  	tab := &Table{
    82  		db:          tmpDB,
    83  		storages:    make(map[NodeType]discoverStorage),
    84  		localLogger: log.NewModuleLogger(log.NetworksP2PDiscover).NewWith("Discover", "Test"),
    85  	}
    86  	storage := createTestData()
    87  	tab.addStorage(NodeTypeUnknown, storage)
    88  	for _, node := range storage.data {
    89  		err := tab.db.updateNode(node)
    90  		if err != nil {
    91  			return nil, err
    92  		}
    93  	}
    94  	return tab, nil
    95  }
    96  
    97  func TestTable_CreateUpdateNodeOnDB(t *testing.T) {
    98  	tab, _ := createTestTable()
    99  	n, _ := ParseNode("kni://31a03810a315b200053ea5905d4e0a32a50eafcf2613e90e17ee877652dbb2aba1c725016ebe44d48529c8755203046a927fb01b97d758c009d248c4d7dfdd8c@0.0.0.0:32323?discport=0")
   100  	err := tab.CreateUpdateNodeOnDB(n)
   101  	if err != nil {
   102  		t.Error("CreateUpdateNodeOnDB is failed", "err", err)
   103  	}
   104  	id, _ := HexID("31a03810a315b200053ea5905d4e0a32a50eafcf2613e90e17ee877652dbb2aba1c725016ebe44d48529c8755203046a927fb01b97d758c009d248c4d7dfdd8c")
   105  	n2 := tab.db.node(id)
   106  	if !n.CompareNode(n2) {
   107  		t.Error("nodes are different", "inserted:", n, "retrieved", n2)
   108  	}
   109  }
   110  
   111  func TestTable_CreateUpdateNodeOnTable(t *testing.T) {
   112  	tab, _ := createTestTable()
   113  	n, _ := ParseNode("kni://31a03810a315b200053ea5905d4e0a32a50eafcf2613e90e17ee877652dbb2aba1c725016ebe44d48529c8755203046a927fb01b97d758c009d248c4d7dfdd8c@0.0.0.0:32323?discport=0")
   114  	err := tab.CreateUpdateNodeOnTable(n)
   115  	if err != nil {
   116  		t.Error("CreateUpdateNodeOnTable is failed", "err", err)
   117  	}
   118  	entries := tab.GetBucketEntries()
   119  	replacements := tab.GetReplacements()
   120  	if !isIn(n, append(entries, replacements...)) {
   121  		t.Errorf("the node does not exist. nodeid: %v", n.ID)
   122  	}
   123  }
   124  
   125  func TestTable_GetNodeFromDB(t *testing.T) {
   126  	tab, _ := createTestTable()
   127  	id0 := MustHexID("a3fd567e0e1bb9f7d7a20385b797563883ebb9d45ff6f05a588b56256f46bd649b7ecc8e3e17cc50df4599c1809463e66ad964f7a3fb6cf4c768c25d647f2c02")
   128  	id1 := MustHexID("bf0d5b99945d5b94bc8430af9ec8019dd3535be586809d04422aa1bacf16b9161cc868c63d11423e30525d8ea41407c28854b1e12058297f8e0ef3c357c8d6c0")
   129  	id2 := MustHexID("418211f65eb3c14ddab49f690ed291f7681bff08742889a518ca58d2176b4afaa8fdaff1cd45957d7a7c14965d1ffd811bd677e70dc2e309cf8baacf73eb2bdc")
   130  	id3 := MustHexID("7ea7fae31c0d1a0a3208607f948b7b8d2eb5c410fb07d27bbcad8359fef1e78ec10e3f9132feaa69b0438ac70d5a3a13af041e47089bc43d90f68ba5fc72a23c")
   131  	id4 := MustHexID("e92f2fcd87ad42b9f6e55aebc2e35c73e5443fc3128a82dc11cc84acf445a14beee202140c5004d73c981d8bf423cb05714e9f7b1cabfd2720e34ed22e819dc3")
   132  	id5 := MustHexID("01a63da798a08b6322ae59d398628addebd87eb582a801976d7d1b2a1143574a15adc4a8ae08d1286e8cb36ef6d904e25ae932d3cb4e695944b48afb58981550")
   133  	ids := []NodeID{id0, id1, id2, id3, id4, id5}
   134  	for idx, id := range ids {
   135  		node1, err := tab.GetNodeFromDB(id)
   136  		if err != nil {
   137  			t.Error("get node is failed.", "err:", err)
   138  		}
   139  		node2, _ := ParseNode(rawUrls[idx])
   140  		if !node1.CompareNode(node2) {
   141  			t.Error("node1 is different from node2.", "node1:", node1, "node2:", node2)
   142  		}
   143  	}
   144  }
   145  
   146  func TestTable_GetBucketEntries(t *testing.T) {
   147  	tab, _ := createTestTable()
   148  	entries := tab.GetBucketEntries()
   149  	if storage, ok := tab.storages[NodeTypeUnknown].(*mockDiscoveryStorage); ok {
   150  		if len(storage.data) != len(entries) {
   151  			t.Error("the length of actual data is different from the result of GetBucketEntries")
   152  		}
   153  		for _, node := range storage.data {
   154  			existed := false
   155  			for _, node2 := range entries {
   156  				if node.CompareNode(node2) {
   157  					existed = true
   158  					break
   159  				}
   160  			}
   161  			if !existed {
   162  				t.Error("node does not existed", "nodeid", node.ID)
   163  			}
   164  		}
   165  		for _, node := range storage.data {
   166  			faultyNode, _ := ParseNode("kni://71cd148865fd6dd9658a233aef8e7d844d279f4d04c9783c91d63c664109709609900ee3bc6e6b8ca7f4bff555be5331c10801e1e6e6713ebfd339674ccc377b@0.0.0.0:32323?discport=0")
   167  			if node.CompareNode(faultyNode) {
   168  				t.Error("the node existed although it is not updated", "nodeid", faultyNode.ID)
   169  			}
   170  		}
   171  	}
   172  }
   173  
   174  func TestTable_DeleteNodeFromDB(t *testing.T) {
   175  	testData1 := MustParseNode(rawUrls[0])
   176  	testData2 := MustParseNode(rawUrls[1])
   177  	tab, _ := createTestTable()
   178  	if n := tab.db.node(testData1.ID); n == nil {
   179  		t.Error("node does not exist", "nodeid", testData1.ID)
   180  	}
   181  	if n := tab.db.node(testData2.ID); n == nil {
   182  		t.Error("node does not exist", "nodeid", testData2.ID)
   183  	}
   184  	err := tab.DeleteNodeFromDB(testData1)
   185  	if err != nil {
   186  		t.Error("delete node from table is failed", "err", err)
   187  	}
   188  	err = tab.DeleteNodeFromDB(testData2)
   189  	if err != nil {
   190  		t.Error("delete node from table is failed", "err", err)
   191  	}
   192  	if n := tab.db.node(testData1.ID); n != nil {
   193  		t.Error("node is not removed", "nodeid", n.ID)
   194  	}
   195  	if n := tab.db.node(testData2.ID); n != nil {
   196  		t.Error("node is not removed", "nodeid", n.ID)
   197  	}
   198  }
   199  
   200  func TestTable_DeleteNodeFromTable(t *testing.T) {
   201  	tab, _ := createTestTable()
   202  	storage, _ := tab.storages[NodeTypeUnknown].(*mockDiscoveryStorage)
   203  	node0 := storage.data[0]
   204  	node1 := storage.data[1]
   205  	err := tab.DeleteNodeFromTable(node0)
   206  	if err != nil {
   207  		t.Error("delete node from table is failed", "err", err)
   208  	}
   209  	err = tab.DeleteNodeFromTable(node1)
   210  	if err != nil {
   211  		t.Error("delete node from table is failed", "err", err)
   212  	}
   213  	if isIn(node0, storage.data) {
   214  		t.Error("the node is not removed", "nodeid", node0.ID)
   215  	}
   216  	if isIn(node1, storage.data) {
   217  		t.Error("the node is not removed", "nodeid", node1.ID)
   218  	}
   219  }