Skip to content

Commit

Permalink
refactor,fix(ssh): use cobra for git commands
Browse files Browse the repository at this point in the history
- Fix git commands errors on invalid args and permissions
- Use Cobra to handle git commands
- Add Git SSH tests
- Better ssh and git pktline error handling
  • Loading branch information
aymanbagabas committed Aug 4, 2023
1 parent b3d5ce8 commit b26060b
Show file tree
Hide file tree
Showing 21 changed files with 586 additions and 377 deletions.
17 changes: 0 additions & 17 deletions server/ssh/cmd.go

This file was deleted.

116 changes: 33 additions & 83 deletions server/ssh/cmd/cmd.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,9 @@ import (
"github.com/charmbracelet/soft-serve/server/sshutils"
"github.com/charmbracelet/soft-serve/server/utils"
"github.com/charmbracelet/ssh"
"github.com/prometheus/client_golang/prometheus"
"github.com/prometheus/client_golang/prometheus/promauto"
"github.com/spf13/cobra"
)

var cliCommandCounter = promauto.NewCounterVec(prometheus.CounterOpts{
Namespace: "soft_serve",
Subsystem: "cli",
Name: "commands_total",
Help: "Total times each command was called",
}, []string{"command"})

var templateFuncs = template.FuncMap{
"trim": strings.TrimSpace,
"trimRightSpace": trimRightSpace,
Expand All @@ -36,7 +27,8 @@ var templateFuncs = template.FuncMap{
}

const (
usageTmpl = `Usage:{{if .Runnable}}
// UsageTemplate is the template used for the help output.
UsageTemplate = `Usage:{{if .Runnable}}
{{.UseLine}}{{end}}{{if .HasAvailableSubCommands}}
{{.SSHCommand}}{{.CommandPath}} [command]{{end}}{{if gt (len .Aliases) 0}}
Expand Down Expand Up @@ -68,35 +60,11 @@ Use "{{.SSHCommand}}{{.CommandPath}} [command] --help" for more information abou
`
)

func trimRightSpace(s string) string {
return strings.TrimRightFunc(s, unicode.IsSpace)
}

// rpad adds padding to the right of a string.
func rpad(s string, padding int) string {
template := fmt.Sprintf("%%-%ds", padding)
return fmt.Sprintf(template, s)
}

func cmdName(args []string) string {
if len(args) == 0 {
return ""
}
return args[0]
}

// RootCommand returns a new cli root command.
func RootCommand(s ssh.Session) *cobra.Command {
ctx := s.Context()
// UsageFunc is a function that can be used as a cobra.Command's
// UsageFunc to render the help output.
func UsageFunc(c *cobra.Command) error {
ctx := c.Context()
cfg := config.FromContext(ctx)

args := s.Command()
cliCommandCounter.WithLabelValues(cmdName(args)).Inc()
rootCmd := &cobra.Command{
Short: "Soft Serve is a self-hostable Git server for the command line.",
SilenceUsage: true,
}

hostname := "localhost"
port := "23231"
url, err := url.Parse(cfg.SSH.PublicURL)
Expand All @@ -111,54 +79,34 @@ func RootCommand(s ssh.Session) *cobra.Command {
}

sshCmd += " " + hostname
rootCmd.SetUsageTemplate(usageTmpl)
rootCmd.SetUsageFunc(func(c *cobra.Command) error {
t := template.New("usage")
t.Funcs(templateFuncs)
template.Must(t.Parse(c.UsageTemplate()))
return t.Execute(c.OutOrStderr(), struct {
*cobra.Command
SSHCommand string
}{
Command: c,
SSHCommand: sshCmd,
})
t := template.New("usage")
t.Funcs(templateFuncs)
template.Must(t.Parse(c.UsageTemplate()))
return t.Execute(c.OutOrStderr(), struct {
*cobra.Command
SSHCommand string
}{
Command: c,
SSHCommand: sshCmd,
})
rootCmd.CompletionOptions.DisableDefaultCmd = true
rootCmd.AddCommand(
repoCommand(),
)
}

rootCmd.SetArgs(args)
if len(args) == 0 {
// otherwise it'll default to os.Args, which is not what we want.
rootCmd.SetArgs([]string{"--help"})
}
rootCmd.SetIn(s)
rootCmd.SetOut(s)
rootCmd.CompletionOptions.DisableDefaultCmd = true
rootCmd.SetErr(s.Stderr())
func trimRightSpace(s string) string {
return strings.TrimRightFunc(s, unicode.IsSpace)
}

user := proto.UserFromContext(ctx)
isAdmin := isPublicKeyAdmin(cfg, s.PublicKey()) || (user != nil && user.IsAdmin())
if user != nil || isAdmin {
if isAdmin {
rootCmd.AddCommand(
settingsCommand(),
userCommand(),
)
}
// rpad adds padding to the right of a string.
func rpad(s string, padding int) string {
template := fmt.Sprintf("%%-%ds", padding)
return fmt.Sprintf(template, s)
}

rootCmd.AddCommand(
infoCommand(),
pubkeyCommand(),
setUsernameCommand(),
jwtCommand(),
tokenCommand(),
)
// CommandName returns the name of the command from the args.
func CommandName(args []string) string {
if len(args) == 0 {
return ""
}

return rootCmd
return args[0]
}

func checkIfReadable(cmd *cobra.Command, args []string) error {
Expand All @@ -178,7 +126,9 @@ func checkIfReadable(cmd *cobra.Command, args []string) error {
return nil
}

func isPublicKeyAdmin(cfg *config.Config, pk ssh.PublicKey) bool {
// IsPublicKeyAdmin returns true if the given public key is an admin key from
// the initial_admin_keys config or environment field.
func IsPublicKeyAdmin(cfg *config.Config, pk ssh.PublicKey) bool {
for _, k := range cfg.AdminKeys() {
if sshutils.KeysEqual(pk, k) {
return true
Expand All @@ -191,7 +141,7 @@ func checkIfAdmin(cmd *cobra.Command, _ []string) error {
ctx := cmd.Context()
cfg := config.FromContext(ctx)
pk := sshutils.PublicKeyFromContext(ctx)
if isPublicKeyAdmin(cfg, pk) {
if IsPublicKeyAdmin(cfg, pk) {
return nil
}

Expand Down
Loading

0 comments on commit b26060b

Please sign in to comment.