add dumpdomain

Signed-off-by: Jeff Carr <jcarr@wit.com>
This commit is contained in:
Jeff Carr 2024-11-01 02:53:12 -05:00
parent 54eda59c6e
commit bd62967a53
2 changed files with 61 additions and 68 deletions

20
argv.go
View File

@ -12,9 +12,7 @@ import (
var argv args var argv args
type args struct { type args struct {
ListRepos bool `arg:"--list-repos" help:"list all repositories"`
Port int `arg:"--port" default:"2520" help:"port to run on"` Port int `arg:"--port" default:"2520" help:"port to run on"`
Start string `arg:"--start" help:"start a droplet"`
} }
func (args) Version() string { func (args) Version() string {
@ -24,3 +22,21 @@ func (args) Version() string {
func init() { func init() {
arg.MustParse(&argv) arg.MustParse(&argv)
} }
func (a args) Description() string {
return `
this daemon talks to virtigo talks to libvirt and/or qemu
This sends data back to virtigo. It helps read out the libvirtxml
and convert it to protobuf.
The name is odd, it's virtigo-D not virti-god.
You can query the status directly:
# the list of running vms:
curl --silent http://localhost:2520/vms
# information about vm foo.bar.com:
curl --silent http://localhost:2520/dumpdroplet?foo.bar.com
`
}

109
http.go
View File

@ -22,12 +22,8 @@ func cleanURL(url string) string {
} }
func okHandler(w http.ResponseWriter, r *http.Request) { func okHandler(w http.ResponseWriter, r *http.Request) {
var tmp string
log.Info("Got URL Path: ", r.URL.Path) log.Info("Got URL Path: ", r.URL.Path)
log.Info("Got URL Query:", r.URL.Query().Get("start")) route := cleanURL(r.URL.Path)
tmp = cleanURL(r.URL.Path)
msg, err := ioutil.ReadAll(r.Body) // Read the body as []byte msg, err := ioutil.ReadAll(r.Body) // Read the body as []byte
if err != nil { if err != nil {
@ -36,33 +32,59 @@ func okHandler(w http.ResponseWriter, r *http.Request) {
} }
log.Info("Got URL msg:", string(msg)) log.Info("Got URL msg:", string(msg))
log.Info("Got URL jcarr2 tmp:", tmp) if route == "/" {
if tmp == "/" {
fmt.Fprintln(w, "OK") fmt.Fprintln(w, "OK")
return return
} }
// curl http://localhost:2520/dumpdomain?domain=foo.bar.com
if route == "/dumpdomain" {
domname := r.URL.Query().Get("domain")
fmt.Fprint(w, "import domain:", domname)
xmldoc, err := virshDumpXML(w, r, domname)
domcfg := &libvirtxml.Domain{}
err = domcfg.Unmarshal(xmldoc)
if err != nil {
fmt.Fprintln(w, "domain.Unmarshal XML failed")
fmt.Fprintln(w, "error =", err)
return
}
d, _, err := virtigolib.ImportXML(domcfg)
if err != nil {
fmt.Fprintln(w, "ImportXML failed for", domname, err)
return
}
fmt.Fprintln(w, "ImportXML worked for", domname)
fmt.Fprintln(w, "should send the protobuf to virtigo here", domname)
d.Current.FullXml = xmldoc
d.DumpDroplet(w, r)
return
}
if route == "/vms" {
s := pollHypervisor(me.hv)
fmt.Fprint(w, s)
return
}
// exit the virtigo daemon & have systemd restart it // exit the virtigo daemon & have systemd restart it
// this can happen & when it does, access to // this can happen & when it does, access to
// to libvirtd will hang (aka: virsh list will hang) // to libvirtd will hang (aka: virsh list will hang)
// One way to trigger this is to not properly close // One way to trigger this is to not properly close
// domain sockets opened from go-qemu/hypervisor // domain sockets opened from go-qemu/hypervisor
// it's a good idea in any case so leave it here // it's a good idea in any case so leave it here
if tmp == "/kill" { if route == "/kill" {
log.Warn("KILLED") log.Warn("KILLED")
fmt.Fprintln(w, "KILLED") fmt.Fprintln(w, "KILLED")
os.Exit(-1) os.Exit(-1)
return return
} }
if tmp == "/vms" { // curl http://localhost:2520/import?domain=foo.bar.com
s := pollHypervisor(me.hv) if route == "/import" {
fmt.Fprint(w, s) domname := r.URL.Query().Get("domain")
return
}
if tmp == "/import" {
domname := r.URL.Query().Get("import")
fmt.Fprint(w, "import domain:", domname) fmt.Fprint(w, "import domain:", domname)
xmldoc, err := virshDumpXML(w, r, domname) xmldoc, err := virshDumpXML(w, r, domname)
@ -87,39 +109,7 @@ func okHandler(w http.ResponseWriter, r *http.Request) {
return return
} }
/* if route == "/start" {
if tmp == "/cluster" {
log.Info("/cluster jcarr actually doing START")
fmt.Fprintln(w, "/cluster jcarr actually doing START")
c := pb.InitCluster()
fmt.Fprintln(w, "cluster len(msg) =", len(msg))
err = c.UnmarshalJSON(msg)
if err != nil {
fmt.Fprintln(w, "cluster dirs failed")
fmt.Fprintln(w, "error =", err)
}
for _, dir := range c.Dirs {
var found bool = false
for _, d := range me.dirs {
if d == dir {
found = true
}
}
if found {
log.Info("dir already here", dir)
fmt.Fprintln(w, "dir already here", dir)
} else {
log.Info("append new dir", dir)
fmt.Fprintln(w, "append new dir", dir)
me.dirs = append(me.dirs, dir)
}
}
return
}
*/
if tmp == "/start" {
log.Info("/start jcarr actually doing START", me.Hostname) log.Info("/start jcarr actually doing START", me.Hostname)
fmt.Fprintln(w, "/start jcarr actually doing START", me.Hostname) fmt.Fprintln(w, "/start jcarr actually doing START", me.Hostname)
start := r.URL.Query().Get("start") start := r.URL.Query().Get("start")
@ -162,11 +152,9 @@ func okHandler(w http.ResponseWriter, r *http.Request) {
} }
cmd := []string{"virsh", "create", xml} cmd := []string{"virsh", "create", xml}
fmt.Fprintln(w, "Handling URL:", tmp, "start droplet")
log.Warn("cmd :", cmd) log.Warn("cmd :", cmd)
fmt.Fprintln(w, "Handling start droplet", cmd)
fmt.Fprintln(w, "Handling URL:", tmp, "start droplet")
fmt.Fprintln(w, "cmd: ", cmd)
err, ok, output := shell.RunCmd("/home/", cmd) err, ok, output := shell.RunCmd("/home/", cmd)
shell.Run(cmd) shell.Run(cmd)
if ok { if ok {
@ -180,24 +168,13 @@ func okHandler(w http.ResponseWriter, r *http.Request) {
return return
} }
if tmp == "/favicon.ico" { if route == "/favicon.ico" {
writeFile(w, "ipv6.png") writeFile(w, "ipv6.png")
return return
} }
if tmp == "/uptime" {
writeFile(w, "uptime.html")
return
}
// used for uptime monitor checking (like Kuma) log.Warn("BAD URL =", route)
if tmp == "/uptime" { fmt.Fprintln(w, "BAD URL =", route)
writeFile(w, "uptime.html")
return
}
log.Warn("BAD URL =", tmp)
fmt.Fprintln(w, "BAD ZOOT")
// badurl(w, r.URL.String())
// fmt.Fprintln(w, "BAD", tmp)
} }
func writeFile(w http.ResponseWriter, filename string) { func writeFile(w http.ResponseWriter, filename string) {