github.com/MetalBlockchain/metalgo@v1.11.9/tests/e2e/p/permissionless_subnets.go (about)

     1  // Copyright (C) 2019-2024, Ava Labs, Inc. All rights reserved.
     2  // See the file LICENSE for licensing terms.
     3  
     4  package p
     5  
     6  import (
     7  	"fmt"
     8  	"time"
     9  
    10  	"github.com/stretchr/testify/require"
    11  
    12  	"github.com/MetalBlockchain/metalgo/ids"
    13  	"github.com/MetalBlockchain/metalgo/tests/fixture/e2e"
    14  	"github.com/MetalBlockchain/metalgo/utils/constants"
    15  	"github.com/MetalBlockchain/metalgo/utils/units"
    16  	"github.com/MetalBlockchain/metalgo/vms/components/avax"
    17  	"github.com/MetalBlockchain/metalgo/vms/components/verify"
    18  	"github.com/MetalBlockchain/metalgo/vms/platformvm"
    19  	"github.com/MetalBlockchain/metalgo/vms/platformvm/reward"
    20  	"github.com/MetalBlockchain/metalgo/vms/platformvm/signer"
    21  	"github.com/MetalBlockchain/metalgo/vms/platformvm/txs"
    22  	"github.com/MetalBlockchain/metalgo/vms/secp256k1fx"
    23  
    24  	ginkgo "github.com/onsi/ginkgo/v2"
    25  )
    26  
    27  var _ = e2e.DescribePChain("[Permissionless Subnets]", func() {
    28  	require := require.New(ginkgo.GinkgoT())
    29  
    30  	ginkgo.It("subnets operations",
    31  		func() {
    32  			nodeURI := e2e.Env.GetRandomNodeURI()
    33  
    34  			keychain := e2e.Env.NewKeychain(1)
    35  			baseWallet := e2e.NewWallet(keychain, nodeURI)
    36  
    37  			pWallet := baseWallet.P()
    38  			xWallet := baseWallet.X()
    39  			xBuilder := xWallet.Builder()
    40  			xContext := xBuilder.Context()
    41  			xChainID := xContext.BlockchainID
    42  
    43  			var validatorID ids.NodeID
    44  			ginkgo.By("retrieving the node ID of a primary network validator", func() {
    45  				pChainClient := platformvm.NewClient(nodeURI.URI)
    46  				validatorIDs, err := pChainClient.SampleValidators(e2e.DefaultContext(), constants.PrimaryNetworkID, 1)
    47  				require.NoError(err)
    48  				validatorID = validatorIDs[0]
    49  			})
    50  
    51  			owner := &secp256k1fx.OutputOwners{
    52  				Threshold: 1,
    53  				Addrs: []ids.ShortID{
    54  					keychain.Keys[0].Address(),
    55  				},
    56  			}
    57  
    58  			var subnetID ids.ID
    59  			ginkgo.By("create a permissioned subnet", func() {
    60  				subnetTx, err := pWallet.IssueCreateSubnetTx(
    61  					owner,
    62  					e2e.WithDefaultContext(),
    63  				)
    64  
    65  				subnetID = subnetTx.ID()
    66  				require.NoError(err)
    67  				require.NotEqual(subnetID, constants.PrimaryNetworkID)
    68  			})
    69  
    70  			var subnetAssetID ids.ID
    71  			ginkgo.By("create a custom asset for the permissionless subnet", func() {
    72  				subnetAssetTx, err := xWallet.IssueCreateAssetTx(
    73  					"RnM",
    74  					"RNM",
    75  					9,
    76  					map[uint32][]verify.State{
    77  						0: {
    78  							&secp256k1fx.TransferOutput{
    79  								Amt:          100 * units.MegaAvax,
    80  								OutputOwners: *owner,
    81  							},
    82  						},
    83  					},
    84  					e2e.WithDefaultContext(),
    85  				)
    86  				require.NoError(err)
    87  				subnetAssetID = subnetAssetTx.ID()
    88  			})
    89  
    90  			ginkgo.By(fmt.Sprintf("Send 100 MegaAvax of asset %s to the P-chain", subnetAssetID), func() {
    91  				_, err := xWallet.IssueExportTx(
    92  					constants.PlatformChainID,
    93  					[]*avax.TransferableOutput{
    94  						{
    95  							Asset: avax.Asset{
    96  								ID: subnetAssetID,
    97  							},
    98  							Out: &secp256k1fx.TransferOutput{
    99  								Amt:          100 * units.MegaAvax,
   100  								OutputOwners: *owner,
   101  							},
   102  						},
   103  					},
   104  					e2e.WithDefaultContext(),
   105  				)
   106  				require.NoError(err)
   107  			})
   108  
   109  			ginkgo.By(fmt.Sprintf("Import the 100 MegaAvax of asset %s from the X-chain into the P-chain", subnetAssetID), func() {
   110  				_, err := pWallet.IssueImportTx(
   111  					xChainID,
   112  					owner,
   113  					e2e.WithDefaultContext(),
   114  				)
   115  				require.NoError(err)
   116  			})
   117  
   118  			ginkgo.By("make subnet permissionless", func() {
   119  				_, err := pWallet.IssueTransformSubnetTx(
   120  					subnetID,
   121  					subnetAssetID,
   122  					50*units.MegaAvax,
   123  					100*units.MegaAvax,
   124  					reward.PercentDenominator,
   125  					reward.PercentDenominator,
   126  					1,
   127  					100*units.MegaAvax,
   128  					time.Second,
   129  					365*24*time.Hour,
   130  					0,
   131  					1,
   132  					5,
   133  					.80*reward.PercentDenominator,
   134  					e2e.WithDefaultContext(),
   135  				)
   136  				require.NoError(err)
   137  			})
   138  
   139  			endTime := time.Now().Add(time.Minute)
   140  			ginkgo.By("add permissionless validator", func() {
   141  				_, err := pWallet.IssueAddPermissionlessValidatorTx(
   142  					&txs.SubnetValidator{
   143  						Validator: txs.Validator{
   144  							NodeID: validatorID,
   145  							End:    uint64(endTime.Unix()),
   146  							Wght:   25 * units.MegaAvax,
   147  						},
   148  						Subnet: subnetID,
   149  					},
   150  					&signer.Empty{},
   151  					subnetAssetID,
   152  					&secp256k1fx.OutputOwners{},
   153  					&secp256k1fx.OutputOwners{},
   154  					reward.PercentDenominator,
   155  					e2e.WithDefaultContext(),
   156  				)
   157  				require.NoError(err)
   158  			})
   159  
   160  			ginkgo.By("add permissionless delegator", func() {
   161  				_, err := pWallet.IssueAddPermissionlessDelegatorTx(
   162  					&txs.SubnetValidator{
   163  						Validator: txs.Validator{
   164  							NodeID: validatorID,
   165  							End:    uint64(endTime.Unix()),
   166  							Wght:   25 * units.MegaAvax,
   167  						},
   168  						Subnet: subnetID,
   169  					},
   170  					subnetAssetID,
   171  					&secp256k1fx.OutputOwners{},
   172  					e2e.WithDefaultContext(),
   173  				)
   174  				require.NoError(err)
   175  			})
   176  		})
   177  })