Files
vctp2/server/handler/vmUpdateDetails.go
Nathan Coad ea1eeb5c21
Some checks failed
continuous-integration/drone Build is passing
CI / Lint (push) Has been cancelled
CI / Test (push) Has been cancelled
CI / End-to-End (push) Has been cancelled
CI / Publish Docker (push) Has been cancelled
update to support postgresql and add godocs
2026-01-13 17:05:14 +11:00

122 lines
3.6 KiB
Go

package handler
import (
"context"
"database/sql"
"fmt"
"net/http"
"vctp/db/queries"
"vctp/internal/vcenter"
)
// VmUpdateDetails refreshes inventory metadata from vCenter.
// @Summary Refresh VM details
// @Description Queries vCenter and updates inventory records with missing details.
// @Tags inventory
// @Produce text/plain
// @Success 200 {string} string "Update completed"
// @Failure 500 {string} string "Server error"
// @Router /api/inventory/vm/update [post]
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")
}