func walletHistoryAction(c *gcli.Context) error { if c.NArg() > 0 { fmt.Printf("Error: invalid argument\n\n") gcli.ShowSubcommandHelp(c) return nil } f := c.String("f") if f == "" { f = filepath.Join(cfg.WalletDir, cfg.DefaultWalletName) } // check the file extension. if !strings.HasSuffix(f, walletExt) { return errWalletName } // check if file name contains path. if filepath.Base(f) != f { af, err := filepath.Abs(f) if err != nil { return fmt.Errorf("invalid wallet file:%v, err:%v", f, err) } f = af } else { f = filepath.Join(cfg.WalletDir, f) } // get all addresses in the wallet. addrs, err := getAddresses(f) if err != nil { return err } // get all the addresses affected uxouts uxouts, err := getAddrUxOuts(addrs) if err != nil { return err } // transmute the uxout to addrHistory, and sort the items by time in ascend order. totalAddrHis := []addrHistory{} for _, ux := range uxouts { addrHis, err := makeAddrHisArray(ux) if err != nil { return err } totalAddrHis = append(totalAddrHis, addrHis...) } sort.Sort(byTime(totalAddrHis)) // print the addr history v, err := json.MarshalIndent(totalAddrHis, "", " ") if err != nil { return errJSONMarshal } fmt.Println(string(v)) return nil }
func write_config(c *cli.Context, files map[string]string) error { user := c.String("user") password := c.String("password") if len(user) == 0 || len(password) == 0 { cli.ShowSubcommandHelp(c) return nil } for n, b := range files { if err := os.MkdirAll(path.Dir(n), 0700); err != nil { return err } fmt.Printf("generate file %s\n", n) fd, err := os.OpenFile( n, os.O_WRONLY|os.O_CREATE|os.O_EXCL, 0600) if err != nil { return err } defer fd.Close() t, err := template.New("").Parse(b) if err != nil { return err } driver := viper.GetString("database.driver") switch driver { case "postgres": driver = "pgsql" } args := viper.GetStringMapString("database.args") if err = t.Execute(fd, struct { Driver string User string Password string Name string Host string Port string UserTable string AliasTable string DomainTable string }{ Driver: driver, Host: args["host"], Name: args["dbname"], Port: args["port"], Password: password, User: user, UserTable: User{}.TableName(), AliasTable: Alias{}.TableName(), DomainTable: Domain{}.TableName(), }); err != nil { return err } } return nil }
func getBlocks(c *gcli.Context) error { // get start start := c.Args().Get(0) end := c.Args().Get(1) if end == "" { end = start } if start == "" { gcli.ShowSubcommandHelp(c) return nil } s, err := strconv.ParseUint(start, 10, 64) if err != nil { return fmt.Errorf("invalid block seq: %v, must be unsigned integer", start) } e, err := strconv.ParseUint(end, 10, 64) if err != nil { return fmt.Errorf("invalid block seq: %v, must be unsigned integer", end) } param := []uint64{s, e} req, err := webrpc.NewRequest("get_blocks", param, "1") if err != nil { return fmt.Errorf("create rpc request failed: %v", err) } rsp, err := webrpc.Do(req, cfg.RPCAddress) if err != nil { return fmt.Errorf("do rpc request failed: %v", err) } if rsp.Error != nil { return fmt.Errorf("rpc response error: %+v", *rsp.Error) } fmt.Println(string(rsp.Result)) return nil }
func commandValidateAction(c *cli.Context) error { fmt.Println("validate fzp file") // get cli flag value fzpFile := c.String("file") fzpDir := c.String("dir") // process data if fzpFile != "" { if err := validateFile(c, fzpFile); err != nil { fmt.Println(err) os.Exit(1) } os.Exit(0) } else if fzpDir != "" { //Logf("read folder '%v'\n", fzpDir) var err []error if err = validateFolder(c, fzpDir); err != nil { os.Exit(1) } os.Exit(0) } else { cli.ShowSubcommandHelp(c) fmt.Println("USAGE-SAMPLES") fmt.Println("") fmt.Printf(" $ %v validate --file file/path.fzp\n", c.App.Name) fmt.Println(" # or") fmt.Printf(" $ %v validate -f file/path.fzp\n", c.App.Name) fmt.Println("") fmt.Printf(" $ %v validate --dir file/dir\n", c.App.Name) fmt.Println(" # or") fmt.Printf(" $ %v validate -d file/dir\n", c.App.Name) fmt.Println("") fmt.Println("also you can combine the other flags (no-check, verbose)") } return nil }
func broadcastTxCMD() gcli.Command { name := "broadcastTransaction" return gcli.Command{ Name: name, Usage: "Broadcast a raw transaction to the network", ArgsUsage: "[raw transaction]", OnUsageError: onCommandUsageError(name), Action: func(c *gcli.Context) error { rawtx := c.Args().First() if rawtx == "" { gcli.ShowSubcommandHelp(c) return nil } txid, err := broadcastTx(rawtx) if err != nil { return err } fmt.Println(txid) return nil }, } // Commands = append(Commands, cmd) }
func newAppFor(executableType ExecutableType) *cli.App { var configDescription string var configEnvVar string switch executableType { case Daemon: configDescription = "Configuration file for daemon." configEnvVar = "CTD_CONFIG" case Control: configDescription = "Configuration file for control." configEnvVar = "CTCTL_CONFIG" default: configDescription = "Configuration file for daemon and control." configEnvVar = "CT_CONFIG" } app := cli.NewApp() app.Version = caretakerd.Version app.Commands = []cli.Command{} app.OnUsageError = func(context *cli.Context, err error, isSubcommand bool) error { fmt.Fprintf(app.Writer, "Error: %v\n\n", err) if isSubcommand { cli.ShowSubcommandHelp(context) } else { cli.ShowAppHelp(context) } return err } app.Flags = []cli.Flag{ cli.GenericFlag{ Name: "config,c", Value: conf, Usage: configDescription, EnvVar: configEnvVar, }, cli.GenericFlag{ Name: "address,a", Value: listenAddress, Usage: "Listen address of the daemon.", }, } if executableType != Daemon { app.Flags = append(app.Flags, cli.GenericFlag{ Name: "pem,p", Value: pemFile, Usage: "Location of PEM file which contains the private public key pair for access to the daemon.", }) } switch executableType { case Daemon: app.Name = caretakerd.DaemonName app.Usage = "Simple control daemon for processes." case Control: app.Name = caretakerd.ControlName app.Usage = "Remote control for " + caretakerd.DaemonName default: app.Name = caretakerd.BaseName app.Usage = "Simple control daemon for processes including remote control for itself." } return app }
func main() { app := cli.NewApp() app.Name = "kənˈtrīv" app.Version = "19.99.0" app.Compiled = time.Now() app.Authors = []cli.Author{ cli.Author{ Name: "Example Human", Email: "*****@*****.**", }, } app.Copyright = "(c) 1999 Serious Enterprise" app.HelpName = "contrive" app.Usage = "demonstrate available API" app.UsageText = "contrive - demonstrating the available API" app.ArgsUsage = "[args and such]" app.Commands = []cli.Command{ cli.Command{ Name: "doo", Aliases: []string{"do"}, Category: "motion", Usage: "do the doo", UsageText: "doo - does the dooing", Description: "no really, there is a lot of dooing to be done", ArgsUsage: "[arrgh]", Flags: []cli.Flag{ cli.BoolFlag{Name: "forever, forevvarr"}, }, Subcommands: cli.Commands{ cli.Command{ Name: "wop", Action: wopAction, }, }, SkipFlagParsing: false, HideHelp: false, Hidden: false, HelpName: "doo!", BashComplete: func(c *cli.Context) { fmt.Fprintf(c.App.Writer, "--better\n") }, Before: func(c *cli.Context) error { fmt.Fprintf(c.App.Writer, "brace for impact\n") return nil }, After: func(c *cli.Context) error { fmt.Fprintf(c.App.Writer, "did we lose anyone?\n") return nil }, Action: func(c *cli.Context) error { c.Command.FullName() c.Command.HasName("wop") c.Command.Names() c.Command.VisibleFlags() fmt.Fprintf(c.App.Writer, "dodododododoodododddooooododododooo\n") if c.Bool("forever") { c.Command.Run(c) } return nil }, OnUsageError: func(c *cli.Context, err error, isSubcommand bool) error { fmt.Fprintf(c.App.Writer, "for shame\n") return err }, }, } app.Flags = []cli.Flag{ cli.BoolFlag{Name: "fancy"}, cli.BoolTFlag{Name: "fancier"}, cli.DurationFlag{Name: "howlong, H", Value: time.Second * 3}, cli.Float64Flag{Name: "howmuch"}, cli.GenericFlag{Name: "wat", Value: &genericType{}}, cli.Int64Flag{Name: "longdistance"}, cli.Int64SliceFlag{Name: "intervals"}, cli.IntFlag{Name: "distance"}, cli.IntSliceFlag{Name: "times"}, cli.StringFlag{Name: "dance-move, d"}, cli.StringSliceFlag{Name: "names, N"}, cli.UintFlag{Name: "age"}, cli.Uint64Flag{Name: "bigage"}, } app.EnableBashCompletion = true app.HideHelp = false app.HideVersion = false app.BashComplete = func(c *cli.Context) { fmt.Fprintf(c.App.Writer, "lipstick\nkiss\nme\nlipstick\nringo\n") } app.Before = func(c *cli.Context) error { fmt.Fprintf(c.App.Writer, "HEEEERE GOES\n") return nil } app.After = func(c *cli.Context) error { fmt.Fprintf(c.App.Writer, "Phew!\n") return nil } app.CommandNotFound = func(c *cli.Context, command string) { fmt.Fprintf(c.App.Writer, "Thar be no %q here.\n", command) } app.OnUsageError = func(c *cli.Context, err error, isSubcommand bool) error { if isSubcommand { return err } fmt.Fprintf(c.App.Writer, "WRONG: %#v\n", err) return nil } app.Action = func(c *cli.Context) error { cli.DefaultAppComplete(c) cli.HandleExitCoder(errors.New("not an exit coder, though")) cli.ShowAppHelp(c) cli.ShowCommandCompletions(c, "nope") cli.ShowCommandHelp(c, "also-nope") cli.ShowCompletions(c) cli.ShowSubcommandHelp(c) cli.ShowVersion(c) categories := c.App.Categories() categories.AddCommand("sounds", cli.Command{ Name: "bloop", }) for _, category := range c.App.Categories() { fmt.Fprintf(c.App.Writer, "%s\n", category.Name) fmt.Fprintf(c.App.Writer, "%#v\n", category.Commands) fmt.Fprintf(c.App.Writer, "%#v\n", category.VisibleCommands()) } fmt.Printf("%#v\n", c.App.Command("doo")) if c.Bool("infinite") { c.App.Run([]string{"app", "doo", "wop"}) } if c.Bool("forevar") { c.App.RunAsSubcommand(c) } c.App.Setup() fmt.Printf("%#v\n", c.App.VisibleCategories()) fmt.Printf("%#v\n", c.App.VisibleCommands()) fmt.Printf("%#v\n", c.App.VisibleFlags()) fmt.Printf("%#v\n", c.Args().First()) if len(c.Args()) > 0 { fmt.Printf("%#v\n", c.Args()[1]) } fmt.Printf("%#v\n", c.Args().Present()) fmt.Printf("%#v\n", c.Args().Tail()) set := flag.NewFlagSet("contrive", 0) nc := cli.NewContext(c.App, set, c) fmt.Printf("%#v\n", nc.Args()) fmt.Printf("%#v\n", nc.Bool("nope")) fmt.Printf("%#v\n", nc.BoolT("nerp")) fmt.Printf("%#v\n", nc.Duration("howlong")) fmt.Printf("%#v\n", nc.Float64("hay")) fmt.Printf("%#v\n", nc.Generic("bloop")) fmt.Printf("%#v\n", nc.Int64("bonk")) fmt.Printf("%#v\n", nc.Int64Slice("burnks")) fmt.Printf("%#v\n", nc.Int("bips")) fmt.Printf("%#v\n", nc.IntSlice("blups")) fmt.Printf("%#v\n", nc.String("snurt")) fmt.Printf("%#v\n", nc.StringSlice("snurkles")) fmt.Printf("%#v\n", nc.Uint("flub")) fmt.Printf("%#v\n", nc.Uint64("florb")) fmt.Printf("%#v\n", nc.GlobalBool("global-nope")) fmt.Printf("%#v\n", nc.GlobalBoolT("global-nerp")) fmt.Printf("%#v\n", nc.GlobalDuration("global-howlong")) fmt.Printf("%#v\n", nc.GlobalFloat64("global-hay")) fmt.Printf("%#v\n", nc.GlobalGeneric("global-bloop")) fmt.Printf("%#v\n", nc.GlobalInt("global-bips")) fmt.Printf("%#v\n", nc.GlobalIntSlice("global-blups")) fmt.Printf("%#v\n", nc.GlobalString("global-snurt")) fmt.Printf("%#v\n", nc.GlobalStringSlice("global-snurkles")) fmt.Printf("%#v\n", nc.FlagNames()) fmt.Printf("%#v\n", nc.GlobalFlagNames()) fmt.Printf("%#v\n", nc.GlobalIsSet("wat")) fmt.Printf("%#v\n", nc.GlobalSet("wat", "nope")) fmt.Printf("%#v\n", nc.NArg()) fmt.Printf("%#v\n", nc.NumFlags()) fmt.Printf("%#v\n", nc.Parent()) nc.Set("wat", "also-nope") ec := cli.NewExitError("ohwell", 86) fmt.Fprintf(c.App.Writer, "%d", ec.ExitCode()) fmt.Printf("made it!\n") return ec } if os.Getenv("HEXY") != "" { app.Writer = &hexWriter{} app.ErrWriter = &hexWriter{} } app.Metadata = map[string]interface{}{ "layers": "many", "explicable": false, "whatever-values": 19.99, } app.Run(os.Args) }
func addPrivateKeyCMD() gcli.Command { name := "addPrivateKey" return gcli.Command{ Name: name, Usage: "Add a private key to specific wallet", ArgsUsage: "[private key]", Description: fmt.Sprintf(`Add a private key to specific wallet, the default wallet(%s/%s) will be used if the wallet file or path is not specified`, cfg.WalletDir, cfg.DefaultWalletName), Flags: []gcli.Flag{ gcli.StringFlag{ Name: "f", Usage: "[wallet file or path] private key will be added to this wallet", }, }, OnUsageError: onCommandUsageError(name), Action: func(c *gcli.Context) error { // get private key skStr := c.Args().First() if skStr == "" { gcli.ShowSubcommandHelp(c) return nil } // get wallet file path w := c.String("f") if w == "" { w = filepath.Join(cfg.WalletDir, cfg.DefaultWalletName) } if !strings.HasSuffix(w, walletExt) { return errWalletName } // only wallet file name, no path. if filepath.Base(w) == w { w = filepath.Join(cfg.WalletDir, w) } wlt, err := wallet.Load(w) if err != nil { errorWithHelp(c, err) return nil } sk, err := cipher.SecKeyFromHex(skStr) if err != nil { return fmt.Errorf("invalid private key: %s, must be an hex string of length 64", skStr) } pk := cipher.PubKeyFromSecKey(sk) addr := cipher.AddressFromPubKey(pk) entry := wallet.WalletEntry{ Address: addr, Public: pk, Secret: sk, } if err := wlt.AddEntry(entry); err != nil { return err } dir, err := filepath.Abs(filepath.Dir(w)) if err != nil { return err } if err := wlt.Save(dir); err != nil { return errors.New("save wallet failed") } fmt.Println("success") return nil }, } // Commands = append(Commands, cmd) }
// Run is @@@ func (c *CLI) Run() { app := cli.NewApp() app.Name = c.Name app.Version = c.Version app.Author = c.Author app.Email = c.Email app.Usage = c.Usage app.EnableBashCompletion = true app.Flags = []cli.Flag{} if c.Config.Cloud == nil { app.Flags = append(app.Flags, cli.StringFlag{ Name: "cloud", Value: "", Usage: "cloud used for this invocation", EnvVar: fmt.Sprintf("%s_CLOUD", c.EnvVarPrefix), }) } app.Flags = append(app.Flags, cli.StringFlag{ Name: "cluster", Value: "", Usage: "cluster used for this invocation", EnvVar: fmt.Sprintf("%s_CLUSTER", c.EnvVarPrefix), }, cli.StringFlag{ Name: "resource-group", Value: "", Usage: "resource group used for this invocation", EnvVar: fmt.Sprintf("%s_RESOURCE_GROUP", c.EnvVarPrefix), }, cli.StringFlag{ Name: "site", Value: "", Usage: "site used for this invocation", EnvVar: fmt.Sprintf("%s_SITE", c.EnvVarPrefix), }, cli.BoolFlag{ Name: "log-http", Usage: "log HTTP interactions", }, ) app.Action = func(ctx *cli.Context) error { c.checkVersion() cli.ShowAppHelp(ctx) return nil } app.Commands = []cli.Command{ { Name: "login", Usage: fmt.Sprintf("authenticate with the %s", c.LongName), Action: c.cmd(loginCmd), }, { Name: "logout", Usage: fmt.Sprintf("invalidate any existing credentials with the %s", c.LongName), Action: c.cmd(logoutCmd), }, { Name: "upgrade", Usage: fmt.Sprintf("upgrade the client to latest version supported by the %s", c.LongName), Action: c.cmd(upgradeCmd), }, { Name: "resource-groups", Usage: "manage resource groups", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "show resource groups to which you belong", Action: c.cmd(c.stdCmd(resourceGroupListCmd)), }, }, }, { Name: "keypairs", Usage: "manage keypairs", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "List keypairs", Action: c.cmd(c.stdCmd(keypairsListCmd)), }, { Name: "create", Usage: "create a keypair", Flags: []cli.Flag{ cli.StringFlag{ Name: "name", Value: "", Usage: "name of keypair", }, }, Action: c.cmd(c.stdCmd(keypairsCreateCmd)), }, { Name: "attach", Usage: "attach keypair to service", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, cli.StringFlag{ Name: "keypair", Value: "", Usage: "name of keypair", }, cli.StringFlag{ Name: "service", Value: "", Usage: "service path", }, }, Action: c.cmd(c.stdCmd(keypairsAttachCmd)), }, { Name: "detach", Usage: "detach keypair from service", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, cli.StringFlag{ Name: "service", Value: "", Usage: "service name", }, }, Action: c.cmd(c.stdCmd(keypairsDetachCmd)), BashComplete: func(ctx *cli.Context) { }, }, { Name: "delete", Usage: "delete a keypair by name", Action: c.cmd(c.stdCmd(keypairsDeleteCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) resourceGroup := c.GetResourceGroup(ctx) keypairs, err := api.KeyPairs.List(&*resourceGroup.URL) if err != nil { return } for i := range keypairs { fmt.Println(*keypairs[i].Name) } }, }, }, }, { Name: "sites", Usage: "manage sites", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "show sites in the resource group", Action: c.cmd(c.stdCmd(sitesListCmd)), }, { Name: "init", Usage: "create a site, production instance and write config", Flags: []cli.Flag{ cli.StringFlag{ Name: "name", Value: "", Usage: "optional name for site", }, }, Action: c.cmd(c.stdCmd(sitesInitCmd)), }, { Name: "create", Usage: "create a site in the resource group", Action: c.cmd(c.stdCmd(sitesCreateCmd)), }, { Name: "delete", Usage: "delete a site in the resource group", Action: c.cmd(c.stdCmd(sitesDeleteCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) resourceGroup := c.GetResourceGroup(ctx) sites, err := api.Sites.List(&*resourceGroup.URL) if err != nil { return } for i := range sites { fmt.Println(*sites[i].Name) } }, }, { Name: "env", Usage: "", Action: c.cmd(c.stdCmd(sitesEnvCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) resourceGroup := c.GetResourceGroup(ctx) sites, err := api.Sites.List(&*resourceGroup.URL) if err != nil { return } for i := range sites { fmt.Println(*sites[i].Name) } }, }, { Name: "users", Usage: "manage users", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "List users for the site", Action: c.cmd(c.stdCmd(sitesUsersListCmd)), }, { Name: "add", Usage: "Add a user to site with a given role", Action: c.cmd(c.stdCmd(sitesUsersAddCmd)), Flags: []cli.Flag{ cli.StringFlag{ Name: "role", Value: "dev", Usage: "desired role for user", }, }, }, }, }, }, }, { Name: "instances", Usage: "manage instances", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "create", Usage: "create new instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "kind", Value: "", Usage: "kind of instance", }, }, Action: c.cmd(c.stdCmd(instancesCreateCmd)), }, { Name: "list", Usage: "", Action: c.cmd(c.stdCmd(instancesListCmd)), }, { Name: "delete", Usage: "", Action: c.cmd(c.stdCmd(instancesDeleteCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) site := c.GetSite(ctx) instances, err := api.Instances.List(&*site.URL) if err != nil { fatal(err.Error()) } for i := range instances { fmt.Println(*instances[i].Label) } }, }, { Name: "env", Usage: "", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(instancesEnvCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) site := c.GetSite(ctx) instances, err := api.Instances.List(&*site.URL) if err != nil { fatal(err.Error()) } for i := range instances { fmt.Println(*instances[i].Label) } }, }, }, }, { Name: "services", Usage: "manage services", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "create", Usage: "create new service", Flags: []cli.Flag{ cli.StringFlag{ Name: "name", Value: "", Usage: "name of the service", }, cli.StringFlag{ Name: "version", Value: "", Usage: "version for the new service", }, cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesCreateCmd)), }, { Name: "list", Usage: "", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesListCmd)), }, { Name: "config", Usage: "", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Subcommands: []cli.Command{ { Name: "get", Usage: "", Action: c.cmd(c.stdCmd(servicesConfigGetCmd)), }, { Name: "set", Usage: "", Action: c.cmd(c.stdCmd(servicesConfigSetCmd)), }, }, }, { Name: "delete", Usage: "", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesDeleteCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, { Name: "env", Usage: "", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesEnvCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, { Name: "scale", Usage: "scale up/down a service on an instance", Flags: []cli.Flag{ cli.IntFlag{ Name: "replicas", Usage: "desired number of replicas", }, cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesScaleCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, { Name: "restart", Usage: "restart a service on a given instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(servicesRestartCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, }, }, { Name: "run", Usage: "run a one-off process", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(runCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, { Name: "deploy", Usage: "create a new release and deploy", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(deployCmd)), }, { Name: "hosts", Usage: "manage hosts for an instance", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "List hosts for an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(hostsListCmd)), }, { Name: "create", Usage: "Create a host for an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(hostsCreateCmd)), }, { Name: "delete", Usage: "Delete a host from an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(hostsDeleteCmd)), }, }, }, { Name: "scheduled-tasks", Usage: "manage scheduled tasks for an instance", Action: c.cmd(func(c *CLI, ctx *cli.Context) { cli.ShowSubcommandHelp(ctx) }), Subcommands: []cli.Command{ { Name: "list", Usage: "List scheduled tasks for an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(scheduledTasksListCmd)), }, { Name: "create", Usage: "Create a scheduled task for an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, cli.StringFlag{ Name: "name", Value: "", Usage: "scheduled task name", }, cli.StringFlag{ Name: "timezone", Value: "UTC", Usage: "scheduled task timezone (default: UTC)", }, cli.StringFlag{ Name: "schedule", Value: "", Usage: "scheduled task schedule (cron syntax)", }, }, Action: c.cmd(c.stdCmd(scheduledTasksCreateCmd)), }, { Name: "delete", Usage: "Delete a scheduled task from an instance", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, Action: c.cmd(c.stdCmd(scheduledTasksDeleteCmd)), }, }, }, { Name: "open", Usage: "open instance URL in browser", Action: c.cmd(c.stdCmd(openCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { if *services[i].Kind == "web" { fmt.Println(*services[i].Name) } } }, Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, }, }, { Name: "logs", Usage: "view logs for an instance or service", Flags: []cli.Flag{ cli.StringFlag{ Name: "instance", Value: "", Usage: "instance label", }, cli.IntFlag{ Name: "lines", Value: 20, Usage: "number of lines to query", }, }, Action: c.cmd(c.stdCmd(logsCmd)), BashComplete: func(ctx *cli.Context) { if len(ctx.Args()) > 0 { return } api := c.GetAPIClient(ctx) instance := c.GetInstance(ctx, nil) services, err := api.Services.List(&*instance.URL) if err != nil { fatal(err.Error()) } for i := range services { fmt.Println(*services[i].Name) } }, }, { Name: "metrics", Usage: "view metrics for a given service", Action: c.cmd(func(c *CLI, ctx *cli.Context) { api := c.GetAPIClient(ctx) site := c.GetSite(ctx) if len(ctx.Args()) != 1 { fatal("missing service") } parts := strings.Split(ctx.Args()[0], "/") instanceLabel := parts[0] serviceName := parts[1] instance, err := api.Instances.Get(*site.URL, instanceLabel) if err != nil { fatal(err.Error()) } service, err := api.Services.Get(*instance.URL, serviceName) if err != nil { fatal(err.Error()) } series, err := api.Metrics.List(*service.URL) if err != nil { fatal(err.Error()) } for i := range series { s := series[i] fmt.Printf("%s = ", s.Name) for j := range s.Points { value := s.Points[j][2] switch *s.Name { case "filesystem/limit_bytes_gauge", "filesystem/usage_bytes_gauge", "memory/usage_bytes_gauge", "memory/working_set_bytes_gauge": fmt.Printf("%s ", bytefmt.ByteSize(uint64(value))) break default: fmt.Printf("%d ", value) } } fmt.Println("") } }), }, } app.Run(os.Args) }