Merge pull request #520 from aaron-prindle/better-status

Added localkube status to minikube status
pull/531/head
dlorenc 2016-09-08 13:47:04 -07:00 committed by GitHub
commit dc60de97db
8 changed files with 127 additions and 14 deletions

View File

@ -17,16 +17,24 @@ limitations under the License.
package cmd
import (
"fmt"
"os"
"text/template"
"github.com/docker/machine/libmachine"
"github.com/docker/machine/libmachine/state"
"github.com/golang/glog"
"github.com/spf13/cobra"
"k8s.io/minikube/pkg/minikube/cluster"
"k8s.io/minikube/pkg/minikube/constants"
)
var statusFormat string
type Status struct {
MinikubeStatus string
LocalkubeStatus string
}
// statusCmd represents the status command
var statusCmd = &cobra.Command{
Use: "status",
@ -35,15 +43,37 @@ var statusCmd = &cobra.Command{
Run: func(cmd *cobra.Command, args []string) {
api := libmachine.NewClient(constants.Minipath, constants.MakeMiniPath("certs"))
defer api.Close()
s, err := cluster.GetHostStatus(api)
ms, err := cluster.GetHostStatus(api)
if err != nil {
glog.Errorln("Error getting machine status:", err)
os.Exit(1)
}
fmt.Fprintln(os.Stdout, s)
ls := "N/A"
if ms == state.Running.String() {
ls, err = cluster.GetLocalkubeStatus(api)
}
if err != nil {
glog.Errorln("Error getting machine status:", err)
os.Exit(1)
}
status := Status{ms, ls}
tmpl, err := template.New("status").Parse(statusFormat)
if err != nil {
glog.Errorln("Error creating status template:", err)
os.Exit(1)
}
err = tmpl.Execute(os.Stdout, status)
if err != nil {
glog.Errorln("Error executing status template:", err)
os.Exit(1)
}
},
}
func init() {
statusCmd.Flags().StringVar(&statusFormat, "format", constants.DefaultStatusFormat,
`Go template format string for the status output. The format for Go templates can be found here: https://golang.org/pkg/text/template/
For the list accessible variables for the template, see the struct values here:https://godoc.org/k8s.io/minikube/cmd/minikube/cmd#Status`)
RootCmd.AddCommand(statusCmd)
}

View File

@ -11,6 +11,13 @@ Gets the status of a local kubernetes cluster.
minikube status
```
### Options
```
--format="minikubeVM: {{.MinikubeStatus}}\nlocalkube: {{.LocalkubeStatus}}\n": Go template format string for the status output. The format for Go templates can be found here: https://golang.org/pkg/text/template/
For the list accessible variables for the template, see the struct values here:https://godoc.org/k8s.io/minikube/cmd/minikube/cmd#Status
```
### Options inherited from parent commands
```

View File

@ -147,6 +147,26 @@ func GetHostStatus(api libmachine.API) (string, error) {
return s.String(), err
}
// GetLocalkubeStatus gets the status of localkube from the host VM.
func GetLocalkubeStatus(api libmachine.API) (string, error) {
host, err := checkIfApiExistsAndLoad(api)
if err != nil {
return "", err
}
s, err := host.RunSSHCommand(localkubeStatusCommand)
if err != nil {
return "", err
}
s = strings.TrimSpace(s)
if state.Running.String() == s {
return state.Running.String(), nil
} else if state.Stopped.String() == s {
return state.Stopped.String(), nil
} else {
return "", fmt.Errorf("Error: Unrecognize output from GetLocalkubeStatus: %s", s)
}
}
type sshAble interface {
RunSSHCommand(string) (string, error)
}
@ -600,7 +620,7 @@ func GetHostLogs(api libmachine.API) (string, error) {
}
s, err := host.RunSSHCommand(logsCommand)
if err != nil {
return "", nil
return "", err
}
return s, err
}

View File

@ -325,6 +325,46 @@ func TestGetHostStatus(t *testing.T) {
checkState(state.Stopped.String())
}
func TestGetLocalkubeStatus(t *testing.T) {
api := tests.NewMockAPI()
s, _ := tests.NewSSHServer()
port, err := s.Start()
if err != nil {
t.Fatalf("Error starting ssh server: %s", err)
}
d := &tests.MockDriver{
Port: port,
BaseDriver: drivers.BaseDriver{
IPAddress: "127.0.0.1",
SSHKeyPath: "",
},
}
api.Hosts[constants.MachineName] = &host.Host{Driver: d}
s.CommandToOutput = map[string]string{
localkubeStatusCommand: state.Running.String(),
}
if _, err := GetLocalkubeStatus(api); err != nil {
t.Fatalf("Error getting localkube status: %s", err)
}
s.CommandToOutput = map[string]string{
localkubeStatusCommand: state.Stopped.String(),
}
if _, err := GetLocalkubeStatus(api); err != nil {
t.Fatalf("Error getting localkube status: %s", err)
}
s.CommandToOutput = map[string]string{
localkubeStatusCommand: "Bad Output",
}
if _, err := GetLocalkubeStatus(api); err == nil {
t.Fatalf("Expected error in getting localkube status as ssh returned bad output")
}
}
func TestSetupCerts(t *testing.T) {
s, _ := tests.NewSSHServer()
port, err := s.Start()

View File

@ -29,7 +29,7 @@ var stopCommand = "sudo killall localkube || true"
var startCommandFmtStr = `
# Run with nohup so it stays up. Redirect logs to useful places.
sudo sh -c 'PATH=/usr/local/sbin:$PATH nohup /usr/local/bin/localkube %s --generate-certs=false --logtostderr=true --node-ip=%s > %s 2> %s < /dev/null &'
sudo sh -c 'PATH=/usr/local/sbin:$PATH nohup /usr/local/bin/localkube %s --generate-certs=false --logtostderr=true --node-ip=%s > %s 2> %s < /dev/null & echo $! > %s &'
`
var logsCommand = fmt.Sprintf("tail -n +1 %s %s", constants.RemoteLocalKubeErrPath, constants.RemoteLocalKubeOutPath)
@ -41,5 +41,13 @@ func GetStartCommand(kubernetesConfig KubernetesConfig) string {
}
}
flags := strings.Join(flagVals, " ")
return fmt.Sprintf(startCommandFmtStr, flags, kubernetesConfig.NodeIP, constants.RemoteLocalKubeErrPath, constants.RemoteLocalKubeOutPath)
return fmt.Sprintf(startCommandFmtStr, flags, kubernetesConfig.NodeIP, constants.RemoteLocalKubeErrPath, constants.RemoteLocalKubeOutPath, constants.LocalkubePIDPath)
}
var localkubeStatusCommand = fmt.Sprintf(`
if ps $(cat %s) 2>&1 1>/dev/null; then
echo "Running"
else
echo "Stopped"
fi
`, constants.LocalkubePIDPath)

View File

@ -62,6 +62,8 @@ const (
DefaultCPUS = 1
DefaultDiskSize = "20g"
DefaultVMDriver = "virtualbox"
DefaultStatusFormat = "minikubeVM: {{.MinikubeStatus}}\n" +
"localkube: {{.LocalkubeStatus}}\n"
)
var DefaultKubernetesVersion = version.Get().GitVersion
@ -69,6 +71,7 @@ var DefaultKubernetesVersion = version.Get().GitVersion
const (
RemoteLocalKubeErrPath = "/var/lib/localkube/localkube.err"
RemoteLocalKubeOutPath = "/var/lib/localkube/localkube.out"
LocalkubePIDPath = "/var/run/localkube.pid"
)
var ConfigFilePath = MakeMiniPath("config")

View File

@ -36,6 +36,7 @@ type SSHServer struct {
Connected bool
Transfers *bytes.Buffer
HadASessionRequested bool
CommandToOutput map[string]string
}
// NewSSHServer returns a NewSSHServer instance, ready for use.
@ -107,6 +108,11 @@ func (s *SSHServer) Start() (int, error) {
return
}
s.Commands[cmd.Command] = 1
// Write specified command output as mocked ssh output
if val, ok := s.CommandToOutput[cmd.Command]; ok {
channel.Write([]byte(val))
}
channel.SendRequest("exit-status", false, []byte{0, 0, 0, 0})
// Store anything that comes in over stdin.

View File

@ -100,8 +100,7 @@ func (m *MinikubeRunner) SetEnvFromEnvCmdOutput(dockerEnvVars string) error {
}
func (m *MinikubeRunner) GetStatus() string {
status := m.RunCommand("status", true)
return strings.Trim(status, "\n")
return m.RunCommand("status --format={{.MinikubeStatus}}", true)
}
func (m *MinikubeRunner) CheckStatus(desired string) {