diff --git a/internal/httpapi/phase3.go b/internal/httpapi/phase3.go index b64f69b..1e64b65 100644 --- a/internal/httpapi/phase3.go +++ b/internal/httpapi/phase3.go @@ -163,7 +163,12 @@ func resolveRunTarget(ctx context.Context, pool *db.Pool, targetSlug string) (ho } if strings.HasPrefix(targetSlug, "lxc:") { var pveID, hostAttr string - if qerr := pool.QueryRow(ctx, "SELECT attributes->>'pve_id', attributes->>'host' FROM entities WHERE slug = $1", targetSlug).Scan(&pveID, &hostAttr); qerr != nil || pveID == "" { + // COALESCE the host column: many older LXC entities (seeded from + // inventory, not provisioned by pct_create) have pve_id but no host + // attribute at all. Scanning a SQL NULL into a plain string errors + // the whole row, wrongly reporting "missing pve_id" even when it was + // present — COALESCE avoids the NULL, "" is handled below. + if qerr := pool.QueryRow(ctx, "SELECT attributes->>'pve_id', COALESCE(attributes->>'host', '') FROM entities WHERE slug = $1", targetSlug).Scan(&pveID, &hostAttr); qerr != nil || pveID == "" { return "", "", nil, fmt.Errorf("LXC not found or missing pve_id: %s", targetSlug) } hostSlug := hostAttr diff --git a/internal/mcp/server.go b/internal/mcp/server.go index 56163e4..bc95888 100644 --- a/internal/mcp/server.go +++ b/internal/mcp/server.go @@ -1196,7 +1196,12 @@ func resolveExecTarget(ctx context.Context, pool *db.Pool, targetSlug string) (h } if strings.HasPrefix(targetSlug, "lxc:") { var pveID, hostAttr string - if qerr := pool.QueryRow(ctx, "SELECT attributes->>'pve_id', attributes->>'host' FROM entities WHERE slug = $1", targetSlug).Scan(&pveID, &hostAttr); qerr != nil || pveID == "" { + // COALESCE the host column: many older LXC entities (seeded from + // inventory, not provisioned by pct_create) have pve_id but no host + // attribute at all. Scanning a SQL NULL into a plain string errors + // the whole row, wrongly reporting "missing pve_id" even when it was + // present — COALESCE avoids the NULL, "" is handled below. + if qerr := pool.QueryRow(ctx, "SELECT attributes->>'pve_id', COALESCE(attributes->>'host', '') FROM entities WHERE slug = $1", targetSlug).Scan(&pveID, &hostAttr); qerr != nil || pveID == "" { return "", "", nil, fmt.Errorf("LXC not found or missing pve_id: %s", targetSlug) } hostSlug := hostAttr