Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ChainWriter unit tests #948

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .mockery.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ packages:
config:
filename: simple_keystore.go
case: underscore
TxManager:
github.com/smartcontractkit/chainlink-solana/pkg/solana/logpoller:
interfaces:
RPCClient:
7 changes: 6 additions & 1 deletion contracts/artifacts/localnet/write_test-keypair.json
Original file line number Diff line number Diff line change
@@ -1 +1,6 @@
[26,39,164,161,246,97,149,0,58,187,146,162,53,35,107,2,117,242,83,171,48,7,63,240,69,221,239,45,97,55,112,106,192,228,214,205,123,71,58,23,62,229,166,213,149,122,96,145,35,150,16,156,247,199,242,108,173,80,62,231,39,196,27,192]
[
26, 39, 164, 161, 246, 97, 149, 0, 58, 187, 146, 162, 53, 35, 107, 2, 117,
242, 83, 171, 48, 7, 63, 240, 69, 221, 239, 45, 97, 55, 112, 106, 192, 228,
214, 205, 123, 71, 58, 23, 62, 229, 166, 213, 149, 122, 96, 145, 35, 150, 16,
156, 247, 199, 242, 108, 173, 80, 62, 231, 39, 196, 27, 192
]
3 changes: 1 addition & 2 deletions contracts/programs/write_test/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,9 @@ pub mod write_test {
data.administrator = ctx.accounts.admin.key();
data.pending_administrator = Pubkey::default();
data.lookup_table = lookup_table;

Ok(())
}

}

#[derive(Accounts)]
Expand Down
1 change: 0 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ require (
github.com/smartcontractkit/chainlink-common v0.3.1-0.20241112140826-0e2daed34ef6
github.com/smartcontractkit/libocr v0.0.0-20241007185508-adbe57025f12
github.com/stretchr/testify v1.9.0
github.com/test-go/testify v1.1.4
go.uber.org/zap v1.27.0
golang.org/x/exp v0.0.0-20240909161429-701f63a606c0
golang.org/x/sync v0.8.0
Expand Down
11 changes: 6 additions & 5 deletions pkg/solana/chain.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import (
"github.com/smartcontractkit/chainlink-solana/pkg/solana/internal"
"github.com/smartcontractkit/chainlink-solana/pkg/solana/monitor"
"github.com/smartcontractkit/chainlink-solana/pkg/solana/txm"
txmutils "github.com/smartcontractkit/chainlink-solana/pkg/solana/txm/utils"
)

type Chain interface {
Expand Down Expand Up @@ -572,12 +573,12 @@ func (c *chain) sendTx(ctx context.Context, from, to string, amount *big.Int, ba

chainTxm := c.TxManager()
err = chainTxm.Enqueue(ctx, "", tx, nil,
txm.SetComputeUnitLimit(500), // reduce from default 200K limit - should only take 450 compute units
txmutils.SetComputeUnitLimit(500), // reduce from default 200K limit - should only take 450 compute units
// no fee bumping and no additional fee - makes validating balance accurate
txm.SetComputeUnitPriceMax(0),
txm.SetComputeUnitPriceMin(0),
txm.SetBaseComputeUnitPrice(0),
txm.SetFeeBumpPeriod(0),
txmutils.SetComputeUnitPriceMax(0),
txmutils.SetComputeUnitPriceMin(0),
txmutils.SetBaseComputeUnitPrice(0),
txmutils.SetFeeBumpPeriod(0),
)
if err != nil {
return fmt.Errorf("transaction failed: %w", err)
Expand Down
6 changes: 3 additions & 3 deletions pkg/solana/chainwriter/ccip_example_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ func TestConfig() {
// 3. Lookup Table content - Get all the accounts from a lookup table
// 4. PDA Account Lookup - Based on another account and a seed/s
// Nested PDA Account with seeds from:
// -> input paramters
// -> input parameters
// -> constant
// PDALookups can resolve to multiple addresses if:
// A) The PublicKey lookup resolves to multiple addresses (i.e. multiple token addresses)
Expand All @@ -102,8 +102,8 @@ func TestConfig() {
},
// Lookup Table content - Get the accounts from the derived lookup table above
AccountsFromLookupTable{
LookupTablesName: "RegistryTokenState",
IncludeIndexes: []int{}, // If left empty, all addresses will be included. Otherwise, only the specified indexes will be included.
LookupTableName: "RegistryTokenState",
IncludeIndexes: []int{}, // If left empty, all addresses will be included. Otherwise, only the specified indexes will be included.
},
// Account Lookup - Based on data from input parameters
// In this case, the user wants to add the destination token addresses to the transaction.
Expand Down
52 changes: 26 additions & 26 deletions pkg/solana/chainwriter/chain_writer.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,12 +21,13 @@ import (

type SolanaChainWriterService struct {
reader client.Reader
txm txm.Txm
txm txm.TxManager
ge fees.Estimator
config ChainWriterConfig
codecs map[string]types.Codec
}

//nolint // ignoring naming suggestion
type ChainWriterConfig struct {
Programs map[string]ProgramConfig
}
Expand All @@ -46,7 +47,7 @@ type MethodConfig struct {
DebugIDLocation string
}

func NewSolanaChainWriterService(reader client.Reader, txm txm.Txm, ge fees.Estimator, config ChainWriterConfig) (*SolanaChainWriterService, error) {
func NewSolanaChainWriterService(reader client.Reader, txm txm.TxManager, ge fees.Estimator, config ChainWriterConfig) (*SolanaChainWriterService, error) {
codecs, err := parseIDLCodecs(config)
if err != nil {
return nil, fmt.Errorf("failed to parse IDL codecs: %w", err)
Expand All @@ -68,7 +69,7 @@ func parseIDLCodecs(config ChainWriterConfig) (map[string]types.Codec, error) {
if err := json.Unmarshal([]byte(programConfig.IDL), &idl); err != nil {
return nil, fmt.Errorf("failed to unmarshal IDL: %w", err)
}
idlCodec, err := codec.NewIDLAccountCodec(idl, binary.LittleEndian())
idlCodec, err := codec.NewIDLInstructionsCodec(idl, binary.LittleEndian())
if err != nil {
return nil, fmt.Errorf("failed to create codec from IDL: %w", err)
}
Expand All @@ -79,7 +80,7 @@ func parseIDLCodecs(config ChainWriterConfig) (map[string]types.Codec, error) {
return nil, fmt.Errorf("failed to create input modifications: %w", err)
}
// add mods to codec
idlCodec, err = codec.NewNamedModifierCodec(idlCodec, WrapItemType(program, method, true), modConfig)
idlCodec, err = codec.NewNamedModifierCodec(idlCodec, method, modConfig)
if err != nil {
return nil, fmt.Errorf("failed to create named codec: %w", err)
}
Expand All @@ -90,14 +91,6 @@ func parseIDLCodecs(config ChainWriterConfig) (map[string]types.Codec, error) {
return codecs, nil
}

func WrapItemType(programName, itemType string, isParams bool) string {
if isParams {
return fmt.Sprintf("params.%s.%s", programName, itemType)
}

return fmt.Sprintf("return.%s.%s", programName, itemType)
}

/*
GetAddresses resolves account addresses from various `Lookup` configurations to build the required `solana.AccountMeta` list
for Solana transactions. It handles constant addresses, dynamic lookups, program-derived addresses (PDAs), and lookup tables.
Expand Down Expand Up @@ -161,7 +154,7 @@ func (s *SolanaChainWriterService) FilterLookupTableAddresses(
for innerIdentifier, metas := range innerMap {
tableKey, err := solana.PublicKeyFromBase58(innerIdentifier)
if err != nil {
fmt.Errorf("error parsing lookup table key: %w", err)
continue
}

// Collect public keys that are actually used
Expand Down Expand Up @@ -198,18 +191,31 @@ func (s *SolanaChainWriterService) FilterLookupTableAddresses(
}

func (s *SolanaChainWriterService) SubmitTransaction(ctx context.Context, contractName, method string, args any, transactionID string, toAddress string, meta *types.TxMeta, value *big.Int) error {
programConfig := s.config.Programs[contractName]
methodConfig := programConfig.Methods[method]
programConfig, exists := s.config.Programs[contractName]
if !exists {
return fmt.Errorf("failed to find program config for contract name: %s", contractName)
}
methodConfig, exists := programConfig.Methods[method]
if !exists {
return fmt.Errorf("failed to find method config for method: %s", method)
}

// Configure debug ID
debugID := ""
if methodConfig.DebugIDLocation != "" {
debugID, err := GetDebugIDAtLocation(args, methodConfig.DebugIDLocation)
var err error
debugID, err = GetDebugIDAtLocation(args, methodConfig.DebugIDLocation)
if err != nil {
return errorWithDebugID(fmt.Errorf("error getting debug ID from input args: %w", err), debugID)
}
}

codec := s.codecs[contractName]
encodedPayload, err := codec.Encode(ctx, args, method)
if err != nil {
return errorWithDebugID(fmt.Errorf("error encoding transaction payload: %w", err), debugID)
}

// Fetch derived and static table maps
derivedTableMap, staticTableMap, err := s.ResolveLookupTables(ctx, args, methodConfig.LookupTables)
if err != nil {
Expand All @@ -232,7 +238,7 @@ func (s *SolanaChainWriterService) SubmitTransaction(ctx context.Context, contra
}

// Prepare transaction
programId, err := solana.PublicKeyFromBase58(contractName)
programID, err := solana.PublicKeyFromBase58(contractName)
if err != nil {
return errorWithDebugID(fmt.Errorf("error parsing program ID: %w", err), debugID)
}
Expand All @@ -242,15 +248,9 @@ func (s *SolanaChainWriterService) SubmitTransaction(ctx context.Context, contra
return errorWithDebugID(fmt.Errorf("error parsing fee payer address: %w", err), debugID)
}

codec := s.codecs[contractName]
encodedPayload, err := codec.Encode(ctx, args, WrapItemType(contractName, method, true))
if err != nil {
return errorWithDebugID(fmt.Errorf("error encoding transaction payload: %w", err), debugID)
}

tx, err := solana.NewTransaction(
[]solana.Instruction{
solana.NewInstruction(programId, accounts, encodedPayload),
solana.NewInstruction(programID, accounts, encodedPayload),
},
blockhash.Value.Blockhash,
solana.TransactionPayer(feePayer),
Expand All @@ -275,7 +275,7 @@ var (

// GetTransactionStatus returns the current status of a transaction in the underlying chain's TXM.
func (s *SolanaChainWriterService) GetTransactionStatus(ctx context.Context, transactionID string) (types.TransactionStatus, error) {
return types.Unknown, nil
return s.txm.GetTransactionStatus(ctx, transactionID)
}

// GetFeeComponents retrieves the associated gas costs for executing a transaction.
Expand All @@ -286,7 +286,7 @@ func (s *SolanaChainWriterService) GetFeeComponents(ctx context.Context) (*types

fee := s.ge.BaseComputeUnitPrice()
return &types.ChainFeeComponents{
ExecutionFee: big.NewInt(int64(fee)),
ExecutionFee: new(big.Int).SetUint64(fee),
DataAvailabilityFee: nil,
}, nil
}
Expand Down
Loading
Loading