From ef6706696c39c77b20dc5127da8c62e89de39cf7 Mon Sep 17 00:00:00 2001
From: obscuren <geffobscura@gmail.com>
Date: Thu, 12 Mar 2015 14:50:35 +0100
Subject: [PATCH] Add additional extra database for non-protocol related data

* Add transaction to extra database after a successful block process
---
 core/block_processor.go      | 20 ++++++++++++++++++--
 core/block_processor_test.go |  2 +-
 core/chain_makers.go         |  2 +-
 core/chain_manager_test.go   |  4 ++--
 eth/backend.go               | 16 +++++++++-------
 5 files changed, 31 insertions(+), 13 deletions(-)

diff --git a/core/block_processor.go b/core/block_processor.go
index 7ac8a1bd2..395622a8e 100644
--- a/core/block_processor.go
+++ b/core/block_processor.go
@@ -12,6 +12,7 @@ import (
 	"github.com/ethereum/go-ethereum/event"
 	"github.com/ethereum/go-ethereum/logger"
 	"github.com/ethereum/go-ethereum/pow"
+	"github.com/ethereum/go-ethereum/rlp"
 	"github.com/ethereum/go-ethereum/state"
 	"gopkg.in/fatih/set.v0"
 )
@@ -23,7 +24,8 @@ type PendingBlockEvent struct {
 var statelogger = logger.NewLogger("BLOCK")
 
 type BlockProcessor struct {
-	db ethutil.Database
+	db      ethutil.Database
+	extraDb ethutil.Database
 	// Mutex for locking the block processor. Blocks can only be handled one at a time
 	mutex sync.Mutex
 	// Canonical block chain
@@ -45,9 +47,10 @@ type BlockProcessor struct {
 	eventMux *event.TypeMux
 }
 
-func NewBlockProcessor(db ethutil.Database, pow pow.PoW, txpool *TxPool, chainManager *ChainManager, eventMux *event.TypeMux) *BlockProcessor {
+func NewBlockProcessor(db, extra ethutil.Database, pow pow.PoW, txpool *TxPool, chainManager *ChainManager, eventMux *event.TypeMux) *BlockProcessor {
 	sm := &BlockProcessor{
 		db:       db,
+		extraDb:  extra,
 		mem:      make(map[string]*big.Int),
 		Pow:      pow,
 		bc:       chainManager,
@@ -230,6 +233,10 @@ func (sm *BlockProcessor) processWithParent(block, parent *types.Block) (td *big
 	// Remove transactions from the pool
 	sm.txpool.RemoveSet(block.Transactions())
 
+	for _, tx := range block.Transactions() {
+		putTx(sm.extraDb, tx)
+	}
+
 	chainlogger.Infof("processed block #%d (%x...)\n", header.Number, block.Hash()[0:4])
 
 	return td, nil
@@ -347,3 +354,12 @@ func (sm *BlockProcessor) GetLogs(block *types.Block) (logs state.Logs, err erro
 
 	return state.Logs(), nil
 }
+
+func putTx(db ethutil.Database, tx *types.Transaction) {
+	rlpEnc, err := rlp.EncodeToBytes(tx)
+	if err != nil {
+		statelogger.Infoln("Failed encoding tx", err)
+		return
+	}
+	db.Put(tx.Hash(), rlpEnc)
+}
diff --git a/core/block_processor_test.go b/core/block_processor_test.go
index a031c2669..ad29404e1 100644
--- a/core/block_processor_test.go
+++ b/core/block_processor_test.go
@@ -14,7 +14,7 @@ func proc() (*BlockProcessor, *ChainManager) {
 	var mux event.TypeMux
 
 	chainMan := NewChainManager(db, db, &mux)
-	return NewBlockProcessor(db, ezp.New(), nil, chainMan, &mux), chainMan
+	return NewBlockProcessor(db, db, ezp.New(), nil, chainMan, &mux), chainMan
 }
 
 func TestNumber(t *testing.T) {
diff --git a/core/chain_makers.go b/core/chain_makers.go
index b5c50dc3d..f140b5c7e 100644
--- a/core/chain_makers.go
+++ b/core/chain_makers.go
@@ -120,7 +120,7 @@ func newChainManager(block *types.Block, eventMux *event.TypeMux, db ethutil.Dat
 
 // block processor with fake pow
 func newBlockProcessor(db ethutil.Database, txpool *TxPool, cman *ChainManager, eventMux *event.TypeMux) *BlockProcessor {
-	bman := NewBlockProcessor(db, FakePow{}, txpool, newChainManager(nil, eventMux, db), eventMux)
+	bman := NewBlockProcessor(db, db, FakePow{}, txpool, newChainManager(nil, eventMux, db), eventMux)
 	return bman
 }
 
diff --git a/core/chain_manager_test.go b/core/chain_manager_test.go
index 91822f9e2..898d37f9c 100644
--- a/core/chain_manager_test.go
+++ b/core/chain_manager_test.go
@@ -257,7 +257,7 @@ func TestChainInsertions(t *testing.T) {
 	var eventMux event.TypeMux
 	chainMan := NewChainManager(db, db, &eventMux)
 	txPool := NewTxPool(&eventMux)
-	blockMan := NewBlockProcessor(db, nil, txPool, chainMan, &eventMux)
+	blockMan := NewBlockProcessor(db, db, nil, txPool, chainMan, &eventMux)
 	chainMan.SetProcessor(blockMan)
 
 	const max = 2
@@ -303,7 +303,7 @@ func TestChainMultipleInsertions(t *testing.T) {
 	var eventMux event.TypeMux
 	chainMan := NewChainManager(db, db, &eventMux)
 	txPool := NewTxPool(&eventMux)
-	blockMan := NewBlockProcessor(db, nil, txPool, chainMan, &eventMux)
+	blockMan := NewBlockProcessor(db, db, nil, txPool, chainMan, &eventMux)
 	chainMan.SetProcessor(blockMan)
 	done := make(chan bool, max)
 	for i, chain := range chains {
diff --git a/eth/backend.go b/eth/backend.go
index 9c497a586..6fd211b35 100644
--- a/eth/backend.go
+++ b/eth/backend.go
@@ -107,9 +107,10 @@ type Ethereum struct {
 	// Channel for shutting down the ethereum
 	shutdownChan chan bool
 
-	// DB interface
-	blockDb ethutil.Database
-	stateDb ethutil.Database
+	// DB interfaces
+	blockDb ethutil.Database // Block chain database
+	stateDb ethutil.Database // State changes database
+	extraDb ethutil.Database // Extra database (txs, etc)
 
 	//*** SERVICES ***
 	// State manager for processing new blocks and managing the over all states
@@ -144,6 +145,7 @@ func New(config *Config) (*Ethereum, error) {
 	if err != nil {
 		return nil, err
 	}
+	extraDb, err := ethdb.NewLDBDatabase(path.Join(config.DataDir, "extra"))
 
 	// Perform database sanity checks
 	d, _ := blockDb.Get([]byte("ProtocolVersion"))
@@ -152,14 +154,13 @@ func New(config *Config) (*Ethereum, error) {
 		path := path.Join(config.DataDir, "blockchain")
 		return nil, fmt.Errorf("Database version mismatch. Protocol(%d / %d). `rm -rf %s`", protov, ProtocolVersion, path)
 	}
-
-	saveProtocolVersion(blockDb)
-	//ethutil.Config.Db = db
+	saveProtocolVersion(extraDb)
 
 	eth := &Ethereum{
 		shutdownChan:   make(chan bool),
 		blockDb:        blockDb,
 		stateDb:        stateDb,
+		extraDb:        extraDb,
 		eventMux:       &event.TypeMux{},
 		logger:         servlogger,
 		accountManager: config.AccountManager,
@@ -169,7 +170,7 @@ func New(config *Config) (*Ethereum, error) {
 	eth.chainManager = core.NewChainManager(blockDb, stateDb, eth.EventMux())
 	pow := ethash.New(eth.chainManager)
 	eth.txPool = core.NewTxPool(eth.EventMux())
-	eth.blockProcessor = core.NewBlockProcessor(stateDb, pow, eth.txPool, eth.chainManager, eth.EventMux())
+	eth.blockProcessor = core.NewBlockProcessor(stateDb, extraDb, pow, eth.txPool, eth.chainManager, eth.EventMux())
 	eth.chainManager.SetProcessor(eth.blockProcessor)
 	eth.whisper = whisper.New()
 	eth.miner = miner.New(eth, pow, config.MinerThreads)
@@ -230,6 +231,7 @@ func (s *Ethereum) Whisper() *whisper.Whisper            { return s.whisper }
 func (s *Ethereum) EventMux() *event.TypeMux             { return s.eventMux }
 func (s *Ethereum) BlockDb() ethutil.Database            { return s.blockDb }
 func (s *Ethereum) StateDb() ethutil.Database            { return s.stateDb }
+func (s *Ethereum) ExtraDb() ethutil.Database            { return s.extraDb }
 func (s *Ethereum) IsListening() bool                    { return true } // Always listening
 func (s *Ethereum) PeerCount() int                       { return s.net.PeerCount() }
 func (s *Ethereum) Peers() []*p2p.Peer                   { return s.net.Peers() }
-- 
GitLab