通過テストによるイーサリアムデータ抽出の整合性の保証

王林
リリース: 2024-07-18 07:48:19
オリジナル
475 人が閲覧しました

Asserting Integrity in Ethereum Data Extraction with Go through tests

はじめに

このチュートリアルでは、テストを使用して Go アプリケーションでの Ethereum データ抽出の整合性を確認する方法を説明します。 Go-Ethereum クライアントを使用してブロック データとトランザクション データを取得し、テストには testify パッケージを使用します。

前提条件

  1. Go プログラミング言語の基本的な理解。
  2. システムにインストールしてください。
  3. (Go-Ethereum) クライアントがインストールされています。
  4. testify パッケージがインストールされました (github.com/stretchr/testify を取得します)。

プロジェクトのセットアップ

  1. Go プロジェクトを作成する:
mkdir ethereum-data-extraction
cd ethereum-data-extraction
go mod init ethereum-data-extraction
ログイン後にコピー
  1. 依存関係をインストールします:
go get github.com/ethereum/go-ethereum
go get github.com/stretchr/testify
ログイン後にコピー

データ抽出のコード

ブロックデータ抽出
まずはブロックデータを抽出する関数から始めましょう。

package blockchain

import (
    "context"
    "log"
    "math/big"

    "github.com/ethereum/go-ethereum"
    "github.com/ethereum/go-ethereum/common"
    "github.com/ethereum/go-ethereum/core/types"
    "github.com/ethereum/go-ethereum/ethclient"
    "github.com/ethereum/go-ethereum/rpc"
)

type BlockData struct {
    Number       *big.Int
    Hash         string
    ParentHash   string
    Nonce        uint64
    Sha3Uncles   string
    Miner        string
    Difficulty   *big.Int
    ExtraData    string
    Size         uint64
    GasLimit     uint64
    GasUsed      uint64
    Timestamp    uint64
    Transactions []string
}

func getClient() (*ethclient.Client, error) {
    client, err := ethclient.Dial("https://mainnet.infura.io/v3/YOUR_INFURA_PROJECT_ID")
    if err != nil {
        return nil, err
    }
    return client, nil
}

func GetBlockData(blockNumber *big.Int) (*BlockData, error) {
    client, err := getClient()
    if err != nil {
        log.Fatal("Failed to get client:", err)
    }

    block, err := client.BlockByNumber(context.Background(), blockNumber)
    if err != nil {
        log.Fatalf("Failed to retrieve the block: %v", err)
        return nil, err
    }

    transactionHashes := make([]string, len(block.Body().Transactions))
    for i, tx := range block.Body().Transactions {
        transactionHashes[i] = tx.Hash().Hex()
    }

    blockData := &BlockData{
        Number:       block.Number(),
        Hash:         block.Hash().Hex(),
        ParentHash:   block.ParentHash().Hex(),
        Nonce:        block.Nonce(),
        Sha3Uncles:   block.UncleHash().Hex(),
        Miner:        block.Coinbase().Hex(),
        Difficulty:   block.Difficulty(),
        ExtraData:    string(block.Extra()),
        Size:         block.Size(),
        GasLimit:     block.GasLimit(),
        GasUsed:      block.GasUsed(),
        Timestamp:    block.Time(),
        Transactions: transactionHashes,
    }

    return blockData, nil
}

ログイン後にコピー

トランザクションデータの抽出

次に、トランザクションデータを抽出する関数を定義します。

package blockchain

import (
    "context"
    "log"
    "math/big"

    "github.com/ethereum/go-ethereum/common"
    "github.com/ethereum/go-ethereum/core/types"
    "github.com/ethereum/go-ethereum/ethclient"
)

type TransactionData struct {
    Hash     string
    Nonce    uint64
    From     string
    To       string
    Value    *big.Int
    Gas      uint64
    GasPrice *big.Int
    Data     string
}

func GetTxData(txHash string) (*TransactionData, error) {
    client, err := getClient()
    if err != nil {
        log.Fatal("Failed to get client:", err)
        return nil, err
    }

    tx, _, err := client.TransactionByHash(context.Background(), common.HexToHash(txHash))
    if err != nil {
        log.Fatal("Failed to retrieve transaction:", err)
        return nil, err
    }

    sender, err := getTxSender(tx)
    if err != nil {
        log.Fatalf("Failed to get sender: %v", err)
        return nil, err
    }

    decodedData := decodeTxData(tx.Data())

    return &TransactionData{
        Hash:     tx.Hash().Hex(),
        Nonce:    tx.Nonce(),
        From:     sender,
        To:       tx.To().Hex(),
        Value:    tx.Value(),
        Gas:      tx.Gas(),
        GasPrice: tx.GasPrice(),
        Data:     decodedData,
    }, nil
}

func getChainId() (*big.Int, error) {
    client, err := getClient()
    if err != nil {
        log.Fatal("Failed to get client:", err)
        return big.NewInt(0), err
    }

    chainId, err := client.NetworkID(context.Background())
    if err != nil {
        log.Fatal("Failed to get chainId:", err)
        return big.NewInt(0), err
    }

    return chainId, nil
}

func getTxSender(tx *types.Transaction) (string, error) {
    chainId, err := getChainId()

    if err != nil {
        log.Fatal("Failed to get chainId:", err)
        return "", err
    }

    sender, err := types.Sender(types.NewLondonSigner(chainId), tx)
    if err != nil {
        log.Fatal("Not able to retrieve sender:", err)
        return "", err
    }

    return sender.Hex(), nil
}

func decodeTxData(data []byte) string {
    dataHex := common.Bytes2Hex(data)
    return dataHex
}

ログイン後にコピー

テストの作成

次に、データ抽出関数の整合性を確認するテストを作成しましょう。

package blockchain

import (
    "fmt"
    "math/big"
    "testing"

    "github.com/stretchr/testify/assert"
)

func TestGetBlockData(t *testing.T) {
    blockNumber := big.NewInt(20076728)
    blockData, err := GetBlockData(blockNumber)

    // Use fmt.Sprintf to format the log message
    t.Log(fmt.Sprintf("Block Data: \n%+v\nError: \n%v", blockData, err))

    assert.Nil(t, err)
    assert.NotNil(t, blockData)
}

func TestGetTransactionData(t *testing.T) {
    blockNumber := big.NewInt(20076728)
    blockData, err := GetBlockData(blockNumber)
    assert.Nil(t, err)
    assert.NotNil(t, blockData)

    if len(blockData.Transactions) > 0 {
        tx := blockData.Transactions[0]
        txData, err := GetTxData(tx)

        // Use fmt.Sprintf to format the log message
        t.Log(fmt.Sprintf("Transaction Data: \n%+v\nError: \n%v", txData, err))

        assert.Nil(t, err)
        assert.NotNil(t, txData)
    } else {
        t.Skip("No transactions found in the block")
    }
}
ログイン後にコピー

次のコマンドを使用してテストを実行します:

go test -v

ログイン後にコピー

出力:

--- PASS: TestGetBlockData (0.95s)
=== RUN   TestGetTransactionData
Current working directory: /mnt/c/github/dfbeat-v2/pkg/blockchain
Current working directory: /mnt/c/github/dfbeat-v2/pkg/blockchain
Current working directory: /mnt/c/github/dfbeat-v2/pkg/blockchain
    blockchain_test.go:33: Transaction Data:
        &{Hash:0x47e80ad8fa5f3bc94160f7eb1a3357f87b2756190007ab815b1a1890ddb65949 Nonce:249 BlockHash: BlockNumber:0 TransactionIndex:0 From:0x71B8CF59230bb295ade15506efd258eb458056A1 To:0x80a64c6D7f12C47B7c66c5B4E20E72bc1FCd5d9e Value:+50000000000000000 Gas:297438 GasPrice:+81175867687 Data:088890dc000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000071b8cf59230bb295ade15506efd258eb458056a1000000000000000000000000000000000000000000000000000000006669c2ac0000000000000000000000005c69bee701ef814a2b6a3edd4b1652cb9cc5aa6f0000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000f3fd27ffb4712278e6d51d7d526a0ce431d454c5}
        Error:
        <nil>
--- PASS: TestGetTransactionData (0.56s)
ログイン後にコピー

結論

このチュートリアルでは、Go と Go-Ethereum クライアントを使用して Ethereum ブロックチェーンからブロック データとトランザクション データを抽出する方法を説明しました。データ抽出プロセスの整合性を確保するためのテストを作成して実行する方法についても説明しました。これらの手順に従うことで、Go アプリケーションでブロックチェーン データを確実に取得して検証できます。

以上が通過テストによるイーサリアムデータ抽出の整合性の保証の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:dev.to
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート
私たちについて 免責事項 Sitemap
PHP中国語ウェブサイト:福祉オンライン PHP トレーニング,PHP 学習者の迅速な成長を支援します!