# Three of five captured pages carried JSON-LD, and one held 96 of the 102 nodes

> Parsed out of five real pages this scanner captured and stored on 15 July 2026, four JSON-LD blocks hold 26,299 bytes and 102 typed nodes. One page accounts for 24,865 of those bytes and 96 of those nodes, 39 of them describing a navigation menu.

- Canonical page: https://lantad.co/blog/three-of-five-pages-carried-json-ld
- This file: https://lantad.co/blog/three-of-five-pages-carried-json-ld.md
- Last substantive update: 2026-08-18

## Key facts

- **Published:** 2026-08-18
- **Category:** Findings
- **Author:** Lantad
- **Length:** 3616 words
- **Takeaway 1:** Five real pages stored as golden fixtures in this repository, captured on 15 July 2026, carry four JSON-LD blocks between them, and two of the five pages carry none at all: astro.build and the developer.mozilla.org landing page for HTML.
- **Takeaway 2:** Those four blocks hold 26,299 bytes and 102 typed nodes, of which webflow.com alone contributes 24,865 bytes and 96 nodes.
- **Takeaway 3:** WebPageElement is the most common type across the five captures at 39 of the 102 nodes, and all 39 sit in webflow.com's single block naming navigation copy such as For Marketers and Publish at scale.
- **Takeaway 4:** Only 17 of the 102 typed nodes carry a type that Lantad's own SCHEMA_REQUIREMENTS recognises as a business fact: 16 Organization nodes and one Article.
- **Takeaway 5:** The JSON-LD in the rendered DOM was byte for byte identical to the raw HTTP response on all five pages, and no page carried a single microdata itemtype attribute in either view.

## Summary

Structured data is the one part of a page written for machines and nobody else. A person reads the headline; a parser reads the block of JSON in the head that says this thing is an Organization, this one is an Article, and here is its name. That asymmetry is why [structured data](https://lantad.co/glossary/structured-data) attracts so much advice and so little measurement. The advice is easy to give because nothing on the visible page changes when you follow it, and the measurement is rarely done because it needs the actual bytes of a real page rather than an opinion about best practice.

This repository keeps those bytes. Six of the golden fixtures in core/fixtures/ are captures of real sites rather than synthetic test documents, and one of them, allbirds.com, answered HTTP 429 on the day of capture and was never rendered. That leaves five pages that returned 200 and store both a raw.html and a rendered.html: the astro.build homepage, the gymshark.com homepage, the developer.mozilla.org landing page for HTML, the webflow.com homepage and the English Wikipedia article on web crawlers. All five were captured on 15 July 2026 within about four minutes of each other. [The same five pages carried the alt text count](https://lantad.co/blog/alt-text-on-466-captured-images) published earlier this month, for the same reason: they are the only real HTML this repository stores twice, once as a plain client received it and once as a browser finished with it, and nobody chose them for their markup. They were captured to exercise [the scoring engine](https://lantad.co/methodology) as a whole. What follows is a census of what they actually declare, counted with a JSON parser over the stored files. It is a count of five pages and it is not a survey of the web, which is a distinction this post keeps making because five is a very small number.

## What five real pages actually published

Four blocks, across five pages. That is the whole corpus, and the first useful thing about it is how unevenly it is distributed. Two pages carry no JSON-LD whatsoever. One carries two small blocks totalling 636 bytes. One carries a single block of 798 bytes. The fifth carries a single block of 24,865 bytes, which is 94.5 percent of all the JSON-LD across the five captures put together.

The two small ones are worth reading in full because they take about ten seconds each. Gymshark's first block is 102 bytes and says there is a WebSite at gymshark.com named Gymshark. Its second block says there is an Organization named Gymshark with that URL and a logo. Wikipedia's single block declares an Article named Web crawler, with a sameAs pointing at the Wikidata entity Q45842, an author node naming Contributors to Wikimedia projects, a publisher node naming Wikimedia Foundation, Inc. with a logo, a datePublished of 2001-04-27 and a dateModified of 2026-07-02. Both are legible at a glance and both say something a machine can act on: here is a named thing, here is what it is, here is where else it is described.

Nothing here says whether any AI system reads these blocks or weights them, because that is a property of code nobody outside those companies can inspect, and this post makes no claim about it. What it can say is what a parser meets, which is the stage this scanner measures and the stage that has to succeed before any of the later ones matter. If a page ships no typed node at all, there is nothing for a retrieval system to key on even in principle, and that is true regardless of how [an AI crawler](https://lantad.co/glossary/ai-crawler) is built. The gap between having a machine-readable identity and not having one is the only part of this that does not depend on unpublished behaviour.

The distribution also tracks how each site is built rather than how carefully each site was optimised. Gymshark runs on Shopify, and both of its blocks have the shape of platform output: minimal, correct, generated from fields the merchant filled in somewhere else. That is the ordinary case for anyone on a hosted platform, and it is the reason the [Shopify guide](https://lantad.co/fix/shopify) treats schema as something to check rather than something to write. Wikipedia's block is MediaWiki output. Webflow's is Webflow's own marketing site, hand-assembled and enormous, and that is the one worth taking apart.

## Where 39 of the 102 typed nodes went

Webflow's single block parses cleanly and contains 96 objects carrying an @type. Counting the types gives 19 distinct values, and the most common by a wide margin is WebPageElement at 39 nodes. Organization is next at 13, then Person at 10, BusinessAudience at 9, Review at 6 and EntryPoint at 4, with the remaining 13 types appearing once or twice each.

Reading the 39 WebPageElement nodes is what makes the shape of the block obvious. Their name values are the site's navigation copy: "For Marketers", "Build together", "Publish at scale", "Optimize for growth", "For Designers", "Design without limits", "Build your design system, live". These are mega menu labels, described in schema.org vocabulary, one node each. [Schema.org defines WebPageElement](https://schema.org/WebPageElement) as "A web page element, like a table or an image", a subtype of CreativeWork, with named subtypes covering site navigation, tables, ad blocks, footers, headers and sidebars. Marking up a navigation menu with it is not misuse. It is precisely what the type is for.

It is also, on any reading, a description of the page's furniture rather than of the business. A parser that consumes all 96 nodes learns that Webflow is an Organization, that it publishes a SoftwareApplication, that six Review nodes and an AggregateRating exist, and then learns the text of forty menu items. The signal-bearing part is a small minority of the volume. Across all five captures, only 17 of the 102 typed nodes carry a type that this scanner's SCHEMA_REQUIREMENTS table recognises as a checkable business fact, and those 17 are 16 Organization nodes and one Article. Everything else is vocabulary that is valid, correctly used, and says nothing a retrieval system could use to answer a question about the company.

This is the practical reason volume is a bad proxy for quality here, and it generalises past these five pages. When [only 16 schema.org types reach 10 million domains](https://lantad.co/blog/sixteen-schema-types-reach-ten-million-domains) while the vocabulary carries 958, the long tail of types is available to anyone, and filling a block with it costs nothing and adds nothing. The question worth asking of your own markup is not how many nodes it contains but how many of them name the entity rather than the layout, which is the same question [Entity Confidence](https://lantad.co/glossary/entity-confidence) exists to score separately from the schema check.

## Two of the five published no JSON-LD at all

astro.build and the developer.mozilla.org landing page for HTML carry zero JSON-LD blocks in the raw response and zero in the rendered DOM. Both are well known technical pages that get linked and quoted constantly, and neither declares a machine-readable identity in the format most advice assumes.

They are not identical cases. astro.build carries no structured vocabulary of any kind: no JSON-LD, no microdata, and no RDFa typeof attribute. What it does carry is 8 distinct Open Graph properties and 6 Twitter card properties, which is the social preview layer rather than a schema layer, plus a meta description. developer.mozilla.org is different: it carries no JSON-LD but does carry three RDFa typeof values, BreadcrumbList, ListItem and WebPage, so the page does describe its own breadcrumb trail in schema.org vocabulary, just not in the syntax a JSON-LD parser reads. It also carries no Open Graph properties at all.

That distinction matters more than it looks, because a check written to count JSON-LD blocks reports both pages as zero and is right about only one of them in spirit. This scanner's schema check reads application/ld+json script elements and nothing else, so MDN's breadcrumbs are invisible to it. We are saying so here rather than in a footnote because it is a real limit on what our number means, and the same limit applies to most tools that report a schema score. Whether any AI system reads RDFa is not something we can measure and not something the crawler documentation published by OpenAI, Anthropic or Perplexity addresses.

The microdata result is the flattest finding in this post and worth one line: across five pages and both views, ten documents in total, there is not a single itemtype attribute. Microdata was for years the syntax Google's own examples used, and on these five captures it has disappeared completely in favour of JSON-LD and, on one page, RDFa. [Schema.org's Organization type](https://schema.org/Organization), defined as "An organization such as a school, NGO, corporation, club, etc." and sitting directly under Thing, is expressible in all three syntaxes. Only one of them showed up here in any quantity, which is a small piece of evidence for writing JSON-LD if you are choosing, and no evidence at all about what happens if you do. If you want the fuller picture of which declarations actually distinguish sites, [the five structural signals behind Entity Confidence](https://lantad.co/blog/five-signals-that-tell-ai-who-you-are) were measured against a larger sample than this one, and the platform guidance for [getting cited in ChatGPT](https://lantad.co/how-to-get-cited/chatgpt) sets out what is documented and what is not.

## JavaScript added no JSON-LD on any of the five pages

Each fixture stores the raw HTTP response and the rendered DOM separately, so the two can be compared directly. On all five pages the JSON-LD is identical between them: the same block count and the same byte count, 0 and 0 for the two pages with none, 2 blocks and 636 bytes for gymshark.com, 1 block and 24,865 bytes for webflow.com, 1 block and 798 bytes for the Wikipedia article. Not one byte of structured data on any of these pages arrived only after JavaScript ran.

That is a narrower result than it sounds and it is worth stating what it does not show. Client-injected schema is a real pattern, common enough that the verdict layer in this codebase carries a cap for it, so that a page whose schema exists only in the rendered view cannot score as if a plain HTTP client could see it. None of these five pages exercised that path. Five pages cannot tell you how often the pattern occurs, only that it did not occur here, and a tag manager injecting a Product block is exactly the case these captures happen not to contain.

What it does add to is a pattern now visible across three separate counts on this same corpus. [Rendering added no new crawl paths](https://lantad.co/blog/javascript-added-no-new-crawl-paths) on these pages, producing three same-host URLs that existed only in the rendered DOM and all three rewrites of links already present. [Heading counts barely moved](https://lantad.co/blog/an-h1-inside-a-header-counted-as-none) between the two views. Now the structured data does not move either. On this small sample, the things a retrieval system would key on are in the first response, and JavaScript changes the visual page far more than it changes the machine-readable one. That is the reason [prose parity](https://lantad.co/glossary/prose-parity) is the heaviest signal in the composite rather than a JavaScript detection heuristic: the interesting failures are pages where the prose is missing without JavaScript, not pages where the schema is.

If you want to see the same comparison on your own page rather than take a five page sample for it, [what GPTBot sees](https://lantad.co/tools/what-gptbot-sees) fetches the raw response the way a plain HTTP client does, which is the view this section is counting.

## What the schema sub-score counts, and what it cannot tell you

Three of the five captures store a schema sub-score of 1.0 and two store 0. Gymshark's 636 bytes score 1.0. Webflow's 24,865 bytes score 1.0. The Wikipedia article's 798 bytes score 1.0. On this corpus the sub-score has two states, and every page that shipped any parseable JSON-LD with an @type reached the top of the scale.

That is the check working as specified rather than a defect, and it is worth being precise about what it asks. It asks whether a block parses, whether its entities carry an @type, and whether an entity of a recognised type carries the properties that type requires. The recognised set is small and deliberate: Organization, Product, Article, FAQPage and BreadcrumbList, plus six aliases mapping NewsArticle, BlogPosting, TechArticle and ScholarlyArticle onto Article, and LocalBusiness and Corporation onto Organization. A page declaring only WebPage and WebSite carries types the check cannot validate against anything, which is why the comment above that table in core/src/schema.ts calls them the types a page can carry while conveying no business fact. Schema is weighted at 10 of the 100 composite points, the smallest of the four weights, and that weighting is a decision recorded in core/src/config.ts rather than a measurement of how much schema matters to anybody.

So a 1.0 means your JSON-LD is well formed, not that it is informative. Webflow's block and Gymshark's block differ by a factor of 39 in size and by 94 in typed nodes, and the sub-score cannot distinguish them because it was never designed to. We have written before about [reading the same markup twice and getting a perfect score and a zero](https://lantad.co/blog/structured-data-measured-twice), which is the fuller treatment of that gap and the reason two different traversals exist in this codebase. This post is the population view of the same problem: not how we read one page, but what five real pages give a reader to read.

There is a family resemblance to two other audits of our own scale. [A robots.txt blocking every citation crawler still grades B](https://lantad.co/blog/a-robots-txt-that-blocks-every-citation-crawler-still-grades-b) because access is 25 points and only 20 of them are lost. [We still score FAQPage](https://lantad.co/blog/faq-rich-result-gone-faqpage-still-scored) after Google removed the FAQ rich result documentation, because a schema type is vocabulary and a rich result is a rendering decision. In each case the number is defensible and the letter on the front of the report is a worse answer than the evidence behind it, which is the argument [for withholding a grade](https://lantad.co/blog/why-we-withhold-a-grade) when the evidence will not support one.

## How to read your own structured data after this

The useful move from a census this small is not to copy what the winning page did, because nothing here establishes that any of these pages wins anything. It is to run the same three questions against your own markup, all of which are answerable in a browser in a couple of minutes with no tool at all.

First, does the raw HTTP response contain a block at all. View source rather than inspecting the DOM, because those are different documents and this post just spent a section on the fact that they can differ. Two of five well built pages here carried nothing, so finding nothing is not exotic and not a crisis; it is a starting point. Second, of the typed nodes in it, how many name your organisation, your product or your article, and how many name the layout. If the answer is that most of them are WebPageElement and SiteNavigationElement, you have a large block that a parser will read as a description of a menu. Third, does anything in it disagree with the visible page, because a claim in JSON-LD that the page does not support is the failure mode with an actual cost, and the same problem [runs through review markup](https://lantad.co/blog/review-authenticity-is-not-in-the-markup) that no crawler can verify.

None of that is a substitute for checking whether the page can be fetched in the first place, which is the part most commonly broken and the part that makes everything else moot. [The AI crawler list](https://lantad.co/tools/ai-crawlers) sets out which tokens are worth testing robots.txt against, and a page that a citation crawler cannot fetch has an [AI visibility](https://lantad.co/glossary/ai-visibility) problem that no amount of schema will touch. [What a crawler meets on a real storefront](https://lantad.co/blog/what-a-crawler-meets-on-a-real-storefront) is the page-by-page reading of these same captures if you want the wider context they sit in.

The honest summary of this post is that five pages is five pages. It shows that two well regarded technical sites publish no JSON-LD, that one marketing homepage publishes 24,865 bytes of it with 39 nodes describing a navigation menu, that JavaScript added none of it anywhere here, and that our own sub-score cannot tell those cases apart. It does not show what any of that is worth in an answer engine, and [our research page](https://lantad.co/research) still declines to publish a picture of the web from samples this size. Any number in this post can be recomputed from files in this repository, which is the property that made it worth writing.

## Questions and answers

**How many of the five captured pages carried JSON-LD?**

Three of five. gymshark.com carried two blocks totalling 636 bytes, webflow.com carried one block of 24,865 bytes, and the English Wikipedia article on web crawlers carried one block of 798 bytes. astro.build and the developer.mozilla.org landing page for HTML carried none in either the raw HTTP response or the rendered DOM. All five pages were captured on 15 July 2026 and are stored as golden fixtures in core/fixtures/.

**Does more JSON-LD produce a better schema score?**

Not in this scanner. The schema sub-score returned 1.0 for gymshark.com's 636 bytes and 1.0 for webflow.com's 24,865 bytes, because it asks whether a block parses, whether entities carry an @type, and whether recognised types carry their required properties. It does not read volume and it does not read the ratio of business nodes to layout nodes. Schema is weighted at 10 of the 100 composite points in core/src/config.ts.

**Is microdata still used instead of JSON-LD?**

Not on these five pages. Across all ten stored documents, five raw responses and five rendered DOMs captured on 15 July 2026, there is not a single itemtype attribute. One page, developer.mozilla.org, carried three RDFa typeof values naming BreadcrumbList, ListItem and WebPage. Five pages cannot establish a trend for the web, and this scanner's schema check reads only application/ld+json, so RDFa on that page scored zero.

**Did JavaScript add structured data on any of these pages?**

No. On all five captures the JSON-LD in the rendered DOM was identical to the raw HTTP response in both block count and byte count. Client-injected schema is a real pattern and the verdict layer in this codebase caps its score for that reason, but none of these five pages exercised it. That is a statement about five pages captured on 15 July 2026, not about how common the pattern is.

---

Lantad measures whether AI crawlers can actually read a page: it fetches as a non-rendering
crawler, renders as a browser, and reports the gap. Free scan, one URL, no signup.

Method and weights: https://lantad.co/methodology | All pages as markdown: https://lantad.co/md | Crawler policy: https://lantad.co/bot
