Skip to content

Where to put the markup

Two decisions here, and only one of them changes whether a crawler reads you.

Where on the page the structured data sits does not. Google documents JSON-LD as valid in the <head> and the <body>, and Geoffy’s own live check searches the whole document rather than a region. Both placements pass, on both sides.

Whether it is server-rendered decides everything. Google can read JSON-LD injected by JavaScript — and that is the trap, because most of the AI crawlers this package exists for cannot. Treat Google as the exception rather than the rule: if the markup is not in the HTML your server sends, assume it is invisible.

Astro can put it in the head, and mildly should

Section titled “Astro can put it in the head, and mildly should”

getGeoffyProductMarkup returns the two surfaces separately, so you can send jsonLdScript to the <head> and place widgetHtml wherever a shopper should see it.

<Layout>
{geoffy && <Fragment set:html={geoffy.jsonLdScript} slot="head" />}
<YourProductUI handle={handle} />
{geoffy && <div data-geoffy-widget set:html={geoffy.widgetHtml} />}
</Layout>

This is a preference, not a requirement. The head is read before the body, and if a crawler truncates a long document the head is the part that survives. That is the whole advantage. Body placement verifies and is read perfectly well — Next.js has no choice but to use it.

A page carrying structured data without the visible widget makes a claim to a crawler that no shopper can see. Geoffy holds such a product at code_not_added rather than publishing it — so keep the two {geoffy && …} guards together, and do not render one arm without the other.

Wherever a shopper should see it. Usually under your description or your buy box. Its position is entirely yours; Geoffy checks that it is present, never where.

Its root is a block-level <details> at width: 100%, so give it a full-width container rather than a narrow column. Its CSS is scoped entirely under .geoffy-widget and inherits your font and colour, so it cannot restyle the rest of your page and needs no dark-mode handling from you.