Skip to main content

iPaaS.com to Zoho Commerce Inventory Mapping Documentation

How iPaaS.com inventory records adjust Zoho Commerce stocking levels through the complementary product-level and variant-level inventory collections, including the routing filter, the delta adjustment model and its timing caveats.

Summary

Zoho Commerce stocking levels can be updated from iPaaS.com inventory records through automatic outbound triggers or on-demand Manual Sync. Rather than writing a stock figure directly, each transfer reads the current level in Zoho Commerce, compares it against the total supplied by iPaaS.com, and submits an inventory adjustment for the difference. Inventory moves in one direction only, from iPaaS.com to Zoho Commerce.

Two mapping collections are covered by this document. Add/Update Zoho Commerce Product Inventory FROM iPaaS.com handles stock for products tracked at the product level, resolving the store's product and then its variant. Add/Update Zoho Commerce Product Variant Inventory FROM iPaaS.com handles stock for products tracked at the variant level, targeting the variant directly. They are complementary rather than alternatives: a mapping filter routes each record to exactly one of them, and both are intended to stay enabled.

ID Format

Manual Sync ID Format

On the iPaaS.com Manual Sync page, enter the iPaaS.com inventory record ID for the stocking level you want to push. This identifies the record and the location whose stock you are adjusting, joined by a vertical bar. Example: 1234|32.

Both collections use the same Manual Sync format, and Manual Sync is always available whether or not the automatic triggers are enabled.

External ID Format

After a successful transfer, iPaaS.com records a composite external ID built from the Zoho Commerce variant identifier and the location whose stock was adjusted, joined by a vertical bar. Example: 4159044000000097115|7465534000000091234.

Both collections save the same shape, and both put the variant identifier on the left — the product-level collection resolves the store's product first and then that product's variant, so what it stores is still a variant identifier. Because the location forms the right half, the location mapping must be populated for the link to be saved at all. Later transfers use the composite link to target the same variant-and-location combination.

Deleted Record Support

Delete is not supported for these collections. Stock is adjusted, never deleted: removing an inventory record in iPaaS.com does not reverse or remove stock in Zoho Commerce, delete mappings are not included in the default templates, and deletions do not propagate.

Mapping Collection Status

Status: Enabled — both collections.

Trigger Events: inventory add and update events, subscribed under Outbound Data Flows in the subscription configuration. No inventory transfers automatically until those subscriptions are enabled.

Duplicate or Conflicting Mappings

The two inventory collections reach the same kind of Zoho Commerce stock but never the same record. The product-level collection's mapping filter claims only inventory for products tracked at the product level; inventory for a product tracked at the variant level is left to the variant-level collection. Every inventory record is therefore claimed by exactly one of the two, no record is processed twice, and leaving both enabled is the intended configuration. Subscribers should not choose between them.

Important: review the mapping filter on the product-level collection before enabling either, and keep the routing intact. Widening it so that the same record qualifies for both collections would have two collections adjusting the same Zoho Commerce stock, with the last transfer to run deciding the result.

Duplicate prevention

Duplicate prevention relies on the composite external-ID link described under ID Format. Once an inventory record has synced, the stored link routes every later transfer to the same variant and location rather than targeting a second one.

Unmapped field overwrite risk

There is none for these collections. Neither collection rewrites the product or variant record — each posts an inventory adjustment carrying only a reason, an adjustment type, the target variant, the location and a quantity difference. No unmapped field on the Zoho Commerce product or variant is touched by an inventory transfer.

Supported Child Collections

None. Both collections are standalone: neither has a parent collection and neither has dependent child collections. Each runs as its own transfer with its own Manual Sync entry point.

Inventory is also dispatched alongside a product or variant transfer, which is how a newly created record receives its opening stock. That is a dispatch relationship, not a collection hierarchy — ongoing stocking levels are maintained by these two collections.

Zoho Commerce Caveats

  • Authentication is tied to the United States Zoho accounts domain: the integration signs in through Zoho's US accounts service, and there is no setting that changes which regional service is used. A store whose Zoho organization is hosted on a data center outside the United States cannot currently connect, so no collection in this integration can transfer for that store.

  • Stock is held against a variant: Zoho Commerce does not hold stock on the product record itself. That is why the product-level collection resolves the store's product and then that product's variant before adjusting.

  • A reason and adjustment type are required: Zoho Commerce records a reason label against each adjustment and expects the adjustment type on every write. Both ship pre-set.

  • The location must be one the store holds: an adjustment targets a specific location in Zoho Commerce. Confirm in a staging environment that the location supplied by LocationId resolves to a location the store actually holds before relying on either collection in production.

  • Multi-variant products and the product-level collection: when the product-level collection resolves a product that has more than one variant in the store, it targets the first variant Zoho Commerce returns, which is not predictable from the source system. Products with real variants should be tracked at the variant level so the mapping filter routes them to the variant-level collection.

  • Call volume matters on large runs: Zoho does not publish a call quota for the Zoho Commerce store API, and a store may still refuse calls made too quickly. Stagger large inventory runs rather than sending everything at once, and validate throughput in a staging environment before a bulk load.

  • Error text comes from the store: when Zoho Commerce declines an adjustment, the text recorded in the iPaaS.com error log is the store's own raw response rather than a rewritten message. See Error Handling.

iPaaS.com Caveats

  • The target must already be linked: these collections adjust stock on an existing Zoho Commerce product or variant; they do not create it. Transfer the product and its variants first.

  • The location must be mapped before the first transfer: LocationId targets the adjustment and forms half of the external-ID link. Without it the link is not saved and later transfers cannot resolve the same record-and-location combination.

  • Organization ID must be configured: inventory transfers will not reach Zoho Commerce unless the subscription's Organization ID is set in the connection settings.

  • A cost value is not required: an inventory adjustment does not require a stock cost.

  • The quantity sent is a total, not a per-location figure: the mapped formula sums the record's full iPaaS.com inventory and applies that total at the single location supplied by LocationId. If you track stock across several locations in iPaaS.com, the combined total lands against that one Zoho Commerce location rather than being distributed.

Setup Requirements

iPaaS.com Configuration

Open the subscription configuration and navigate to Outbound Data Flows, then subscribe to the inventory add and update triggers that should dispatch these mapping collections. Confirm the location field is mapped on both collections before the first transfer — without it the external-ID link is not saved. Leave both collections enabled so the routing filter can claim each record for the right one. Manual Sync is available whether or not the triggers are enabled.

Zoho Commerce Configuration

Confirm the locations you intend to adjust exist in the store, and that the products and variants whose stock you are adjusting have already transferred. Beyond that, no inventory-specific setup is required past a connected store with an administrator-level account. The connection credentials and the Organization ID are configured once for the subscription — see the Zoho Commerce Connections and Settings article and the Zoho Commerce Installation Instructions article.

Integration Flow

  1. An inventory add or update event is raised in iPaaS.com, a subscriber runs a Manual Sync, or a product or variant transfer dispatches its inventory alongside it.

  2. The product-level collection's mapping filter checks how the product is tracked in iPaaS.com. Product-level tracking is claimed here; variant-level tracking is passed over so the variant-level collection handles it.

  3. The integration resolves the Zoho Commerce variant to adjust. The product-level collection looks up the store's product linked to the iPaaS.com product and then takes that product's variant; the variant-level collection looks up the linked variant directly.

  4. The integration reads the variant's current stocking level in Zoho Commerce.

  5. It totals the record's iPaaS.com inventory to produce the target quantity, sending zero if the total is negative, and calculates the difference against the level it just read.

  6. It submits an inventory adjustment for that difference at the location supplied by LocationId, carrying the fixed adjustment type and reason label.

  7. The composite external ID — variant plus location — is saved so later transfers target the same combination.

Steps 4 and 6 are separate operations. Nothing locks the stock level between them, which is the source of the timing caveats under Additional Notes.

Mappings

Add/Update Zoho Commerce Product Inventory FROM iPaaS.com

iPaaS.com data type: Product Inventory

Mapping Filter

var productType = await GetProductType(Convert.ToInt64(ParentId));
if (productType == "Product"){return true;}
else {return false;}

Filter Description. The filter routes inventory by how the product is tracked in iPaaS.com. It reads the product type — the productType value — for the product the inventory record belongs to, and takes one of two branches:

  • The product is tracked at the product level. The record passes the filter and this collection adjusts its stock.

  • The product is tracked any other way, including at the variant level. The record does not pass, and this collection takes no action on it. Nothing is written and no error is raised — the record is claimed instead by Add/Update Zoho Commerce Product Variant Inventory FROM iPaaS.com.

This is the mechanism that makes the two inventory collections complementary rather than competing. Subscribers or their MiSP can edit the filter, but leaving it in place is what keeps each inventory record claimed by exactly one collection.

Description: Adjusts the stocking level of a Zoho Commerce product's variant at a specified location so the store reaches the total quantity supplied by iPaaS.com.

Mapping Type

Source Field (iPaaS.com)

Destination Field (Zoho Commerce)

Description

Dynamic Formula

Parent product's Zoho Commerce link, resolved to that product's first variant

VariantId

Required. Identifies the Zoho Commerce record whose stock is being adjusted. Zoho Commerce holds stock against a variant rather than the product itself, so this first resolves the store's product already linked to the iPaaS.com parent product, then resolves that product's variant and targets it. If the parent product has not yet transferred there is no link to resolve and the adjustment cannot be applied.

Field

Product Inventory LocationId

LocationId

Required, and it must be mapped before the first transfer. Identifies the Zoho Commerce location whose stock is being adjusted. Beyond targeting the adjustment, the location forms half of the composite external-ID link saved after a successful transfer, so an unmapped location means the link is not saved and later transfers cannot resolve the same record-and-location combination. The location referenced must be a valid Zoho Commerce location; an adjustment aimed at a location that does not exist in the store is rejected.

Dynamic Formula

Parent product inventory — the total across all stocking records

QuantityAvailable

Required — the adjustment has no target quantity without it. Supplies the stock figure Zoho Commerce should end up at, totalling the product's full iPaaS.com inventory across its stocking records. If the total comes out below zero, zero is sent instead, so a negative stock position is never pushed to the storefront. The figure is compared against the current store level and only the difference is submitted.

Static

"quantity"

adjustment_type

Required for every Zoho Commerce inventory adjustment. Tells the store that this adjustment changes the stock quantity, as opposed to a value or cost adjustment. This is a fixed setting the integration relies on for the collection to behave correctly — leave it as configured rather than changing or removing it.

Static

"iPaaS Inventory Adjustment"

reason

Required — Zoho Commerce expects a reason on every adjustment. This is the label recorded against the adjustment so the change is identifiable in the store's adjustment history as having come from iPaaS.com. The value is a designed constant rather than an environment-specific placeholder, so it does not need to be replaced during implementation. Subscribers who prefer different wording in their adjustment history can change it.

Dynamic formula bodies — Product Inventory

VariantId — resolves the store's product from the iPaaS.com parent product, then that product's variant:

var parentProductId = await GetExternalIdAsync(ParentId, "Product", SpaceportSystemId);
if (parentProductId != null){
  return await GetVariantIdByProductId(parentProductId);
} else {return null;}

QuantityAvailable — sums the product's full iPaaS.com inventory and returns zero when the total is negative:

var result = await SumFullInventoryForProductAsync(Convert.ToInt64(ParentId));
if (result < 0 )
return "0";
return result.ToString();

Choosing the source quantity: available versus on hand

Which Zoho Commerce level the target quantity is compared against depends on how the collection is mapped:

  • As delivered, QuantityAvailable is compared against the store's available-for-sale level — what remains after stock committed to open orders is taken into account. This assumes the total sent from iPaaS.com already accounts for those commitments.

  • Mapping QuantityOnHand as well compares against the store's on-hand level instead, which is the physical stock figure before order reservations are deducted.

  • When both are mapped, QuantityOnHand decides the comparison and QuantityAvailable is inert. Map only the one that matches how your source system counts stock, and confirm the resulting level in a staging environment before relying on it in production.

Add/Update Zoho Commerce Product Variant Inventory FROM iPaaS.com

iPaaS.com data type: Product Variant Inventory

Description: Adjusts a Zoho Commerce variant's stocking level at a specified location so the store reaches the total quantity supplied by iPaaS.com, targeting the variant directly through its saved link.

Mapping Type

Source Field (iPaaS.com)

Destination Field (Zoho Commerce)

Description

Dynamic Formula

return await GetExternalIdAsync(ParentId, "Product Variant", SpaceportSystemId);

VariantId

Required. Identifies the Zoho Commerce variant whose stock is being adjusted, by looking up the variant already linked to the iPaaS.com parent variant record. If the parent variant has not yet transferred there is no link to resolve and the adjustment cannot be applied — transfer the product and its variants first. This is the difference between this collection and the product-level one: this targets the variant directly, rather than resolving a product and then finding its variant.

Field

Product Variant Inventory LocationId

LocationId

Required, and it must be mapped before the first transfer. Identifies the Zoho Commerce location whose stock is being adjusted. Beyond targeting the adjustment, the location forms half of the composite external-ID link saved after a successful transfer, so an unmapped location means the link is not saved and later transfers cannot resolve the same record-and-location combination. The location referenced must be a valid Zoho Commerce location; an adjustment aimed at a location that does not exist in the store is rejected.

Dynamic Formula

Parent variant inventory — the total across all stocking records

QuantityAvailable

Required — the adjustment has no target quantity without it. Supplies the stock figure Zoho Commerce should end up at for this variant, totalling the variant's full iPaaS.com inventory across its stocking records. If the total comes out below zero, zero is sent instead, so a negative stock position is never pushed to the storefront. The figure is compared against the current store level and only the difference is submitted.

Static

"quantity"

adjustment_type

Required for every Zoho Commerce inventory adjustment. Tells the store that this adjustment changes the stock quantity, as opposed to a value or cost adjustment. This is a fixed setting the integration relies on for the collection to behave correctly — leave it as configured rather than changing or removing it.

Static

"iPaaS Inventory Adjustment"

reason

Required — Zoho Commerce expects a reason on every adjustment. This is the label recorded against the adjustment so the change is identifiable in the store's adjustment history as having come from iPaaS.com. The value is a designed constant rather than an environment-specific placeholder, so it does not need to be replaced during implementation. Subscribers who prefer different wording in their adjustment history can change it.

Dynamic formula body — Product Variant Inventory

QuantityAvailable — sums the variant's full iPaaS.com inventory and returns zero when the total is negative:

var result = await SumFullInventoryForVariantAsync(Convert.ToInt64(ParentId));
if (result < 0 )
return "0";
return result.ToString();

The available-versus-on-hand behavior described for the product-level collection applies identically here: QuantityAvailable as delivered compares against the store's available-for-sale level (what remains after stock committed to open orders is taken into account), mapping QuantityOnHand compares against the on-hand level (physical stock before order reservations are deducted) instead, and mapping both makes QuantityAvailable inert.

Error Handling

Subscriber-visible errors raised during an inventory transfer appear under Dashboard / Integration Monitoring / Error Logs.

  • "Variant id is required" — the Zoho Commerce variant to adjust could not be resolved, so the adjustment has no target. This happens when the iPaaS.com product or variant has not yet transferred and carries no Zoho Commerce link, or when the product-level collection resolves a product that has no variant in the store. Resolution: transfer the product and its variants first, confirm the record carries an external-ID link, then re-run the inventory transfer.

  • Messages returned by Zoho Commerce — when the store declines an adjustment, the text recorded in the error log is the store's own raw response, carrying Zoho Commerce's wording rather than a rewritten message. This covers a location the store does not hold, a store that cannot be resolved because the Organization ID is wrong, and a resulting quantity the store did not accept. Resolution: read the message to identify what the store objected to, confirm the location and connection settings, and re-run the transfer.

Conditions that produce no error

  • An inventory record for a product tracked at the variant level does not pass the product-level collection's mapping filter. Nothing is written and nothing is logged as an error — the record is handled by the variant-level collection instead. This is normal routing, not a failure.

  • A quantity that lands wrong because of the timing described under Additional Notes produces a successful transfer with an incorrect final level. Re-running the transfer corrects it against the then-current level.

Validation Rules

  • Product-type routing: enforced by the product-level collection's mapping filter. Only inventory for a product tracked at the product level is processed there; everything else is passed over silently for the variant-level collection to claim.

  • A resolvable variant is mandatory: an adjustment cannot be submitted without a Zoho Commerce variant to target. Enforcement is the Variant id is required error.

  • The location must exist in the store: enforcement is a rejection by Zoho Commerce, surfaced as the store's own message.

  • Negative totals are floored at zero: enforced by the quantity formula on both collections, so a negative stock position is never pushed to the storefront.

Testing & Validation

Test Scenarios

  1. Push a stocking level for an already-transferred product that is tracked at the product level, and confirm the Zoho Commerce quantity ends at the target figure rather than being offset by it.

  2. Push a stocking level for an already-transferred variant using the variant-level collection and confirm the variant's stock ends at the target figure.

  3. Confirm the routing: transfer inventory for a product tracked at the product level and for one tracked at the variant level, and confirm each was handled by exactly one collection and neither was processed twice.

  4. Push the same target quantity a second time and confirm no further change occurs — the calculated difference should be zero.

  5. Push a lower target quantity and confirm the resulting adjustment reduces stock to the target.

  6. Push a total that would be negative and confirm zero is sent rather than a negative stock position.

  7. Attempt an inventory transfer for a product that has not yet transferred and confirm Variant id is required is raised.

  8. Attempt a transfer with the location unmapped and confirm the composite external-ID link is not saved.

  9. Run a Manual Sync using the documented iPaaS.com inventory record ID format and confirm the transfer succeeds.

  10. Confirm the adjustment appears in the Zoho Commerce adjustment history with the expected reason label.

  11. Run a product transfer for a new product and confirm its opening stock is applied, then confirm a subsequent inventory transfer maintains it.

Validation Checklist

  • Zoho Commerce stock for the variant and location ends at the target quantity supplied by iPaaS.com, not offset by it.

  • A repeat transfer of an unchanged quantity produces no net change.

  • Each inventory record is claimed by exactly one of the two collections, and both collections remain enabled.

  • The composite external-ID link — variant plus location — is recorded after the first successful transfer, with the variant identifier on the left.

  • Adjustments appear in the store's adjustment history with the expected reason label.

  • A negative source total results in zero being sent, never a negative stock level.

  • Inventory dispatched alongside a product or variant transfer produces the same result as a standalone inventory transfer.

Additional Notes

The following describe behavior at the time this documentation was written.

  • The read and the write are separate steps, so timing matters. Each adjustment is calculated from the level read at the start of that transfer, and the difference is submitted afterwards. A storefront sale, or another adjustment, landing between those two steps is not reflected in the calculated difference, so the final quantity can be wrong. Re-running the transfer corrects it against the then-current level.

  • Concurrent adjustments can double-apply a change. Two adjustments for the same record running at the same time both read the same starting level and each submit their full difference. Starting from zero, two jobs each targeting 41 leave the store at 82 rather than 41. Stagger mass inventory jobs rather than running them concurrently for the same records, avoid running them during heavy storefront activity, and reconcile levels after a bulk run.

  • One stocking level is synced per transfer. Each collection maintains a single quantity for its record at the supplied location. It does not distribute a quantity across multiple Zoho Commerce locations, and no cross-location reconciliation is performed.

  • Call volume matters on large runs: stagger a bulk inventory load rather than sending everything at once, and validate throughput in a staging environment first.

  • An absolute stock figure is never set directly: Zoho Commerce is always sent a difference, never a replace-the-value instruction.

  • Inbound inventory sync is out of scope: these collections send stocking levels from iPaaS.com to Zoho Commerce only. Stock changes made directly in Zoho Commerce, including depletion from storefront orders, are not read back into iPaaS.com through these collections.

  • Inventory deletion is out of scope: see Deleted Record Support.

Related Documents

Did this answer your question?