mirror of
https://github.com/foomo/posh.git
synced 2025-10-16 12:45:38 +00:00
feat: add env command (#45)
* feat: add env command * fix: add pad * fix: hostname separator * feat: remove enforced $H * refactor: rename pkg to internal * revert: hostname separation
This commit is contained in:
parent
71afc97283
commit
8929c62a64
@ -1,6 +1,6 @@
|
|||||||
module {{ .module }}/posh
|
module {{ .module }}/posh
|
||||||
|
|
||||||
go 1.19
|
go 1.21
|
||||||
|
|
||||||
replace (
|
replace (
|
||||||
github.com/c-bata/go-prompt v0.2.6 => github.com/franklinkim/go-prompt v0.2.7-0.20210427061716-a8f4995d7aa5
|
github.com/c-bata/go-prompt v0.2.6 => github.com/franklinkim/go-prompt v0.2.7-0.20210427061716-a8f4995d7aa5
|
||||||
|
|||||||
@ -3,7 +3,7 @@ package command
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
|
||||||
"{{.module}}/posh/pkg/config"
|
"{{.module}}/posh/internal/config"
|
||||||
"github.com/foomo/posh/pkg/log"
|
"github.com/foomo/posh/pkg/log"
|
||||||
"github.com/foomo/posh/pkg/readline"
|
"github.com/foomo/posh/pkg/readline"
|
||||||
"github.com/spf13/viper"
|
"github.com/spf13/viper"
|
||||||
@ -1,4 +1,4 @@
|
|||||||
package pkg
|
package internal
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
@ -15,7 +15,7 @@ import (
|
|||||||
"github.com/foomo/posh/pkg/prompt/history"
|
"github.com/foomo/posh/pkg/prompt/history"
|
||||||
"github.com/foomo/posh/pkg/readline"
|
"github.com/foomo/posh/pkg/readline"
|
||||||
"github.com/foomo/posh/pkg/require"
|
"github.com/foomo/posh/pkg/require"
|
||||||
pkgcommand "{{.module}}/posh/pkg/command"
|
icommand "{{.module}}/posh/internal/command"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Plugin struct {
|
type Plugin struct {
|
||||||
@ -39,8 +39,8 @@ func New(l log.Logger) (plugin.Plugin, error) {
|
|||||||
|
|
||||||
// Welcome
|
// Welcome
|
||||||
inst.commands.MustAdd(
|
inst.commands.MustAdd(
|
||||||
pkgcommand.NewWelcome(l,
|
icommand.NewWelcome(l,
|
||||||
pkgcommand.WelcomeWithConfigKey("welcome"),
|
icommand.WelcomeWithConfigKey("welcome"),
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -1,12 +1,12 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"{{.module}}/posh/pkg"
|
"{{.module}}/posh/internal"
|
||||||
"github.com/foomo/posh/cmd"
|
"github.com/foomo/posh/cmd"
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
cmd.Init(pkg.New)
|
cmd.Init(internal.New)
|
||||||
}
|
}
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
|
|||||||
@ -33,11 +33,11 @@ func NewCache(l log.Logger, cache cache.Cache) *Cache {
|
|||||||
}
|
}
|
||||||
inst.tree = tree.New(&tree.Node{
|
inst.tree = tree.New(&tree.Node{
|
||||||
Name: "cache",
|
Name: "cache",
|
||||||
Description: "manage the internal cache",
|
Description: "Manage the internal cache",
|
||||||
Nodes: tree.Nodes{
|
Nodes: tree.Nodes{
|
||||||
{
|
{
|
||||||
Name: "clear",
|
Name: "clear",
|
||||||
Description: "clear caches",
|
Description: "Clear caches",
|
||||||
Args: tree.Args{
|
Args: tree.Args{
|
||||||
{
|
{
|
||||||
Name: "Namespace",
|
Name: "Namespace",
|
||||||
@ -53,7 +53,7 @@ func NewCache(l log.Logger, cache cache.Cache) *Cache {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
Name: "list",
|
Name: "list",
|
||||||
Description: "list all caches",
|
Description: "List all caches",
|
||||||
Execute: inst.list,
|
Execute: inst.list,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
111
pkg/command/env.go
Normal file
111
pkg/command/env.go
Normal file
@ -0,0 +1,111 @@
|
|||||||
|
package command
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/foomo/posh/pkg/command/tree"
|
||||||
|
"github.com/foomo/posh/pkg/log"
|
||||||
|
"github.com/foomo/posh/pkg/prompt/goprompt"
|
||||||
|
"github.com/foomo/posh/pkg/readline"
|
||||||
|
"github.com/pterm/pterm"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Env struct {
|
||||||
|
l log.Logger
|
||||||
|
tree tree.Root
|
||||||
|
}
|
||||||
|
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
// ~ Constructor
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
func NewEnv(l log.Logger) *Env {
|
||||||
|
inst := &Env{
|
||||||
|
l: l,
|
||||||
|
}
|
||||||
|
inst.tree = tree.New(&tree.Node{
|
||||||
|
Name: "env",
|
||||||
|
Description: "Manage internal environment variables",
|
||||||
|
Nodes: tree.Nodes{
|
||||||
|
{
|
||||||
|
Name: "list",
|
||||||
|
Description: "List all environment variables",
|
||||||
|
Execute: inst.list,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Name: "set",
|
||||||
|
Description: "Set an internal environment variable",
|
||||||
|
Args: tree.Args{
|
||||||
|
{
|
||||||
|
Name: "Key",
|
||||||
|
Description: "Key of the environment variable.",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Name: "Value",
|
||||||
|
Optional: true,
|
||||||
|
Description: "Value of the environment variable.",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Execute: inst.set,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
Name: "unset",
|
||||||
|
Description: "Unset an environment variable",
|
||||||
|
Args: tree.Args{
|
||||||
|
{
|
||||||
|
Name: "Key",
|
||||||
|
Description: "Key of the environment variable.",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Execute: inst.unset,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
return inst
|
||||||
|
}
|
||||||
|
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
// ~ Public methods
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
func (c *Env) Name() string {
|
||||||
|
return c.tree.Node().Name
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) Description() string {
|
||||||
|
return c.tree.Node().Description
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) Complete(ctx context.Context, r *readline.Readline) []goprompt.Suggest {
|
||||||
|
return c.tree.Complete(ctx, r)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) Execute(ctx context.Context, r *readline.Readline) error {
|
||||||
|
return c.tree.Execute(ctx, r)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) Help(ctx context.Context, r *readline.Readline) string {
|
||||||
|
return c.tree.Help(ctx, r)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
// ~ Private methods
|
||||||
|
// ------------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
func (c *Env) set(ctx context.Context, r *readline.Readline) error {
|
||||||
|
return os.Setenv(r.Args().At(0), r.Args().AtDefault(1, ""))
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) unset(ctx context.Context, r *readline.Readline) error {
|
||||||
|
return os.Unsetenv(r.Args().At(0))
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Env) list(ctx context.Context, r *readline.Readline) error {
|
||||||
|
data := pterm.TableData{{"Name", "Value"}}
|
||||||
|
for _, s := range os.Environ() {
|
||||||
|
data = append(data, strings.SplitN(s, "=", 2))
|
||||||
|
}
|
||||||
|
return pterm.DefaultTable.WithHasHeader(true).WithData(data).Render()
|
||||||
|
}
|
||||||
@ -134,19 +134,20 @@ func (c *Node) find(ctx context.Context, r *readline.Readline, i int) (*Node, in
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *Node) help(ctx context.Context, r *readline.Readline) string {
|
func (c *Node) help(ctx context.Context, r *readline.Readline) string {
|
||||||
|
pad := " "
|
||||||
ret := c.Description
|
ret := c.Description
|
||||||
|
|
||||||
if len(c.Nodes) > 0 {
|
if len(c.Nodes) > 0 {
|
||||||
ret += "\n\nUsage:\n"
|
ret += "\n\nUsage:\n"
|
||||||
ret += " " + c.Name + " [command]"
|
ret += pad + c.Name + " [command]"
|
||||||
|
|
||||||
ret += "\n\nAvailable Commands:\n"
|
ret += "\n\nAvailable Commands:\n"
|
||||||
for _, node := range c.Nodes {
|
for _, node := range c.Nodes {
|
||||||
ret += " " + xstrings.PadEnd(node.Name, " ", 30) + node.Description + "\n"
|
ret += pad + xstrings.PadEnd(node.Name, " ", 30) + node.Description + "\n"
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
ret += "\n\nUsage:\n"
|
ret += "\n\nUsage:\n"
|
||||||
ret += " " + c.Name
|
ret += pad + c.Name
|
||||||
|
|
||||||
for _, arg := range c.Args {
|
for _, arg := range c.Args {
|
||||||
ret += " "
|
ret += " "
|
||||||
@ -167,7 +168,7 @@ func (c *Node) help(ctx context.Context, r *readline.Readline) string {
|
|||||||
if len(c.Args) > 0 {
|
if len(c.Args) > 0 {
|
||||||
ret += "\n\nArguments:\n"
|
ret += "\n\nArguments:\n"
|
||||||
for _, arg := range c.Args {
|
for _, arg := range c.Args {
|
||||||
ret += " " + xstrings.PadEnd(arg.Name, " ", 30) + arg.Description + "\n"
|
ret += pad + xstrings.PadEnd(arg.Name, " ", 30) + arg.Description + "\n"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -31,7 +31,7 @@ func TestRoot(t *testing.T) {
|
|||||||
|
|
||||||
r := tree.New(&tree.Node{
|
r := tree.New(&tree.Node{
|
||||||
Name: "root",
|
Name: "root",
|
||||||
Description: "root tree",
|
Description: "Root tree",
|
||||||
Execute: func(ctx context.Context, r *readline.Readline) error {
|
Execute: func(ctx context.Context, r *readline.Readline) error {
|
||||||
return ErrRoot
|
return ErrRoot
|
||||||
},
|
},
|
||||||
|
|||||||
@ -11,7 +11,7 @@ func DefaultFlair(title string) error {
|
|||||||
pterm.FgGray.Println()
|
pterm.FgGray.Println()
|
||||||
if err := pterm.DefaultBigText.WithLetters(
|
if err := pterm.DefaultBigText.WithLetters(
|
||||||
putils.LettersFromStringWithStyle(strings.ToUpper(title), pterm.NewStyle(pterm.FgCyan)),
|
putils.LettersFromStringWithStyle(strings.ToUpper(title), pterm.NewStyle(pterm.FgCyan)),
|
||||||
putils.LettersFromStringWithStyle("$H", pterm.NewStyle(pterm.FgGreen))).
|
).
|
||||||
Render(); err != nil {
|
Render(); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|||||||
@ -289,7 +289,7 @@ func (s *Prompt) complete(d prompt.Document) []prompt.Suggest {
|
|||||||
if s.readline.IsModeDefault() && s.readline.Args().LenIs(0) {
|
if s.readline.IsModeDefault() && s.readline.Args().LenIs(0) {
|
||||||
var suggests []prompt.Suggest
|
var suggests []prompt.Suggest
|
||||||
for key, value := range s.aliases {
|
for key, value := range s.aliases {
|
||||||
suggests = append(suggests, prompt.Suggest{Text: key, Description: "alias: " + value})
|
suggests = append(suggests, prompt.Suggest{Text: key, Description: "Alias: " + value})
|
||||||
}
|
}
|
||||||
for _, inst := range s.Commands().List() {
|
for _, inst := range s.Commands().List() {
|
||||||
suggests = append(suggests, prompt.Suggest{Text: inst.Name(), Description: inst.Description()})
|
suggests = append(suggests, prompt.Suggest{Text: inst.Name(), Description: inst.Description()})
|
||||||
|
|||||||
@ -14,6 +14,14 @@ func (a Args) At(v int) string {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (a Args) AtDefault(v int, fallback string) string {
|
||||||
|
if a.HasIndex(v) {
|
||||||
|
return a[v]
|
||||||
|
} else {
|
||||||
|
return fallback
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func (a Args) Shift() (string, Args) {
|
func (a Args) Shift() (string, Args) {
|
||||||
if a.HasIndex(0) {
|
if a.HasIndex(0) {
|
||||||
return a[0], a[1:]
|
return a[0], a[1:]
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user