summaryrefslogtreecommitdiff
path: root/cmd/cmd.go
blob: d0b341c64346d5375aa1aee56fb681b942d9ffe1 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
// Package cmd used for command line options for the complete tool
package cmd

import (
	"errors"
	"flag"
	"fmt"
	"os"
	"strings"

	"github.com/posener/complete/cmd/install"
)

// Run is used when running complete in command line mode.
// this is used when the complete is not completing words, but to
// install it or uninstall it.
func Run(cmd string) {
	c := parseFlags(cmd)
	err := c.validate()
	if err != nil {
		os.Stderr.WriteString(err.Error() + "\n")
		os.Exit(1)
	}
	if !c.yes && !prompt(c.action(), cmd) {
		fmt.Println("Cancelling...")
		os.Exit(2)
	}
	fmt.Println(c.action() + "ing...")
	if c.install {
		err = install.Install(cmd)
	} else {
		err = install.Uninstall(cmd)
	}
	if err != nil {
		fmt.Printf("%s failed! %s\n", c.action(), err)
		os.Exit(3)
	}
	fmt.Println("Done!")
}

// prompt use for approval
func prompt(action, cmd string) bool {
	fmt.Printf("%s completion for %s? ", action, cmd)
	var answer string
	fmt.Scanln(&answer)

	switch strings.ToLower(answer) {
	case "y", "yes":
		return true
	default:
		return false
	}
}

// config for command line
type config struct {
	install   bool
	uninstall bool
	yes       bool
}

// create a config from command line arguments
func parseFlags(cmd string) config {
	var c config
	flag.BoolVar(&c.install, "install", false,
		fmt.Sprintf("Install completion for %s command", cmd))
	flag.BoolVar(&c.uninstall, "uninstall", false,
		fmt.Sprintf("Uninstall completion for %s command", cmd))
	flag.BoolVar(&c.yes, "y", false, "Don't prompt user for typing 'yes'")
	flag.Parse()
	return c
}

// validate the config
func (c config) validate() error {
	if c.install && c.uninstall {
		return errors.New("Install and uninstall are exclusive")
	}
	if !c.install && !c.uninstall {
		return errors.New("Must specify -install or -uninstall")
	}
	return nil
}

// action name according to the config values.
func (c config) action() string {
	if c.install {
		return "Install"
	}
	return "Uninstall"
}