Skip to content
This repository has been archived by the owner on Nov 16, 2022. It is now read-only.

Commit

Permalink
Merge pull request #2058 from bandprotocol/faucet-server
Browse files Browse the repository at this point in the history
chain:Implement faucet service for testnet
  • Loading branch information
Benzbeeb authored Jun 24, 2020
2 parents 07ed2b5 + 98280db commit 3a8282d
Show file tree
Hide file tree
Showing 13 changed files with 490 additions and 6 deletions.
1 change: 1 addition & 0 deletions CHANGELOG_UNRELEASED.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

### Chain

- (feat) [\#2058](https://github.com/bandprotocol/bandchain/pull/2058) Implement faucet service for testnet.
- (impv) [\#2057](https://github.com/bandprotocol/bandchain/pull/2057) Change wasm execute gas to 100000.
- (chore) [\#2053](https://github.com/bandprotocol/bandchain/pull/2053) Remove data sources and oracle scripts from repo.
- (chore) [\#2056](https://github.com/bandprotocol/bandchain/pull/2056) Remove IBCInfo from current v0.38 release.
Expand Down
2 changes: 1 addition & 1 deletion chain/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,6 @@ COPY chain/ /chain

COPY chain/docker-config/run.sh .

RUN make install
RUN make install && make faucet

CMD bandd start --rpc.laddr tcp://0.0.0.0:26657
3 changes: 3 additions & 0 deletions chain/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@ install: go.sum
go install -mod=readonly $(BUILD_FLAGS) ./cmd/bandcli
go install -mod=readonly $(BUILD_FLAGS) ./cmd/bandoracled2

faucet: go.sum
go install -mod=readonly $(BUILD_FLAGS) ./cmd/faucet

release: go.sum
env GOOS=linux GOARCH=amd64 \
go build -mod=readonly -o ./build/bandd_linux_amd64 $(BUILD_FLAGS) ./cmd/bandd
Expand Down
7 changes: 3 additions & 4 deletions chain/cmd/bandoracled2/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,9 @@ import (
)

const (
flagValidator = "validator"
flagLogLevel = "log-level"
flagExecutor = "executor"
flagChainRestServerURI = "chain-rest-server"
flagValidator = "validator"
flagLogLevel = "log-level"
flagExecutor = "executor"
)

// Config data structure for bandoracled daemon.
Expand Down
20 changes: 20 additions & 0 deletions chain/cmd/faucet/config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package main

import (
"github.com/spf13/cobra"
"github.com/spf13/viper"
)

func configCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "config [key] [value]",
Aliases: []string{"c"},
Short: "Set faucet configuration environment",
Args: cobra.ExactArgs(2),
RunE: func(cmd *cobra.Command, args []string) error {
viper.Set(args[0], args[1])
return viper.WriteConfig()
},
}
return cmd
}
14 changes: 14 additions & 0 deletions chain/cmd/faucet/context.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package main

import (
"github.com/cosmos/cosmos-sdk/crypto/keys"
sdk "github.com/cosmos/cosmos-sdk/types"
rpcclient "github.com/tendermint/tendermint/rpc/client"
)

type Context struct {
client rpcclient.Client
gasPrices sdk.DecCoins
keys chan keys.Info
amount sdk.Coins
}
82 changes: 82 additions & 0 deletions chain/cmd/faucet/handler.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
package main

import (
"fmt"
"net/http"

"github.com/bandprotocol/bandchain/chain/app"
sdkctx "github.com/cosmos/cosmos-sdk/client/context"
ckeys "github.com/cosmos/cosmos-sdk/client/keys"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/x/auth"
"github.com/cosmos/cosmos-sdk/x/bank"
"github.com/gin-gonic/gin"
)

type Request struct {
Address string `json:"address" binding:"required"`
}

type Response struct {
TxHash string `json:"txHash"`
}

var (
cdc = app.MakeCodec()
)

func handleRequest(gc *gin.Context, c *Context) {
key := <-c.keys
defer func() {
c.keys <- key
}()

var req Request
if err := gc.ShouldBindJSON(&req); err != nil {
gc.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
return
}
to, err := sdk.AccAddressFromBech32(req.Address)
if err != nil {
gc.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
return
}
msg := bank.NewMsgSend(key.GetAddress(), to, c.amount)
if err := msg.ValidateBasic(); err != nil {
gc.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
return
}

cliCtx := sdkctx.CLIContext{Client: c.client}
acc, err := auth.NewAccountRetriever(cliCtx).GetAccount(key.GetAddress())
if err != nil {
gc.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
return
}

txBldr := auth.NewTxBuilder(
auth.DefaultTxEncoder(cdc), acc.GetAccountNumber(), acc.GetSequence(),
200000, 1, false, cfg.ChainID, "", sdk.NewCoins(), c.gasPrices,
)
out, err := txBldr.WithKeybase(keybase).BuildAndSign(key.GetName(), ckeys.DefaultKeyPass, []sdk.Msg{msg})
if err != nil {
gc.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
return
}

res, err := cliCtx.BroadcastTxCommit(out)
if err != nil {
gc.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
return
}
if res.Code != 0 {
gc.JSON(http.StatusInternalServerError, gin.H{
"error": fmt.Sprintf(":exploding_head: Tx returned nonzero code %d with log %s, tx hash: %s",
res.Code, res.RawLog, res.TxHash,
)})
return
}
gc.JSON(200, Response{
TxHash: res.TxHash,
})
}
165 changes: 165 additions & 0 deletions chain/cmd/faucet/keys.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,165 @@
package main

import (
"bufio"
"fmt"

"github.com/cosmos/cosmos-sdk/client/input"
ckeys "github.com/cosmos/cosmos-sdk/client/keys"
"github.com/cosmos/cosmos-sdk/crypto/keys"
"github.com/cosmos/go-bip39"
"github.com/spf13/cobra"
)

const (
flagAccount = "account"
flagIndex = "index"
flagCoinType = "coin-type"
flagRecover = "recover"
)

func keysCmd(c *Context) *cobra.Command {
cmd := &cobra.Command{
Use: "keys",
Aliases: []string{"k"},
Short: "Manage key held by the oracle process",
}
cmd.AddCommand(keysAddCmd(c))
cmd.AddCommand(keysDeleteCmd(c))
cmd.AddCommand(keysListCmd(c))
cmd.AddCommand(keysShowCmd(c))
return cmd
}

func keysAddCmd(c *Context) *cobra.Command {
cmd := &cobra.Command{
Use: "add [name]",
Aliases: []string{"a"},
Short: "Add a new key to the keychain",
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
var mnemonic string
recover, err := cmd.Flags().GetBool(flagRecover)
if err != nil {
return err
}
if recover {
inBuf := bufio.NewReader(cmd.InOrStdin())
var err error
mnemonic, err = input.GetString("Enter your bip39 mnemonic", inBuf)
if err != nil {
return err
}
} else {
seed, err := bip39.NewEntropy(256)
if err != nil {
return err
}
mnemonic, err = bip39.NewMnemonic(seed)
if err != nil {
return err
}
fmt.Printf("Mnemonic: %s\n", mnemonic)
}

if err != nil {
return err
}
account, err := cmd.Flags().GetUint32(flagAccount)
if err != nil {
return err
}
index, err := cmd.Flags().GetUint32(flagIndex)
if err != nil {
return err
}
hdPath := keys.CreateHDPath(account, index)
info, err := keybase.CreateAccount(args[0], mnemonic, "", ckeys.DefaultKeyPass, hdPath.String(), keys.Secp256k1)
if err != nil {
return err
}
fmt.Printf("Address: %s\n", info.GetAddress().String())
return nil
},
}
cmd.Flags().Bool(flagRecover, false, "Provide seed phrase to recover existing key instead of creating")
cmd.Flags().Uint32(flagAccount, 0, "Account number for HD derivation")
cmd.Flags().Uint32(flagIndex, 0, "Address index number for HD derivation")
return cmd
}

func keysDeleteCmd(c *Context) *cobra.Command {
cmd := &cobra.Command{
Use: "delete [name]",
Aliases: []string{"d"},
Short: "Delete a key from the keychain",
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
name := args[0]

_, err := keybase.Get(name)
if err != nil {
return err
}

inBuf := bufio.NewReader(cmd.InOrStdin())
confirmInput, err := input.GetString("Key will be deleted. Continue?[y/N]", inBuf)
if err != nil {
return err
}

if confirmInput != "y" {
fmt.Println("Cancel")
return nil
}

if err := keybase.Delete(name, "", true); err != nil {
return err
}

fmt.Printf("Deleted key: %s\n", name)
return nil
},
}
return cmd
}

func keysListCmd(c *Context) *cobra.Command {
cmd := &cobra.Command{
Use: "list",
Aliases: []string{"l"},
Short: "List all the keys in the keychain",
Args: cobra.ExactArgs(0),
RunE: func(cmd *cobra.Command, args []string) error {
keys, err := keybase.List()
if err != nil {
return err
}
for _, key := range keys {
fmt.Printf("%s => %s\n", key.GetName(), key.GetAddress().String())
}
return nil
},
}
return cmd
}

func keysShowCmd(c *Context) *cobra.Command {
cmd := &cobra.Command{
Use: "show [name]",
Aliases: []string{"s"},
Short: "Show address from name in the keychain",
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
name := args[0]

key, err := keybase.Get(name)
if err != nil {
return err
}
fmt.Println(key.GetAddress().String())
return nil
},
}
return cmd
}
Loading

0 comments on commit 3a8282d

Please sign in to comment.