How Fixed Bundles Work in Shopify

TLDR

  • A fixed bundle's configuration is stored in a metafield on the parent variant, so each variant of a product can be its own bundle
  • Adding the parent variant to cart is all it takes. The Cart Transform reads the metafield and expands the parent into its components
  • Fixed bundles are priced by the parent variant and need no custom theme code
  • Attributes can be set per component in the app, or passed at add-to-cart with the _attributes line item property

This is a follow-up to How Native Bundles Work in Shopify, which covers the foundation: every bundle is a parent plus components, the parent carries a configuration, and the Cart Transform Function expands the parent into its components on every cart event.

A fixed bundle is the simplest version of that. The merchant decides exactly what's in the box, and the customer just adds it to cart.

The configuration lives on the parent variant

A fixed bundle's configuration is stored in an app-owned metafield on the parent variant: $app:fixed_config. When you build a fixed bundle in Flex Bundles, that's what the app writes.

A simplified version looks like this:

{
  "id": 1042,
  "active": true,
  "bundle_type": "fixed",
  "parent": { "product_id": 8812345678901, "variant_id": 45123456789012 },
  "components": [
    { "product_id": 8811111111111, "variant_id": 45111111111111, "quantity": 1 },
    { "product_id": 8812222222222, "variant_id": 45122222222222, "quantity": 1 },
    { "product_id": 8813333333333, "variant_id": 45133333333333, "quantity": 2,
      "attributes": { "Finish": "Matte" } }
  ],
  "settings": { "title": "The Weekend Kit", "image": "https://cdn.shopify.com/..." }
}

The important parts:

  • components is the full list of variants and quantities that make up the bundle. It's decided ahead of time, not by the customer.
  • attributes (optional) are key/value pairs added to that component's line item, for things like a finish, a kit label, or a fulfillment note.
  • settings (optional) override the bundle's title and image in cart and checkout.

Because the metafield sits on the variant rather than the product, each variant of a parent product can be a different bundle. A "Starter" variant and a "Pro" variant of the same product can expand into completely different sets of components.

How a fixed bundle gets expanded

  1. The customer adds the parent variant to cart. Nothing special is needed: a normal add-to-cart button, a cart permalink, or a Buy Button all work.
  2. On the cart event, Shopify runs the Cart Transform Function.
  3. The function reads each cart line's variant and checks for a fixed_config metafield.
  4. If it finds an active fixed configuration, it expands the parent line into the configured components, with their quantities and attributes.

The storefront never sends the component list. It only ever adds the parent. That's why fixed bundles work without any custom theme code.

Pricing

Fixed bundles are priced by the parent variant. Whatever the parent variant costs is what the customer pays for the bundle, and Shopify allocates that amount across the component line items so the order totals stay accurate.

If you want to run a bundle discount, set the parent variant's price (or its compare-at price) accordingly. Pricing a fixed bundle is the same as pricing any other product.

Adding attributes at add-to-cart

Attributes set in the app are the same for every customer. When you need something per order, like a gift message or a monogram, pass an _attributes line item property with the parent variant:

await fetch('/cart/add.js', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify({
    items: [{
      id: 45123456789012, // the fixed bundle parent variant
      quantity: 1,
      properties: {
        _attributes: JSON.stringify({
          "Gift Message": "Happy Birthday!",
          "Gift Wrap": "Yes"
        })
      }
    }]
  })
});

Every key/value pair is added to each component line in the bundle, merged over the attributes set in the app. If both define the same key, the _attributes value wins. Malformed JSON is ignored and the bundle still expands normally. Full details are in the Cart API integration docs.

What the order looks like

On the order, the parent is gone. The components are real line items with their own SKUs, inventory, and allocated prices, grouped under a "Part of" label in the Shopify admin. Each component also carries a _flex_bundle property referencing the bundle, and the order is tagged flex-bundles-has-bundle. Your warehouse, 3PL, and reporting all see actual products instead of one mystery SKU.

Orders that skip checkout

The Cart Transform only runs in the cart and checkout. Some orders never go through checkout with the bundle in the cart:

  • Post-purchase and thank you page upsells, which add products through an order edit
  • Marketplace and channel orders, such as TikTok Shop, Amazon, and the Shop app

On those orders, the fixed bundle arrives as a single parent line with no components. Each fixed bundle has an Expand bundle on order edits setting for this. When it's on, Flex Bundles watches for the parent variant arriving without its components and expands it after the fact with Shopify's Order Editing API: it adds the components, removes and restocks the parent, and balances the line prices so the customer isn't charged or refunded anything. See Bundle Types for the order tags it uses.

When to use a fixed bundle

Fixed bundles are the right choice when you decide what goes in the box: curated kits, gift sets, starter packs, seasonal boxes. They're the fastest to launch because they need no theme work.

When the customer decides what goes in the box, you want a flex bundle instead.

If you're not sure which fits your catalog, book a demo and we'll walk through it with your products.

Frequently Asked Questions

Where is a fixed bundle's configuration stored?

In an app-owned metafield on the parent variant ($app:fixed_config). It lists the component variants and quantities, plus optional attributes, a custom title, and a custom image. The Cart Transform Function reads it on every cart event.

Do fixed bundles need custom theme code?

No. The storefront just adds the parent variant to cart like any other product. The Cart Transform finds the configuration on that variant and expands it, so a standard add-to-cart button, a cart permalink, or a Buy Button all work.

How are fixed bundles priced?

By the parent variant's price. The customer pays whatever the parent variant costs, and Shopify allocates that amount across the component line items.

What happens when a fixed bundle is sold outside Shopify checkout?

Orders from post-purchase upsells, marketplaces, and channels like TikTok Shop or Amazon never pass through checkout, so the Cart Transform never runs and the parent arrives as a single line. With Expand bundle on order edits turned on, Flex Bundles expands the parent after the fact using Shopify's Order Editing API.