Skip to main content
Version: 1.2

Query resources with the API

Use the Insights API to query your whole fleet from the terminal you already work in. One hub kubectl context reaches every connected control plane, so you can list, filter, and count resources across all of them without switching contexts.

Before you begin​

Several steps send query parameters with kubectl get --raw. Use Hub APIs with kubectl explains why, and how paging and counts work.

List resources​

  1. Request the first page of resources.

    kubectl --context=hub get --raw \
    '/apis/inventory.hub.upbound.io/v1beta1/resources?pageSize=25' \
    | jq -r '.items[] | [.location.controlPlane, .source.kind, .source.name] | @tsv'

    Each item carries the resource's identity on its control plane in source, its control plane and realm in location, and Hub's sync and relationship data in hub.

  2. Read the number of matches from metadata.total.

    kubectl --context=hub get --raw \
    '/apis/inventory.hub.upbound.io/v1beta1/resources?pageSize=25' \
    | jq '.metadata'
    {
    "total": { "count": 614, "relation": "eq" },
    "page": 1,
    "pageSize": 25
    }

    Request the next page with page=2. Above 1000 matches, total reads 1000 with relation set to gt. Count resources for an exact number.

Search and filter​

  1. Search with search. It matches a substring of the name, namespace, kind, API group, API version, UID, or Crossplane type.

    kubectl --context=hub get --raw \
    '/apis/inventory.hub.upbound.io/v1beta1/resources?search=payments&pageSize=25'
  2. Filter with an expression. Reference fields by name, such as kind, realm, or conditions.ready.status, and URL-encode the expression. See Encode a filter expression.

    FILTER=$(jq -rn --arg f 'conditions.ready.status == "False" && realm == "production"' '$f|@uri')
    kubectl --context=hub get --raw \
    "/apis/inventory.hub.upbound.io/v1beta1/resources?pageSize=100&filter=$FILTER" \
    | jq -r '.items[] | "\(.location.controlPlane)\t\(.source.kind)\t\(.source.name)"'

    The Filter expression reference lists the operators, gives examples of common queries, and explains each error.

  3. If a filter returns no items, read message in the response. An invalid expression returns an error rather than an empty list:

    {
    "message": "ERROR: <input>:1:1: undeclared reference to 'source'\n | source.kind == \"Pod\"\n | ^"
    }

Count resources​

Create a ResourceStats to count resources by health. An empty query counts everything you can see:

kubectl --context=hub create -o json -f - <<'EOF'
apiVersion: inventory.hub.upbound.io/v1beta1
kind: ResourceStats
query: {}
EOF

The response counts each condition on its own:

{
"results": {
"summary": {
"totalCount": 614,
"readyTrue": 27,
"readyFalse": 0,
"readyUnknown": 587,
"syncedTrue": 2,
"syncedFalse": 0,
"syncedUnknown": 612,
"healthyTrue": 4,
"healthyFalse": 0,
"healthyUnknown": 610
}
}
}

A resource can fail more than one condition, so the condition counts can add up to more than the total number of resources.

Inspect one resource​

  1. Find the resource's record name. Hub names each record itself, so search for the resource and read metadata.name:

    NAME=$(kubectl --context=hub get --raw \
    '/apis/inventory.hub.upbound.io/v1beta1/resources?search=example-bucket&pageSize=1' \
    | jq -r '.items[0].metadata.name')
  2. Get the record.

    kubectl --context=hub get resources.inventory.hub.upbound.io "$NAME" -o yaml
  3. Read its events.

    kubectl --context=hub get --raw \
    "/apis/inventory.hub.upbound.io/v1beta1/resources/$NAME/events"
  4. Read its relationships.

    kubectl --context=hub get --raw \
    "/apis/inventory.hub.upbound.io/v1beta1/resourcerelationships/$NAME"

    The response lists the resources this one composes, the ones it references, and the ones that reference it. For the whole tree below a composite resource, request resourcerelationshiptrees/$NAME instead.

Troubleshoot​

SymptomCause
A list request fails with "the list matches more than 500 items"The request has no pageSize. Add pageSize, and page for later pages.
A filter returns 400The expression is invalid. See Errors.
Fewer resources than you expectResults reflect your access, and Hub may not have synced a new resource yet. See How Insights data works.
resourcerelationships returns an error without a nameRelationship endpoints answer for one resource. Add the record name to the path.

Next steps​