tabteca
Sign in
ES EN

Structured data: what to mark up and what not

JSON-LD without the hype: which types actually do something, how to stop the schema promising things the page doesn't show, and why it doesn't raise rankings but does raise clicks.

Structured data doesn’t raise rankings: it changes how your result looks on the search page, and a result with expandable questions or breadcrumbs earns more clicks from the same position. That is the whole promise, and it is enough to make it worth doing properly.

What can push you down is marking up things that aren’t on the page. Google calls that structured data spam and treats it as what it is: promising something and not delivering.

Which format to use

JSON-LD, in a <script type="application/ld+json">. It is what Google recommends and the only one you can read without diving into the HTML.

The alternatives — microdata and RDFa — are embedded in the content’s tags, which sounds neat and in practice means a layout change breaks the markup silently. With JSON-LD the block sits apart and is generated from the same data the page renders.

The types that actually earn their keep

There are hundreds of schema.org types and a minority produce any visible effect. These are the ones that pay:

Type What for What changes in the result
Organization / WebSite Once for the whole site Brand panel, search box
BreadcrumbList Any page with hierarchy The path instead of the raw URL
FAQPage Pages with questions and answers Expandable questions under the result
HowTo Genuine step-by-step guides The steps listed out
Article / BlogPosting Articles Date, author, eligibility for aggregators
Product / Offer Products with a price Price and availability

The rest rarely repays the effort. And a warning: eligibility for rich results changes over time. Google has repeatedly narrowed where it shows FAQPage and HowTo. Marking them up is still worthwhile — AI assistants read them too — but don’t build a strategy on a specific format appearing.

The rule that prevents every problem

Mark up only what the person can see on the page.

It sounds banal and it settles ninety per cent of cases:

  • Schema says there are five FAQs? There must be five visible FAQs.
  • Says the article was updated yesterday? The date should be on the page.
  • Declares a HowTo with six steps? Six numbered, visible steps must exist.

The failure isn’t marking up too much in one go: it is the slow drift. Someone rewrites the article, removes two questions, and the JSON-LD keeps promising five because it lives somewhere else.

How to stop that drift

The structural fix is not to hand-write the schema. Generate it from the same source that renders the content.

On our blog, for example, the FAQPage isn’t declared in the article’s front matter: it is extracted from the body of the text. The code finds the FAQ section in the Markdown, reads the questions and their answers, and builds the JSON-LD from that. The practical effect is that if someone deletes a question from the article, it disappears from the schema in the same commit. There is no way for them to say different things.

Same with HowTo steps: they are read from the numbered headings in the text itself. And with breadcrumbs, which come from the same list the visible navigation renders.

It is more work the first time and it removes an entire class of error for good.

Concrete mistakes you see a lot

Marking up HowTo on something that isn’t a guide. Numbering sections is ordinary writing. “The 7 limits nobody reads” has numbered headings and is not a procedure: you don’t execute them in order. That is an ItemList, not a HowTo.

Putting the same FAQs on every page. A FAQ block repeated site-wide adds nothing and reads as an attempt to game the result format.

Inventing ratings. Marking up AggregateRating with reviews that don’t exist is one of the few things that reliably earns a manual action. Don’t.

Marking up content behind an account. If the crawler can’t see what the schema describes, the markup is worth nothing.

Leaving contradictory blocks. Two Article objects on the same page with different dates is worse than none.

How to check it

Three levels, cheapest to slowest:

  1. That it is valid JSON. Sounds like a joke until an unescaped quote breaks the whole block and nobody sees it. Put it in your SEO check script: walk every application/ld+json block on each page and try to parse it. Ours sits there, alongside the rest of the technical SEO checks.
  2. Google’s Rich Results Test, to find out whether the type is eligible.
  3. The Search Console enhancements report, weeks later, which is where errors on the real site surface.

An upside that is no longer only about Google

Structured data was written for search engines and is now read by AI assistants too, which greatly prefer a clean JSON block over guessing from HTML. A well-built FAQPage is literally question-and-answer pairs ready to cite.

It pulls in the same direction as llms.txt and the rest of what we cover in how to get AI assistants to cite your site: handing the machine the fact rather than making it extract one.

Frequently asked questions

Does structured data improve rankings? Not directly: it is not a ranking factor. What it improves is how your result looks, which raises click-through rate at the same position. It also helps a search engine or assistant understand what the page is about, which matters indirectly.

Can I put several JSON-LD blocks on one page? Yes, and it is normal: one for the organisation, one for breadcrumbs, one for the article. What matters is that they don’t contradict each other.

What happens if I mark up something that isn’t on the page? Best case, Google ignores the markup. Worst case, if the pattern repeats, a manual action removes rich results across the whole site. It isn’t worth it.

Does FAQPage still work? Google has narrowed where it displays it, so don’t count on expandable questions as guaranteed. It is still worth marking up: it is cheap when generated automatically, and AI assistants make use of it.

Do I need a library to generate JSON-LD? No. They are objects you serialise with JSON.stringify. One function per type, fed from the same data the template renders, is all it takes — and it avoids the dependency.

The directory is the other half of this

115 services with a genuinely free plan, each one with its limits spelled out. No sign-up needed to start looking.

Explore the directory

← All articles

Keep reading

5 min read

Free SEO tools for a small project

The seven pieces you need to measure and fix the SEO of a small project without paying anything, and what to check in each one's free plan before you set it up.

SEOFree planGuides

6 min read

How to get AI assistants to cite your site

ChatGPT, Perplexity and Google's AI summaries cite specific sources. What makes them pick yours: direct answers, HTML without JavaScript, structured data and an llms.txt.

SEOAIGuides

5 min read

hreflang: SEO for a bilingual site

How to get Google to index both versions of your site instead of treating one as a copy of the other. With the canonical mistake that erases an entire language from the index.

SEOInternationalisationGuides