diff --git a/Makefile b/Makefile index 206234a..dea0e61 100644 --- a/Makefile +++ b/Makefile @@ -10,8 +10,8 @@ all: install @echo build worked virtigo list droplets virtigo list droplets --on - virtigo droplet start --name coriolis virtigo droplet show --name coriolis + virtigo droplet start --name coriolis build: goimports vet GO111MODULE=off go build \ diff --git a/doAdminGui.go b/doAdminGui.go index fba8b5e..6418d9b 100644 --- a/doAdminGui.go +++ b/doAdminGui.go @@ -109,7 +109,7 @@ func doLocalhostAdminGui() *adminT { log.Info("droplets not initialized") return } - admin.dwin = newDropletsWindow() + admin.dwin = newDropletsWindow(admin) admin.dwin.win.Custom = func() { log.Info("hiding droplet table window") } @@ -225,7 +225,7 @@ func (admin *adminT) doAdminGui() { log.Info("droplets not initialized") return } - admin.dwin = newDropletsWindow() + admin.dwin = newDropletsWindow(admin) admin.dwin.win.Custom = func() { log.Info("hiding droplet table window") } @@ -320,7 +320,7 @@ func (admin *adminT) makeClusterGroup(c *virtpb.Cluster) { log.Info("droplets not initialized") return } - admin.dwin = newDropletsWindow() + admin.dwin = newDropletsWindow(admin) admin.dwin.win.Custom = func() { log.Info("hiding droplet table window") } @@ -382,3 +382,28 @@ func postData(url string, data []byte) ([]byte, error) { return body, nil } + +func (admin *adminT) postEvent(e *virtpb.Event) error { + var result *virtpb.Event + result = new(virtpb.Event) + + msg, err := e.Marshal() + if err != nil { + log.Info("postEvent() marshal() failed", err, e) + return err + } + + // update the droplet list + if data, err := postData(admin.url.String()+"/event", msg); err != nil { + log.Info("postEvent() /event Error:", err) + return err + } else { + if err := result.Unmarshal(data); err != nil { + log.Println("postEvent() result marshal failed", err, "len(dat) =", len(data)) + log.Println("postEvent() data =", string(data)) + return err + } + } + log.Printf("Event type: %s\n", result.DropletUuid) + return nil +} diff --git a/doDroplet.go b/doDroplet.go index 804897e..38d9903 100644 --- a/doDroplet.go +++ b/doDroplet.go @@ -71,10 +71,25 @@ func doDroplet() (string, error) { for all.Scan() { vm := all.Next() if argv.Droplet.Name == vm.Hostname { - log.Info(vm.SprintHeader()) - txt := vm.FormatTEXT() - log.Info(txt) - return "droplet found", nil + if argv.Droplet.Show != nil { + log.Info(vm.SprintHeader()) + txt := vm.FormatTEXT() + log.Info(txt) + return "droplet status", nil + } + if argv.Droplet.Start != nil { + log.Info("should start droplet here") + log.Info(vm.SprintHeader()) + e := new(virtpb.Event) + e.Etype = virtpb.EventType_POWERON + e.DropletUuid = vm.Uuid + + if err := admin.postEvent(e); err != nil { + return "droplet start err", err + } + return "droplet start", nil + } + return "droplet found", fmt.Errorf("do what to the droplet?") } found.Append(vm) } @@ -82,3 +97,16 @@ func doDroplet() (string, error) { } return "", fmt.Errorf("droplet %s not found", argv.Droplet.Name) } + +func doEvent(e *virtpb.Event) *virtpb.Event { + result := new(virtpb.Event) + if e.Etype == virtpb.EventType_POWERON { + log.Println("power on droplet on local cluster here", e.DropletUuid) + result.State = virtpb.Event_DONE + rs, err := Start(e.DropletUuid) + log.Println("Start() returned", rs) + log.Println("Start() returned err", err) + } + + return result +} diff --git a/http.go b/http.go index 452ff74..6afff8b 100644 --- a/http.go +++ b/http.go @@ -21,8 +21,8 @@ func cleanURL(url string) string { func okHandler(w http.ResponseWriter, r *http.Request) { var route string route = cleanURL(r.URL.Path) - log.HttpMode(w) - defer log.HttpMode(nil) + // log.HttpMode(w) + // defer log.HttpMode(nil) msg, err := ioutil.ReadAll(r.Body) // Read the body as []byte if err != nil { @@ -70,26 +70,24 @@ func okHandler(w http.ResponseWriter, r *http.Request) { return } - if route == "/start" { - hostname := r.URL.Query().Get("hostname") - if hostname == "" { - log.Warn("start failed. hostname is blank", cleanURL(r.URL.Path)) + if route == "/event" { + var e *virtpb.Event + e = new(virtpb.Event) + if err := e.Unmarshal(msg); err != nil { + log.Info("proto.Unmarshal() failed on wire message len", len(msg)) + log.Info("error =", err) return } - log.Warn("hostname is", hostname) - - // log.Warn("Handling URL:", tmp, "start droplet", start) - result, err := Start(hostname) - if err == nil { - log.Info(result) - log.Info(hostname, "started output ok") - log.Info(hostname, "need to parse the output here") - log.Info(hostname, "todo: switch to protobuf here") - } else { - log.Info(result) - log.Info(err) - log.Info(hostname, "start failed") + log.Info("/event proto.Unmarshal() worked on msg len", len(msg), "hostname =", e.DropletUuid) + result := doEvent(e) + data, err := result.Marshal() + if err != nil { + log.Info("/event marshal failed", err, "len(data) =", len(data)) + fmt.Fprintln(w, "/event failed", err) + return } + w.Write(data) + // fmt.Fprintln("droplet marshal failed", err) return } diff --git a/main.go b/main.go index f02df52..d570322 100644 --- a/main.go +++ b/main.go @@ -76,9 +76,9 @@ func main() { if argv.Server != "" { log.Info("start admin interface") - me.admin = new(adminT) + admin := new(adminT) var err error - me.admin.url, err = url.Parse(argv.Server) + admin.url, err = url.Parse(argv.Server) if err != nil { badExit(err) } @@ -94,7 +94,7 @@ func main() { badExit(err) } - me.admin.doAdminGui() + admin.doAdminGui() okExit("admin close") } diff --git a/start.go b/start.go index 5426471..e5bf0fd 100644 --- a/start.go +++ b/start.go @@ -29,7 +29,7 @@ func isClusterStable() (string, error) { // for now, because sometimes this should write to stdout and // sometimes to http socket, it returns a string -func Start(name string) (string, error) { +func Start(id string) (string, error) { var result string if s, err := isClusterStable(); err != nil { @@ -38,9 +38,9 @@ func Start(name string) (string, error) { } // lookup the droplet by name - d := me.cluster.FindDropletByName(name) + d := me.cluster.FindDropletByName(id) if d == nil { - result = "can't start unknown droplet: " + name + result = "can't start unknown droplet: " + id return result, errors.New(result) } @@ -66,12 +66,12 @@ func Start(name string) (string, error) { if ok { return result + b, nil } - return result + b, errors.New("start " + name + " on hypervisor " + h.pb.Hostname) + return result + b, errors.New("start " + d.Hostname + " on hypervisor " + h.pb.Hostname) } // skip hypervisors marked inactive if h.pb.Active != true { - result += fmt.Sprintln("hypervisor is inactive:", name, "for", h.pb.Hostname, h.pb.Active) + result += fmt.Sprintln("hypervisor is inactive:", d.Hostname, "for", h.pb.Hostname, h.pb.Active) continue } @@ -82,10 +82,10 @@ func Start(name string) (string, error) { if ok { return result + b, nil } - return result + b, errors.New("start " + name + " on hypervisor " + h.pb.Hostname) + return result + b, errors.New("start " + d.Hostname + " on hypervisor " + h.pb.Hostname) } - result += fmt.Sprintln("hypervisor ready:", name, "for", h.pb.Hostname, h.pb.Active) + result += fmt.Sprintln("hypervisor ready:", d.Hostname, "for", h.pb.Hostname, h.pb.Active) pool = append(pool, h) } @@ -106,5 +106,5 @@ func Start(name string) (string, error) { if ok { return result + output, nil } - return result + output, errors.New("start " + name + " on hypervisor " + h.pb.Hostname) + return result + output, errors.New("start " + d.Hostname + " on hypervisor " + h.pb.Hostname) } diff --git a/structs.go b/structs.go index 9a00e35..7534360 100644 --- a/structs.go +++ b/structs.go @@ -25,7 +25,6 @@ func (b *virtigoT) Enable() { // this app's variables type virtigoT struct { pp *arg.Parser // go-arg parser - cluster *virtpb.OldCluster // basic cluster settings myGui *gui.Node // the gui toolkit handle e *virtpb.Events // virt protobuf events hmap map[*virtpb.Hypervisor]*HyperT // map to the local struct @@ -40,10 +39,11 @@ type virtigoT struct { missingDropletTimeout time.Duration // how long a droplet can be missing for status *gui.Node // the cluster status lastuptime *gui.Node // the last time uptime was checked by Kuma - admin *adminT // the admin struct clusters *virtpb.Clusters // clusters protobuf cmap map[*virtpb.Cluster]*adminT // map to local GUI objects and the protobuf gwin *gadgets.GenericWindow // main window + cluster *virtpb.OldCluster // basic cluster settings + // admin *adminT // the admin struct } // cluster "admin" mode diff --git a/windowDroplets.go b/windowDroplets.go index 3fc1bab..807ff41 100644 --- a/windowDroplets.go +++ b/windowDroplets.go @@ -35,7 +35,7 @@ func (w *stdDropletTableWin) Toggle() { w.win.Toggle() } -func newDropletsWindow() *stdDropletTableWin { +func newDropletsWindow(admin *adminT) *stdDropletTableWin { dwin := new(stdDropletTableWin) dwin.win = gadgets.NewGenericWindow("virtigo current droplets", "Options") dwin.win.Custom = func() { @@ -46,7 +46,7 @@ func newDropletsWindow() *stdDropletTableWin { grid.NewButton("Active", func() { var found *virtpb.Droplets found = virtpb.NewDroplets() - all := me.admin.cluster.Droplets.All() + all := admin.cluster.Droplets.All() for all.Scan() { vm := all.Next() if vm.Current.State != virtpb.DropletState_ON { @@ -60,7 +60,7 @@ func newDropletsWindow() *stdDropletTableWin { grid.NewButton("Inactive", func() { var found *virtpb.Droplets found = virtpb.NewDroplets() - all := me.admin.cluster.Droplets.All() + all := admin.cluster.Droplets.All() for all.Scan() { vm := all.Next() if vm.Current.State == virtpb.DropletState_ON {