This commit is contained in:
Sagar Rambhia 2014-03-14 02:03:33 +00:00
commit c0a642fd21
12 changed files with 208 additions and 128 deletions

20
Makefile Normal file
View file

@ -0,0 +1,20 @@
UNAME = $(shell uname)
# Default is building
all:
go install
install:
# Linux build
ifeq ($(UNAME),Linux)
mkdir /usr/local/ethereal
files=(wallet.qml net.png network.png new.png tx.png)
for file in "${files[@]}"; do
cp $file /usr/share/ethereal
done
cp $GOPATH/bin/go-ethereum /usr/local/bin/ethereal
endif
# OS X build
ifeq ($(UNAME),Darwin)
# Execute py script
endif

View file

@ -5,8 +5,7 @@ Ethereum
Ethereum Go Client (c) Jeffrey Wilcke Ethereum Go Client (c) Jeffrey Wilcke
The current state is "Proof of Concept 3". For build instructions see The current state is "Proof of Concept 3".
the [Wiki](https://github.com/ethereum/go-ethereum/wiki/Building-Edge).
For the development Go Package please see [eth-go package](https://github.com/ethereum/eth-go). For the development Go Package please see [eth-go package](https://github.com/ethereum/eth-go).

View file

@ -158,11 +158,11 @@ func (i *Console) ParseInput(input string) bool {
fmt.Println(value) fmt.Println(value)
case "getaddr": case "getaddr":
encoded, _ := hex.DecodeString(tokens[1]) encoded, _ := hex.DecodeString(tokens[1])
addr := i.ethereum.BlockManager.BlockChain().CurrentBlock.GetAddr(encoded) addr := i.ethereum.BlockChain().CurrentBlock.State().GetAccount(encoded)
fmt.Println("addr:", addr) fmt.Println("addr:", addr)
case "block": case "block":
encoded, _ := hex.DecodeString(tokens[1]) encoded, _ := hex.DecodeString(tokens[1])
block := i.ethereum.BlockManager.BlockChain().GetBlock(encoded) block := i.ethereum.BlockChain().GetBlock(encoded)
info := block.BlockInfo() info := block.BlockInfo()
fmt.Printf("++++++++++ #%d ++++++++++\n%v\n", info.Number, block) fmt.Printf("++++++++++ #%d ++++++++++\n%v\n", info.Number, block)
case "say": case "say":
@ -182,7 +182,7 @@ func (i *Console) ParseInput(input string) bool {
key := ethutil.Config.Db.GetKeys()[0] key := ethutil.Config.Db.GetKeys()[0]
tx.Sign(key.PrivateKey) tx.Sign(key.PrivateKey)
i.ethereum.TxPool.QueueTransaction(tx) i.ethereum.TxPool().QueueTransaction(tx)
fmt.Printf("%x\n", tx.Hash()) fmt.Printf("%x\n", tx.Hash())
} }
@ -204,7 +204,7 @@ func (i *Console) ParseInput(input string) bool {
key := ethutil.Config.Db.GetKeys()[0] key := ethutil.Config.Db.GetKeys()[0]
contract.Sign(key.PrivateKey) contract.Sign(key.PrivateKey)
i.ethereum.TxPool.QueueTransaction(contract) i.ethereum.TxPool().QueueTransaction(contract)
fmt.Printf("%x\n", contract.Hash()[12:]) fmt.Printf("%x\n", contract.Hash()[12:])
case "exit", "quit", "q": case "exit", "quit", "q":

View file

@ -144,7 +144,7 @@ func main() {
} }
if ShowGenesis { if ShowGenesis {
fmt.Println(ethereum.BlockManager.BlockChain().Genesis()) fmt.Println(ethereum.BlockChain().Genesis())
os.Exit(0) os.Exit(0)
} }
@ -183,22 +183,24 @@ func main() {
addr := keyRing.Get(1).Bytes() addr := keyRing.Get(1).Bytes()
for { for {
txs := ethereum.TxPool.Flush() txs := ethereum.TxPool().Flush()
// Create a new block which we're going to mine // Create a new block which we're going to mine
block := ethereum.BlockManager.BlockChain().NewBlock(addr, txs) block := ethereum.BlockChain().NewBlock(addr, txs)
log.Println("Mining on new block. Includes", len(block.Transactions()), "transactions")
// Apply all transactions to the block // Apply all transactions to the block
ethereum.BlockManager.ApplyTransactions(block, block.Transactions()) ethereum.StateManager().ApplyTransactions(block, block.Transactions())
ethereum.BlockManager.AccumelateRewards(block, block) ethereum.StateManager().AccumelateRewards(block, block)
// Search the nonce // Search the nonce
block.Nonce = pow.Search(block) block.Nonce = pow.Search(block)
ethereum.Broadcast(ethwire.MsgBlockTy, []interface{}{block.Value().Val}) ethereum.Broadcast(ethwire.MsgBlockTy, []interface{}{block.Value().Val})
err := ethereum.BlockManager.ProcessBlock(block) err := ethereum.StateManager().ProcessBlock(block)
if err != nil { if err != nil {
log.Println(err) log.Println(err)
} else { } else {
log.Println("\n+++++++ MINED BLK +++++++\n", ethereum.BlockManager.BlockChain().CurrentBlock) //log.Println("\n+++++++ MINED BLK +++++++\n", ethereum.BlockChain().CurrentBlock)
log.Printf("🔨 Mined block %x\n", block.Hash())
} }
} }
}() }()

BIN
net.pxm

Binary file not shown.

View file

@ -85,7 +85,7 @@ ApplicationWindow {
anchors.right: parent.right anchors.right: parent.right
height: 200 height: 200
Image { Image {
source: "tx.png" source: ui.assetPath("tx.png")
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
MouseArea { MouseArea {
anchors.fill: parent anchors.fill: parent
@ -95,7 +95,7 @@ ApplicationWindow {
} }
} }
Image { Image {
source: "new.png" source: ui.assetPath("new.png")
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
MouseArea { MouseArea {
anchors.fill: parent anchors.fill: parent
@ -105,7 +105,7 @@ ApplicationWindow {
} }
} }
Image { Image {
source: "net.png" source: ui.assetPath("net.png")
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
MouseArea { MouseArea {
anchors.fill: parent anchors.fill: parent
@ -115,116 +115,141 @@ ApplicationWindow {
} }
} }
} }
}
property var txModel: ListModel {
id: txModel
} }
Rectangle { Rectangle {
id: historyView id: mainView
property var title: "Transactions"
anchors.right: parent.right
anchors.left: menu.right
anchors.bottom: parent.bottom
anchors.top: parent.top
TableView {
id: txTableView
anchors.fill: parent
TableViewColumn{ role: "value" ; title: "Value" ; width: 100 }
TableViewColumn{ role: "address" ; title: "Address" ; width: 430 }
model: txModel
}
}
Rectangle {
id: newTxView
property var title: "New transaction"
visible: false
anchors.right: parent.right
anchors.left: menu.right
anchors.bottom: parent.bottom
anchors.top: parent.top
color: "#00000000" color: "#00000000"
anchors.right: parent.right
anchors.left: menu.right
anchors.bottom: parent.bottom
anchors.top: parent.top
ColumnLayout { property var txModel: ListModel {
width: 400 id: txModel
anchors.left: parent.left }
anchors.top: parent.top
anchors.leftMargin: 5
anchors.topMargin: 5
TextField {
id: txAmount
width: 200
placeholderText: "Amount"
}
TextField { Rectangle {
id: txReceiver id: historyView
placeholderText: "Receiver Address (or empty for contract)" anchors.fill: parent
Layout.fillWidth: true
}
Label { property var title: "Transactions"
text: "Transaction data" TableView {
id: txTableView
anchors.fill: parent
TableViewColumn{ role: "value" ; title: "Value" ; width: 100 }
TableViewColumn{ role: "address" ; title: "Address" ; width: 430 }
model: txModel
} }
TextArea { }
id: codeView
Rectangle {
id: newTxView
property var title: "New transaction"
visible: false
anchors.fill: parent
color: "#00000000"
ColumnLayout {
width: 400
anchors.left: parent.left
anchors.top: parent.top
anchors.leftMargin: 5
anchors.topMargin: 5 anchors.topMargin: 5
Layout.fillWidth: true TextField {
width: parent.width /2 id: txAmount
} width: 200
placeholderText: "Amount"
}
Button { TextField {
text: "Send" id: txReceiver
onClicked: { placeholderText: "Receiver Address (or empty for contract)"
console.log(eth.createTx(txReceiver.text, txAmount.text, codeView.text)) Layout.fillWidth: true
}
Label {
text: "Transaction data"
}
TextArea {
id: codeView
anchors.topMargin: 5
Layout.fillWidth: true
width: parent.width /2
}
Button {
text: "Send"
onClicked: {
console.log(eth.createTx(txReceiver.text, txAmount.text, codeView.text))
}
} }
} }
} }
}
Rectangle { Rectangle {
id: networkView id: networkView
property var title: "Network" property var title: "Network"
visible: false visible: false
anchors.right: parent.right anchors.fill: parent
anchors.bottom: parent.bottom
anchors.top: parent.top
TableView { TableView {
id: blockTable id: blockTable
width: parent.width width: parent.width
anchors.top: parent.top anchors.top: parent.top
anchors.bottom: logView.top anchors.bottom: logView.top
TableViewColumn{ role: "number" ; title: "#" ; width: 100 } TableViewColumn{ role: "number" ; title: "#" ; width: 100 }
TableViewColumn{ role: "hash" ; title: "Hash" ; width: 560 } TableViewColumn{ role: "hash" ; title: "Hash" ; width: 560 }
model: blockModel model: blockModel
onDoubleClicked: { /*
popup.visible = true onDoubleClicked: {
popup.block = eth.getBlock(blockModel.get(row).hash) popup.visible = true
popup.hashLabel.text = popup.block.hash popup.block = eth.getBlock(blockModel.get(row).hash)
popup.hashLabel.text = popup.block.hash
}
*/
}
property var logModel: ListModel {
id: logModel
}
TableView {
id: logView
width: parent.width
height: 150
anchors.bottom: parent.bottom
TableViewColumn{ role: "description" ; title: "log" }
model: logModel
} }
} }
property var logModel: ListModel { /*
id: logModel signal addPlugin(string name)
Component {
id: pluginWindow
Rectangle {
anchors.fill: parent
Label {
id: pluginTitle
anchors.centerIn: parent
text: "Hello world"
}
Component.onCompleted: setView(this)
}
} }
TableView { onAddPlugin: {
id: logView var pluginWin = pluginWindow.createObject(mainView)
width: parent.width console.log(pluginWin)
height: 150 pluginWin.pluginTitle.text = "Test"
anchors.bottom: parent.bottom
TableViewColumn{ role: "description" ; title: "log" }
model: logModel
} }
*/
} }
} }
@ -249,6 +274,7 @@ ApplicationWindow {
} }
text: "Connect" text: "Connect"
} }
Button { Button {
id: importAppButton id: importAppButton
anchors.left: connectButton.right anchors.left: connectButton.right
@ -274,7 +300,7 @@ ApplicationWindow {
id: peerImage id: peerImage
anchors.right: parent.right anchors.right: parent.right
width: 10; height: 10 width: 10; height: 10
source: "network.png" source: ui.assetPath("network.png")
} }
} }
} }
@ -304,6 +330,10 @@ ApplicationWindow {
anchors.left: parent.left anchors.left: parent.left
anchors.leftMargin: 10 anchors.leftMargin: 10
placeholderText: "address:port" placeholderText: "address:port"
onAccepted: {
ui.connectToPeer(addrField.text)
addPeerWin.visible = false
}
} }
Button { Button {
anchors.left: addrField.right anchors.left: addrField.right
@ -315,6 +345,9 @@ ApplicationWindow {
addPeerWin.visible = false addPeerWin.visible = false
} }
} }
Component.onCompleted: {
addrField.focus = true
}
} }
Window { Window {
@ -332,7 +365,7 @@ ApplicationWindow {
width: 150 width: 150
fillMode: Image.PreserveAspectFit fillMode: Image.PreserveAspectFit
smooth: true smooth: true
source: "facet.png" source: ui.assetPath("facet.png")
x: 10 x: 10
y: 10 y: 10
} }
@ -346,6 +379,11 @@ ApplicationWindow {
} }
function loadPlugin(name) {
console.log("Loading plugin" + name)
mainView.addPlugin(name)
}
function setWalletValue(value) { function setWalletValue(value) {
walletValueLabel.text = value walletValueLabel.text = value
} }

BIN
tx.pxm

Binary file not shown.

View file

@ -9,8 +9,6 @@ import (
"github.com/ethereum/eth-go/ethdb" "github.com/ethereum/eth-go/ethdb"
"github.com/ethereum/eth-go/ethutil" "github.com/ethereum/eth-go/ethutil"
"github.com/niemeyer/qml" "github.com/niemeyer/qml"
"bitbucket.org/kardianos/osext"
"path/filepath"
"math/big" "math/big"
"strings" "strings"
) )
@ -59,7 +57,7 @@ type Gui struct {
// Create GUI, but doesn't start it // Create GUI, but doesn't start it
func New(ethereum *eth.Ethereum) *Gui { func New(ethereum *eth.Ethereum) *Gui {
lib := &EthLib{blockManager: ethereum.BlockManager, blockChain: ethereum.BlockManager.BlockChain(), txPool: ethereum.TxPool} lib := &EthLib{stateManager: ethereum.StateManager(), blockChain: ethereum.BlockChain(), txPool: ethereum.TxPool()}
db, err := ethdb.NewLDBDatabase("tx_database") db, err := ethdb.NewLDBDatabase("tx_database")
if err != nil { if err != nil {
panic(err) panic(err)
@ -68,7 +66,7 @@ func New(ethereum *eth.Ethereum) *Gui {
key := ethutil.Config.Db.GetKeys()[0] key := ethutil.Config.Db.GetKeys()[0]
addr := key.Address() addr := key.Address()
ethereum.BlockManager.WatchAddr(addr) ethereum.StateManager().WatchAddr(addr)
return &Gui{eth: ethereum, lib: lib, txDb: db, addr: addr} return &Gui{eth: ethereum, lib: lib, txDb: db, addr: addr}
} }
@ -86,27 +84,23 @@ func (ui *Gui) Start() {
ethutil.Config.Log.Infoln("[GUI] Starting GUI") ethutil.Config.Log.Infoln("[GUI] Starting GUI")
// Create a new QML engine // Create a new QML engine
ui.engine = qml.NewEngine() ui.engine = qml.NewEngine()
// Get Binary Directory
exedir , _ := osext.ExecutableFolder()
// Load the main QML interface
component, err := ui.engine.LoadFile(filepath.Join(exedir, "wallet.qml"))
if err != nil {
panic(err)
}
ui.engine.LoadFile(filepath.Join(exedir, "transactions.qml"))
ui.win = component.CreateWindow(nil)
context := ui.engine.Context() context := ui.engine.Context()
// Expose the eth library and the ui library to QML // Expose the eth library and the ui library to QML
context.SetVar("eth", ui.lib) context.SetVar("eth", ui.lib)
context.SetVar("ui", &UiLib{engine: ui.engine, eth: ui.eth}) context.SetVar("ui", &UiLib{engine: ui.engine, eth: ui.eth})
// Load the main QML interface
component, err := ui.engine.LoadFile(AssetPath("qml/wallet.qml"))
if err != nil {
panic(err)
}
ui.engine.LoadFile(AssetPath("qml/transactions.qml"))
ui.win = component.CreateWindow(nil)
// Register the ui as a block processor // Register the ui as a block processor
ui.eth.BlockManager.SecondaryBlockProcessor = ui //ui.eth.BlockManager.SecondaryBlockProcessor = ui
//ui.eth.TxPool.SecondaryProcessor = ui //ui.eth.TxPool.SecondaryProcessor = ui
// Add the ui as a log system so we can log directly to the UGI // Add the ui as a log system so we can log directly to the UGI
@ -125,7 +119,7 @@ func (ui *Gui) Start() {
func (ui *Gui) setInitialBlockChain() { func (ui *Gui) setInitialBlockChain() {
// Load previous 10 blocks // Load previous 10 blocks
chain := ui.eth.BlockManager.BlockChain().GetChain(ui.eth.BlockManager.BlockChain().CurrentBlock.Hash(), 10) chain := ui.eth.BlockChain().GetChain(ui.eth.BlockChain().CurrentBlock.Hash(), 10)
for _, block := range chain { for _, block := range chain {
ui.ProcessBlock(block) ui.ProcessBlock(block)
} }
@ -149,9 +143,9 @@ func (ui *Gui) ProcessBlock(block *ethchain.Block) {
// Simple go routine function that updates the list of peers in the GUI // Simple go routine function that updates the list of peers in the GUI
func (ui *Gui) update() { func (ui *Gui) update() {
txChan := make(chan ethchain.TxMsg, 1) txChan := make(chan ethchain.TxMsg, 1)
ui.eth.TxPool.Subscribe(txChan) ui.eth.TxPool().Subscribe(txChan)
account := ui.eth.BlockManager.GetAddrState(ui.addr).Account account := ui.eth.StateManager().GetAddrState(ui.addr).Account
unconfirmedFunds := new(big.Int) unconfirmedFunds := new(big.Int)
ui.win.Root().Call("setWalletValue", fmt.Sprintf("%v", ethutil.CurrencyToString(account.Amount))) ui.win.Root().Call("setWalletValue", fmt.Sprintf("%v", ethutil.CurrencyToString(account.Amount)))
for { for {
@ -164,7 +158,7 @@ func (ui *Gui) update() {
ui.win.Root().Call("addTx", NewTxFromTransaction(tx)) ui.win.Root().Call("addTx", NewTxFromTransaction(tx))
ui.txDb.Put(tx.Hash(), tx.RlpEncode()) ui.txDb.Put(tx.Hash(), tx.RlpEncode())
ui.eth.BlockManager.GetAddrState(ui.addr).Nonce += 1 ui.eth.StateManager().GetAddrState(ui.addr).Nonce += 1
unconfirmedFunds.Sub(unconfirmedFunds, tx.Value) unconfirmedFunds.Sub(unconfirmedFunds, tx.Value)
} else if bytes.Compare(tx.Recipient, ui.addr) == 0 { } else if bytes.Compare(tx.Recipient, ui.addr) == 0 {
ui.win.Root().Call("addTx", NewTxFromTransaction(tx)) ui.win.Root().Call("addTx", NewTxFromTransaction(tx))

View file

@ -9,7 +9,7 @@ import (
) )
type EthLib struct { type EthLib struct {
blockManager *ethchain.BlockManager stateManager *ethchain.StateManager
blockChain *ethchain.BlockChain blockChain *ethchain.BlockChain
txPool *ethchain.TxPool txPool *ethchain.TxPool
} }
@ -32,7 +32,7 @@ func (lib *EthLib) CreateTx(receiver, a, data string) string {
amount := ethutil.Big(a) amount := ethutil.Big(a)
code := ethchain.Compile(strings.Split(data, "\n")) code := ethchain.Compile(strings.Split(data, "\n"))
tx := ethchain.NewTransaction(hash, amount, code) tx := ethchain.NewTransaction(hash, amount, code)
tx.Nonce = lib.blockManager.GetAddrState(keyRing.Get(1).Bytes()).Nonce tx.Nonce = lib.stateManager.GetAddrState(keyRing.Get(1).Bytes()).Nonce
tx.Sign(keyRing.Get(0).Bytes()) tx.Sign(keyRing.Get(0).Bytes())

View file

@ -1,9 +1,13 @@
package ethui package ethui
import ( import (
"bitbucket.org/kardianos/osext"
"github.com/ethereum/eth-go" "github.com/ethereum/eth-go"
"github.com/ethereum/eth-go/ethutil" "github.com/ethereum/eth-go/ethutil"
"github.com/niemeyer/qml" "github.com/niemeyer/qml"
"path"
"path/filepath"
"runtime"
) )
// UI Library that has some basic functionality exposed // UI Library that has some basic functionality exposed
@ -38,3 +42,26 @@ func (ui *UiLib) Connect(button qml.Object) {
func (ui *UiLib) ConnectToPeer(addr string) { func (ui *UiLib) ConnectToPeer(addr string) {
ui.eth.ConnectToPeer(addr) ui.eth.ConnectToPeer(addr)
} }
func (ui *UiLib) AssetPath(p string) string {
return AssetPath(p)
}
func AssetPath(p string) string {
var base string
switch runtime.GOOS {
case "darwin":
// Get Binary Directory
exedir, _ := osext.ExecutableFolder()
base = filepath.Join(exedir, "../Resources")
base = "/Users/jeffrey/go/src/github.com/ethereum/go-ethereum"
case "linux":
base = "/usr/share/ethereal"
case "window":
fallthrough
default:
base = "."
}
return path.Join(base, p)
}