Is there an easy way to filter metafield by including only those with definitions?

I have products set up with metafield definitions with various namespaces, I was wondering if there is an easy way to get all 250 metafields with definitions in one query:

when I look at arguments for metafields: MetafieldConnection!, it doesn’t allow filtering by metafields with definitions only and it only allows filter by one namespace and a list of keys rather than multiple namespaces from all definitions that I know in one query.

Depending on the amount of namespaces, I think the best solution is to query based off that.

{
  product(id: $id) {
    metafields(first: 250, namespace: "custom") {
      nodes {
        ...
      }
    }
  }
}

I’m honestly not sure what something like this would do

{
  product(id: $id) {
    metafieldDefinitions(first: 250) {
      nodes {
        name
        metafields(first: 250) {
          nodes {
            key
            namespace
            value
          }
        }
      }
    }
  }
}

this works if I query the product one by one, it won’t work if I do products: products - GraphQL Admin

  products(first: 250) {
    nodes{
    metafields(include the metafields with definitions, which is always at most 250) {
     namespace
    key
    value
     }
  }
}

try this

{
  products(first: 250) {
    nodes {
      id
      ... on Product {
        metafields(first: 250) {
          nodes {
            namespace
            key
            value
          }
        }
      }
    }
  }
}

What does the … on Product do, does it exclude the metafields w/o definitions?

Anyways I ended up doing this instead because I needed to filter out shopify standard metafields from metafield definitions and only grab the custom metafields for my use case by looping through all definitions, which could be more than 250 because the standard definitions are also returned in addition to the 250 custom ones I created:

query {
  metafieldDefinitions(first: 250, ownerType: PRODUCT) {
    edges {
      node {
        id
        namespace
        key
        type {
          name
        }
      }
    }
    pageInfo {
      hasNextPage
      endCursor
    }
  }
}

and for each metafield definition, I only select those with namespaces belonging to custom metafields I created and run another query for each definition to get the actual values:

query queryWithVariables($after: String, $id: ID!) {
  metafieldDefinition(id: $id) {
        metafields(first: 250, after: $after) {
          nodes{
            key
            namespace
            value
...

The ... on Product syntax is an inline fragment used to retrieve specific data in a query. You can read more about it here.

Your use case isn’t entirely clear, but based on the documentation, if you omit the namespace, the app-reserved namespace will be used.

I haven’t tested this, but in theory, the following query should return only metafields created by your app:

{
  products(first: 250) {
    nodes {
      id
      ... on Product {
        metafields(first: 250) {
          nodes {
            namespace
            key
            value
            definition {
              id
              key
              type {
                name
              }
            }
          }
        }
      }
    }
  }
}
1 Like
query products($first:Int, $queryStr: String){
  products(first: $first, reverse: true, sortKey: UPDATED_AT query: $queryStr) {
    edges {
      node {
        id
        title
        metafields(first: 250){
            edges{
                node{
                        id
                        key
                        name
                        namespace
                }
           }
        }
      }
    }
}

I tried this but it does include unstructured metafields (metafields without definitions)