Restructure statediff directory

This commit is contained in:
Elizabeth Engelman 2018-12-13 10:59:31 -06:00
parent 869a34cf5a
commit 5b63446b6e
18 changed files with 128 additions and 334 deletions

View File

@ -58,7 +58,7 @@ import (
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
whisper "github.com/ethereum/go-ethereum/whisper/whisperv6" whisper "github.com/ethereum/go-ethereum/whisper/whisperv6"
"gopkg.in/urfave/cli.v1" "gopkg.in/urfave/cli.v1"
"github.com/ethereum/go-ethereum/statediff" "github.com/ethereum/go-ethereum/statediff/service"
) )
var ( var (
@ -1334,7 +1334,7 @@ func RegisterStateDiffService(stack *node.Node) {
ctx.Service(&ethServ) ctx.Service(&ethServ)
chainDb := ethServ.ChainDb() chainDb := ethServ.ChainDb()
blockChain := ethServ.BlockChain() blockChain := ethServ.BlockChain()
return statediff.NewStateDiffService(chainDb, blockChain) return service.NewStateDiffService(chainDb, blockChain)
}); err != nil { }); err != nil {
Fatalf("Failed to register State Diff Service", err) Fatalf("Failed to register State Diff Service", err)
} }

View File

@ -17,7 +17,7 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff package builder
import ( import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
@ -50,7 +50,6 @@ func (sdb *builder) BuildStateDiff(oldStateRoot, newStateRoot common.Hash, block
oldTrie, err := trie.New(oldStateRoot, sdb.trieDB) oldTrie, err := trie.New(oldStateRoot, sdb.trieDB)
if err != nil { if err != nil {
log.Debug("error creating oldTrie", err) log.Debug("error creating oldTrie", err)
//getting this error: error creating oldTrie missing trie node ddfbb83966d870891aa47147269447a83564d1defaefad5f9844a3a3a2a08433 (path )
return nil, err return nil, err
} }
newTrie, err := trie.New(newStateRoot, sdb.trieDB) newTrie, err := trie.New(newStateRoot, sdb.trieDB)

View File

@ -0,0 +1,13 @@
package builder_test
import (
"testing"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
)
func TestBuilder(t *testing.T) {
RegisterFailHandler(Fail)
RunSpecs(t, "Builder Suite")
}

View File

@ -17,7 +17,7 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff_test package builder_test
import ( import (
"github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
@ -29,8 +29,8 @@ import (
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"math/big" "math/big"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/statediff"
"github.com/onsi/gomega" "github.com/onsi/gomega"
b "github.com/ethereum/go-ethereum/statediff/builder"
) )
@ -50,8 +50,8 @@ var (
contractCode = common.Hex2Bytes("606060405260cc8060106000396000f360606040526000357c01000000000000000000000000000000000000000000000000000000009004806360cd2685146041578063c16431b914606b57603f565b005b6055600480803590602001909190505060a9565b6040518082815260200191505060405180910390f35b60886004808035906020019091908035906020019091905050608a565b005b80600060005083606481101560025790900160005b50819055505b5050565b6000600060005082606481101560025790900160005b5054905060c7565b91905056") contractCode = common.Hex2Bytes("606060405260cc8060106000396000f360606040526000357c01000000000000000000000000000000000000000000000000000000009004806360cd2685146041578063c16431b914606b57603f565b005b6055600480803590602001909190505060a9565b6040518082815260200191505060405180910390f35b60886004808035906020019091908035906020019091905050608a565b005b80600060005083606481101560025790900160005b50819055505b5050565b6000600060005082606481101560025790900160005b5054905060c7565b91905056")
contractAddr common.Address contractAddr common.Address
emptyAccountDiffEventualMap = make(map[common.Address]statediff.AccountDiffEventual) emptyAccountDiffEventualMap = make(map[common.Address]b.AccountDiffEventual)
emptyAccountDiffIncrementalMap = make(map[common.Address]statediff.AccountDiffIncremental) emptyAccountDiffIncrementalMap = make(map[common.Address]b.AccountDiffIncremental)
) )
/* /*
contract test { contract test {
@ -121,10 +121,10 @@ var _ = ginkgo.FDescribe("", func() {
var ( var (
block0Hash, block1Hash, block2Hash, block3Hash common.Hash block0Hash, block1Hash, block2Hash, block3Hash common.Hash
block0, block1, block2, block3 *types.Block block0, block1, block2, block3 *types.Block
builder statediff.Builder builder b.Builder
miningReward = int64(3000000000000000000) miningReward = int64(3000000000000000000)
burnAddress = common.HexToAddress("0x0") burnAddress = common.HexToAddress("0x0")
diff *statediff.StateDiff diff *b.StateDiff
err error err error
) )
@ -139,11 +139,11 @@ var _ = ginkgo.FDescribe("", func() {
block1 = blocks[block1Hash] block1 = blocks[block1Hash]
block2 = blocks[block2Hash] block2 = blocks[block2Hash]
block3 = blocks[block3Hash] block3 = blocks[block3Hash]
builder = statediff.NewBuilder(testdb) builder = b.NewBuilder(testdb)
}) })
ginkgo.It("returns empty account diff collections when the state root hasn't changed", func() { ginkgo.It("returns empty account diff collections when the state root hasn't changed", func() {
expectedDiff := statediff.StateDiff{ expectedDiff := b.StateDiff{
BlockNumber: block0.Number().Int64(), BlockNumber: block0.Number().Int64(),
BlockHash: block0Hash, BlockHash: block0Hash,
CreatedAccounts: emptyAccountDiffEventualMap, CreatedAccounts: emptyAccountDiffEventualMap,
@ -177,7 +177,7 @@ var _ = ginkgo.FDescribe("", func() {
}) })
ginkgo.It("returns balance diffs for updated accounts", func() { ginkgo.It("returns balance diffs for updated accounts", func() {
expectedBankBalanceDiff := statediff.DiffBigInt{ expectedBankBalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(testBankFunds.Int64() - balanceChange), NewValue: big.NewInt(testBankFunds.Int64() - balanceChange),
OldValue: testBankFunds, OldValue: testBankFunds,
} }
@ -187,12 +187,12 @@ var _ = ginkgo.FDescribe("", func() {
}) })
ginkgo.It("returns balance diffs for new accounts", func() { ginkgo.It("returns balance diffs for new accounts", func() {
expectedAccount1BalanceDiff := statediff.DiffBigInt{ expectedAccount1BalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(balanceChange), NewValue: big.NewInt(balanceChange),
OldValue: nil, OldValue: nil,
} }
expectedBurnAddrBalanceDiff := statediff.DiffBigInt{ expectedBurnAddrBalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(miningReward), NewValue: big.NewInt(miningReward),
OldValue: nil, OldValue: nil,
} }
@ -228,17 +228,17 @@ var _ = ginkgo.FDescribe("", func() {
}) })
ginkgo.It("returns balance diffs for updated accounts", func() { ginkgo.It("returns balance diffs for updated accounts", func() {
expectedBankBalanceDiff := statediff.DiffBigInt{ expectedBankBalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(block1BankBalance - balanceChange), NewValue: big.NewInt(block1BankBalance - balanceChange),
OldValue: big.NewInt(block1BankBalance), OldValue: big.NewInt(block1BankBalance),
} }
expectedAccount1BalanceDiff := statediff.DiffBigInt{ expectedAccount1BalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(block1Account1Balance - balanceChange + balanceChange), NewValue: big.NewInt(block1Account1Balance - balanceChange + balanceChange),
OldValue: big.NewInt(block1Account1Balance), OldValue: big.NewInt(block1Account1Balance),
} }
expectedBurnBalanceDiff := statediff.DiffBigInt{ expectedBurnBalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(miningReward + miningReward), NewValue: big.NewInt(miningReward + miningReward),
OldValue: big.NewInt(miningReward), OldValue: big.NewInt(miningReward),
} }
@ -250,12 +250,12 @@ var _ = ginkgo.FDescribe("", func() {
}) })
ginkgo.It("returns balance diffs for new accounts", func() { ginkgo.It("returns balance diffs for new accounts", func() {
expectedAccount2BalanceDiff := statediff.DiffBigInt{ expectedAccount2BalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(balanceChange), NewValue: big.NewInt(balanceChange),
OldValue: nil, OldValue: nil,
} }
expectedContractBalanceDiff := statediff.DiffBigInt{ expectedContractBalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(0), NewValue: big.NewInt(0),
OldValue: nil, OldValue: nil,
} }
@ -290,23 +290,23 @@ var _ = ginkgo.FDescribe("", func() {
ginkgo.It("returns balance, storage and nonce diffs for updated accounts", func() { ginkgo.It("returns balance, storage and nonce diffs for updated accounts", func() {
block2Account2Balance := int64(1000) block2Account2Balance := int64(1000)
expectedAcct2BalanceDiff := statediff.DiffBigInt{ expectedAcct2BalanceDiff := b.DiffBigInt{
NewValue: big.NewInt(block2Account2Balance + miningReward), NewValue: big.NewInt(block2Account2Balance + miningReward),
OldValue: big.NewInt(block2Account2Balance), OldValue: big.NewInt(block2Account2Balance),
} }
expectedContractStorageDiff := make(map[string]statediff.DiffString) expectedContractStorageDiff := make(map[string]b.DiffString)
newVal := "0x03" newVal := "0x03"
oldVal := "0x0" oldVal := "0x0"
path := "0x405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5ace" path := "0x405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5ace"
expectedContractStorageDiff[path] = statediff.DiffString{ expectedContractStorageDiff[path] = b.DiffString{
NewValue: &newVal, NewValue: &newVal,
OldValue: &oldVal, OldValue: &oldVal,
} }
oldNonce := uint64(2) oldNonce := uint64(2)
newNonce := uint64(3) newNonce := uint64(3)
expectedBankNonceDiff := statediff.DiffUint64{ expectedBankNonceDiff := b.DiffUint64{
NewValue: &newNonce, NewValue: &newNonce,
OldValue: &oldNonce, OldValue: &oldNonce,
} }

View File

@ -17,7 +17,7 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff package builder
import ( import (
"sort" "sort"

View File

@ -17,7 +17,7 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff package builder
import ( import (
"encoding/json" "encoding/json"

View File

@ -17,10 +17,12 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff package extractor
import ( import (
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/statediff/builder"
"github.com/ethereum/go-ethereum/statediff/publisher"
) )
type Extractor interface { type Extractor interface {
@ -28,11 +30,11 @@ type Extractor interface {
} }
type extractor struct { type extractor struct {
Builder Builder // Interface for building state diff objects from two blocks Builder builder.Builder // Interface for building state diff objects from two blocks
Publisher Publisher // Interface for publishing state diff objects to a datastore (e.g. IPFS) Publisher publisher.Publisher // Interface for publishing state diff objects to a datastore (e.g. IPFS)
} }
func NewExtractor(builder Builder, publisher Publisher) (*extractor, error) { func NewExtractor(builder builder.Builder, publisher publisher.Publisher) (*extractor, error) {
return &extractor{ return &extractor{
Builder: builder, Builder: builder,
Publisher: publisher, Publisher: publisher,

View File

@ -0,0 +1,13 @@
package extractor_test
import (
"testing"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
)
func TestExtractor(t *testing.T) {
RegisterFailHandler(Fail)
RunSpecs(t, "Extractor Suite")
}

View File

@ -17,30 +17,31 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff_test package extractor_test
import ( import (
"github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"github.com/ethereum/go-ethereum/statediff"
"github.com/onsi/gomega" "github.com/onsi/gomega"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"math/rand" "math/rand"
"github.com/ethereum/go-ethereum/statediff/testhelpers" "github.com/ethereum/go-ethereum/statediff/testhelpers"
"math/big" "math/big"
e "github.com/ethereum/go-ethereum/statediff/extractor"
b "github.com/ethereum/go-ethereum/statediff/builder"
) )
var _ = ginkgo.Describe("Extractor", func() { var _ = ginkgo.Describe("Extractor", func() {
var publisher testhelpers.MockPublisher var publisher testhelpers.MockPublisher
var builder testhelpers.MockBuilder var builder testhelpers.MockBuilder
var currentBlockNumber *big.Int var currentBlockNumber *big.Int
var parentBlock, currentBlock *types.Block var parentBlock, currentBlock *types.Block
var expectedStateDiff statediff.StateDiff var expectedStateDiff b.StateDiff
var extractor statediff.Extractor var extractor e.Extractor
var err error var err error
ginkgo.BeforeEach(func() { ginkgo.BeforeEach(func() {
publisher = testhelpers.MockPublisher{} publisher = testhelpers.MockPublisher{}
builder = testhelpers.MockBuilder{} builder = testhelpers.MockBuilder{}
extractor, err = statediff.NewExtractor(&builder, &publisher) extractor, err = e.NewExtractor(&builder, &publisher)
gomega.Expect(err).NotTo(gomega.HaveOccurred()) gomega.Expect(err).NotTo(gomega.HaveOccurred())
blockNumber := rand.Int63() blockNumber := rand.Int63()
@ -49,7 +50,7 @@ var _ = ginkgo.Describe("Extractor", func() {
parentBlock = types.NewBlock(&types.Header{Number: parentBlockNumber}, nil, nil, nil) parentBlock = types.NewBlock(&types.Header{Number: parentBlockNumber}, nil, nil, nil)
currentBlock = types.NewBlock(&types.Header{Number: currentBlockNumber}, nil, nil, nil) currentBlock = types.NewBlock(&types.Header{Number: currentBlockNumber}, nil, nil, nil)
expectedStateDiff = statediff.StateDiff{ expectedStateDiff = b.StateDiff{
BlockNumber: blockNumber, BlockNumber: blockNumber,
BlockHash: currentBlock.Hash(), BlockHash: currentBlock.Hash(),
CreatedAccounts: nil, CreatedAccounts: nil,

View File

@ -1,58 +0,0 @@
// Copyright 2015 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features.
package ipfs
import (
"context"
"github.com/ipfs/go-ipfs/core"
"github.com/ipfs/go-ipfs/repo/fsrepo"
ipld "gx/ipfs/QmWi2BYBL5gJ3CiAiQchg6rn1A8iBsrWy51EYxvHVjFvLb/go-ipld-format"
)
type Adder interface {
Add(node ipld.Node) error
}
type adder struct {
n *core.IpfsNode
ctx context.Context
}
func (a adder) Add(node ipld.Node) error {
return a.n.DAG.Add(a.n.Context(), node) // For some reason DAG.Add method is not being exposed by the ipld.DAGService
}
func NewAdder(repoPath string) (*adder, error) {
r, err := fsrepo.Open(repoPath)
if err != nil {
return nil, err
}
ctx := context.Background()
cfg := &core.BuildCfg{
Online: false,
Repo: r,
}
ipfsNode, err := core.NewNode(ctx, cfg)
if err != nil {
return nil, err
}
return &adder{n: ipfsNode, ctx: ctx}, nil
}

View File

@ -1,80 +0,0 @@
// Copyright 2015 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features.
package ipfs
import (
"bytes"
"encoding/gob"
ipld "gx/ipfs/QmWi2BYBL5gJ3CiAiQchg6rn1A8iBsrWy51EYxvHVjFvLb/go-ipld-format"
"github.com/ethereum/go-ethereum/statediff"
"github.com/ethereum/go-ethereum/common"
)
const (
EthStateDiffCode = 0x99 // Register custom codec for state diff?
)
type DagPutter interface {
DagPut(sd *statediff.StateDiff) (string, error)
}
type dagPutter struct {
Adder
}
func NewDagPutter(adder Adder) *dagPutter {
return &dagPutter{Adder: adder}
}
func (bhdp *dagPutter) DagPut(sd *statediff.StateDiff) (string, error) {
nd, err := bhdp.getNode(sd)
if err != nil {
return "", err
}
err = bhdp.Add(nd)
if err != nil {
return "", err
}
return nd.Cid().String(), nil
}
func (bhdp *dagPutter) getNode(sd *statediff.StateDiff) (ipld.Node, error) {
var buff bytes.Buffer
enc := gob.NewEncoder(&buff)
err := enc.Encode(sd)
if err != nil {
return nil, err
}
raw := buff.Bytes()
cid, err := RawToCid(EthStateDiffCode, raw)
if err != nil {
return nil, err
}
return &StateDiffNode{
StateDiff: sd,
cid: cid,
rawdata: raw,
}, nil
}

View File

@ -1,38 +0,0 @@
// Copyright 2015 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features.
package ipfs
import (
mh "gx/ipfs/QmZyZDi491cCNTLfAhwcaDii2Kg4pwKRkhqQzURGDvY6ua/go-multihash"
"gx/ipfs/QmapdYm1b22Frv3k17fqrBYTFRxwiaVJkB299Mfn33edeB/go-cid"
)
func RawToCid(codec uint64, raw []byte) (*cid.Cid, error) {
c, err := cid.Prefix{
Codec: codec,
Version: 1,
MhType: mh.KECCAK_256,
MhLength: -1,
}.Sum(raw)
if err != nil {
return nil, err
}
return c, nil
}

View File

@ -1,78 +0,0 @@
// Copyright 2015 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features.
package ipfs
import (
ipld "gx/ipfs/QmWi2BYBL5gJ3CiAiQchg6rn1A8iBsrWy51EYxvHVjFvLb/go-ipld-format"
"gx/ipfs/QmapdYm1b22Frv3k17fqrBYTFRxwiaVJkB299Mfn33edeB/go-cid"
"github.com/i-norden/go-ethereum/statediff"
)
type StateDiffNode struct {
*statediff.StateDiff
cid *cid.Cid
rawdata []byte
}
func (sdn *StateDiffNode) RawData() []byte {
return sdn.rawdata
}
func (sdn *StateDiffNode) Cid() *cid.Cid {
return sdn.cid
}
func (sdn StateDiffNode) String() string {
return sdn.cid.String()
}
func (sdn StateDiffNode) Loggable() map[string]interface{} {
return sdn.cid.Loggable()
}
func (sdn StateDiffNode) Resolve(path []string) (interface{}, []string, error) {
panic("implement me")
}
func (sdn StateDiffNode) Tree(path string, depth int) []string {
panic("implement me")
}
func (sdn StateDiffNode) ResolveLink(path []string) (*ipld.Link, []string, error) {
panic("implement me")
}
func (sdn StateDiffNode) Copy() ipld.Node {
panic("implement me")
}
func (sdn StateDiffNode) Links() []*ipld.Link {
panic("implement me")
}
func (sdn StateDiffNode) Stat() (*ipld.NodeStat, error) {
panic("implement me")
}
func (sdn StateDiffNode) Size() (uint64, error) {
panic("implement me")
}

View File

@ -17,7 +17,7 @@
// Contains a batch of utility type declarations used by the tests. As the node // Contains a batch of utility type declarations used by the tests. As the node
// operates on unique types, a lot of them are needed to check various features. // operates on unique types, a lot of them are needed to check various features.
package statediff package publisher
import ( import (
"os" "os"
@ -25,14 +25,16 @@ import (
"time" "time"
"strconv" "strconv"
"strings" "strings"
"github.com/ethereum/go-ethereum/statediff/builder"
"github.com/ethereum/go-ethereum/statediff"
) )
type Publisher interface { type Publisher interface {
PublishStateDiff(sd *StateDiff) (string, error) PublishStateDiff(sd *builder.StateDiff) (string, error)
} }
type publisher struct { type publisher struct {
Config Config Config statediff.Config
} }
var ( var (
@ -51,22 +53,22 @@ var (
updatedAccountAction = "updated" updatedAccountAction = "updated"
) )
func NewPublisher(config Config) (*publisher, error) { func NewPublisher(config statediff.Config) (*publisher, error) {
return &publisher{ return &publisher{
Config: config, Config: config,
}, nil }, nil
} }
func (p *publisher) PublishStateDiff(sd *StateDiff) (string, error) { func (p *publisher) PublishStateDiff(sd *builder.StateDiff) (string, error) {
switch p.Config.Mode { switch p.Config.Mode {
case CSV: case statediff.CSV:
return "", p.publishStateDiffToCSV(*sd) return "", p.publishStateDiffToCSV(*sd)
default: default:
return "", p.publishStateDiffToCSV(*sd) return "", p.publishStateDiffToCSV(*sd)
} }
} }
func (p *publisher) publishStateDiffToCSV(sd StateDiff) error { func (p *publisher) publishStateDiffToCSV(sd builder.StateDiff) error {
now := time.Now() now := time.Now()
timeStamp := now.Format(timeStampFormat) timeStamp := now.Format(timeStampFormat)
filePath := p.Config.Path + timeStamp + ".csv" filePath := p.Config.Path + timeStamp + ".csv"
@ -102,7 +104,7 @@ func (p *publisher) publishStateDiffToCSV(sd StateDiff) error {
return nil return nil
} }
func accumulateUpdatedAccountRows(sd StateDiff) [][]string { func accumulateUpdatedAccountRows(sd builder.StateDiff) [][]string {
var updatedAccountRows [][]string var updatedAccountRows [][]string
for _, accountDiff := range sd.UpdatedAccounts { for _, accountDiff := range sd.UpdatedAccounts {
formattedAccountData := formatAccountDiffIncremental(accountDiff, sd, updatedAccountAction) formattedAccountData := formatAccountDiffIncremental(accountDiff, sd, updatedAccountAction)
@ -113,7 +115,7 @@ func accumulateUpdatedAccountRows(sd StateDiff) [][]string {
return updatedAccountRows return updatedAccountRows
} }
func accumulateDeletedAccountRows(sd StateDiff) [][]string { func accumulateDeletedAccountRows(sd builder.StateDiff) [][]string {
var deletedAccountRows [][]string var deletedAccountRows [][]string
for _, accountDiff := range sd.DeletedAccounts { for _, accountDiff := range sd.DeletedAccounts {
formattedAccountData := formatAccountDiffEventual(accountDiff, sd, deletedAccountAction) formattedAccountData := formatAccountDiffEventual(accountDiff, sd, deletedAccountAction)
@ -124,7 +126,7 @@ func accumulateDeletedAccountRows(sd StateDiff) [][]string {
return deletedAccountRows return deletedAccountRows
} }
func accumulateCreatedAccountRows(sd StateDiff) [][]string { func accumulateCreatedAccountRows(sd builder.StateDiff) [][]string {
var createdAccountRows [][]string var createdAccountRows [][]string
for _, accountDiff := range sd.CreatedAccounts { for _, accountDiff := range sd.CreatedAccounts {
formattedAccountData := formatAccountDiffEventual(accountDiff, sd, createdAccountAction) formattedAccountData := formatAccountDiffEventual(accountDiff, sd, createdAccountAction)
@ -135,7 +137,7 @@ func accumulateCreatedAccountRows(sd StateDiff) [][]string {
return createdAccountRows return createdAccountRows
} }
func formatAccountDiffEventual(accountDiff AccountDiffEventual, sd StateDiff, accountAction string) []string { func formatAccountDiffEventual(accountDiff builder.AccountDiffEventual, sd builder.StateDiff, accountAction string) []string {
oldContractRoot := accountDiff.ContractRoot.OldValue oldContractRoot := accountDiff.ContractRoot.OldValue
newContractRoot := accountDiff.ContractRoot.NewValue newContractRoot := accountDiff.ContractRoot.NewValue
var storageDiffPaths []string var storageDiffPaths []string
@ -159,7 +161,7 @@ func formatAccountDiffEventual(accountDiff AccountDiffEventual, sd StateDiff, ac
return formattedAccountData return formattedAccountData
} }
func formatAccountDiffIncremental(accountDiff AccountDiffIncremental, sd StateDiff, accountAction string) []string { func formatAccountDiffIncremental(accountDiff builder.AccountDiffIncremental, sd builder.StateDiff, accountAction string) []string {
oldContractRoot := accountDiff.ContractRoot.OldValue oldContractRoot := accountDiff.ContractRoot.OldValue
newContractRoot := accountDiff.ContractRoot.NewValue newContractRoot := accountDiff.ContractRoot.NewValue
var storageDiffPaths []string var storageDiffPaths []string

View File

@ -0,0 +1,13 @@
package publisher_test
import (
"testing"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
)
func TestPublisher(t *testing.T) {
RegisterFailHandler(Fail)
RunSpecs(t, "Publisher Suite")
}

View File

@ -1,4 +1,4 @@
package statediff_test package publisher_test
import ( import (
"github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
@ -12,12 +12,14 @@ import (
"path/filepath" "path/filepath"
"strings" "strings"
"strconv" "strconv"
p "github.com/ethereum/go-ethereum/statediff/publisher"
"github.com/ethereum/go-ethereum/statediff/builder"
) )
var _ = ginkgo.Describe("Publisher", func() { var _ = ginkgo.Describe("Publisher", func() {
ginkgo.Context("default CSV publisher", func() { ginkgo.Context("default CSV publisher", func() {
var ( var (
publisher statediff.Publisher publisher p.Publisher
err error err error
config = statediff.Config{ config = statediff.Config{
Path: "./test-", Path: "./test-",
@ -36,21 +38,21 @@ var _ = ginkgo.Describe("Publisher", func() {
storagePath = "0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470" storagePath = "0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"
oldStorage = "0x0" oldStorage = "0x0"
newStorage = "0x03" newStorage = "0x03"
storage = map[string]statediff.DiffString{storagePath: { storage = map[string]builder.DiffString{storagePath: {
NewValue: &newStorage, NewValue: &newStorage,
OldValue: &oldStorage, OldValue: &oldStorage,
}} }}
address = common.HexToAddress("0xaE9BEa628c4Ce503DcFD7E305CaB4e29E7476592") address = common.HexToAddress("0xaE9BEa628c4Ce503DcFD7E305CaB4e29E7476592")
createdAccounts = map[common.Address]statediff.AccountDiffEventual{address: { createdAccounts = map[common.Address]builder.AccountDiffEventual{address: {
Nonce: statediff.DiffUint64{ Nonce: builder.DiffUint64{
NewValue: &newNonceValue, NewValue: &newNonceValue,
OldValue: &oldNonceValue, OldValue: &oldNonceValue,
}, },
Balance: statediff.DiffBigInt{ Balance: builder.DiffBigInt{
NewValue: big.NewInt(newBalanceValue), NewValue: big.NewInt(newBalanceValue),
OldValue: big.NewInt(oldBalanceValue), OldValue: big.NewInt(oldBalanceValue),
}, },
ContractRoot: statediff.DiffString{ ContractRoot: builder.DiffString{
NewValue: &contractRoot, NewValue: &contractRoot,
OldValue: &contractRoot, OldValue: &contractRoot,
}, },
@ -59,33 +61,33 @@ var _ = ginkgo.Describe("Publisher", func() {
Storage: storage, Storage: storage,
}} }}
updatedAccounts = map[common.Address]statediff.AccountDiffIncremental{address: { updatedAccounts = map[common.Address]builder.AccountDiffIncremental{address: {
Nonce: statediff.DiffUint64{ Nonce: builder.DiffUint64{
NewValue: &newNonceValue, NewValue: &newNonceValue,
OldValue: &oldNonceValue, OldValue: &oldNonceValue,
}, },
Balance: statediff.DiffBigInt{ Balance: builder.DiffBigInt{
NewValue: big.NewInt(newBalanceValue), NewValue: big.NewInt(newBalanceValue),
OldValue: big.NewInt(oldBalanceValue), OldValue: big.NewInt(oldBalanceValue),
}, },
CodeHash: codeHash, CodeHash: codeHash,
ContractRoot: statediff.DiffString{ ContractRoot: builder.DiffString{
NewValue: &contractRoot, NewValue: &contractRoot,
OldValue: &contractRoot, OldValue: &contractRoot,
}, },
Storage: storage, Storage: storage,
}} }}
deletedAccounts = map[common.Address]statediff.AccountDiffEventual{address: { deletedAccounts = map[common.Address]builder.AccountDiffEventual{address: {
Nonce: statediff.DiffUint64{ Nonce: builder.DiffUint64{
NewValue: &newNonceValue, NewValue: &newNonceValue,
OldValue: &oldNonceValue, OldValue: &oldNonceValue,
}, },
Balance: statediff.DiffBigInt{ Balance: builder.DiffBigInt{
NewValue: big.NewInt(newBalanceValue), NewValue: big.NewInt(newBalanceValue),
OldValue: big.NewInt(oldBalanceValue), OldValue: big.NewInt(oldBalanceValue),
}, },
ContractRoot: statediff.DiffString{ ContractRoot: builder.DiffString{
NewValue: &contractRoot, NewValue: &contractRoot,
OldValue: &contractRoot, OldValue: &contractRoot,
}, },
@ -94,7 +96,7 @@ var _ = ginkgo.Describe("Publisher", func() {
Storage: storage, Storage: storage,
}} }}
testStateDiff = statediff.StateDiff{ testStateDiff = builder.StateDiff{
BlockNumber: blockNumber, BlockNumber: blockNumber,
BlockHash: common.HexToHash(blockHash), BlockHash: common.HexToHash(blockHash),
CreatedAccounts: createdAccounts, CreatedAccounts: createdAccounts,
@ -106,7 +108,7 @@ var _ = ginkgo.Describe("Publisher", func() {
var lines [][]string var lines [][]string
var file *os.File var file *os.File
ginkgo.BeforeEach(func() { ginkgo.BeforeEach(func() {
publisher, err = statediff.NewPublisher(config) publisher, err = p.NewPublisher(config)
gomega.Expect(err).NotTo(gomega.HaveOccurred()) gomega.Expect(err).NotTo(gomega.HaveOccurred())
_, err := publisher.PublishStateDiff(&testStateDiff) _, err := publisher.PublishStateDiff(&testStateDiff)
@ -127,7 +129,7 @@ var _ = ginkgo.Describe("Publisher", func() {
ginkgo.It("persists the column headers to a CSV file", func() { ginkgo.It("persists the column headers to a CSV file", func() {
gomega.Expect(len(lines) > 1).To(gomega.BeTrue()) gomega.Expect(len(lines) > 1).To(gomega.BeTrue())
gomega.Expect(lines[0]).To(gomega.Equal(statediff.Headers)) gomega.Expect(lines[0]).To(gomega.Equal(p.Headers))
}) })
ginkgo.It("persists the created account diffs to a CSV file", func() { ginkgo.It("persists the created account diffs to a CSV file", func() {
@ -203,4 +205,3 @@ func getTestCSVFiles(rootPath string) []string{
gomega.Expect(err).NotTo(gomega.HaveOccurred()) gomega.Expect(err).NotTo(gomega.HaveOccurred())
return files return files
} }

View File

@ -1,4 +1,4 @@
package statediff package service
import ( import (
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
@ -7,23 +7,27 @@ import (
"github.com/ethereum/go-ethereum/rpc" "github.com/ethereum/go-ethereum/rpc"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
"log" "log"
e "github.com/ethereum/go-ethereum/statediff/extractor"
b "github.com/ethereum/go-ethereum/statediff/builder"
"github.com/ethereum/go-ethereum/statediff"
p "github.com/ethereum/go-ethereum/statediff/publisher"
) )
type StateDiffService struct { type StateDiffService struct {
builder *builder builder *b.Builder
extractor *extractor extractor e.Extractor
blockchain *core.BlockChain blockchain *core.BlockChain
} }
func NewStateDiffService(db ethdb.Database, blockChain *core.BlockChain) (*StateDiffService, error) { func NewStateDiffService(db ethdb.Database, blockChain *core.BlockChain) (*StateDiffService, error) {
config := Config{} config := statediff.Config{}
builder := NewBuilder(db) builder := b.NewBuilder(db)
publisher, err := NewPublisher(config) publisher, err := p.NewPublisher(config)
if err != nil { if err != nil {
return nil, nil return nil, nil
} }
extractor, _ := NewExtractor(builder, publisher) extractor, _ := e.NewExtractor(builder, publisher)
return &StateDiffService{ return &StateDiffService{
blockchain: blockChain, blockchain: blockChain,
extractor: extractor, extractor: extractor,

View File

@ -2,8 +2,8 @@ package testhelpers
import ( import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/statediff"
"errors" "errors"
"github.com/ethereum/go-ethereum/statediff/builder"
) )
var MockError = errors.New("mock error") var MockError = errors.New("mock error")
@ -13,11 +13,11 @@ type MockBuilder struct {
NewStateRoot common.Hash NewStateRoot common.Hash
BlockNumber int64 BlockNumber int64
BlockHash common.Hash BlockHash common.Hash
stateDiff *statediff.StateDiff stateDiff *builder.StateDiff
builderError error builderError error
} }
func (builder *MockBuilder) BuildStateDiff(oldStateRoot, newStateRoot common.Hash, blockNumber int64, blockHash common.Hash) (*statediff.StateDiff, error) { func (builder *MockBuilder) BuildStateDiff(oldStateRoot, newStateRoot common.Hash, blockNumber int64, blockHash common.Hash) (*builder.StateDiff, error) {
builder.OldStateRoot = oldStateRoot builder.OldStateRoot = oldStateRoot
builder.NewStateRoot = newStateRoot builder.NewStateRoot = newStateRoot
builder.BlockNumber = blockNumber builder.BlockNumber = blockNumber
@ -26,7 +26,7 @@ func (builder *MockBuilder) BuildStateDiff(oldStateRoot, newStateRoot common.Has
return builder.stateDiff, builder.builderError return builder.stateDiff, builder.builderError
} }
func (builder *MockBuilder) SetStateDiffToBuild(stateDiff *statediff.StateDiff) { func (builder *MockBuilder) SetStateDiffToBuild(stateDiff *builder.StateDiff) {
builder.stateDiff = stateDiff builder.stateDiff = stateDiff
} }
@ -35,11 +35,11 @@ func (builder *MockBuilder) SetBuilderError(err error) {
} }
type MockPublisher struct{ type MockPublisher struct{
StateDiff *statediff.StateDiff StateDiff *builder.StateDiff
publisherError error publisherError error
} }
func (publisher *MockPublisher) PublishStateDiff(sd *statediff.StateDiff) (string, error) { func (publisher *MockPublisher) PublishStateDiff(sd *builder.StateDiff) (string, error) {
publisher.StateDiff = sd publisher.StateDiff = sd
return "", publisher.publisherError return "", publisher.publisherError
} }