diff --git a/api/proto/message/server.go b/api/proto/message/server.go index 0506391a5..6c1995eae 100644 --- a/api/proto/message/server.go +++ b/api/proto/message/server.go @@ -40,13 +40,17 @@ func (s *Server) Process(ctx context.Context, message *Message) (*Response, erro return nil, ErrEnterMethod } return &Response{}, nil - } else if lotteryRequest.GetType() == LotteryRequest_RESULT { - // if err := s.GetResult(); err != nil { - // return &Response{}, ErrResultMethod - // } else { - // return &Response{}, nil - // } + players, balances := s.GetResult() + ret := &Response{ + Response: &Response_LotteryResponse{ + LotteryResponse: &LotteryResponse{ + Players: players, + Balances: balances, + }, + }, + } + return ret, nil } return &Response{}, nil } diff --git a/cmd/demo/main.go b/cmd/demo/main.go index 21b80f203..51b32d514 100644 --- a/cmd/demo/main.go +++ b/cmd/demo/main.go @@ -2,8 +2,10 @@ package main import ( "encoding/json" + "fmt" "net" "net/http" + "strconv" "github.com/gorilla/mux" msg_pb "github.com/harmony-one/harmony/api/proto/message" @@ -11,7 +13,7 @@ import ( // Constants for main demo. const ( - Port = "313131" + Port = "31313" LocalIP = "127.0.0.1" ) @@ -23,13 +25,52 @@ var ( // Enter processes /enter end point. func Enter(w http.ResponseWriter, r *http.Request) { w.Header().Set("Content-Type", "application/json") - json.NewEncoder(w).Encode("") + key := r.FormValue("key") + amount, err := strconv.ParseInt(r.FormValue("amount"), 10, 0) + if err != nil { + fmt.Println(err) + json.NewEncoder(w).Encode("") + return + } + + msg := &msg_pb.Message{ + Request: &msg_pb.Message_LotteryRequest{ + LotteryRequest: &msg_pb.LotteryRequest{ + Type: msg_pb.LotteryRequest_ENTER, + PrivateKey: key, + Amount: amount, + }, + }, + } + res, err := grpcClient.Process(msg) + if err != nil { + fmt.Println(err) + json.NewEncoder(w).Encode("") + return + } + json.NewEncoder(w).Encode(res) } // Result processes /result end point. func Result(w http.ResponseWriter, r *http.Request) { w.Header().Set("Content-Type", "application/json") + json.NewEncoder(w).Encode("") + msg := &msg_pb.Message{ + Request: &msg_pb.Message_LotteryRequest{ + LotteryRequest: &msg_pb.LotteryRequest{ + Type: msg_pb.LotteryRequest_RESULT, + }, + }, + } + + res, err := grpcClient.Process(msg) + if err != nil { + fmt.Println(err) + json.NewEncoder(w).Encode("") + return + } + json.NewEncoder(w).Encode(res) } func main() { @@ -37,11 +78,12 @@ func main() { router := mux.NewRouter() // Set up router for server. - router.Path("/enter").Queries("key", "{[0-9A-Fa-fx]*?}", "ether", "[0-9]*").HandlerFunc(Enter).Methods("GET") + router.Path("/enter").Queries("key", "{[0-9A-Fa-fx]*?}", "amount", "[0-9]*").HandlerFunc(Enter).Methods("GET") router.Path("/enter").HandlerFunc(Enter) router.Path("/result").HandlerFunc(Result) server := &http.Server{Addr: addr, Handler: router} + fmt.Println("Serving") server.ListenAndServe() } diff --git a/contracts/structs/structs.go b/contracts/structs/structs.go index 666751127..273a4391a 100644 --- a/contracts/structs/structs.go +++ b/contracts/structs/structs.go @@ -22,3 +22,9 @@ type StakeInfo struct { LockPeriodCount *big.Int // The number of locking period the token will be locked. Amount *big.Int } + +// PlayersInfo stores the result of getPlayers. +type PlayersInfo struct { + Players []common.Address + Balances []*big.Int +} diff --git a/node/contract.go b/node/contract.go index 3aa03b3e9..9885d5e56 100644 --- a/node/contract.go +++ b/node/contract.go @@ -118,6 +118,15 @@ func (node *Node) GetNonceOfAddress(address common.Address) uint64 { return state.GetNonce(address) } +// GetBalanceOfAddress returns balance of an address. +func (node *Node) GetBalanceOfAddress(address common.Address) uint64 { + state, err := node.blockchain.State() + if err != nil { + log.Error("Failed to get chain state", "Error", err) + } + return state.GetBalance(address).Uint64() +} + // AddFaucetContractToPendingTransactions adds the faucet contract the genesis block. func (node *Node) AddFaucetContractToPendingTransactions() { // Add a contract deployment transactionv @@ -154,8 +163,8 @@ func (node *Node) callGetFreeTokenWithNonce(address common.Address, nonce uint64 if err != nil { utils.GetLogInstance().Error("Failed to generate ABI function bytes data", "error", err) } - utils.GetLogInstance().Info("Sending Free Token to ", "Address", address.Hex()) tx, _ := types.SignTx(types.NewTransaction(nonce, node.ContractAddresses[0], node.Consensus.ShardID, big.NewInt(0), params.TxGasContractCreation*10, nil, bytesData), types.HomesteadSigner{}, node.ContractDeployerKey) + utils.GetLogInstance().Info("Sending Free Token to ", "Address", address.Hex()) node.addPendingTransactions(types.Transactions{tx}) return tx.Hash() diff --git a/node/demo_contract.go b/node/demo_contract.go index 076f3350e..4b406cea2 100644 --- a/node/demo_contract.go +++ b/node/demo_contract.go @@ -43,6 +43,7 @@ func (node *Node) AddLotteryContract() { types.HomesteadSigner{}, priKey) node.DemoContractAddress = crypto.CreateAddress(crypto.PubkeyToAddress(priKey.PublicKey), uint64(0)) + node.DemoContractPrivateKey = priKey node.addPendingTransactions(types.Transactions{demoContract}) } @@ -64,11 +65,13 @@ func (node *Node) CreateTransactionForEnterMethod(amount int64, priKey string) e key, err := crypto.HexToECDSA(priKey) nonce := node.GetNonceOfAddress(crypto.PubkeyToAddress(key.PublicKey)) + Amount := big.NewInt(amount) + Amount = Amount.Mul(Amount, big.NewInt(params.Ether)) tx := types.NewTransaction( nonce, toAddress, 0, - big.NewInt(amount), + Amount, params.TxGas*10, nil, bytesData, @@ -86,7 +89,62 @@ func (node *Node) CreateTransactionForEnterMethod(amount int64, priKey string) e return err } +// GetResult2 get current players and their balances. +func (node *Node) GetResult2() (players []string, balances []uint64) { + for _, account := range contract_constants.DemoAccounts { + players = append(players, account.Address) + key, err := crypto.HexToECDSA(account.Private) + if err != nil { + utils.GetLogInstance().Error("Error when HexToECDSA") + } + address := crypto.PubkeyToAddress(key.PublicKey) + balances = append(balances, node.GetBalanceOfAddress(address)) + } + return players, balances +} + // GetResult get current players and their balances. func (node *Node) GetResult() (players []string, balances []uint64) { - return []string{}, []uint64{} + return node.GetResult2() + // abi, err := abi.JSON(strings.NewReader(contracts.LotteryABI)) + // if err != nil { + // utils.GetLogInstance().Error("Failed to generate staking contract's ABI", "error", err) + // } + // bytesData, err := abi.Pack("getPlayers") + // if err != nil { + // utils.GetLogInstance().Error("Failed to generate ABI function bytes data", "error", err) + // } + + // demoContractAddress := node.DemoContractAddress + // demoContractPrivateKey := node.DemoContractPrivateKey + + // tx := types.NewTransaction( + // node.GetNonceOfAddress(demoContractAddress), + // demoContractAddress, + // 0, + // nil, + // math.MaxUint64, + // nil, + // bytesData, + // ) + // signedTx, err := types.SignTx(tx, types.HomesteadSigner{}, demoContractPrivateKey) + // if err != nil { + // utils.GetLogInstance().Error("Failed to sign contract call tx", "error", err) + // return nil + // } + // output, err := node.ContractCaller.CallContract(signedTx) + + // if err != nil { + // utils.GetLogInstance().Error("Failed to call staking contract", "error", err) + // return nil + // } + + // ret := &structs.PlayersInfo{} + // err = abi.Unpack(ret, "getPlayers", output) + + // if err != nil { + // utils.GetLogInstance().Error("Failed to unpack stake info", "error", err) + // return nil + // } + // return ret } diff --git a/node/node.go b/node/node.go index 3a19f286c..ca5a9df06 100644 --- a/node/node.go +++ b/node/node.go @@ -134,9 +134,12 @@ type Node struct { //Staked Accounts and Contract CurrentStakes map[common.Address]*structs.StakeInfo //This will save the latest information about staked nodes. StakingContractAddress common.Address - DemoContractAddress common.Address WithdrawStakeFunc []byte + // Demo account. + DemoContractAddress common.Address + DemoContractPrivateKey *ecdsa.PrivateKey + //Node Account AccountKey *ecdsa.PrivateKey Address common.Address diff --git a/node/node_genesis.go b/node/node_genesis.go index f14268e7f..a2f10f4c7 100644 --- a/node/node_genesis.go +++ b/node/node_genesis.go @@ -7,6 +7,8 @@ import ( "strings" "time" + "github.com/harmony-one/harmony/internal/utils" + "github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/ethdb" @@ -95,4 +97,11 @@ func AddNodeAddressesToGenesisAlloc(genesisAlloc core.GenesisAlloc) { address := common.HexToAddress(account.Address) genesisAlloc[address] = core.GenesisAccount{Balance: testBankFunds} } + for _, account := range contract.DemoAccounts { + testBankFunds := big.NewInt(InitFreeFundInEther) + testBankFunds = testBankFunds.Mul(testBankFunds, big.NewInt(params.Ether)) + address := common.HexToAddress(account.Address) + genesisAlloc[address] = core.GenesisAccount{Balance: testBankFunds} + utils.GetLogInstance().Info("****free money****", "address", address, "balance", testBankFunds) + } } diff --git a/node/node_handler.go b/node/node_handler.go index ea639965e..4cff8e422 100644 --- a/node/node_handler.go +++ b/node/node_handler.go @@ -333,6 +333,17 @@ func (node *Node) PostConsensusProcessing(newBlock *types.Block) { } } } + + // TODO(minhdoan): clean debug later. + // node.Debug() +} + +// Debug -- +func (node *Node) Debug() { + players, balances := node.GetResult() + for i := range players { + utils.GetLogInstance().Info("******RESULT****", "player", players[i], "balance", balances[i]) + } } // AddNewBlock is usedd to add new block into the blockchain.