github.com/koko1123/flow-go-1@v0.29.6/network/p2p/translator/unstaked_translator_test.go (about)

     1  package translator_test
     2  
     3  import (
     4  	"crypto/rand"
     5  	"math"
     6  	"testing"
     7  
     8  	"github.com/libp2p/go-libp2p/core/peer"
     9  	"github.com/stretchr/testify/require"
    10  
    11  	"github.com/koko1123/flow-go-1/network/p2p/translator"
    12  
    13  	"github.com/koko1123/flow-go-1/network/p2p/keyutils"
    14  	fcrypto "github.com/onflow/flow-go/crypto"
    15  )
    16  
    17  // For these test, refer to https://github.com/libp2p/specs/blob/master/peer-ids/peer-ids.md for libp2p
    18  // PeerID specifications and how they relate to keys.
    19  
    20  // This test shows we can't use ECDSA P-256 keys for libp2p and expect PeerID <=> PublicKey bijections
    21  func TestIDTranslationP256(t *testing.T) {
    22  	loops := 50
    23  	for i := 0; i < loops; i++ {
    24  		pID := createPeerIDFromAlgo(t, fcrypto.ECDSAP256)
    25  
    26  		// check that we can not extract the public key back
    27  		// This makes sense: the x509 serialization of ECDSA P-256 keys in uncompressed form is 64 + 2 bytes,
    28  		// and libp2p uses multihash.IDENTITY only on serializations of less than 42 bytes
    29  		_, err := pID.ExtractPublicKey()
    30  		require.NotNil(t, err)
    31  
    32  	}
    33  }
    34  
    35  // This test shows we can use ECDSA Secp256k1 keys for libp2p and expect PeerID <=> PublicKey bijections
    36  func TestIDTranslationSecp256k1(t *testing.T) {
    37  	loops := 50
    38  	for i := 0; i < loops; i++ {
    39  		pID := createPeerIDFromAlgo(t, fcrypto.ECDSASecp256k1)
    40  
    41  		// check that we can extract the public key back
    42  		// This makes sense: the compressed serialization of ECDSA Secp256k1 keys is 33 + 2 bytes,
    43  		// and libp2p uses multihash.IDENTITY on serializations of less than 42 bytes
    44  		_, err := pID.ExtractPublicKey()
    45  		require.NoError(t, err)
    46  
    47  	}
    48  }
    49  
    50  func TestUnstakedTranslationRoundTrip(t *testing.T) {
    51  	max_iterations := 50
    52  	unstakedTranslator := translator.NewPublicNetworkIDTranslator()
    53  
    54  	tested_vectors := 0
    55  
    56  	for ok := true; ok; ok = tested_vectors < max_iterations {
    57  		pID := createPeerIDFromAlgo(t, fcrypto.ECDSASecp256k1)
    58  
    59  		pk, err := pID.ExtractPublicKey()
    60  		require.NoError(t, err)
    61  
    62  		// for a secp256k1 key, this is just the compressed representation
    63  		pkBytes, err := pk.Raw()
    64  		require.NoError(t, err)
    65  
    66  		// key is positive, roundtrip should be possible
    67  		if pkBytes[0] == 0x02 {
    68  			tested_vectors++
    69  
    70  			flowID, err := unstakedTranslator.GetFlowID(pID)
    71  			require.NoError(t, err)
    72  			retrievedPeerID, err := unstakedTranslator.GetPeerID(flowID)
    73  			require.NoError(t, err)
    74  			require.Equal(t, pID, retrievedPeerID)
    75  		}
    76  
    77  	}
    78  }
    79  
    80  func createPeerIDFromAlgo(t *testing.T, sa fcrypto.SigningAlgorithm) peer.ID {
    81  	seed := createSeed(t)
    82  
    83  	// this matches GenerateNetworkingKeys, and is intended to validate the choices in cmd/bootstrap
    84  	key, err := fcrypto.GeneratePrivateKey(sa, seed)
    85  	require.NoError(t, err)
    86  
    87  	// get the public key
    88  	pubKey := key.PublicKey()
    89  
    90  	// extract the corresponding libp2p public Key
    91  	libp2pPubKey, err := keyutils.LibP2PPublicKeyFromFlow(pubKey)
    92  	require.NoError(t, err)
    93  
    94  	// obtain the PeerID based on libp2p's own rules
    95  	pID, err := peer.IDFromPublicKey(libp2pPubKey)
    96  	require.NoError(t, err)
    97  
    98  	return pID
    99  }
   100  
   101  func createSeed(t *testing.T) []byte {
   102  	seedLen := int(math.Max(fcrypto.KeyGenSeedMinLenECDSAP256, fcrypto.KeyGenSeedMinLenECDSASecp256k1))
   103  	seed := make([]byte, seedLen)
   104  	n, err := rand.Read(seed)
   105  	require.NoError(t, err)
   106  	require.Equal(t, n, seedLen)
   107  	return seed
   108  }