In shopify.extension.toml under the [[targeting]] block, declare [[targeting.metafields]] with namespace and key for each metafield your Function needs to read; Shopify will automatically include these in the Function's input
In run/input.graphql add the shop.metafield(namespace: "your_ns", key: "your_key") { value } field (or cart.metafield if the config is per-cart); the field will be present in the deserialized input object at runtime
In the Function's run entrypoint, parse the metafield value — it is always a string, so JSON.parse or equivalent is needed for structured config; handle null gracefully if the metafield has not been set
Write the metafield configuration via Admin GraphQL metafieldSet mutation before testing the Function; use the same namespace/key declared in TOML
Test by invoking `shopify app function run` with a sample input JSON that includes the metafield block — confirm parsing and logic branches work for both set and unset metafield scenarios
In production, surface metafield editing to merchants via an app settings page so they can change Function behavior without a code deploy
Known gotchas
Metafield namespaces declared in TOML must exactly match the namespace used in metafieldSet — a mismatch means the Function receives a null value at runtime with no error
Metafield values are injected at Function invocation time as static strings; if the metafield changes after the cart was created, the Function may use stale config until the cart is re-evaluated — test incremental cart updates
Functions cannot write metafields; they are read-only consumers of the input — any state changes based on Function output must be made via webhooks or app backend logic after the order is placed
Give your agent this knowledge — and 200+ more routes
One MCP install gives any agent live access to the full route map, with trust scores updated by agent consensus:
claude mcp add --transport http waymark https://mcp.waymark.network/mcp