unit testing place for review

This commit is contained in:
Dustin Brickwood 2018-06-13 13:07:17 -04:00
parent 0f9bbd2e62
commit 13258b70ac
77 changed files with 7893 additions and 230 deletions

2
.gitignore vendored
View file

@ -49,3 +49,5 @@ $HOME
# Remove Shyft Data # Remove Shyft Data
shyftData/* shyftData/*
shyft-cli/web3/token_test/node_modules
shyft-cli/web3/transfer-through-master/node_modules

View file

@ -1,5 +1,5 @@
language: go language: go
go_import_path: github.com/ethereum/go-ethereum go_import_path: github.com/ShyftNetwork/shyft_go-ethereum
sudo: false sudo: false
matrix: matrix:
include: include:
@ -151,7 +151,7 @@ matrix:
- export GOROOT=`pwd`/go - export GOROOT=`pwd`/go
- export GOPATH=$HOME/go - export GOPATH=$HOME/go
script: script:
# Build the Android archive and upload it to Maven Central and Azure # Build the Android archive and upload it gto Maven Central and Azure
- curl https://dl.google.com/android/repository/android-ndk-r15c-linux-x86_64.zip -o android-ndk-r15c.zip - curl https://dl.google.com/android/repository/android-ndk-r15c-linux-x86_64.zip -o android-ndk-r15c.zip
- unzip -q android-ndk-r15c.zip && rm android-ndk-r15c.zip - unzip -q android-ndk-r15c.zip && rm android-ndk-r15c.zip
- mv android-ndk-r15c $HOME - mv android-ndk-r15c $HOME
@ -178,6 +178,7 @@ matrix:
- gem uninstall cocoapods -a -x - gem uninstall cocoapods -a -x
- gem install cocoapods - gem install cocoapods
- mv ~/.cocoapods/repos/master ~/.cocoapods/repos/master.bak - mv ~/.cocoapods/repos/master ~/.cocoapods/repos/master.bak
- sed -i '.bak' 's/repo.join/!repo.join/g' $(dirname `gem which cocoapods`)/cocoapods/sources_manager.rb - sed -i '.bak' 's/repo.join/!repo.join/g' $(dirname `gem which cocoapods`)/cocoapods/sources_manager.rb
- if [ "$TRAVIS_PULL_REQUEST" = "false" ]; then git clone --depth=1 https://github.com/CocoaPods/Specs.git ~/.cocoapods/repos/master && pod setup --verbose; fi - if [ "$TRAVIS_PULL_REQUEST" = "false" ]; then git clone --depth=1 https://github.com/CocoaPods/Specs.git ~/.cocoapods/repos/master && pod setup --verbose; fi
@ -201,9 +202,9 @@ matrix:
script: script:
- go run build/ci.go purge -store gethstore/builds -days 14 - go run build/ci.go purge -store gethstore/builds -days 14
notifications: # notifications:
webhooks: # webhooks:
urls: # urls:
- https://webhooks.gitter.im/e/e09ccdce1048c5e03445 # - https://webhooks.gitter.im/e/e09ccdce1048c5e03445
on_success: change # on_success: change
on_failure: always # on_failure: always

View file

@ -6,7 +6,7 @@ Official golang implementation of the Ethereum protocol.
https://camo.githubusercontent.com/915b7be44ada53c290eb157634330494ebe3e30a/68747470733a2f2f676f646f632e6f72672f6769746875622e636f6d2f676f6c616e672f6764646f3f7374617475732e737667 https://camo.githubusercontent.com/915b7be44ada53c290eb157634330494ebe3e30a/68747470733a2f2f676f646f632e6f72672f6769746875622e636f6d2f676f6c616e672f6764646f3f7374617475732e737667
)](https://godoc.org/github.com/ethereum/go-ethereum) )](https://godoc.org/github.com/ethereum/go-ethereum)
[![Go Report Card](https://goreportcard.com/badge/github.com/ethereum/go-ethereum)](https://goreportcard.com/report/github.com/ethereum/go-ethereum) [![Go Report Card](https://goreportcard.com/badge/github.com/ethereum/go-ethereum)](https://goreportcard.com/report/github.com/ethereum/go-ethereum)
[![Travis](https://travis-ci.org/ethereum/go-ethereum.svg?branch=master)](https://travis-ci.org/ethereum/go-ethereum) [![Build Status](https://travis-ci.org/ShyftNetwork/shyft_go-ethereum.svg?branch=master)](https://travis-ci.org/ShyftNetwork/shyft_go-ethereum)
[![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ethereum/go-ethereum?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge) [![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ethereum/go-ethereum?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge)
Automated builds are available for stable releases and the unstable master branch. Automated builds are available for stable releases and the unstable master branch.
@ -95,7 +95,7 @@ Specifying the `--testnet` flag however will reconfigure your Geth instance a bi
`geth attach <datadir>/testnet/geth.ipc`. Windows users are not affected by this. `geth attach <datadir>/testnet/geth.ipc`. Windows users are not affected by this.
* Instead of connecting the main Ethereum network, the client will connect to the test network, * Instead of connecting the main Ethereum network, the client will connect to the test network,
which uses different P2P bootnodes, different network IDs and genesis states. which uses different P2P bootnodes, different network IDs and genesis states.
*Note: Although there are some internal protective measures to prevent transactions from crossing *Note: Although there are some internal protective measures to prevent transactions from crossing
over between the main network and test network, you should make sure to always use separate accounts over between the main network and test network, you should make sure to always use separate accounts
for play-money and real-money. Unless you manually move accounts, Geth will by default correctly for play-money and real-money. Unless you manually move accounts, Geth will by default correctly
@ -277,6 +277,16 @@ Which will start mining blocks and transactions on a single CPU thread, creditin
the account specified by `--etherbase`. You can further tune the mining by changing the default gas the account specified by `--etherbase`. You can further tune the mining by changing the default gas
limit blocks converge to (`--targetgaslimit`) and the price transactions are accepted at (`--gasprice`). limit blocks converge to (`--targetgaslimit`) and the price transactions are accepted at (`--gasprice`).
## SHYFT NOTES
#### CLI
Run `./shyft-geth.sh` with one of the following flags:
- `--setup` - Setups postgres and the shyft chain db.
- `--start` - Starts geth.
- `--reset` - Drops postgress and chain db, and reinstantiates both.
- `--js [web3 filename]` - Executes web3 calls with a passed file name. If the file name is `sendTransactions.js`, `./shyft-geth.sh --js sendTransactions`.
## Contribution ## Contribution
Thank you for considering to help out with the source code! We welcome contributions from Thank you for considering to help out with the source code! We welcome contributions from

View file

@ -12,5 +12,7 @@ import (
func main() { func main() {
router := NewRouter() router := NewRouter()
log.Fatal(http.ListenAndServe(":8080", handlers.CORS(handlers.AllowedHeaders([]string{"X-Requested-With", "Content-Type", "Authorization"}), handlers.AllowedMethods([]string{"GET", "POST", "PUT", "HEAD", "OPTIONS"}), handlers.AllowedOrigins([]string{"*"}))(router))) port := "8080"
log.Printf("Listening on port " + " " + port)
log.Fatal(http.ListenAndServe(":"+port, handlers.CORS(handlers.AllowedHeaders([]string{"X-Requested-With", "Content-Type", "Authorization"}), handlers.AllowedMethods([]string{"GET", "POST", "PUT", "HEAD", "OPTIONS"}), handlers.AllowedOrigins([]string{"*"}))(router)))
} }

View file

@ -38,7 +38,6 @@ import (
"github.com/ethereum/go-ethereum/trie" "github.com/ethereum/go-ethereum/trie"
"github.com/syndtr/goleveldb/leveldb/util" "github.com/syndtr/goleveldb/leveldb/util"
"gopkg.in/urfave/cli.v1" "gopkg.in/urfave/cli.v1"
"database/sql"
) )
var ( var (
@ -169,13 +168,7 @@ func initGenesis(ctx *cli.Context) error {
if err != nil { if err != nil {
utils.Fatalf("Failed to open database: %v", err) utils.Fatalf("Failed to open database: %v", err)
} }
// @NOTE:shyft instantiate BlockExplorerDB here _, hash, err := core.SetupGenesisBlock(chaindb, genesis)
connStr := "user=postgres dbname=shyftdb sslmode=disable"
blockExplorerDb, err := sql.Open("postgres", connStr)
if err != nil {
return nil
}
_, hash, err := core.SetupGenesisBlock(chaindb, genesis, blockExplorerDb)
if err != nil { if err != nil {
utils.Fatalf("Failed to write genesis block: %v", err) utils.Fatalf("Failed to write genesis block: %v", err)
} }
@ -321,6 +314,7 @@ func copyDb(ctx *cli.Context) error {
syncmode := *utils.GlobalTextMarshaler(ctx, utils.SyncModeFlag.Name).(*downloader.SyncMode) syncmode := *utils.GlobalTextMarshaler(ctx, utils.SyncModeFlag.Name).(*downloader.SyncMode)
dl := downloader.New(syncmode, chainDb, new(event.TypeMux), chain, nil, nil) dl := downloader.New(syncmode, chainDb, new(event.TypeMux), chain, nil, nil)
// Create a source peer to satisfy downloader requests from // Create a source peer to satisfy downloader requests from
db, err := ethdb.NewLDBDatabase(ctx.Args().First(), ctx.GlobalInt(utils.CacheFlag.Name), 256) db, err := ethdb.NewLDBDatabase(ctx.Args().First(), ctx.GlobalInt(utils.CacheFlag.Name), 256)
if err != nil { if err != nil {

View file

@ -57,9 +57,6 @@ import (
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
whisper "github.com/ethereum/go-ethereum/whisper/whisperv5" whisper "github.com/ethereum/go-ethereum/whisper/whisperv5"
"gopkg.in/urfave/cli.v1" "gopkg.in/urfave/cli.v1"
// @shyft
"database/sql"
) )
var ( var (
@ -1219,7 +1216,7 @@ func MakeChain(ctx *cli.Context, stack *node.Node) (chain *core.BlockChain, chai
var err error var err error
chainDb = MakeChainDatabase(ctx, stack) chainDb = MakeChainDatabase(ctx, stack)
config, _, err := core.SetupGenesisBlock(chainDb, MakeGenesis(ctx), nil) config, _, err := core.SetupGenesisBlock(chainDb, MakeGenesis(ctx))
if err != nil { if err != nil {
Fatalf("%v", err) Fatalf("%v", err)
} }
@ -1252,14 +1249,8 @@ func MakeChain(ctx *cli.Context, stack *node.Node) (chain *core.BlockChain, chai
} }
vmcfg := vm.Config{EnablePreimageRecording: ctx.GlobalBool(VMEnableDebugFlag.Name)} vmcfg := vm.Config{EnablePreimageRecording: ctx.GlobalBool(VMEnableDebugFlag.Name)}
// @NOTE:shyft instantiate BlockExplorerDB here?
connStr := "user=postgres dbname=shyftdb sslmode=disable"
blockExplorerDb, err := sql.Open("postgres", connStr)
if err != nil {
return nil, nil
}
fmt.Println("Calling NewBlock CHAIN in flags.go ******************************") fmt.Println("Calling NewBlock CHAIN in flags.go ******************************")
chain, err = core.NewBlockChain(chainDb, blockExplorerDb,cache, config, engine, vmcfg) chain, err = core.NewBlockChain(chainDb,cache, config, engine, vmcfg)
if err != nil { if err != nil {
Fatalf("Can't create BlockChain: %v", err) Fatalf("Can't create BlockChain: %v", err)
} }

View file

@ -45,7 +45,7 @@ HTTPHost = "127.0.0.1"
HTTPPort = 8545 HTTPPort = 8545
HTTPCors = ["*"] HTTPCors = ["*"]
HTTPVirtualHosts = ["localhost"] HTTPVirtualHosts = ["localhost"]
HTTPModules = ["net", "web3", "eth", "shh"] HTTPModules = ["net", "web3", "eth", "shh", "admin", "debug"]
WSPort = 8546 WSPort = 8546
WSModules = ["net", "web3", "eth", "shh"] WSModules = ["net", "web3", "eth", "shh"]

View file

@ -31,7 +31,6 @@ import (
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/log"
set "gopkg.in/fatih/set.v0" set "gopkg.in/fatih/set.v0"
) )
@ -565,6 +564,5 @@ func accumulateRewards(config *params.ChainConfig, state *state.StateDB, header
if (config.IsShyftNetwork(header.Number)) { if (config.IsShyftNetwork(header.Number)) {
state.AddBalance(ShyftNetworkConduitAddress, ShyftNetworkBlockReward) state.AddBalance(ShyftNetworkConduitAddress, ShyftNetworkBlockReward)
log.Info("ShyftNetwork")
} }
} }

View file

@ -46,9 +46,6 @@ import (
"github.com/ethereum/go-ethereum/trie" "github.com/ethereum/go-ethereum/trie"
"github.com/hashicorp/golang-lru" "github.com/hashicorp/golang-lru"
"gopkg.in/karalabe/cookiejar.v2/collections/prque" "gopkg.in/karalabe/cookiejar.v2/collections/prque"
// @shyft
"database/sql"
) )
var ( var (
@ -96,7 +93,6 @@ type BlockChain struct {
cacheConfig *CacheConfig // Cache configuration for pruning cacheConfig *CacheConfig // Cache configuration for pruning
db ethdb.Database // Low level persistent database to store final content in db ethdb.Database // Low level persistent database to store final content in
blockExplorerDb *sql.DB
triegc *prque.Prque // Priority queue mapping block numbers to tries to gc triegc *prque.Prque // Priority queue mapping block numbers to tries to gc
gcproc time.Duration // Accumulates canonical block processing for trie dumping gcproc time.Duration // Accumulates canonical block processing for trie dumping
@ -141,8 +137,7 @@ type BlockChain struct {
// NewBlockChain returns a fully initialised block chain using information // NewBlockChain returns a fully initialised block chain using information
// available in the database. It initialises the default Ethereum Validator and // available in the database. It initialises the default Ethereum Validator and
// Processor. // Processor.
func NewBlockChain(db ethdb.Database, blockExplorerDb *sql.DB, cacheConfig *CacheConfig, chainConfig *params.ChainConfig, engine consensus.Engine, vmConfig vm.Config) (*BlockChain, error) { func NewBlockChain(db ethdb.Database, cacheConfig *CacheConfig, chainConfig *params.ChainConfig, engine consensus.Engine, vmConfig vm.Config) (*BlockChain, error) {
fmt.Printf("+++++++++++++++++core/blockchain.GO+++++++++++++++++++++++++NewBlockChain()")
if cacheConfig == nil { if cacheConfig == nil {
cacheConfig = &CacheConfig{ cacheConfig = &CacheConfig{
TrieNodeLimit: 256 * 1024 * 1024, TrieNodeLimit: 256 * 1024 * 1024,
@ -159,7 +154,6 @@ func NewBlockChain(db ethdb.Database, blockExplorerDb *sql.DB, cacheConfig *Cach
chainConfig: chainConfig, chainConfig: chainConfig,
cacheConfig: cacheConfig, cacheConfig: cacheConfig,
db: db, db: db,
blockExplorerDb: blockExplorerDb,
triegc: prque.New(), triegc: prque.New(),
stateCache: state.NewDatabase(db), stateCache: state.NewDatabase(db),
quit: make(chan struct{}), quit: make(chan struct{}),
@ -908,7 +902,7 @@ func (bc *BlockChain) WriteBlockWithState(block *types.Block, receipts []*types.
return NonStatTy, err return NonStatTy, err
} }
// @NOTE:SHYFT - Write block data for block explorer // @NOTE:SHYFT - Write block data for block explorer
if err := shyftdb.WriteBlock(bc.blockExplorerDb, block, receipts); err != nil { if err := shyftdb.WriteBlock(block, receipts); err != nil {
return NonStatTy, err return NonStatTy, err
} }

View file

@ -28,9 +28,6 @@ import (
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
// @shyft
"database/sql"
) )
// So we can deterministically seed different blockchains // So we can deterministically seed different blockchains
@ -169,9 +166,7 @@ func GenerateChain(config *params.ChainConfig, parent *types.Block, engine conse
genblock := func(i int, parent *types.Block, statedb *state.StateDB) (*types.Block, types.Receipts) { genblock := func(i int, parent *types.Block, statedb *state.StateDB) (*types.Block, types.Receipts) {
// TODO(karalabe): This is needed for clique, which depends on multiple blocks. // TODO(karalabe): This is needed for clique, which depends on multiple blocks.
// It's nonetheless ugly to spin up a blockchain here. Get rid of this somehow. // It's nonetheless ugly to spin up a blockchain here. Get rid of this somehow.
connStr := "user=postgres dbname=shyftdb sslmode=disable" blockchain, _ := NewBlockChain(db, nil, config, engine, vm.Config{})
blockExplorerDb, _ := sql.Open("postgres", connStr)
blockchain, _ := NewBlockChain(db, blockExplorerDb,nil, config, engine, vm.Config{})
defer blockchain.Stop() defer blockchain.Stop()
b := &BlockGen{i: i, parent: parent, chain: blocks, chainReader: blockchain, statedb: statedb, config: config, engine: engine} b := &BlockGen{i: i, parent: parent, chain: blocks, chainReader: blockchain, statedb: statedb, config: config, engine: engine}
@ -253,9 +248,7 @@ func newCanonical(engine consensus.Engine, n int, full bool) (ethdb.Database, *B
gspec := new(Genesis) gspec := new(Genesis)
db, _ := ethdb.NewMemDatabase() db, _ := ethdb.NewMemDatabase()
genesis := gspec.MustCommit(db) genesis := gspec.MustCommit(db)
connStr := "user=postgres dbname=shyftdb sslmode=disable" blockchain, _ := NewBlockChain(db, nil, params.AllEthashProtocolChanges, engine, vm.Config{})
blockExplorerDb, _ := sql.Open("postgres", connStr)
blockchain, _ := NewBlockChain(db, blockExplorerDb, nil, params.AllEthashProtocolChanges, engine, vm.Config{})
// Create and inject the requested chain // Create and inject the requested chain
if n == 0 { if n == 0 {
return db, blockchain, nil return db, blockchain, nil

View file

@ -35,6 +35,7 @@ import (
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/rlp" "github.com/ethereum/go-ethereum/rlp"
"github.com/ethereum/go-ethereum/shyftdb"
"database/sql" "database/sql"
"strconv" "strconv"
"time" "time"
@ -142,13 +143,9 @@ func (e *GenesisMismatchError) Error() string {
//WriteShyftGen writes the genesis block to Shyft db //WriteShyftGen writes the genesis block to Shyft db
//@NOTE:SHYFT //@NOTE:SHYFT
func WriteShyftGen(sqldb *sql.DB, gen *Genesis, block *types.Block) { func WriteShyftGen(gen *Genesis, block *types.Block) {
if sqldb == nil {
log.Info("Initializing Shyft Postgres DB") sqldb, _ := shyftdb.DBConnection()
connStr := "user=postgres dbname=shyftdb sslmode=disable"
blockExplorerDb, _ := sql.Open("postgres", connStr)
sqldb = blockExplorerDb
}
for k := range gen.Alloc { for k := range gen.Alloc {
addr := k.String() addr := k.String()
@ -196,13 +193,9 @@ func WriteShyftGen(sqldb *sql.DB, gen *Genesis, block *types.Block) {
log.Info("Found Genesis Block") log.Info("Found Genesis Block")
}}} }}}
func WriteShyftBlockZero(sqldb *sql.DB, block *types.Block, gen *Genesis) error { func WriteShyftBlockZero(block *types.Block, gen *Genesis) error {
if sqldb == nil {
log.Info("Initializing Shyft Postgres DB") sqldb, _ := shyftdb.DBConnection()
connStr := "user=postgres dbname=shyftdb sslmode=disable"
blockExplorerDb, _ := sql.Open("postgres", connStr)
sqldb = blockExplorerDb
}
coinbase := block.Header().Coinbase.String() coinbase := block.Header().Coinbase.String()
number := block.Header().Number.String() number := block.Header().Number.String()
@ -252,7 +245,7 @@ func WriteShyftBlockZero(sqldb *sql.DB, block *types.Block, gen *Genesis) error
// error is a *params.ConfigCompatError and the new, unwritten config is returned. // error is a *params.ConfigCompatError and the new, unwritten config is returned.
// //
// The returned chain configuration is never nil. // The returned chain configuration is never nil.
func SetupGenesisBlock(db ethdb.Database, genesis *Genesis, sqldb *sql.DB) (*params.ChainConfig, common.Hash, error) { func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig, common.Hash, error) {
if genesis != nil && genesis.Config == nil { if genesis != nil && genesis.Config == nil {
return params.AllEthashProtocolChanges, common.Hash{}, errGenesisNoConfig return params.AllEthashProtocolChanges, common.Hash{}, errGenesisNoConfig
} }
@ -267,9 +260,9 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis, sqldb *sql.DB) (*par
} }
block, err := genesis.Commit(db) block, err := genesis.Commit(db)
//@NOTE:SHYFT WRITE TO BLOCK ZERO DB //@NOTE:SHYFT WRITE TO BLOCK ZERO DB
WriteShyftBlockZero(sqldb, block, genesis) WriteShyftBlockZero(block, genesis)
//@NOTE:SHYFT WRITE TO DB //@NOTE:SHYFT WRITE TO DB
WriteShyftGen(sqldb, genesis, block) WriteShyftGen(genesis, block)
return genesis.Config, block.Hash(), err return genesis.Config, block.Hash(), err
} }

View file

@ -532,6 +532,11 @@ func (api *PrivateDebugAPI) computeStateDB(block *types.Block, reexec uint64) (*
// TraceTransaction returns the structured logs created during the execution of EVM // TraceTransaction returns the structured logs created during the execution of EVM
// and returns them as a JSON object. // and returns them as a JSON object.
func (api *PrivateDebugAPI) TraceTransaction(ctx context.Context, hash common.Hash, config *TraceConfig) (interface{}, error) { func (api *PrivateDebugAPI) TraceTransaction(ctx context.Context, hash common.Hash, config *TraceConfig) (interface{}, error) {
fmt.Println("\n\n\t[API LOG]", api, "\n")
fmt.Printf("%+v\n", api.config)
fmt.Println("\n")
fmt.Printf("%+v\n", api.eth)
fmt.Println("\n")
// Retrieve the transaction and assemble its EVM context // Retrieve the transaction and assemble its EVM context
tx, blockHash, _, index := core.GetTransaction(api.eth.ChainDb(), hash) tx, blockHash, _, index := core.GetTransaction(api.eth.ChainDb(), hash)
if tx == nil { if tx == nil {
@ -546,6 +551,9 @@ func (api *PrivateDebugAPI) TraceTransaction(ctx context.Context, hash common.Ha
return nil, err return nil, err
} }
// Trace the transaction and return // Trace the transaction and return
//fmt.Println("\n\n\t\tRETURN")
//fmt.Println(api.traceTx(ctx, msg, vmctx, statedb, config))
//fmt.Println("RETURN FINISHED")
return api.traceTx(ctx, msg, vmctx, statedb, config) return api.traceTx(ctx, msg, vmctx, statedb, config)
} }

View file

@ -47,9 +47,6 @@ import (
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/rlp" "github.com/ethereum/go-ethereum/rlp"
"github.com/ethereum/go-ethereum/rpc" "github.com/ethereum/go-ethereum/rpc"
// @shyft
"database/sql"
) )
type LesServer interface { type LesServer interface {
@ -76,7 +73,6 @@ type Ethereum struct {
// DB interfaces // DB interfaces
chainDb ethdb.Database // Block chain database chainDb ethdb.Database // Block chain database
blockExplorerDb *sql.DB
eventMux *event.TypeMux eventMux *event.TypeMux
engine consensus.Engine engine consensus.Engine
@ -116,16 +112,10 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
return nil, err return nil, err
} }
// @NOTE:shyft instantiate BlockExplorerDB here
// @TODO: Create Genesis Block // @TODO: Create Genesis Block
// @NOTE:shyft instantiate BlockExplorerDB here?
connStr := "user=postgres dbname=shyftdb sslmode=disable"
blockExplorerDb, err := sql.Open("postgres", connStr)
if err != nil {
return nil, err
}
stopDbUpgrade := upgradeDeduplicateData(chainDb) stopDbUpgrade := upgradeDeduplicateData(chainDb)
chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis, blockExplorerDb) chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis)
if _, ok := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !ok { if _, ok := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !ok {
return nil, genesisErr return nil, genesisErr
} }
@ -134,7 +124,6 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
eth := &Ethereum{ eth := &Ethereum{
config: config, config: config,
chainDb: chainDb, chainDb: chainDb,
blockExplorerDb: blockExplorerDb,
chainConfig: chainConfig, chainConfig: chainConfig,
eventMux: ctx.EventMux, eventMux: ctx.EventMux,
accountManager: ctx.AccountManager, accountManager: ctx.AccountManager,
@ -161,7 +150,7 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
vmConfig = vm.Config{EnablePreimageRecording: config.EnablePreimageRecording} vmConfig = vm.Config{EnablePreimageRecording: config.EnablePreimageRecording}
cacheConfig = &core.CacheConfig{Disabled: config.NoPruning, TrieNodeLimit: config.TrieCache, TrieTimeLimit: config.TrieTimeout} cacheConfig = &core.CacheConfig{Disabled: config.NoPruning, TrieNodeLimit: config.TrieCache, TrieTimeLimit: config.TrieTimeout}
) )
eth.blockchain, err = core.NewBlockChain(chainDb, blockExplorerDb, cacheConfig, eth.chainConfig, eth.engine, vmConfig) eth.blockchain, err = core.NewBlockChain(chainDb, cacheConfig, eth.chainConfig, eth.engine, vmConfig)
if err != nil { if err != nil {
return nil, err return nil, err
} }

View file

@ -496,6 +496,9 @@ func wrapError(context string, err error) error {
// CaptureStart implements the Tracer interface to initialize the tracing operation. // CaptureStart implements the Tracer interface to initialize the tracing operation.
func (jst *Tracer) CaptureStart(from common.Address, to common.Address, create bool, input []byte, gas uint64, value *big.Int) error { func (jst *Tracer) CaptureStart(from common.Address, to common.Address, create bool, input []byte, gas uint64, value *big.Int) error {
//fmt.Println("\n\n\t\t type: ", reflect.TypeOf(input))
fmt.Println("\t\t [TRACER INPUT]:", input)
fmt.Println("\t\t [TRACER INPUT STRING]:", string(input[:len(input)]), "\n\n")
jst.ctx["type"] = "CALL" jst.ctx["type"] = "CALL"
if create { if create {
jst.ctx["type"] = "CREATE" jst.ctx["type"] = "CREATE"
@ -564,6 +567,9 @@ func (jst *Tracer) CaptureFault(env *vm.EVM, pc uint64, op vm.OpCode, gas, cost
// CaptureEnd is called after the call finishes to finalize the tracing. // CaptureEnd is called after the call finishes to finalize the tracing.
func (jst *Tracer) CaptureEnd(output []byte, gasUsed uint64, t time.Duration, err error) error { func (jst *Tracer) CaptureEnd(output []byte, gasUsed uint64, t time.Duration, err error) error {
//fmt.Println("\n\n\t\t", reflect.TypeOf(output))
fmt.Println("\t\t [TRACER OUTPUT]:", output[:len(output)])
fmt.Println("\t\t [TRACER OUTPUT STRING]:", string(output[:len(output)]), "\n\n")
jst.ctx["output"] = output jst.ctx["output"] = output
jst.ctx["gasUsed"] = gasUsed jst.ctx["gasUsed"] = gasUsed
jst.ctx["time"] = t.String() jst.ctx["time"] = t.String()

View file

@ -84,7 +84,7 @@ func New(ctx *node.ServiceContext, config *eth.Config) (*LightEthereum, error) {
if err != nil { if err != nil {
return nil, err return nil, err
} }
chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis, nil) chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis)
if _, isCompat := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !isCompat { if _, isCompat := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !isCompat {
return nil, genesisErr return nil, genesisErr
} }

View file

@ -38,12 +38,3 @@ CREATE TABLE IF NOT EXISTS accounts (
balance numeric, balance numeric,
txCountAccount numeric txCountAccount numeric
); );
CREATE TABLE IF NOT EXISTS contracts (
txHash text
);
CREATE TABLE IF NOT EXISTS mined_blocks (
blockNumber bigint,
addr text
);

View file

@ -1,5 +1,3 @@
DROP TABLE txs; DROP TABLE txs;
DROP TABLE blocks; DROP TABLE blocks;
DROP TABLE accounts; DROP TABLE accounts;
DROP TABLE contracts;
DROP TABLE mined_blocks;

View file

@ -1 +1,4 @@
#!/bin/bash
cd ./shyft-cli/postgres_setup
psql -U postgres -d shyftdb -f drop_tables.psql psql -U postgres -d shyftdb -f drop_tables.psql

View file

@ -1 +1,4 @@
#!/bin/bash
cd ./shyft-cli/postgres_setup
psql -U postgres -d shyftdb -f create_tables.psql psql -U postgres -d shyftdb -f create_tables.psql

View file

@ -0,0 +1,4 @@
#!/bin/bash
cd ./shyft-cli/postgres_setup
psql -U postgres -f create_shyftdb.psql

View file

@ -1,4 +1,4 @@
file=$1 file=$1
echo $file echo Executing "${file}"...
runthing="./build/bin/geth --exec 'loadScript(\""$file"\")' attach http://127.0.0.1:8545" runthing="./build/bin/geth --exec 'loadScript(\""$file"\")' attach http://127.0.0.1:8545"
eval $runthing eval $runthing

17
shyft-cli/setup.sh Normal file
View file

@ -0,0 +1,17 @@
#!/bin/bash
if ! psql -lqt | cut -d \| -f 1 | grep -qw shyftdb; then # Check if db is instantiated
echo Creating postgres db...
sh ./shyft-cli/postgres_setup/initdb.sh && # Init DB
echo Successfully created postgres db! &&
sh ./shyft-cli/postgres_setup/init_tables.sh && # Init tables
sh ./shyft-cli/resetShyftGeth.sh && # Reset geth data
sh ./shyft-cli/initShyftGeth.sh # Init Shyft Geth
else
echo Postgres DB found!
sh ./shyft-cli/postgres_setup/drop_tables.sh && # Drop tables
sh ./shyft-cli/postgres_setup/init_tables.sh && # Init tables
sh ./shyft-cli/resetShyftGeth.sh && # Reset geth data
sh ./shyft-cli/initShyftGeth.sh # Init Shyft Geth
fi

View file

@ -0,0 +1,12 @@
#!/bin/bash
if ! psql -lqt | cut -d \| -f 1 | grep -qw shyftdb; then
echo Creating postgres db...
sh ./shyft-cli/postgres_setup/initdb.sh &&
echo Successfully created postgres db!
fi
sh ./shyft-cli/postgres_setup/drop_tables.sh && # Drop tables
sh ./shyft-cli/postgres_setup/init_tables.sh && # Init tables
sh ./shyft-cli/resetShyftGeth.sh && # Reset geth data
sh ./shyft-cli/initShyftGeth.sh # Init Shyft Geth

View file

@ -0,0 +1,31 @@
var _message = "Hello" ;
var inboxContract = web3.eth.contract([{"constant":false,"inputs":[{"name":"_newMessage","type":"string"}],"name":"setMessage","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"message","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"_message","type":"string"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"name":"_newMessage","type":"string"}],"name":"EventMessage","type":"event"}]);
var inbox = inboxContract.new(
_message,
{
from: web3.eth.accounts[0],
data: '0x6060604052341561000f57600080fd5b604051610454380380610454833981016040528080518201919050508060009080519060200190610041929190610048565b50506100ed565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f1061008957805160ff19168380011785556100b7565b828001600101855582156100b7579182015b828111156100b657825182559160200191906001019061009b565b5b5090506100c491906100c8565b5090565b6100ea91905b808211156100e65760008160009055506001016100ce565b5090565b90565b610358806100fc6000396000f30060606040526000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff168063368b877214610048578063e21f37ce146100a557600080fd5b341561005357600080fd5b6100a3600480803590602001908201803590602001908080601f01602080910402602001604051908101604052809392919081815260200183838082843782019150505050505091905050610133565b005b34156100b057600080fd5b6100b86101e9565b6040518080602001828103825283818151815260200191508051906020019080838360005b838110156100f85780820151818401526020810190506100dd565b50505050905090810190601f1680156101255780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b8060009080519060200190610149929190610287565b507f2ec385c52f10e65de137fbbeb2582bb0f4a8460a2163012971e923d179d73ea7816040518080602001828103825283818151815260200191508051906020019080838360005b838110156101ac578082015181840152602081019050610191565b50505050905090810190601f1680156101d95780820380516001836020036101000a031916815260200191505b509250505060405180910390a150565b60008054600181600116156101000203166002900480601f01602080910402602001604051908101604052809291908181526020018280546001816001161561010002031660029004801561027f5780601f106102545761010080835404028352916020019161027f565b820191906000526020600020905b81548152906001019060200180831161026257829003601f168201915b505050505081565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106102c857805160ff19168380011785556102f6565b828001600101855582156102f6579182015b828111156102f55782518255916020019190600101906102da565b5b5090506103039190610307565b5090565b61032991905b8082111561032557600081600090555060010161030d565b5090565b905600a165627a7a72305820c83fcf90975f9c6996cf8dde1a2a1f4fab1f408588a2f8587487833ac98665630029',
gas: '4700000'
}, function (e, contract){
if(!e) {
// NOTE: The callback will fire twice!
// Once the contract has the transactionHash property set and once its deployed on an address.
// e.g. check tx hash on the first call (transaction send)
if(!contract.address) {
console.log("TX hash:")
console.log(contract.transactionHash) // The hash of the transaction, which deploys the contract
} else {
console.log("Contract address:")
console.log(contract.address) // the contract address
contract.methods.setMessage('New').call({from: web3.eth.accounts[0]}, function(error, result){
if (error) {
console.log(error)
} else {
console.log('[METHOD RESULT]: ', result)
}
});
}
}
});

View file

@ -0,0 +1,58 @@
var testContract = web3.eth.contract([{"constant":true,"inputs":[],"name":"owner","outputs":[{"name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[],"name":"live","outputs":[{"name":"success","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"inputs":[],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"name":"_bool","type":"bool"}],"name":"Live","type":"event"}]);
var test = testContract.new(
{
from: web3.eth.accounts[0],
data: '0x6060604052341561000f57600080fd5b336000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506101698061005e6000396000f30060606040526004361061004c576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff1680638da5cb5b14610051578063957aa58c146100a6575b600080fd5b341561005c57600080fd5b6100646100d3565b604051808273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200191505060405180910390f35b34156100b157600080fd5b6100b96100f8565b604051808215151515815260200191505060405180910390f35b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1681565b60007f63f89985c88a92552c6e2ce4d4e46e9fbb7a06168c4536e662261decae02f9e76001604051808215151515815260200191505060405180910390a160019050905600a165627a7a7230582091089d445770c1c9bb2f0f86f6c0b8552ef59af41930e1f7ecfac34326b20e590029',
gas: '4700000'
}, function (e, contract){
if (e) {
console.log("Error: ", e)
}
console.log("TX Hash:", contract.transactionHash)
if (typeof contract.address !== 'undefined') {
console.log('Contract address: ' + contract.address)
console.log('TransactionHash: ' + contract.transactionHash);
interact(contract.address);
}
});
function waitBlock(callback) {
function innerWaitBlock() {
var receipt = web3.eth.getTransactionReceipt(test.transactionHash);
if (receipt && receipt.contractAddress) {
callback(receipt);
} else {
// console.log("Waiting a mined block to include your contract... currently in block " + web3.eth.blockNumber);
setTimeout(innerWaitBlock(), 4000);
}
}
innerWaitBlock();
}
waitBlock(function (receipt) {
// do stuff here now that the contract has been deployed
console.log("[Receipt] Contract Address: ", receipt.contract.address)
});
function interact(addr) {
var contract = testContract.at(addr);
contract.live({
from: web3.eth.accounts[0],
gas: '4700000'
}, function (e, res) {
if (e) {
console.log(e)
}
console.log('Live TxHash: ', res)
});
contract.live.call({
from: web3.eth.accounts[0],
gas: '4700000'
}, function (e, res) {
if (e) {
console.log(e)
}
console.log('Live Response: ', res)
})
}

View file

@ -0,0 +1,32 @@
`npm install`
run `node deploy.js` to deploy the contract.
this will log out a contract in the geth logs.
set the ADDR environment variable to this contract address.
ie `export ADDR=<contract_addr>`
then run `node calltx.js`
(TODO: trigger the `calltx.js` function in the `deploy.js` file immediately)
## TEST GREETERS / contract to contract txes
First run `node deploy_greeter_contracts.js`
this will log the address of the greeter and proxygreeter contracts and run various transactions on the contracts.
To re-run transactions on these contracts you'll need to set the env variables, using the addresses logged during the `node deploy_greeter_contracts.js` process:
```
export GREETER=<greeter_address>
export PROXYGREETER=<proxy_greeter_address>
```
Then we can run:
`node call_greeter_fns.js`
This will run several write transactions, the hash will be logged to the geth logs.
To run trace transaction on these txes, run `./build/bin/geth attach http://127.0.0.1:8545`, which will open an admin console (similar to a node console). Then run `debug.traceTransaction("<tx_hash>", {tracer: "callTracer"})`, or `debug.traceTransaction("<tx_hash>")`

View file

@ -0,0 +1,7 @@
var Web3 = require('web3')
var web3 = new Web3(new Web3.providers.HttpProvider('http://127.0.0.1:8545'))
var sendTxes = require('./call_greeter_fns').sendTxes
var greeter_addr = process.env.GREETER
var proxy_greeter_addr = process.env.PROXYGREETER
sendTxes(web3, greeter_addr, proxy_greeter_addr)

View file

@ -0,0 +1,83 @@
var greetings = [
'My new greeting',
'greeting 3',
'greeting four',
'greeting five'
]
sendTxes = async (web3, greeter, proxyGreeter) => {
var greeterContractAddr = greeter
var proxyGreeterAddr = proxyGreeter
var greeterContract = web3.eth
.contract([
{
constant: false,
inputs: [{ name: '_greeting', type: 'string' }],
name: 'setGreeting',
outputs: [],
payable: false,
stateMutability: 'nonpayable',
type: 'function'
},
{
constant: true,
inputs: [],
name: 'greet',
outputs: [{ name: '', type: 'string' }],
payable: false,
stateMutability: 'view',
type: 'function'
},
{
constant: true,
inputs: [],
name: 'greeting',
outputs: [{ name: '', type: 'string' }],
payable: false,
stateMutability: 'view',
type: 'function'
},
{
inputs: [{ name: '_greeting', type: 'string' }],
payable: false,
stateMutability: 'nonpayable',
type: 'constructor'
}
])
.at(greeterContractAddr)
var proxygreeterContract = web3.eth
.contract([
{
constant: false,
inputs: [{ name: '_greeting', type: 'string' }],
name: 'proxySetGreeting',
outputs: [],
payable: false,
stateMutability: 'nonpayable',
type: 'function'
},
{
inputs: [{ name: '_address', type: 'address' }],
payable: false,
stateMutability: 'nonpayable',
type: 'constructor'
}
])
.at(proxyGreeterAddr)
for (i = 0; i < greetings.length; i++) {
console.log(greetings[i])
var res = await proxygreeterContract.proxySetGreeting.sendTransaction(
greetings[i],
{ from: '0x43EC6d0942f7fAeF069F7F63D0384a27f529B062', gas: 3000000 }
)
console.log(res)
await sleep(10000)
console.log(greeterContract.greet())
}
}
function sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms))
}
module.exports = { sendTxes: sendTxes }

View file

@ -0,0 +1,22 @@
var Web3 = require('web3')
var web3 = new Web3(new Web3.providers.HttpProvider("http://127.0.0.1:8545"));
var initialSupply = 1000000000000000
var mytokenContract = web3.eth.contract([{"constant":true,"inputs":[{"name":"","type":"address"}],"name":"balanceOf","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"_to","type":"address"},{"name":"_value","type":"uint256"}],"name":"transfer","outputs":[{"name":"_bool","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"inputs":[{"name":"initialSupply","type":"uint256"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]);
var mytoken = mytokenContract.new(
initialSupply,
{
from: web3.eth.accounts[0],
data: '0x6060604052341561000f57600080fd5b60405160208061032f83398101604052808051906020019091905050806000803373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550506102b18061007e6000396000f30060606040526000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806370a0823114610048578063a9059cbb1461009557600080fd5b341561005357600080fd5b61007f600480803573ffffffffffffffffffffffffffffffffffffffff169060200190919050506100ef565b6040518082815260200191505060405180910390f35b34156100a057600080fd5b6100d5600480803573ffffffffffffffffffffffffffffffffffffffff16906020019091908035906020019091905050610107565b604051808215151515815260200191505060405180910390f35b60006020528060005260406000206000915090505481565b6000816000803373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541015151561015657600080fd5b6000808473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054826000808673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205401101515156101e357600080fd5b816000803373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008282540392505081905550816000808573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000206000828254019250508190555060019050929150505600a165627a7a723058207dba9cbbfe34ea34b40caa5e6d2b53f9194dafa2420207342bebe3a5c949840c0029',
gas: '4700000'
}, function (e, contract) {
if (e) console.log("err1", e);
if (typeof contract.address !== 'undefined') {
console.log('Contract mined! address: ' + contract.address + ' transactionHash: ' + contract.transactionHash);
var a = mytokenContract.at(contract.address);
a.transfer.sendTransaction(web3.eth.accounts[0], 5000000, {from: web3.eth.accounts[0]}, function (err, res) {
if (err) console.log("err", err);
console.log(res)
})
}
});

View file

@ -0,0 +1,94 @@
var Web3 = require('web3')
var web3 = new Web3(new Web3.providers.HttpProvider('http://127.0.0.1:8545'))
var sendTxes = require('./call_greeter_fns').sendTxes
// deploy javascript adapted from the remix templates
var _greeting = 'Greeting one'
var greeterAddress
var greeterContract = web3.eth.contract([
{
constant: false,
inputs: [{ name: '_greeting', type: 'string' }],
name: 'setGreeting',
outputs: [],
payable: false,
stateMutability: 'nonpayable',
type: 'function'
},
{
constant: true,
inputs: [],
name: 'greet',
outputs: [{ name: '', type: 'string' }],
payable: false,
stateMutability: 'view',
type: 'function'
},
{
inputs: [{ name: '_greeting', type: 'string' }],
payable: false,
stateMutability: 'nonpayable',
type: 'constructor'
}
])
var greeterAddr
var proxyGreeterAddr
var greeter = greeterContract.new(
_greeting,
{
from: web3.eth.accounts[0],
data:
'0x608060405234801561001057600080fd5b5060405161041c38038061041c833981018060405281019080805182019291905050508060009080519060200190610049929190610050565b50506100f5565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f1061009157805160ff19168380011785556100bf565b828001600101855582156100bf579182015b828111156100be5782518255916020019190600101906100a3565b5b5090506100cc91906100d0565b5090565b6100f291905b808211156100ee5760008160009055506001016100d6565b5090565b90565b610318806101046000396000f30060806040526004361061004c576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff168063a413686214610051578063cfae3217146100ba575b600080fd5b34801561005d57600080fd5b506100b8600480360381019080803590602001908201803590602001908080601f016020809104026020016040519081016040528093929190818152602001838380828437820191505050505050919291929050505061014a565b005b3480156100c657600080fd5b506100cf6101a5565b6040518080602001828103825283818151815260200191508051906020019080838360005b8381101561010f5780820151818401526020810190506100f4565b50505050905090810190601f16801561013c5780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b33600160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555080600090805190602001906101a1929190610247565b5050565b606060008054600181600116156101000203166002900480601f01602080910402602001604051908101604052809291908181526020018280546001816001161561010002031660029004801561023d5780601f106102125761010080835404028352916020019161023d565b820191906000526020600020905b81548152906001019060200180831161022057829003601f168201915b5050505050905090565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f1061028857805160ff19168380011785556102b6565b828001600101855582156102b6579182015b828111156102b557825182559160200191906001019061029a565b5b5090506102c391906102c7565b5090565b6102e991905b808211156102e55760008160009055506001016102cd565b5090565b905600a165627a7a7230582006a0234c8e31f8b96b20b9fb2f0ddddde4463524c8091978b490c87277170b620029',
gas: '4700000'
},
function(e, contract) {
if (typeof contract.address !== 'undefined') {
var _address = contract.address
console.log(
'Greeter Contract mined! address: ' +
_address +
' transactionHash: ' +
contract.transactionHash
)
greeterAddr = _address
var proxygreeterContract = web3.eth.contract([
{
constant: false,
inputs: [{ name: '_greeting', type: 'string' }],
name: 'proxySetGreeting',
outputs: [],
payable: false,
stateMutability: 'nonpayable',
type: 'function'
},
{
inputs: [{ name: '_address', type: 'address' }],
payable: false,
stateMutability: 'nonpayable',
type: 'constructor'
}
])
var proxygreeter = proxygreeterContract.new(
_address,
{
from: web3.eth.accounts[0],
data:
'0x608060405234801561001057600080fd5b5060405160208061026e83398101806040528101908080519060200190929190505050806000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550506101eb806100836000396000f300608060405260043610610041576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806369c92f6a14610046575b600080fd5b34801561005257600080fd5b506100ad600480360381019080803590602001908201803590602001908080601f01602080910402602001604051908101604052809392919081815260200183838082843782019150505050505091929192905050506100af565b005b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663a4136862826040518263ffffffff167c01000000000000000000000000000000000000000000000000000000000281526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561015857808201518184015260208101905061013d565b50505050905090810190601f1680156101855780820380516001836020036101000a031916815260200191505b5092505050600060405180830381600087803b1580156101a457600080fd5b505af11580156101b8573d6000803e3d6000fd5b50505050505600a165627a7a72305820946d166088750797f5bc3f5953806fd10118c88c95eac53d7aa7628997b69a310029',
gas: '4700000'
},
function(e, contract) {
if (typeof contract.address !== 'undefined') {
proxyGreeterAddr = contract.address
console.log(
'Proxy Greeter Contract mined! address: ' +
contract.address +
' transactionHash: ' +
contract.transactionHash
)
sendTxes(web3, greeterAddr, proxyGreeterAddr)
}
}
)
}
}
)

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1,43 @@
{
"name": "token_contract",
"version": "1.0.0",
"lockfileVersion": 1,
"requires": true,
"dependencies": {
"bignumber.js": {
"version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934"
},
"crypto-js": {
"version": "3.1.8",
"resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz",
"integrity": "sha1-cV8HC/YBTyrpkqmLOSkli3E/CNU="
},
"utf8": {
"version": "2.1.2",
"resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.2.tgz",
"integrity": "sha1-H6DZJw6b6FDZsFAn9jUZv0ZFfZY="
},
"web3": {
"version": "0.20.6",
"resolved": "https://registry.npmjs.org/web3/-/web3-0.20.6.tgz",
"integrity": "sha1-PpcwauAk+yThCj11yIQwJWIhUSA=",
"requires": {
"bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934",
"crypto-js": "3.1.8",
"utf8": "2.1.2",
"xhr2": "0.1.4",
"xmlhttprequest": "1.8.0"
}
},
"xhr2": {
"version": "0.1.4",
"resolved": "https://registry.npmjs.org/xhr2/-/xhr2-0.1.4.tgz",
"integrity": "sha1-f4dliEdxbbUCYyOBL4GMras4el8="
},
"xmlhttprequest": {
"version": "1.8.0",
"resolved": "https://registry.npmjs.org/xmlhttprequest/-/xmlhttprequest-1.8.0.tgz",
"integrity": "sha1-Z/4HXFwk/vOfnWX197f+dRcZaPw="
}
}
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,423 @@
{
"contractName": "Transfers2",
"abi": [
{
"constant": false,
"inputs": [
{
"name": "_addr",
"type": "address"
}
],
"name": "transfer",
"outputs": [],
"payable": true,
"stateMutability": "payable",
"type": "function"
}
],
"bytecode": "0x608060405234801561001057600080fd5b5060ed8061001f6000396000f300608060405260043610603f576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff1680631a695230146044575b600080fd5b6076600480360381019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506078565b005b8073ffffffffffffffffffffffffffffffffffffffff166108fc349081150290604051600060405180830381858888f1935050505015801560bd573d6000803e3d6000fd5b50505600a165627a7a72305820e95f74106a3328ffadd8b0adb916d92497daab65998ee73cf40afff57dc4b29b0029",
"deployedBytecode": "0x608060405260043610603f576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff1680631a695230146044575b600080fd5b6076600480360381019080803573ffffffffffffffffffffffffffffffffffffffff1690602001909291905050506078565b005b8073ffffffffffffffffffffffffffffffffffffffff166108fc349081150290604051600060405180830381858888f1935050505015801560bd573d6000803e3d6000fd5b50505600a165627a7a72305820e95f74106a3328ffadd8b0adb916d92497daab65998ee73cf40afff57dc4b29b0029",
"sourceMap": "26:106:2:-;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;26:106:2;;;;;;;",
"deployedSourceMap": "26:106:2:-;;;;;;;;;;;;;;;;;;;;;;;;49:81;;;;;;;;;;;;;;;;;;;;;;;;;;;;;101:5;:14;;:25;116:9;101:25;;;;;;;;;;;;;;;;;;;;;;;;8:9:-1;5:2;;;45:16;42:1;39;24:38;77:16;74:1;67:27;5:2;101:25:2;49:81;:::o",
"source": "pragma solidity ^0.4.19;\n\ncontract Transfers2 {\n\tfunction transfer(address _addr) public payable {\n\t\t_addr.transfer(msg.value);\n\t}\n}",
"sourcePath": "/Users/gregmarkou/Jobs/Jobs/ChainSafe/shyftNetwork/shyft_go-ethereum/shyft-cli/web3/transfer-through-master/contracts/Transfers2.sol",
"ast": {
"absolutePath": "/Users/gregmarkou/Jobs/Jobs/ChainSafe/shyftNetwork/shyft_go-ethereum/shyft-cli/web3/transfer-through-master/contracts/Transfers2.sol",
"exportedSymbols": {
"Transfers2": [
249
]
},
"id": 250,
"nodeType": "SourceUnit",
"nodes": [
{
"id": 235,
"literals": [
"solidity",
"^",
"0.4",
".19"
],
"nodeType": "PragmaDirective",
"src": "0:24:2"
},
{
"baseContracts": [],
"contractDependencies": [],
"contractKind": "contract",
"documentation": null,
"fullyImplemented": true,
"id": 249,
"linearizedBaseContracts": [
249
],
"name": "Transfers2",
"nodeType": "ContractDefinition",
"nodes": [
{
"body": {
"id": 247,
"nodeType": "Block",
"src": "97:33:2",
"statements": [
{
"expression": {
"argumentTypes": null,
"arguments": [
{
"argumentTypes": null,
"expression": {
"argumentTypes": null,
"id": 243,
"name": "msg",
"nodeType": "Identifier",
"overloadedDeclarations": [],
"referencedDeclaration": 264,
"src": "116:3:2",
"typeDescriptions": {
"typeIdentifier": "t_magic_message",
"typeString": "msg"
}
},
"id": 244,
"isConstant": false,
"isLValue": false,
"isPure": false,
"lValueRequested": false,
"memberName": "value",
"nodeType": "MemberAccess",
"referencedDeclaration": null,
"src": "116:9:2",
"typeDescriptions": {
"typeIdentifier": "t_uint256",
"typeString": "uint256"
}
}
],
"expression": {
"argumentTypes": [
{
"typeIdentifier": "t_uint256",
"typeString": "uint256"
}
],
"expression": {
"argumentTypes": null,
"id": 240,
"name": "_addr",
"nodeType": "Identifier",
"overloadedDeclarations": [],
"referencedDeclaration": 237,
"src": "101:5:2",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
}
},
"id": 242,
"isConstant": false,
"isLValue": false,
"isPure": false,
"lValueRequested": false,
"memberName": "transfer",
"nodeType": "MemberAccess",
"referencedDeclaration": null,
"src": "101:14:2",
"typeDescriptions": {
"typeIdentifier": "t_function_transfer_nonpayable$_t_uint256_$returns$__$",
"typeString": "function (uint256)"
}
},
"id": 245,
"isConstant": false,
"isLValue": false,
"isPure": false,
"kind": "functionCall",
"lValueRequested": false,
"names": [],
"nodeType": "FunctionCall",
"src": "101:25:2",
"typeDescriptions": {
"typeIdentifier": "t_tuple$__$",
"typeString": "tuple()"
}
},
"id": 246,
"nodeType": "ExpressionStatement",
"src": "101:25:2"
}
]
},
"documentation": null,
"id": 248,
"implemented": true,
"isConstructor": false,
"isDeclaredConst": false,
"modifiers": [],
"name": "transfer",
"nodeType": "FunctionDefinition",
"parameters": {
"id": 238,
"nodeType": "ParameterList",
"parameters": [
{
"constant": false,
"id": 237,
"name": "_addr",
"nodeType": "VariableDeclaration",
"scope": 248,
"src": "67:13:2",
"stateVariable": false,
"storageLocation": "default",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
},
"typeName": {
"id": 236,
"name": "address",
"nodeType": "ElementaryTypeName",
"src": "67:7:2",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
}
},
"value": null,
"visibility": "internal"
}
],
"src": "66:15:2"
},
"payable": true,
"returnParameters": {
"id": 239,
"nodeType": "ParameterList",
"parameters": [],
"src": "97:0:2"
},
"scope": 249,
"src": "49:81:2",
"stateMutability": "payable",
"superFunction": null,
"visibility": "public"
}
],
"scope": 250,
"src": "26:106:2"
}
],
"src": "0:132:2"
},
"legacyAST": {
"absolutePath": "/Users/gregmarkou/Jobs/Jobs/ChainSafe/shyftNetwork/shyft_go-ethereum/shyft-cli/web3/transfer-through-master/contracts/Transfers2.sol",
"exportedSymbols": {
"Transfers2": [
249
]
},
"id": 250,
"nodeType": "SourceUnit",
"nodes": [
{
"id": 235,
"literals": [
"solidity",
"^",
"0.4",
".19"
],
"nodeType": "PragmaDirective",
"src": "0:24:2"
},
{
"baseContracts": [],
"contractDependencies": [],
"contractKind": "contract",
"documentation": null,
"fullyImplemented": true,
"id": 249,
"linearizedBaseContracts": [
249
],
"name": "Transfers2",
"nodeType": "ContractDefinition",
"nodes": [
{
"body": {
"id": 247,
"nodeType": "Block",
"src": "97:33:2",
"statements": [
{
"expression": {
"argumentTypes": null,
"arguments": [
{
"argumentTypes": null,
"expression": {
"argumentTypes": null,
"id": 243,
"name": "msg",
"nodeType": "Identifier",
"overloadedDeclarations": [],
"referencedDeclaration": 264,
"src": "116:3:2",
"typeDescriptions": {
"typeIdentifier": "t_magic_message",
"typeString": "msg"
}
},
"id": 244,
"isConstant": false,
"isLValue": false,
"isPure": false,
"lValueRequested": false,
"memberName": "value",
"nodeType": "MemberAccess",
"referencedDeclaration": null,
"src": "116:9:2",
"typeDescriptions": {
"typeIdentifier": "t_uint256",
"typeString": "uint256"
}
}
],
"expression": {
"argumentTypes": [
{
"typeIdentifier": "t_uint256",
"typeString": "uint256"
}
],
"expression": {
"argumentTypes": null,
"id": 240,
"name": "_addr",
"nodeType": "Identifier",
"overloadedDeclarations": [],
"referencedDeclaration": 237,
"src": "101:5:2",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
}
},
"id": 242,
"isConstant": false,
"isLValue": false,
"isPure": false,
"lValueRequested": false,
"memberName": "transfer",
"nodeType": "MemberAccess",
"referencedDeclaration": null,
"src": "101:14:2",
"typeDescriptions": {
"typeIdentifier": "t_function_transfer_nonpayable$_t_uint256_$returns$__$",
"typeString": "function (uint256)"
}
},
"id": 245,
"isConstant": false,
"isLValue": false,
"isPure": false,
"kind": "functionCall",
"lValueRequested": false,
"names": [],
"nodeType": "FunctionCall",
"src": "101:25:2",
"typeDescriptions": {
"typeIdentifier": "t_tuple$__$",
"typeString": "tuple()"
}
},
"id": 246,
"nodeType": "ExpressionStatement",
"src": "101:25:2"
}
]
},
"documentation": null,
"id": 248,
"implemented": true,
"isConstructor": false,
"isDeclaredConst": false,
"modifiers": [],
"name": "transfer",
"nodeType": "FunctionDefinition",
"parameters": {
"id": 238,
"nodeType": "ParameterList",
"parameters": [
{
"constant": false,
"id": 237,
"name": "_addr",
"nodeType": "VariableDeclaration",
"scope": 248,
"src": "67:13:2",
"stateVariable": false,
"storageLocation": "default",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
},
"typeName": {
"id": 236,
"name": "address",
"nodeType": "ElementaryTypeName",
"src": "67:7:2",
"typeDescriptions": {
"typeIdentifier": "t_address",
"typeString": "address"
}
},
"value": null,
"visibility": "internal"
}
],
"src": "66:15:2"
},
"payable": true,
"returnParameters": {
"id": 239,
"nodeType": "ParameterList",
"parameters": [],
"src": "97:0:2"
},
"scope": 249,
"src": "49:81:2",
"stateMutability": "payable",
"superFunction": null,
"visibility": "public"
}
],
"scope": 250,
"src": "26:106:2"
}
],
"src": "0:132:2"
},
"compiler": {
"name": "solc",
"version": "0.4.24+commit.e67f0147.Emscripten.clang"
},
"networks": {
"1": {
"events": {},
"links": {},
"address": "0xa863f8203ad95e9078f6300e7857a4cca4fb4c60",
"transactionHash": "0xb836110657221cb8ac728c0345ae03da1cb4313cfa0bb61285f31b780907af50"
},
"1528420224459": {
"events": {},
"links": {},
"address": "0x411410538c50b116663acd654e34dc6bed601cf0",
"transactionHash": "0x43f3fed1df72adfe12dd0c2432f0625b4b50b0c151f9583a166722ed74786ce3"
}
},
"schemaVersion": "2.0.0",
"updatedAt": "2018-06-08T15:58:27.899Z"
}

View file

@ -0,0 +1,23 @@
pragma solidity ^0.4.23;
contract Migrations {
address public owner;
uint public last_completed_migration;
constructor() public {
owner = msg.sender;
}
modifier restricted() {
if (msg.sender == owner) _;
}
function setCompleted(uint completed) public restricted {
last_completed_migration = completed;
}
function upgrade(address new_address) public restricted {
Migrations upgraded = Migrations(new_address);
upgraded.setCompleted(last_completed_migration);
}
}

View file

@ -0,0 +1,44 @@
pragma solidity ^0.4.19;
import "./Transfers2.sol";
contract Transfers {
mapping (address => uint) public balance;
Transfers2 t;
address t_addr;
constructor() public {
t = new Transfers2();
t_addr = address(t);
}
function transfer(address _addr, uint _value) public {
require(balance[msg.sender] >= _value);
bytes4 sig = bytes4(keccak256("transfer(address)"));
t_addr.call.value(_value)(sig, _addr);
}
function myBalance() public returns (uint) {
return balance[msg.sender];
}
function deposit() public payable returns (uint) {
balance[msg.sender] += msg.value;
return balance[msg.sender];
}
function withdraw(address _addr, uint _value) public {
require(balance[msg.sender] >= _value);
balance[msg.sender] -= _value;
_addr.transfer(_value);
}
function withdrawMulti(address[] _addrs, uint _value) public {
uint l = _addrs.length;
require(balance[msg.sender] >= _value * l);
balance[msg.sender] -= _value * l;
for (uint i = 0; i < l; i++){
_addrs[i].transfer(_value);
}
}
}

View file

@ -0,0 +1,7 @@
pragma solidity ^0.4.19;
contract Transfers2 {
function transfer(address _addr) public payable {
_addr.transfer(msg.value);
}
}

View file

@ -0,0 +1,5 @@
var Migrations = artifacts.require("./Migrations.sol");
module.exports = function(deployer) {
deployer.deploy(Migrations);
};

View file

@ -0,0 +1,7 @@
var Transfers = artifacts.require('./Transfers.sol')
var Transfers2 = artifacts.require('./Transfers2.sol')
module.exports = function (deployer) {
deployer.deploy(Transfers)
deployer.deploy(Transfers2)
}

View file

@ -0,0 +1,5 @@
{
"name": "transfers",
"version": "1.0.0",
"lockfileVersion": 1
}

View file

@ -0,0 +1,15 @@
{
"name": "transfers",
"version": "1.0.0",
"description": "",
"main": "truffle-config.js",
"directories": {
"test": "test"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [],
"author": "",
"license": "ISC"
}

View file

@ -0,0 +1,41 @@
var Transfers = artifacts.require("Transfers");
var Transfers2 = artifacts.require("Transfers2");
contract('Transfers', function(accounts) {
var addressA = web3.eth.accounts[0];
var addressB = web3.eth.accounts[1];
var transfers;
web3.eth.defaultAccount = web3.eth.accounts[0];
it("should initialize", async() => {
transfers = await Transfers.new();
transfers2 = await Transfers2.new();
assert(transfers !== undefined, "");
assert(transfers2 !== undefined, "");
})
it("should deposit", async() => {
let hash = await transfers.deposit({from: addressA, value: web3.toWei(4, "ether")});
let bal = await transfers.deposit.call({from: addressA});
console.log("\t\t[DEPOSIT TX]", hash.tx)
//console.log(bal);
})
it("should withdraw", async() => {
let prevB = await web3.eth.getBalance(addressB);
let hash = await transfers.withdraw(addressB, web3.toWei(1, "ether"), {from: addressA});
let postB = await web3.eth.getBalance(addressB);
console.log("\t\t[WITHDRAW TX]", hash.tx)
//assert(postB - prevB == val, "");
})
it("should transfer through other contract", async() => {
let val = 10;
let prevB = await web3.eth.getBalance(addressB);
let hash = await transfers.transfer(addressB, web3.toWei(1, "ether"), {from: addressA});
let postB = await web3.eth.getBalance(addressB);
console.log("\t\t[TRANSFER THROUGH TX]", hash.tx)
// assert(web3.fromWei(prevB,'wei') - web3.fromWei(postB,'wei') == val, "");
})
})

View file

@ -0,0 +1,12 @@
module.exports = {
// See <http://truffleframework.com/docs/advanced/configuration>
// to customize your Truffle configuration!
networks: {
geth_testnet: {
host: "127.0.0.1",
port: 8545,
netword_id: "*"
}
}
};

View file

@ -0,0 +1,10 @@
module.exports = {
networks: {
development: {
host: 'localhost',
port: 8545,
network_id: '*',
//gasLimit: 6.7e6
}
}
};

47
shyft-geth.sh Executable file
View file

@ -0,0 +1,47 @@
#!/bin/bash
if [[ $# -lt 1 ]]; then
echo
echo Shyft-Geth: No flags detected, see help:
echo
echo " --setup: Setups postgres and the shyft chain db."
echo " --start: Starts geth."
echo " --reset: Drops postgress and chain db, and reinstantiates both."
echo " --js [filename]: Executes web3 calls with a passed file name. If the file name is sendTransactions.js, $ ./shyft-geth.sh --js sendTransactions"
echo
exit 1
fi
illegalCommands=()
while [[ $# -gt 0 ]]
do
key="$1"
case $key in
--setup)
sh ./shyft-cli/setup.sh
shift # past argument
;;
--start)
sh ./shyft-cli/startShyftGeth.sh
shift # past argument
;;
--js)
sh ./shyft-cli/runJs.sh ./shyft-cli/web3/$2.js
shift # past argument
shift # past argument
;;
--reset)
sh ./shyft-cli/shyftFullReset.sh
shift # past argument
;;
*) # unknown option
illegalCommands+=("$1") # save it in an array for later
shift # past argument
;;
esac
done
if [[ "${#illegalCommands[@]}" -gt "0" ]]; then
echo Shyft-Geth: The following commands are not supported: "${illegalCommands[*]}"
fi

View file

@ -0,0 +1,18 @@
package main
//@NOTE SHYFT main func for api, sets up router and spins up a server
//to run server 'go run shyftBlockExplorerApi/*.go'
import (
"log"
"net/http"
"github.com/gorilla/handlers"
)
func main() {
router := NewRouter()
port := "8080"
log.Printf("Listening on port " + " " + port)
log.Fatal(http.ListenAndServe(":"+port, handlers.CORS(handlers.AllowedHeaders([]string{"X-Requested-With", "Content-Type", "Authorization"}), handlers.AllowedMethods([]string{"GET", "POST", "PUT", "HEAD", "OPTIONS"}), handlers.AllowedOrigins([]string{"*"}))(router)))
}

View file

@ -10,6 +10,9 @@ import (
"github.com/ethereum/go-ethereum/shyftdb" "github.com/ethereum/go-ethereum/shyftdb"
"github.com/gorilla/mux" "github.com/gorilla/mux"
"bytes"
"io/ioutil"
"encoding/json"
) )
// GetTransaction gets txs // GetTransaction gets txs
@ -244,3 +247,39 @@ func GetInternalTransactionsHash(w http.ResponseWriter, r *http.Request) {
fmt.Fprintln(w, "Get Internal Transaction Hash", transactionHash) fmt.Fprintln(w, "Get Internal Transaction Hash", transactionHash)
} }
func BroadcastTx(w http.ResponseWriter, r *http.Request) {
// Example return result (returns tx hash):
// {"jsonrpc":"2.0","id":1,"result":"0xafa4c62f29dbf16bbfac4eea7cbd001a9aa95c59974043a17f863172f8208029"}
// http params
vars := mux.Vars(r)
transactionHash := vars["transaction_hash"]
// format the transactionHash into a proper sendRawTransaction jsonrpc request
formatted_json := []byte(fmt.Sprintf(`{"jsonrpc":"2.0","method":"eth_sendRawTransaction","params":["%s"],"id":0}`, transactionHash))
// send json rpc request
resp, _ := http.Post("http://localhost:8545", "application/json", bytes.NewBuffer(formatted_json))
body, _ := ioutil.ReadAll(resp.Body)
byt := []byte(string(body))
// read json and return result as http response, be it an error or tx hash
var dat map[string]interface{}
if err := json.Unmarshal(byt, &dat); err != nil {
w.Header().Set("Content-Type", "application/json; charset=UTF-8")
w.WriteHeader(http.StatusOK)
fmt.Fprintln(w, "ERROR parsing json")
}
tx_hash := dat["result"]
if(tx_hash == nil) {
errMap := dat["error"].(map[string]interface{})
w.Header().Set("Content-Type", "application/json; charset=UTF-8")
w.WriteHeader(http.StatusOK)
fmt.Fprintln(w, "ERROR:", errMap["message"])
} else {
w.Header().Set("Content-Type", "application/json; charset=UTF-8")
w.WriteHeader(http.StatusOK)
fmt.Fprintln(w, "Transaction Hash:", tx_hash)
}
}

View file

@ -87,4 +87,10 @@ var routes = Routes{
"/api/get_internal_transactions_hash/{transactions_hash}", "/api/get_internal_transactions_hash/{transactions_hash}",
GetInternalTransactionsHash, GetInternalTransactionsHash,
}, },
Route{
"BroadcastTx",
"GET",
"/api/broadcast_tx/{transaction_hash}",
BroadcastTx,
},
} }

37
shyftDb/db.go Normal file
View file

@ -0,0 +1,37 @@
package shyftdb
import (
"fmt"
"database/sql"
"os"
)
var blockExplorerDb *sql.DB
func InitDB() (*sql.DB, error){
var connStr string
if "test" == os.Getenv("SHYFT_ENV") {
connStr = "user=postgres dbname=shyftdbtest sslmode=disable"
} else {
connStr = "user=postgres dbname=shyftdb sslmode=disable"
}
db, err := sql.Open("postgres", connStr)
if err != nil {
fmt.Println("ERROR OPENING DB, NOT INITIALIZING")
fmt.Println(err)
return nil, err
} else {
blockExplorerDb = db
return blockExplorerDb, nil
}
}
func DBConnection() (*sql.DB, error) {
if (blockExplorerDb == nil) {
_, err := InitDB()
if(err != nil) {
return nil, err
}
}
return blockExplorerDb, nil
}

View file

@ -1 +0,0 @@
psql -U postgres -f create_shyftdb.psql

View file

@ -0,0 +1 @@
CREATE DATABASE shyftdbTest

View file

@ -0,0 +1,40 @@
CREATE TABLE IF NOT EXISTS blocks (
hash text primary key,
coinbase text,
gasUsed numeric,
gasLimit numeric,
txCount numeric,
uncleCount numeric,
age timestamp,
parentHash text,
uncleHash text,
difficulty bigint,
size text,
nonce numeric,
rewards numeric,
number bigint
);
CREATE TABLE IF NOT EXISTS txs (
txHash text,
to_addr text,
from_addr text,
blockhash text references blocks(hash),
blocknumber text,
amount numeric,
gasprice numeric,
gas numeric,
gasLimit numeric,
txFee numeric,
nonce numeric,
txStatus text,
isContract bool,
age timestamp,
data bytea
);
CREATE TABLE IF NOT EXISTS accounts (
addr text primary key unique,
balance numeric,
txCountAccount numeric
);

View file

@ -0,0 +1,3 @@
DROP TABLE txs;
DROP TABLE blocks;
DROP TABLE accounts;

View file

@ -0,0 +1 @@
psql -U postgres -d shyftdbtest -f drop_tables_test.psql

View file

@ -0,0 +1 @@
psql -U postgres -f create_shyftdb_test.psql

View file

@ -0,0 +1 @@
psql -U postgres -d shyftdbtest -f create_tables_test.psql

42
shyftDb/postgres_test.go Normal file
View file

@ -0,0 +1,42 @@
package shyftdb
import (
"database/sql"
"fmt"
)
func InitTestDB() *sql.DB {
connStr := "user=postgres dbname=shyftdbtest sslmode=disable"
blockExplorerDbTest, err := sql.Open("postgres", connStr)
if err != nil {
fmt.Println(err)
}
return blockExplorerDbTest
}
func ClearTables() {
connStr := "user=postgres dbname=shyftdbtest sslmode=disable"
blockExplorerDbTest, err := sql.Open("postgres", connStr)
if err != nil {
fmt.Println(err)
}
sqlStatementTx:= `DELETE FROM txs`
_, err = blockExplorerDbTest.Exec(sqlStatementTx)
if err != nil {
panic(err)
}
sqlStatementAcc:= `DELETE FROM accounts`
_, err = blockExplorerDbTest.Exec(sqlStatementAcc)
if err != nil {
panic(err)
}
sqlStatement := `DELETE FROM blocks`
_, err = blockExplorerDbTest.Exec(sqlStatement)
if err != nil {
panic(err)
}
}

View file

@ -20,16 +20,16 @@ type SBlock struct {
Hash string Hash string
Coinbase string Coinbase string
Number string Number string
GasUsed string GasUsed uint64
GasLimit string GasLimit uint64
TxCount string TxCount int
UncleCount string UncleCount int
Age string Age string
ParentHash string ParentHash string
UncleHash string UncleHash string
Difficulty string Difficulty string
Size string Size string
Nonce string Nonce uint64
Rewards string Rewards string
} }
@ -80,7 +80,7 @@ type ShyftTxEntryPretty struct {
Amount string Amount string
GasPrice uint64 GasPrice uint64
Gas uint64 Gas uint64
GasLimit string GasLimit uint64
Cost uint64 Cost uint64
Nonce uint64 Nonce uint64
Status string Status string
@ -104,8 +104,14 @@ type SendAndReceive struct {
} }
//WriteBlock writes to block info to sql db //WriteBlock writes to block info to sql db
func WriteBlock(sqldb *sql.DB, block *types.Block, receipts []*types.Receipt) error { func WriteBlock(block *types.Block, receipts []*types.Receipt) error {
rewards := WriteMinerRewards(sqldb,block)
sqldb, err := DBConnection()
if (err != nil) {
panic(err)
}
rewards := writeMinerRewards(sqldb,block)
coinbase := block.Header().Coinbase.String() coinbase := block.Header().Coinbase.String()
number := block.Header().Number.String() number := block.Header().Number.String()
gasUsed := block.Header().GasUsed gasUsed := block.Header().GasUsed
@ -132,21 +138,20 @@ func WriteBlock(sqldb *sql.DB, block *types.Block, receipts []*types.Receipt) er
if block.Transactions().Len() > 0 { if block.Transactions().Len() > 0 {
for _, tx := range block.Transactions() { for _, tx := range block.Transactions() {
WriteTransactions(sqldb, tx, block.Header().Hash(), block.Header().Number.String(), receipts, age, gasLimit) writeTransactions(sqldb, tx, block.Header().Hash(), block.Header().Number.String(), receipts, age, gasLimit)
if block.Transactions()[0].To() != nil { if block.Transactions()[0].To() != nil {
WriteFromBalance(sqldb, tx) writeFromBalance(sqldb, tx)
} }
if block.Transactions()[0].To() == nil { if block.Transactions()[0].To() == nil {
WriteContractBalance(sqldb, tx) writeContractBalance(sqldb, tx)
WriteContractsTxHashReferences(sqldb, tx)
} }
} }
} }
return nil return nil
} }
//WriteTransactions writes to sqldb //writeTransactions writes to sqldb
func WriteTransactions(sqldb *sql.DB, tx *types.Transaction, blockHash common.Hash, blockNumber string, receipts []*types.Receipt, age time.Time, gasLimit uint64) error { func writeTransactions(sqldb *sql.DB, tx *types.Transaction, blockHash common.Hash, blockNumber string, receipts []*types.Receipt, age time.Time, gasLimit uint64) error {
txData := ShyftTxEntry{ txData := ShyftTxEntry{
TxHash: tx.Hash(), TxHash: tx.Hash(),
From: tx.From(), From: tx.From(),
@ -217,22 +222,15 @@ func WriteTransactions(sqldb *sql.DB, tx *types.Transaction, blockHash common.Ha
return nil return nil
} }
func WriteContractsTxHashReferences(sqldb *sql.DB, tx *types.Transaction) error { func writeContractBalance(sqldb *sql.DB, tx *types.Transaction) error {
txHash := tx.Hash().Hex() sendAndReceiveData := SendAndReceive{
From: tx.From().Hex(),
sqlStatement := `INSERT INTO contracts(txHash) VALUES(($1)) RETURNING txHash` Amount: tx.Value().String(),
insertErr := sqldb.QueryRow(sqlStatement, txHash).Scan(&txHash)
if insertErr != nil {
panic(insertErr)
} }
return nil
}
func WriteContractBalance(sqldb *sql.DB, tx *types.Transaction) error {
sendAndReceiveData,balanceSen,accountNonceSen := WriteContractBalanceHelper(sqldb, tx)
fromAddr := sendAndReceiveData.From fromAddr := sendAndReceiveData.From
amount := sendAndReceiveData.Amount amount := sendAndReceiveData.Amount
balanceSender := balanceSen accountNonceSen := tx.Nonce()
var response string var response string
sqlExistsStatement := `SELECT balance from accounts WHERE addr = ($1)` sqlExistsStatement := `SELECT balance from accounts WHERE addr = ($1)`
@ -244,9 +242,14 @@ func WriteContractBalance(sqldb *sql.DB, tx *types.Transaction) error {
if insertErr != nil { if insertErr != nil {
panic(insertErr) panic(insertErr)
} }
case err != nil:
log.Fatal(err)
default: default:
getAccountBalanceSender:= GetAccount(sqldb, fromAddr)
var senderBalance SendAndReceive
if err := json.Unmarshal([]byte(getAccountBalanceSender), &senderBalance); err != nil {
log.Fatal(err)
}
balanceSender := senderBalance.Balance
var newBalanceSender big.Int var newBalanceSender big.Int
var newAccountNonceSender big.Int var newAccountNonceSender big.Int
var nonceIncrement = big.NewInt(1) var nonceIncrement = big.NewInt(1)
@ -258,16 +261,12 @@ func WriteContractBalance(sqldb *sql.DB, tx *types.Transaction) error {
log.Println("error scanning value:", error) log.Println("error scanning value:", error)
} }
accountS := new(big.Int) senderAccountNonce := new(big.Int).SetUint64(accountNonceSen)
_, errors := fmt.Sscan(accountNonceSen, accountS)
if errors != nil {
log.Println("error scanning value:", error)
}
newBalanceSender.Sub(s, tx.Value()) newBalanceSender.Sub(s, tx.Value())
newAccountNonceSender.Add(accountS, nonceIncrement) newAccountNonceSender.Add(senderAccountNonce, nonceIncrement)
_, err = sqldb.Exec(updateSQLStatement, fromAddr, newBalanceSender.String(), newAccountNonceSender.String()) _, err := sqldb.Exec(updateSQLStatement, fromAddr, newBalanceSender.String(), newAccountNonceSender.String())
if err != nil { if err != nil {
panic(err) panic(err)
} }
@ -275,28 +274,9 @@ func WriteContractBalance(sqldb *sql.DB, tx *types.Transaction) error {
return nil return nil
} }
func WriteContractBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, string, string) { //writeFromBalance writes senders balance to accounts db
sendAndReceiveData := SendAndReceive{ func writeFromBalance(sqldb *sql.DB, tx *types.Transaction) error {
From: tx.From().Hex(), sendAndReceiveData, balanceRec, balanceSen, accountNonceRec, accountNonceSen := writeBalanceHelper(sqldb, tx)
Amount: tx.Value().String(),
}
fromAddr := sendAndReceiveData.From
getAccountBalanceSender:= GetAccount(sqldb, fromAddr)
var senderBalance SendAndReceive
if err := json.Unmarshal([]byte(getAccountBalanceSender), &senderBalance); err != nil {
log.Fatal(err)
}
balanceSender := senderBalance.Balance
accountNonceSender := senderBalance.TxCountAccount
return sendAndReceiveData, balanceSender, accountNonceSender
}
//WriteFromBalance writes senders balance to accounts db
func WriteFromBalance(sqldb *sql.DB, tx *types.Transaction) error {
sendAndReceiveData, balanceRec, balanceSen, accountNonceRec, accountNonceSen := WriteBalanceHelper(sqldb, tx)
toAddr := sendAndReceiveData.To toAddr := sendAndReceiveData.To
fromAddr := sendAndReceiveData.From fromAddr := sendAndReceiveData.From
amount := sendAndReceiveData.Amount amount := sendAndReceiveData.Amount
@ -306,14 +286,12 @@ func WriteFromBalance(sqldb *sql.DB, tx *types.Transaction) error {
var response string var response string
sqlExistsStatement := `SELECT balance from accounts WHERE addr = ($1)` sqlExistsStatement := `SELECT balance from accounts WHERE addr = ($1)`
err := sqldb.QueryRow(sqlExistsStatement, toAddr).Scan(&response) err := sqldb.QueryRow(sqlExistsStatement, toAddr).Scan(&response)
switch { switch {
case err == sql.ErrNoRows: case err == sql.ErrNoRows:
i, err := strconv.Atoi(accountNonceRec) txCountAccount := strconv.FormatUint(tx.Nonce(), 10)
if err != nil {
fmt.Println(err)
}
sqlStatement := `INSERT INTO accounts(addr, balance, txCountAccount) VALUES(($1), ($2), ($3)) RETURNING addr` sqlStatement := `INSERT INTO accounts(addr, balance, txCountAccount) VALUES(($1), ($2), ($3)) RETURNING addr`
insertErr := sqldb.QueryRow(sqlStatement, toAddr, amount, i).Scan(&toAddr) insertErr := sqldb.QueryRow(sqlStatement, toAddr, amount, txCountAccount).Scan(&toAddr)
if insertErr != nil { if insertErr != nil {
panic(insertErr) panic(insertErr)
} }
@ -370,7 +348,7 @@ func WriteFromBalance(sqldb *sql.DB, tx *types.Transaction) error {
return nil return nil
} }
func WriteBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, string, string, string, string) { func writeBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, string, string, string, string) {
sendAndReceiveData := SendAndReceive{ sendAndReceiveData := SendAndReceive{
To: tx.To().Hex(), To: tx.To().Hex(),
From: tx.From().Hex(), From: tx.From().Hex(),
@ -379,7 +357,6 @@ func WriteBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, s
toAddr := sendAndReceiveData.To toAddr := sendAndReceiveData.To
fromAddr := sendAndReceiveData.From fromAddr := sendAndReceiveData.From
getAccountBalanceReceiver := GetAccount(sqldb, toAddr) getAccountBalanceReceiver := GetAccount(sqldb, toAddr)
getAccountBalanceSender:= GetAccount(sqldb, fromAddr) getAccountBalanceSender:= GetAccount(sqldb, fromAddr)
@ -395,7 +372,6 @@ func WriteBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, s
balanceReceiver := receiverBalance.Balance balanceReceiver := receiverBalance.Balance
balanceSender := senderBalance.Balance balanceSender := senderBalance.Balance
accountNonceReceiver := receiverBalance.TxCountAccount accountNonceReceiver := receiverBalance.TxCountAccount
accountNonceSender := senderBalance.TxCountAccount accountNonceSender := senderBalance.TxCountAccount
@ -406,7 +382,7 @@ func WriteBalanceHelper(sqldb *sql.DB, tx *types.Transaction) (SendAndReceive, s
// uncle blocks, account balance updates based on reorgs, diverges that get dropped. // uncle blocks, account balance updates based on reorgs, diverges that get dropped.
// Reason for this is because the accounts are not deterministic like the block and tx hashes. // Reason for this is because the accounts are not deterministic like the block and tx hashes.
// @TODO: Calculate reorg // @TODO: Calculate reorg
func WriteMinerRewards(sqldb *sql.DB, block *types.Block) string { func writeMinerRewards(sqldb *sql.DB, block *types.Block) string {
minerAddr := block.Coinbase().String() minerAddr := block.Coinbase().String()
shyftConduitAddress := Rewards.ShyftNetworkConduitAddress.String() shyftConduitAddress := Rewards.ShyftNetworkConduitAddress.String()
// Calculate the total gas used in the block // Calculate the total gas used in the block
@ -436,13 +412,13 @@ func WriteMinerRewards(sqldb *sql.DB, block *types.Block) string {
uncleAddrs = append(uncleAddrs, uncle.Coinbase.String()) uncleAddrs = append(uncleAddrs, uncle.Coinbase.String())
} }
StoreReward(sqldb, minerAddr, totalMinerReward) storeReward(sqldb, minerAddr, totalMinerReward)
StoreReward(sqldb, shyftConduitAddress, Rewards.ShyftNetworkBlockReward) storeReward(sqldb, shyftConduitAddress, Rewards.ShyftNetworkBlockReward)
var uncRewards = new(big.Int) var uncRewards = new(big.Int)
for i := 0; i < len(uncleAddrs); i++ { for i := 0; i < len(uncleAddrs); i++ {
uncRewards := uncleRewards[i] uncRewards := uncleRewards[i]
fmt.Println(uncRewards) fmt.Println(uncRewards)
StoreReward(sqldb, uncleAddrs[i], uncleRewards[i]) storeReward(sqldb, uncleAddrs[i], uncleRewards[i])
} }
fullRewardValue := new(big.Int) fullRewardValue := new(big.Int)
@ -452,7 +428,7 @@ func WriteMinerRewards(sqldb *sql.DB, block *types.Block) string {
return fullRewardValue.String() return fullRewardValue.String()
} }
func StoreReward(sqldb *sql.DB, address string, reward *big.Int) { func storeReward(sqldb *sql.DB, address string, reward *big.Int) {
// Check if address exists // Check if address exists
var addressBalance string var addressBalance string
addressExistsStatement := `SELECT balance from accounts WHERE addr = ($1)` addressExistsStatement := `SELECT balance from accounts WHERE addr = ($1)`
@ -497,6 +473,10 @@ func StoreReward(sqldb *sql.DB, address string, reward *big.Int) {
// Getters // Getters
////////// //////////
//GetAllBlocks returns []SBlock blocks for API //GetAllBlocks returns []SBlock blocks for API
//Look into postgres functions array_to_json(array_agg(lap))
//Example select array_to_json(array_agg(lap))
//from ( select * from blocks)lap;
func GetAllBlocks(sqldb *sql.DB) string { func GetAllBlocks(sqldb *sql.DB) string {
var arr blockRes var arr blockRes
var blockArr string var blockArr string
@ -510,16 +490,16 @@ func GetAllBlocks(sqldb *sql.DB) string {
for rows.Next() { for rows.Next() {
var hash string var hash string
var coinbase string var coinbase string
var gasUsed string var gasUsed uint64
var gasLimit string var gasLimit uint64
var txCount string var txCount int
var uncleCount string var uncleCount int
var age string var age string
var parentHash string var parentHash string
var uncleHash string var uncleHash string
var difficulty string var difficulty string
var size string var size string
var nonce string var nonce uint64
var rewards string var rewards string
var num string var num string
@ -570,16 +550,16 @@ func GetBlock(sqldb *sql.DB, blockNumber string) string {
row := sqldb.QueryRow(sqlStatement, blockNumber) row := sqldb.QueryRow(sqlStatement, blockNumber)
var hash string var hash string
var coinbase string var coinbase string
var gasUsed string var gasUsed uint64
var gasLimit string var gasLimit uint64
var txCount string var txCount int
var uncleCount string var uncleCount int
var age string var age string
var parentHash string var parentHash string
var uncleHash string var uncleHash string
var difficulty string var difficulty string
var size string var size string
var nonce string var nonce uint64
var rewards string var rewards string
var num string var num string
row.Scan( row.Scan(
@ -623,16 +603,16 @@ func GetRecentBlock(sqldb *sql.DB) string {
row := sqldb.QueryRow(sqlStatement) row := sqldb.QueryRow(sqlStatement)
var hash string var hash string
var coinbase string var coinbase string
var gasUsed string var gasUsed uint64
var gasLimit string var gasLimit uint64
var txCount string var txCount int
var uncleCount string var uncleCount int
var age string var age string
var parentHash string var parentHash string
var uncleHash string var uncleHash string
var difficulty string var difficulty string
var size string var size string
var nonce string var nonce uint64
var rewards string var rewards string
var num string var num string
row.Scan( row.Scan(
@ -689,7 +669,7 @@ func GetAllTransactionsFromBlock(sqldb *sql.DB, blockNumber string) string {
var amount string var amount string
var gasprice uint64 var gasprice uint64
var gas uint64 var gas uint64
var gasLimit string var gasLimit uint64
var txfee uint64 var txfee uint64
var nonce uint64 var nonce uint64
var status string var status string
@ -752,16 +732,16 @@ func GetAllBlocksMinedByAddress(sqldb *sql.DB, coinbase string) string {
for rows.Next() { for rows.Next() {
var hash string var hash string
var coinbase string var coinbase string
var gasUsed string var gasUsed uint64
var gasLimit string var gasLimit uint64
var txCount string var txCount int
var uncleCount string var uncleCount int
var age string var age string
var parentHash string var parentHash string
var uncleHash string var uncleHash string
var difficulty string var difficulty string
var size string var size string
var nonce string var nonce uint64
var rewards string var rewards string
var num string var num string
@ -824,7 +804,7 @@ func GetAllTransactions(sqldb *sql.DB) string {
var amount string var amount string
var gasprice uint64 var gasprice uint64
var gas uint64 var gas uint64
var gasLimit string var gasLimit uint64
var txfee uint64 var txfee uint64
var nonce uint64 var nonce uint64
var status string var status string
@ -886,7 +866,7 @@ func GetTransaction(sqldb *sql.DB, txHash string) string {
var amount string var amount string
var gasprice uint64 var gasprice uint64
var gas uint64 var gas uint64
var gasLimit string var gasLimit uint64
var txfee uint64 var txfee uint64
var nonce uint64 var nonce uint64
var status string var status string
@ -1011,7 +991,7 @@ func GetAccountTxs(sqldb *sql.DB, address string) string {
var amount string var amount string
var gasprice uint64 var gasprice uint64
var gas uint64 var gas uint64
var gasLimit string var gasLimit uint64
var txfee uint64 var txfee uint64
var nonce uint64 var nonce uint64
var status string var status string

View file

@ -0,0 +1,451 @@
package shyftdb
import (
"testing"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"math/big"
//"time"
"encoding/json"
"github.com/ethereum/go-ethereum/crypto"
"strconv"
)
func TestBlockToReturnBlock(t *testing.T) {
key, _ := crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
signer := types.NewEIP155Signer(big.NewInt(2147483647))
//Nonce, To Address,Value, GasLimit, Gasprice, data
tx1 := types.NewTransaction(1, common.BytesToAddress([]byte{0x11}), big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
mytx,_ := types.SignTx(tx1, signer, key)
tx2 := types.NewTransaction(2, common.BytesToAddress([]byte{0x22}), big.NewInt(222), 2222, big.NewInt(22222), []byte{0x22, 0x22, 0x22})
mytx2,_ := types.SignTx(tx2, signer, key)
tx3 := types.NewTransaction(3, common.BytesToAddress([]byte{0x33}), big.NewInt(333), 3333, big.NewInt(33333), []byte{0x33, 0x33, 0x33})
mytx3,_ := types.SignTx(tx3, signer, key)
txs := []*types.Transaction{mytx, mytx2, mytx3}
receipt := &types.Receipt{
Status: types.ReceiptStatusSuccessful,
CumulativeGasUsed: 1,
Logs: []*types.Log{
{Address: common.BytesToAddress([]byte{0x11})},
{Address: common.BytesToAddress([]byte{0x01, 0x11})},
},
TxHash: common.BytesToHash([]byte{0x11, 0x11}),
ContractAddress: common.BytesToAddress([]byte{0x01, 0x11, 0x11}),
GasUsed: 111111,
}
receipts := []*types.Receipt{receipt}
block := types.NewBlock(&types.Header{Number: big.NewInt(315)}, txs, nil, receipts)
// Write and verify the block in the database
if err := WriteBlock(block, receipts); err != nil {
t.Fatalf("Failed to write block into database: %v", err)
}
sqldb, err := DBConnection()
if (err != nil) {
panic(err)
}
entry := GetBlock(sqldb, block.Number().String())
byt := []byte(entry)
var data SBlock
json.Unmarshal(byt, &data)
//TODO Difficulty, rewards, age
if block.Hash().String() != data.Hash {
t.Fatalf("Block Hash [%v]: Block hash not found", block.Hash().String())
}
if block.Coinbase().String() != data.Coinbase {
t.Fatalf("Block coinbase [%v]: Block coinbase not found", block.Coinbase().String())
}
if block.Number().String() != data.Number {
t.Fatalf("Block number [%v]: Block number not found", block.Number().String())
}
if block.GasUsed() != data.GasUsed {
t.Fatalf("Gas Used [%v]: Gas used not found", block.GasUsed())
}
if block.GasLimit() != data.GasLimit {
t.Fatalf("Gas Limit [%v]: Gas limit not found", block.GasLimit())
}
if block.Transactions().Len() != data.TxCount {
t.Fatalf("Tx Count [%v]: Tx Count not found", block.Transactions().Len())
}
if len(block.Uncles()) != data.UncleCount {
t.Fatalf("Uncle count [%v]: Uncle count not found", len(block.Uncles()))
}
if block.ParentHash().String() != data.ParentHash {
t.Fatalf("Parent hash [%v]: Parent hash not found", block.ParentHash().String())
}
if block.UncleHash().String() != data.UncleHash {
t.Fatalf("Uncle hash [%v]: Uncle hash not found", block.UncleHash().String())
}
if block.Size().String() != data.Size {
t.Fatalf("Size [%v]: Size not found", block.Size().String())
}
if block.Nonce() != data.Nonce {
t.Fatalf("Block nonce [%v]: Block nonce not found", block.Nonce())
}
if getAllBlocks := GetAllBlocks(sqldb); len(getAllBlocks) == 0 {
t.Fatalf("GetAllBlocks [%v]: GetAllBlocks did not return correctly", getAllBlocks)
}
if getAllBlocksMinedByAddress := GetAllBlocksMinedByAddress(sqldb, block.Coinbase().String()); len(getAllBlocksMinedByAddress) == 0 {
t.Fatalf("GetAllBlocksMinedByAddress [%v]: GetAllBlocksMinedByAddress did not return correctly", getAllBlocksMinedByAddress)
}
ClearTables()
}
func TestGetRecentBlock(t *testing.T) {
db := InitTestDB()
key, _ := crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
signer := types.NewEIP155Signer(big.NewInt(2147483647))
//Nonce, To Address,Value, GasLimit, Gasprice, data
tx1 := types.NewTransaction(1, common.BytesToAddress([]byte{0x11}), big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
mytx,_ := types.SignTx(tx1, signer, key)
tx2 := types.NewTransaction(2, common.BytesToAddress([]byte{0x22}), big.NewInt(222), 2222, big.NewInt(22222), []byte{0x22, 0x22, 0x22})
mytx2,_ := types.SignTx(tx2, signer, key)
tx3 := types.NewTransaction(3, common.BytesToAddress([]byte{0x33}), big.NewInt(333), 3333, big.NewInt(33333), []byte{0x33, 0x33, 0x33})
mytx3,_ := types.SignTx(tx3, signer, key)
txs := []*types.Transaction{mytx, mytx2}
txs1 := []*types.Transaction{mytx3}
receipt1 := &types.Receipt{
Status: types.ReceiptStatusSuccessful,
CumulativeGasUsed: 1,
Logs: []*types.Log{
{Address: common.BytesToAddress([]byte{0x11})},
{Address: common.BytesToAddress([]byte{0x01, 0x11})},
},
TxHash: common.BytesToHash([]byte{0x11, 0x11}),
ContractAddress: common.BytesToAddress([]byte{0x01, 0x11, 0x11}),
GasUsed: 111111,
}
receipts := []*types.Receipt{receipt1}
block := types.NewBlock(&types.Header{Number: big.NewInt(322)}, txs, nil, receipts)
block2 := types.NewBlock(&types.Header{Number: big.NewInt(320)}, txs1, nil, receipts)
blocks := []*types.Block{block, block2}
for _, bc := range blocks {
// Write and verify the block in the database
if err := WriteBlock(bc, receipts); err != nil {
t.Fatalf("Failed to write block into database: %v", err)
}
}
response := GetRecentBlock(db)
byteRes := []byte(response)
var recentBlock SBlock
json.Unmarshal(byteRes, &recentBlock)
if block.Hash().String() != recentBlock.Hash {
t.Fatalf("Block Hash [%v]: Block hash not found", block.Hash().String())
}
if block.Coinbase().String() != recentBlock.Coinbase {
t.Fatalf("Block coinbase [%v]: Block coinbase not found", block.Coinbase().String())
}
if block.Number().String() != recentBlock.Number {
t.Fatalf("Block number [%v]: Block number not found", block.Number().String())
}
if block.GasUsed() != recentBlock.GasUsed {
t.Fatalf("Gas Used [%v]: Gas used not found", block.GasUsed())
}
if block.GasLimit() != recentBlock.GasLimit {
t.Fatalf("Gas Limit [%v]: Gas limit not found", block.GasLimit())
}
if block.Transactions().Len() != recentBlock.TxCount {
t.Fatalf("Tx Count [%v]: Tx Count not found", block.Transactions().Len())
}
if len(block.Uncles()) != recentBlock.UncleCount {
t.Fatalf("Uncle count [%v]: Uncle count not found", len(block.Uncles()))
}
if block.ParentHash().String() != recentBlock.ParentHash {
t.Fatalf("Parent hash [%v]: Parent hash not found", block.ParentHash().String())
}
if block.UncleHash().String() != recentBlock.UncleHash {
t.Fatalf("Uncle hash [%v]: Uncle hash not found", block.UncleHash().String())
}
if block.Size().String() != recentBlock.Size {
t.Fatalf("Size [%v]: Size not found", block.Size().String())
}
if block.Nonce() != recentBlock.Nonce {
t.Fatalf("Block nonce [%v]: Block nonce not found", block.Nonce())
}
if allTxsFromBlock:= GetAllTransactionsFromBlock(db, block2.Number().String()); len(allTxsFromBlock) == 0 {
t.Fatalf("GetAllTransactionsFromBlock [%v]: GetAllTransactionsFromBlock did not return correctly", allTxsFromBlock)
}
ClearTables()
}
func TestContractCreationTx(t *testing.T) {
key, _ := crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
signer := types.NewEIP155Signer(big.NewInt(2147483647))
//Nonce,Value, GasLimit, Gasprice, data
contractCreation := types.NewContractCreation(1, big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
mytx,_ := types.SignTx(contractCreation, signer, key)
txs := []*types.Transaction{mytx}
receipt2 := &types.Receipt{
Status: types.ReceiptStatusSuccessful,
CumulativeGasUsed: 1,
Logs: []*types.Log{
{Address: common.BytesToAddress([]byte{0x11})},
{Address: common.BytesToAddress([]byte{0x01, 0x11})},
},
TxHash: common.BytesToHash([]byte{0x11, 0x11}),
ContractAddress: common.BytesToAddress([]byte{0x01, 0x11, 0x11}),
GasUsed: 111111,
}
receipts := []*types.Receipt{receipt2}
block := types.NewBlock(&types.Header{Number: big.NewInt(314)}, txs, nil, receipts)
if err := WriteBlock(block, receipts); err != nil {
t.Fatalf("Failed to write block into database: %v", err)
}
var contractAddressFromReciept string
for _, receipt := range receipts {
contractAddressFromReciept = (*types.ReceiptForStorage)(receipt).ContractAddress.String()
}
sqldb, err := DBConnection()
if (err != nil) {
panic(err)
}
for _, tx := range txs {
txn := GetTransaction(sqldb, tx.Hash().String())
byt := []byte(txn)
var data ShyftTxEntryPretty
json.Unmarshal(byt, &data)
if tx.Hash().String() != data.TxHash {
t.Fatalf("txHash [%v]: tx Hash not found", tx.Hash().String())
}
if contractAddressFromReciept != data.To {
t.Fatalf("Contract Addr [%v]: Contract addr not found", contractAddressFromReciept)
}
if tx.From().String() != data.From {
t.Fatalf("From Addr [%v]: From addr not found", tx.From().String())
}
if tx.Nonce() != data.Nonce {
t.Fatalf("Nonce [%v]: Nonce not found", tx.Nonce())
}
if tx.Gas() != data.Gas {
t.Fatalf("Gas [%v]: Gas not found", tx.Gas())
}
if tx.GasPrice().Uint64() != data.GasPrice {
t.Fatalf("Gas Price [%v]: Gas price not found", tx.GasPrice().String())
}
if block.GasLimit() != data.GasLimit {
t.Fatalf("Gas Limit [%v]: Gas limit not found", block.GasLimit())
}
if block.Hash().String() != data.BlockHash {
t.Fatalf("Block Hash [%v]: Block hash not found", block.Hash().String())
}
if block.Number().String() != data.BlockNumber {
t.Fatalf("Block Number [%v]: Block number not found", block.Number().String())
}
if tx.Value().String() != data.Amount {
t.Fatalf("Amount [%v]: Amount not found", tx.Value().String())
}
if tx.Cost().Uint64() != data.Cost {
t.Fatalf("Cost [%v]: Cost not found", tx.Cost().String())
}
var status string
if receipt2.Status == 1 {
status = "SUCCESS"
}
if receipt2.Status == 0 {
status = "FAIL"
}
if status != data.Status {
t.Fatalf("Receipt status [%v]: Receipt status not found", status)
}
var isContract bool
if tx.To() != nil {
isContract = false
} else {
isContract = true
}
if isContract != data.IsContract {
t.Fatalf("isContract [%v]: isContract bool is incorrect", isContract)
}
}
ClearTables()
}
func TestTransactionsToReturnTransactions(t *testing.T) {
key, _ := crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
signer := types.NewEIP155Signer(big.NewInt(2147483647))
//Nonce, To Address,Value, GasLimit, Gasprice, data
tx1 := types.NewTransaction(1, common.BytesToAddress([]byte{0x11}), big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
mytx,_ := types.SignTx(tx1, signer, key)
tx2 := types.NewTransaction(2, common.BytesToAddress([]byte{0x22}), big.NewInt(222), 2222, big.NewInt(22222), []byte{0x22, 0x22, 0x22})
mytx2,_ := types.SignTx(tx2, signer, key)
tx3 := types.NewTransaction(3, common.BytesToAddress([]byte{0x33}), big.NewInt(333), 3333, big.NewInt(33333), []byte{0x33, 0x33, 0x33})
mytx3,_ := types.SignTx(tx3, signer, key)
txs := []*types.Transaction{mytx, mytx2, mytx3}
receipt1 := &types.Receipt{
Status: types.ReceiptStatusSuccessful,
CumulativeGasUsed: 1,
Logs: []*types.Log{
{Address: common.BytesToAddress([]byte{0x11})},
{Address: common.BytesToAddress([]byte{0x01, 0x11})},
},
TxHash: common.BytesToHash([]byte{0x11, 0x11}),
ContractAddress: common.BytesToAddress([]byte{0x01, 0x11, 0x11}),
GasUsed: 111111,
}
receipts := []*types.Receipt{receipt1}
block := types.NewBlock(&types.Header{Number: big.NewInt(314)}, txs, nil, receipts)
if err := WriteBlock(block, receipts); err != nil {
t.Fatalf("Failed to write block into database: %v", err)
}
sqldb, err := DBConnection()
if (err != nil) {
panic(err)
}
for _, tx := range txs {
txn := GetTransaction(sqldb, tx.Hash().String())
byt := []byte(txn)
var data ShyftTxEntryPretty
json.Unmarshal(byt, &data)
//TODO age, data
if tx.Hash().String() != data.TxHash {
t.Fatalf("txHash [%v]: tx Hash not found", tx.Hash().String())
}
if tx.From().String() != data.From {
t.Fatalf("From Addr [%v]: From addr not found", tx.From().String())
}
if tx.To().String() != data.To {
t.Fatalf("To Addr [%v]: To addr not found", tx.To().String())
}
if tx.Nonce() != data.Nonce {
t.Fatalf("Nonce [%v]: Nonce not found", tx.Nonce())
}
if tx.Gas() != data.Gas {
t.Fatalf("Gas [%v]: Gas not found", tx.Gas())
}
if tx.GasPrice().Uint64() != data.GasPrice {
t.Fatalf("Gas Price [%v]: Gas price not found", tx.GasPrice().String())
}
if block.GasLimit() != data.GasLimit {
t.Fatalf("Gas Limit [%v]: Gas limit not found", block.GasLimit())
}
if block.Hash().String() != data.BlockHash {
t.Fatalf("Block Hash [%v]: Block hash not found", block.Hash().String())
}
if block.Number().String() != data.BlockNumber {
t.Fatalf("Block Number [%v]: Block number not found", block.Number().String())
}
if tx.Value().String() != data.Amount {
t.Fatalf("Amount [%v]: Amount not found", tx.Value().String())
}
if tx.Cost().Uint64() != data.Cost {
t.Fatalf("Cost [%v]: Cost not found", tx.Cost().String())
}
var status string
if receipt1.Status == 1 {
status = "SUCCESS"
}
if receipt1.Status == 0 {
status = "FAIL"
}
if status != data.Status {
t.Fatalf("Receipt status [%v]: Receipt status not found", status)
}
var isContract bool
if tx.To() != nil {
isContract = false
} else {
isContract = true
}
if isContract != data.IsContract {
t.Fatalf("isContract [%v]: isContract bool is incorrect", isContract)
}
}
if getAllTx := GetAllTransactions(sqldb); len(getAllTx) == 0 {
t.Fatalf("GetAllTransactions [%v]: GetAllTransactions did not return correctly", getAllTx)
}
ClearTables()
}
func TestAccountsToReturnAccounts(t *testing.T) {
db := InitTestDB()
key, _ := crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
signer := types.NewEIP155Signer(big.NewInt(2147483647))
//Nonce, To Address,Value, GasLimit, Gasprice, data
tx1 := types.NewTransaction(1, common.BytesToAddress([]byte{0x11}), big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
mytx,_ := types.SignTx(tx1, signer, key)
tx2 := types.NewTransaction(2, common.BytesToAddress([]byte{0x22}), big.NewInt(222), 2222, big.NewInt(22222), []byte{0x22, 0x22, 0x22})
mytx2,_ := types.SignTx(tx2, signer, key)
tx3 := types.NewTransaction(3, common.BytesToAddress([]byte{0x33}), big.NewInt(333), 3333, big.NewInt(33333), []byte{0x33, 0x33, 0x33})
mytx3,_ := types.SignTx(tx3, signer, key)
txs := []*types.Transaction{mytx, mytx2, mytx3}
receipt1 := &types.Receipt{
Status: types.ReceiptStatusSuccessful,
CumulativeGasUsed: 1,
Logs: []*types.Log{
{Address: common.BytesToAddress([]byte{0x11})},
{Address: common.BytesToAddress([]byte{0x01, 0x11})},
},
TxHash: common.BytesToHash([]byte{0x11, 0x11}),
ContractAddress: common.BytesToAddress([]byte{0x01, 0x11, 0x11}),
GasUsed: 111111,
}
receipts := []*types.Receipt{receipt1}
block := types.NewBlock(&types.Header{Number: big.NewInt(315)}, txs, nil, receipts)
if err := WriteBlock(block, receipts); err != nil {
t.Fatalf("Failed to write block into database: %v", err)
}
for _, tx := range txs {
accountAddrTo := GetAccount(db, tx.To().String())
byts := []byte(accountAddrTo)
var accountDataTo SAccounts
json.Unmarshal(byts, &accountDataTo)
if tx.To().String() != accountDataTo.Addr {
t.Fatalf("To address [%v]: To address not found", accountDataTo.Addr)
}
if tx.Value().String() != accountDataTo.Balance {
t.Fatalf("To address balance [%v]: To address balance not found", accountDataTo.Balance)
}
if strconv.FormatUint(tx.Nonce(), 10) != accountDataTo.TxCountAccount {
t.Fatalf("To account nonce [%v]: To account nonce not found", accountDataTo.TxCountAccount)
}
if getAllAccountTxs := GetAccountTxs(db, tx.To().String()); len(getAllAccountTxs) == 0 {
t.Fatalf("GetAccountTxs [%v]: GetAccountTxs did not return correctly", getAllAccountTxs)
}
}
if getAllAccounts := GetAllAccounts(db); len(getAllAccounts) == 0 {
t.Fatalf("GetAllAccounts [%v]: GetAllAccounts did not return correctly", getAllAccounts)
}
ClearTables()
}

View file

@ -1,5 +0,0 @@
cd ./shyftDb/postgres_setup
sh drop_tables.sh && sh init_tables.sh
cd ..
cd ..
sh resetShyftGeth.sh && sh initShyftGeth.sh

View file

@ -1,27 +0,0 @@
// using contract from https://www.ethereum.org/greeter
// compiled on remix
var _greeting = "Greeter Contract" ;
var greeterContract = web3.eth.contract([{"constant":false,"inputs":[],"name":"kill","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"greet","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"inputs":[{"name":"_greeting","type":"string"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"}]);
var greeter = greeterContract.new(
_greeting,
{
from: web3.eth.accounts[0],
data: '0x6060604052341561000f57600080fd5b6040516103a93803806103a983398101604052808051820191905050336000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508060019080519060200190610081929190610088565b505061012d565b828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106100c957805160ff19168380011785556100f7565b828001600101855582156100f7579182015b828111156100f65782518255916020019190600101906100db565b5b5090506101049190610108565b5090565b61012a91905b8082111561012657600081600090555060010161010e565b5090565b90565b61026d8061013c6000396000f30060606040526004361061004c576000357c0100000000000000000000000000000000000000000000000000000000900463ffffffff16806341c0e1b514610051578063cfae321714610066575b600080fd5b341561005c57600080fd5b6100646100f4565b005b341561007157600080fd5b610079610185565b6040518080602001828103825283818151815260200191508051906020019080838360005b838110156100b957808201518184015260208101905061009e565b50505050905090810190601f1680156100e65780820380516001836020036101000a031916815260200191505b509250505060405180910390f35b6000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff163373ffffffffffffffffffffffffffffffffffffffff161415610183576000809054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16ff5b565b61018d61022d565b60018054600181600116156101000203166002900480601f0160208091040260200160405190810160405280929190818152602001828054600181600116156101000203166002900480156102235780601f106101f857610100808354040283529160200191610223565b820191906000526020600020905b81548152906001019060200180831161020657829003601f168201915b5050505050905090565b6020604051908101604052806000815250905600a165627a7a7230582015882dcaabcda0ebdb1b26a10e36f26a424e148671f4703dde3c1956ebaa67830029',
gas: '4700000'
}, function (e, contract){
if(!e) {
// NOTE: The callback will fire twice!
// Once the contract has the transactionHash property set and once its deployed on an address.
// e.g. check tx hash on the first call (transaction send)
if(!contract.address) {
console.log("TX hash:")
console.log(contract.transactionHash) // The hash of the transaction, which deploys the contract
} else {
console.log("Contract address:")
console.log(contract.address) // the contract address
}
}
})

View file

@ -1,9 +0,0 @@
`npm install`
run `node deploy.js` to deploy the contract.
this will log out a contract in the geth logs.
set the ADDR environment variable to this contract address.
ie `export ADDR=<contract_addr>`
then run `node calltx.js`