add vm inventory update endpoint
Some checks are pending
CI / Lint (push) Waiting to run
CI / Test (push) Waiting to run
CI / End-to-End (push) Waiting to run
CI / Publish Docker (push) Blocked by required conditions
continuous-integration/drone/push Build is passing

This commit is contained in:
2024-09-30 15:30:38 +10:00
parent 6a41528f41
commit 380707cf23
11 changed files with 254 additions and 23 deletions

View File

@@ -6,6 +6,7 @@ import (
"net/http"
"vctp/db"
"vctp/internal/secrets"
"vctp/internal/settings"
"vctp/internal/vcenter"
"github.com/a-h/templ"
@@ -20,6 +21,7 @@ type Handler struct {
GoVersion string
VcCreds *vcenter.VcenterLogin
Secret *secrets.Secrets
Settings *settings.Settings
}
func (h *Handler) html(ctx context.Context, w http.ResponseWriter, status int, t templ.Component) {

View File

@@ -0,0 +1,114 @@
package handler
import (
"context"
"database/sql"
"fmt"
"net/http"
"vctp/db/queries"
"vctp/internal/vcenter"
)
// VmUpdate receives the CloudEvent for a VM modification or move
func (h *Handler) VmUpdateDetails(w http.ResponseWriter, r *http.Request) {
var matchFound bool
var inventoryId int64
var srmPlaceholder string
var vmUuid string
var dbUuid string
ctx := context.Background()
// reload settings in case vcenter list has changed
h.Settings.ReadYMLSettings()
for _, url := range h.Settings.Values.Settings.VcenterAddresses {
h.Logger.Debug("connecting to vcenter", "url", url)
vc := vcenter.New(h.Logger, h.VcCreds)
vc.Login(url)
// Get list of VMs from vcenter
vms, err := vc.GetAllVmReferences()
// Get list of VMs from inventory table
h.Logger.Debug("Querying inventory table")
results, err := h.Database.Queries().GetInventoryByVcenter(ctx, url)
if err != nil {
h.Logger.Error("Unable to query inventory table", "error", err)
w.WriteHeader(http.StatusInternalServerError)
fmt.Fprintf(w, "Unable to query inventory table %s\n", err)
}
if len(results) == 0 {
h.Logger.Error("Empty inventory results")
}
// Iterate VMs from vcenter and see if they were in the database
for _, vm := range vms {
matchFound = false
inventoryId = 0
srmPlaceholder = "FALSE" // Default assumption
vmUuid = ""
for _, dbvm := range results {
if dbvm.VmId.String == vm.Reference().Value {
h.Logger.Debug("Found VM in database", "vm_name", dbvm.Name, "id", dbvm.VmId.String)
matchFound = true
inventoryId = dbvm.Iid
dbUuid = dbvm.VmUuid.String
break
}
}
if matchFound {
//h.Logger.Debug("Need to update VM in inventory table", "MoRef", vm.Reference())
vmObj, err := vc.ConvertObjToMoVM(vm)
if err != nil {
h.Logger.Error("Received error getting vm managedobject", "error", err)
continue
}
if vmObj.Config != nil {
vmUuid = vmObj.Config.Uuid
// Determine if the VM is a normal VM or an SRM placeholder
if vmObj.Config.ManagedBy != nil && vmObj.Config.ManagedBy.ExtensionKey == "com.vmware.vcDr" {
if vmObj.Config.ManagedBy.Type == "placeholderVm" {
h.Logger.Debug("VM is a placeholder")
srmPlaceholder = "TRUE"
} else {
h.Logger.Debug("VM is managed by SRM but not a placeholder", "details", vmObj.Config.ManagedBy)
}
}
if srmPlaceholder == "TRUE" || vmUuid != dbUuid {
h.Logger.Debug("Need to update vm", "name", vmObj.Name, "srm_placeholder", srmPlaceholder, "uuid", vmUuid)
params := queries.InventoryUpdateParams{
Iid: inventoryId,
SrmPlaceholder: srmPlaceholder,
Uuid: sql.NullString{String: vmUuid, Valid: vmUuid != ""},
}
h.Logger.Debug("database params", "params", params)
err := h.Database.Queries().InventoryUpdate(context.Background(), params)
if err != nil {
h.Logger.Error("Error received updating inventory for VM", "name", vmObj.Name, "error", err)
}
}
} else {
h.Logger.Warn("VM no longer present in vcenter or missing config values", "MoRef", vm.Reference())
}
}
}
}
h.Logger.Debug("Processed vm update successfully")
w.WriteHeader(http.StatusOK)
// TODO - return some JSON
fmt.Fprintf(w, "Processed vm update successfully")
}

View File

@@ -7,12 +7,13 @@ import (
"vctp/db"
"vctp/dist"
"vctp/internal/secrets"
"vctp/internal/settings"
"vctp/internal/vcenter"
"vctp/server/handler"
"vctp/server/middleware"
)
func New(logger *slog.Logger, database db.Database, buildTime string, sha1ver string, goVersion string, creds *vcenter.VcenterLogin, secret *secrets.Secrets) http.Handler {
func New(logger *slog.Logger, database db.Database, buildTime string, sha1ver string, goVersion string, creds *vcenter.VcenterLogin, secret *secrets.Secrets, settings *settings.Settings) http.Handler {
h := &handler.Handler{
Logger: logger,
Database: database,
@@ -21,6 +22,7 @@ func New(logger *slog.Logger, database db.Database, buildTime string, sha1ver st
GoVersion: goVersion,
VcCreds: creds,
Secret: secret,
Settings: settings,
}
mux := http.NewServeMux()
@@ -34,9 +36,13 @@ func New(logger *slog.Logger, database db.Database, buildTime string, sha1ver st
mux.HandleFunc("/api/import/vm", h.VmImport)
// Use this when we need to manually remove a VM from the database to clean up
mux.HandleFunc("/api/inventory/vm/delete", h.VmCleanup)
// add missing data to VMs
mux.HandleFunc("/api/inventory/vm/update", h.VmUpdateDetails)
// temporary endpoint
//mux.HandleFunc("/api/cleanup/updates", h.UpdateCleanup)
mux.HandleFunc("/api/cleanup/vcenter", h.VcCleanup)
//mux.HandleFunc("/api/cleanup/vcenter", h.VcCleanup)
mux.HandleFunc("/api/report/inventory", h.InventoryReportDownload)
mux.HandleFunc("/api/report/updates", h.UpdateReportDownload)