GraphQL Filters in the LightMesh API

Use SubnetFilter and related filter inputs correctly in GraphQL queries. Avoid common field-name, operator, and type mistakes that cause API errors.

Many list queries in the LightMesh GraphQL API accept a structured filter argument (for example SubnetFilter on the subnets query). The UI uses the same concepts when you filter subnets by name, zone, site, or customer—API filters are the programmatic equivalent, with stricter typing.

This guide shows a safe request pattern, points to the published schema for exact input types, and lists mistakes that often produce GraphQL validation errors or failed requests in automation.

Before you start

  • Authentication and endpoint: See LightMesh API for the GraphQL URL, token header, and Postman setup.
  • Canonical schema: Field names, filter input types, and operators are defined at LightMesh API Documentation. Always confirm the filter type for your query (for example SubnetFilter, IPAddressFilter, SiteFilter) in that reference before you ship automation.
  • CLI alternative: If you only need search and export, the LightMesh CLI exposes search flags such as --zoneName and --subnetName that map to common lookups. Those flags are not identical to GraphQL filter objects—API field names must still match the schema.

How filters fit the subnets query

The subnets query supports both simple top-level arguments (such as zoneName as a plain String) and a nested filter of type SubnetFilter. They solve similar problems but are not interchangeable shapes.

Mechanism Example shape Typical use
Top-level zoneName "zoneName": "DCN" Quick zone scoping (same idea as CLI --zoneName="DCN")
filter.zoneName { "zoneName": { "eq": "DCN" } } Structured filters with operators and composition
filter.site { "site": { "name": { "eq": "…" } } } Match UI filters on site (nested SiteFilter)

Other list queries follow the same pattern: a filter argument whose type name ends in Filter. Open the query in API documentation and follow the link on the filter argument to the correct input object.

Use GraphQL variables for filter, limit, and offset—the same approach as the subnet-by-id example and audit logging queries.

Postman body (raw JSON):

{
  "query": "query ($limit: Int, $offset: Int, $zoneName: String, $filter: SubnetFilter) { subnets(limit: $limit, offset: $offset, zoneName: $zoneName, filter: $filter, sort_by: \"name\", sort_dir: \"ASC\") { count total results { id name networkAddress zone { name } site { name } } } }",
  "variables": {
    "limit": 50,
    "offset": 0,
    "zoneName": "DCN",
    "filter": {
      "name": { "ilike": "%WAN%" },
      "site": {
        "name": { "eq": "DCN Customer Support Warehouse" }
      }
    }
  }
}

Adjust field names and operators using SubnetFilter and nested types (SiteFilter, CustomerFilter, and so on) in the schema browser.

String operators

String fields use StringFilter. Documented operators include eq, neq, in, like, ilike, contains, startsWith, endsWith, regex, iregex, and null checks via is: NULL or is: NOT_NULL (FilterIs). Prefer eq or ilike for exact or case-insensitive name matches unless you need pattern matching.

Combining conditions

SubnetFilter supports logical composition with and, or, and not (schema). Each entry in those arrays must be a full SubnetFilter object, not a bare string.

"filter": {
  "and": [
    { "zoneName": { "eq": "DCN" } },
    { "name": { "contains": "WAN" } }
  ]
}

Pagination with filters

Filtered list queries return count (rows in the current page) and often total (matches across all pages). Request the next page by increasing offset by the previous limit, as described in Audit logging — Pagination pattern.

"variables": {
  "limit": 50,
  "offset": 50,
  "filter": { "zoneName": { "eq": "DCN" } }
}

If results look truncated, raise limit within what your integration can handle, or page with offset until offset + count reaches total.

Common mistakes (and how to fix them)

Wrong or UI-only field names

GraphQL filter fields are schema names, not always the labels shown in the UI. Examples on SubnetFilter:

  • Use site with a nested SiteFilter, not a top-level siteName string on the filter object.
  • Use customers / contacts with the nested filter types from the schema, not informal names from spreadsheets.
  • Relational fields (zone, region, privateNetwork) expect nested filter objects, not a single concatenated string.

Fix: Open the filter type for your query in api-documentation.lightmesh.com and copy field names from the Input Field table.

Passing a plain string where a filter object is required

Invalid:

"filter": { "name": "SGDC WAN" }

Valid (exact match):

"filter": { "name": { "eq": "SGDC WAN" } }

Invalid:

"filter": { "zoneName": "DCN", "name": { "eq": "Core" } }

when the client declared $filter: String—the variable type must be SubnetFilter (or the correct *Filter type for that query).

Mixing up top-level arguments and filter

The subnets query accepts zoneName as a String at the top level and zoneName as a StringFilter inside filter. Sending { "eq": "DCN" } as the top-level zoneName variable fails type checking.

Fix: Use "zoneName": "DCN" at the top level, or "filter": { "zoneName": { "eq": "DCN" } } inside filter, not both shapes swapped.

Empty, null, or {} filters

  • Omit filter entirely when you do not need it.
  • Do not send filter: null unless your client and query signature explicitly allow it; prefer omitting the key.
  • An empty object "filter": {} is usually valid but matches broadly—combine with limit and meaningful criteria to avoid accidental full-table scans in automation.

For “field is empty / not empty” conditions on strings, use is: NULL or is: NOT_NULL on StringFilter, not an empty string with eq.

Type mismatches on numeric fields

Fields such as id, vlan, and available on SubnetFilter use IntFilter, not strings. Quoted numbers or string operators on those fields cause GraphQL validation errors.

Fix: Use numeric JSON values and IntFilter operators from the schema (eq, in, and so on).

Invalid operators or values for the field type

Operators belong to the filter input type, not the GraphQL output field. Do not reuse SQL or REST query syntax ($gt, ~, free-text search strings inside filter) unless the schema lists that operator on that input.

Fix: Restrict operators to those listed on StringFilter, IntFilter, DateFilter, and related types in the documentation.

Regex and special characters

regex and iregex expect patterns the API accepts as documented on StringFilter. Unescaped metacharacters or invalid patterns can fail at execution time.

Fix: Prefer eq, ilike, or contains for simple automation; test regex filters manually in Postman before embedding them in jobs.

Pagination ignored while filtering

Automation that only reads the first page of a filtered subnets call may miss rows even when total is larger than count.

Fix: Loop on offset or use a sufficient limit, and compare against total when present.

When filters are exploratory or you need CSV export, CLI search flags are often simpler. Examples from LightMesh CLI Tips:

lightmesh subnet search --zoneName="DCN" --output=DNC_Zone_Subnets.csv
lightmesh ip-address search --subnetName="SGDC WAN" --output=SGDC_WAN_IP_Addresses.csv

The CLI still talks to the same API underneath; when you move to raw GraphQL, translate those concepts into the matching schema fields and filter operators.