All posts
Ray Iyer
Ray Iyer
Co-founder, Anglera

Getting enriched product data onto Oracle Commerce product pages

How an enriched Oracle Commerce catalog attribute travels from a product type property to rendered PDP HTML and JSON-LD, with steps to validate.

Getting enriched product data onto Oracle Commerce product pages

Oracle Commerce (Oracle CX Commerce, the platform formerly branded Oracle Commerce Cloud) separates the catalog data model from the storefront rendering layer cleanly, which is good news once your attributes are enriched: getting a new field onto the page is a templating exercise, not a data migration. This guide walks through one enriched attribute — a product spec like "Effective Pixels" or "UPC Code" — from where it's stored, to how it's exposed to the storefront, to the exact template change that puts it in the rendered HTML, plus how to confirm it actually made it there.

Where the attribute lives in the catalog

In Oracle Commerce, product data is governed by product types (Catalog page → Manage Catalogs → Product Types), which act as schemas that every product or SKU created from that type inherits. A product type has three property groups:

  • Product Properties — attributes shared by the whole product (e.g., a spec like "Effective Pixels"), split into Standard (you set the value) and Shopper Input (the buyer supplies it at purchase).
  • SKU Properties — attributes that vary by SKU (e.g., "UPC Code").
  • Variant Properties — attributes that generate SKU variations (e.g., "Color").

When you add a Standard property, you set a Property ID, a Label, a data type (Short Text, Number, Selection List, Rich Text, Date, Check Box, etc.), and — critically for this guide — a Display Properties setting of "Visible in Storefront" versus "Internal Only." Only storefront-visible properties are exposed to the rendering layer at all, so this is the first gate an enriched attribute has to pass through. Product types can also be created and edited programmatically through the Admin API (createProductTypeSpecification for product types, createSkuProperty for SKU-level properties), which is the path most PIM-to-Commerce integrations use.

How the attribute reaches the storefront runtime

Oracle CX Commerce's default storefront (Storefront Classic) is a client-side rendered Knockout.js single-page application — it is not server-rendered on every request. (Oracle's newer, opt-in Open Storefront Framework, built on Node.js and React, does render every page server-side; don't assume that behavior if your instance is still on Storefront Classic.) Once a property is marked storefront-visible, it's serialized onto the product or SKU JSON object the storefront fetches for that page — reachable in widget code as widget.product().propertyId for a product-level property, or, for SKU-level ones, via widget.product().skuProperties() (the list of defined SKU property IDs/labels) combined with widget.selectedSku() to read the actual value for the shopper's chosen variant. The property exists on that object whether or not any widget renders it; the remaining step is purely template work. Separately, Commerce's SEO snapshot feature regenerates a static, prerendered copy of each storefront page on a schedule (roughly every 24 hours, or when you publish) and can route recognized search-engine crawler user agents to that snapshot instead of the live Knockout page — a detail that matters once you get to validation below.

Binding the attribute into the Product Details widget

For a single product-level property, the fastest path is a direct binding inside the Product Details widget's display.template (edited through an extension, not by hand-patching OOTB files):

<!-- oc section: effective-pixels -->
<div class="spec-row" data-bind="if: product() && product().effective_pixels">
  <span class="spec-label">Effective Pixels</span>
  <span class="spec-value" data-bind="text: product().effective_pixels"></span>
</div>
<!-- /oc -->

The oc section comment wrapper (shown above around the div) is what makes the block a manageable fragment on the Design page rather than opaque markup baked into the widget.

For a SKU-level property (varies per variant, like a UPC code) or anything you want reusable across widgets and drag-and-drop editable, Oracle's supported pattern is a small element — three files packaged in an extension:

// element.js
define(['knockout'], function (ko) {
  return {
    elementName: 'sku-properties',
    onLoad: function (widget) {
      var self = this;
      self.mySkuProps = ko.computed(function () {
        var rows = [];
        if (widget.selectedSku()) {
          var sku = widget.selectedSku();
          widget.product().skuProperties().forEach(function (prop) {
            if (sku[prop.id]) {
              rows.push({ label: prop.label, id: prop.id, value: sku[prop.id] });
            }
          });
        }
        return rows;
      });
    }
  };
});
<!-- template.txt -->
<div>
  <!-- ko foreach: $data['sku-properties'].mySkuProps() -->
  <div class="spec-row">
    <span class="spec-label" data-bind="text: label"></span>
    <span class="spec-value" data-bind="text: value"></span>
  </div>
  <!-- /ko -->
</div>
// element.json
{
  "inline": true,
  "supportedWidgetType": ["productDetails"],
  "translations": [
    { "language": "en_EN", "title": "SKU Properties", "description": "Renders SKU-level catalog properties" }
  ]
}

After deploying the extension, add the corresponding oc section block and an element: 'sku-properties' data-bind to the Product Details widget's display.template and widget.template, then place it on the page from Design → Product Layout, where a merchandiser can reposition it without another code deploy.

Making the attribute visible to AI agents and crawlers

Rendered HTML gets you human buyers; structured data gets you AI shopping agents and rich results. Oracle Commerce auto-generates JSON-LD for Product, Breadcrumb, ItemList, Review, WebSite, and Organization types on home, product, and collection pages out of the box. You can turn off the default Product markup for a page type and substitute a custom script template driven by the same product context the page already has, which is how you get an enriched attribute (like a spec or identifier) into additionalProperty rather than leaving it as page copy only:

{
  "@context": "https://schema.org/",
  "@type": "Product",
  "name": "{{product.displayName}}",
  "sku": "{{product.id}}",
  "additionalProperty": [
    {
      "@type": "PropertyValue",
      "name": "Effective Pixels",
      "value": "{{product.effective_pixels}}"
    }
  ]
}

Treat the interpolation syntax above as illustrative — the exact variable-reference mechanism in the structured-data template editor is release-specific, so confirm current syntax against your instance's admin panel before shipping this in production.

How to validate

  • Plain curl vs. rendered DOM: on Storefront Classic, a bare curl -s your-pdp-url returns the pre-Knockout page shell, not the populated markup — the attribute will only show up in the browser's rendered DOM inspector, not in that curl output. Don't mistake the missing curl result for a bug; it's expected for a client-rendered page.
  • curl the crawler-facing snapshot: to check what search engines actually see, spoof a recognized crawler user agent, e.g. curl -s -A "Googlebot/2.1 (+http://www.google.com/bot.html)" your-pdp-url | grep -A2 effective_pixels. If the value is missing there but present in the browser DOM, the SEO snapshot hasn't regenerated yet (it refreshes roughly every 24 hours or on publish) or your instance's crawler-routing settings send that bot to the live page instead.
  • curl the JSON-LD block: run the same crawler-spoofed curl and grep -A5 application/ld+json against it to confirm the attribute made it into the structured-data script tag, not just the visible page copy.
  • Google's Rich Results Test (search.google.com/test/rich-results) against the live PDP URL to confirm the JSON-LD parses and the new property doesn't break existing Product markup.
  • Search Console's Structured Data report to watch for warnings across the catalog once the template change is live everywhere, not just on the one PDP you tested.

Verified as of July 2026 against Oracle CX Commerce (Storefront Classic) documentation for product types, SKU property elements, and structured-data customization; menu paths and template syntax can shift between releases, so confirm against your instance's admin before shipping.

None of this rendering work matters if the attribute isn't clean and populated in the first place, which is the harder problem in practice. Anglera enriches product data continuously — attributes, specs, use-cases, identifiers — and writes it back to the fields your Oracle Commerce catalog already reads, as an addition to your PIM or commerce platform rather than a replacement. Your catalog stores the data; the templates above are how it gets on the page.

Ray Iyer

About the author

Ray IyerCo-founder, Anglera

Ray is a co-founder of Anglera, building the product-data infrastructure for agentic commerce — turning messy catalogs into structured, AI-readable data that buyers and answer engines can find. Previously product at Uber; Stanford CS.

See it on your own SKUs.

A 30-minute walkthrough on your categories and your supplier data.

Book a demo