ddtcorex

24 Sept 2026 · 6 min read

MSI with bundle and configurable children

Untangle MSI salability for bundle and configurable products where children live in different sources

Part 5 of the MSI / Inventory series — composite products multiply every stock question.

A simple product asks one stock question: is there salable qty in this website's stock? A configurable with twelve children across three sources asks twelve questions, then combines the answers. A bundle with required options asks a harder question still: is every required choice simultaneously fulfillable? Get one child assignment wrong and the parent vanishes from category pages, search, and cart, while each child still shows qty in the admin. The support ticket says "product disappeared" and the stock grid says everything is fine.

This post untangles how MSI evaluates composite salability, where bundle and configurable logic diverge, and how to structure sources so parents stay visible.

How configurable salability actually works

A configurable product carries no qty of its own. Its salability is derived per stock: the parent is salable in a website's stock when at least one associated child is salable in that same stock. "Salable" here means the full MSI check passes for the child: assigned to the stock through a source, qty plus reservations above the out-of-stock threshold, in stock status, and shippable from at least one source in the stock.

The critical detail is "in that same stock." MSI resolves children through the stock linked to the sales channel (website), not through the global pool. If child A lives in source East linked to stock US, and the website sells from stock EU, child A contributes nothing to that website's configurable. The admin stock grid shows qty; the storefront shows out of stock. Both are telling the truth about different scopes.

Shipments sharpen this further. When the order ships, MSI decrements the specific source the shipment was created from. For configurables this is straightforward because exactly one child ships. The planning question is only whether at least one child remains salable after each deduction, which is why high-velocity configurables need per-child safety buffers rather than a single parent-level number.

How bundle salability diverges

Bundles invert the logic. A bundle is salable only when every required option has at least one salable selection. One missing required option blocks the whole bundle, even if nine other options are deep in stock. Optional options do not block salability, but they create a subtler failure: the bundle stays purchasable, the customer selects an option that cannot ship from any source in the stock, and the order lands in a split-shipment or backorder state nobody planned for.

Source selection at shipment time is where bundle complexity bites. Each bundle selection ships from a source, and MSI's Source Selection Algorithm resolves per item against the stock's sources by priority and qty. If two required selections only exist in different sources with no overlap, the order requires two shipments. That is legitimate, but it doubles pick, pack, and freight cost and surprises a merchant who priced shipping as one parcel. The fix is structural: keep the selections that are commonly bought together in at least one shared source, or mark the option set as shippable separately and price accordingly.

Dynamic versus fixed pricing adds inventory risk too. A bundle with dynamic pricing and a zero-qty selection can silently discount the bundle while the selection shows unavailable at checkout. Audit bundle option input types after every bulk import: a required checkbox that became optional, or a fixed-qty selection reset to user-defined zero, changes both price and salability.

Keep children and parent in the same stock

The single highest-leverage rule: every child of a visible composite must be assigned to at least one source inside the stock that serves the parent's website. Audit this with a query, not by clicking through products:

SELECT c.sku AS child_sku, s.name AS source_name, st.name AS stock_name
FROM catalog_product_entity c
LEFT JOIN inventory_source_item i ON i.sku = c.sku
LEFT JOIN inventory_source s ON s.source_code = i.source_code
LEFT JOIN inventory_stock_source_link l ON l.source_code = i.source_code
LEFT JOIN inventory_stock st ON st.stock_id = l.stock_id
WHERE c.type_id IN ('simple', 'virtual')
AND c.entity_id IN (SELECT product_id FROM catalog_product_super_link)
ORDER BY child_sku;

Any child with no row in the website's stock is invisible demand waiting to become a ticket. Pay special attention after bulk imports and ERP syncs, which commonly create the simple children first with a default source assignment and link them to configurables before the source topology is corrected.

For bundles, extend the audit to required options: list each required option's selections and confirm each has salable qty in the stock. A bundle whose required option has three selections, all assigned to a pickup-only source the checkout cannot ship from, is a purchasable product that can never convert.

Pickup-only sources and the ghost unavailability

In-store pickup sources are the most common cause of ghost unavailability for composites. A child assigned only to a pickup source is salable for pickup orders but not for ship-to-home checkout. If the theme or checkout does not surface pickup availability per child, the configurable looks broken: salable in one fulfillment context, dead in another.

Decide the policy explicitly. Either exclude pickup-only sources from the stock that feeds ship-to-home checkout and duplicate the qty into a shippable source, or make the storefront communicate per-option fulfillment ("Size M ships in 3 days, Size L pickup only"). What you cannot do is leave the assignment ambiguous and hope customers interpret it.

Indexers after bulk child import

Composite salability is indexed, not computed live on every category render. After importing hundreds of children, the inventory indexer must rebuild the salability view before parents reappear. During that window the storefront lies: children have qty, parents show out of stock. Schedule the indexer run as part of the import job, not as an afterthought, and verify with a storefront probe on two or three parent SKUs before declaring the import done. The reindex performance tactics for large catalogs are the subject of the next post.

Pitfalls

  • Children assigned to different stocks than the parent website. The classic ghost. The child has qty somewhere, just not where the website sells from. Audit by stock, not globally.
  • Required bundle options sourced from pickup-only locations. The bundle looks purchasable for shipping checkout and fails at source selection. Either add a shippable source or convert the option to optional with clear messaging.
  • Indexers lagging after bulk child import. Parents stay hidden until the inventory indexer catches up. Chain the reindex into the import and probe parent SKUs afterward.
  • Bundle qty semantics misunderstood. Bundle selections carry their own qty; the parent's qty field is decorative. Setting parent qty high while selections sit at zero fixes nothing.
  • Shared-source planning skipped for bundles. Selections spread across non-overlapping sources force split shipments. Co-locate commonly combined selections or price split fulfillment deliberately.

Closing

Composite products do not add new MSI concepts; they multiply the existing ones by the number of children and then apply AND/OR logic across the results. Configurables OR across children, bundles AND across required options. Design the source topology so the combination resolves the way the merchandising team expects, audit it with queries rather than clicks, and reindex before judging the result.

Next in this series:

magento2-msi-reindex-perf

magento2msiinventory