How to Add JSON-LD Schema Markup to Any Website(No Plugin)

Quick answer: To add JSON-LD schema markup without a plugin, write your structured data inside a <script type=”application/ld+json”> tag, paste it into the page’s <head> or <body>, and make sure it matches what visitors can see. Then test the live URL in Google’s Rich Results Test. Every platform works this way. Only the place you paste it changes.

A few weeks ago, an Ahrefs audit flagged a Google rich results error on the free QR code tool on my own site. The tool worked fine. The JSON-LD schema markup behind it didn’t.

My SEO plugin was describing a tool page as a blog article, complete with a Person author. On top of that, I’d added a SoftwareApplication block with no rating or review, and Google needs one of those for that rich result. So the page was telling Google two wrong things at once.

How to Add JSON-LD Schema
Photo by Florian Olivo on Unsplash

The fix was small. I removed my block, switched off the plugin’s automatic schema for that page, and kept only markup that matched what was on the screen.

I still use an SEO plugin, and you may want one too. There’s a good roundup here on dewebkiller of the best SEO plugins for WordPress. But a plugin only guesses from your post type. When you need exact control, or you aren’t on WordPress at all, a few lines of JSON-LD do the job.

Here’s exactly how to add it, with copy-paste code for six platforms and a way to test it.

What JSON-LD Schema Markup Is (and What It Isn’t)

JSON-LD (JavaScript Object Notation for Linked Data) is a way to write structured data as a small block of JSON inside a script tag. It tells search engines what a page is, such as an article, a product or a business, without touching your visible HTML. It’s a W3C standard.

Schema markup is the vocabulary you use inside that block. It comes from schema.org. So JSON-LD is the format, and schema.org supplies the words.

There are two older formats, and you’ll still see them in old themes:

FormatWhere it livesWhy you’d pick it
JSON-LDOne separate script blockEasiest to add, read and update. Google recommends it.
MicrodataAttributes mixed into your HTMLOnly if your templates already use it
RDFaAttributes mixed into your HTMLOnly if your templates already use it

Google’s structured data guide says all three are fine when they’re valid. It recommends JSON-LD because it’s the easiest to maintain, and I agree. You can change it without breaking your layout.

One thing that trips people up: JSON-LD is not JSON Schema. JSON Schema checks the shape of data, such as an API response. It has nothing to do with SEO.

Pick the Right Schema Type First

Don’t start with code. Start with the page. Ask what it really is, then use the type that describes it. Here’s where things stand in November 2026, based on Google’s search gallery:

PageSchema typeRich result on Google?
Blog post or news storyArticleYes
Product pageProduct with OfferYes
Shop or officeLocalBusinessYes
Event pageEventYes
Page with a videoVideoObjectYes
Any inner pageBreadcrumbListYes
App or web toolSoftwareApplicationYes, with a rating or review
Home pageOrganization and WebSiteNo card, but it describes your brand
FAQ sectionFAQPageNo, it stopped on 7 May 2026
Step-by-step guideHowToNo, it ended in September 2023

Those last two rows matter. Google removed the FAQ rich result this year, and HowTo went in 2023. Plenty of tutorials still promise both. FAQPage and HowTo remain valid schema.org types, but they won’t earn you those results on Google.

Also, markup only makes a page eligible. Google says it doesn’t guarantee a rich result, even when your code is perfect.

Step 1: Write Your JSON-LD Block

Every block has the same parts. Once you can read these four, you can read any example.

  • @context tells the reader you’re using schema.org words.
  • @type says what the thing is.
  • @id is an optional label, so other items can point to this one.
  • @graph holds several items in one block.

This one goes on your home page. It describes your business and your website, and it links them with @id:

<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@graph": [
    {
      "@type": "Organization",
      "@id": "https://example.com/#org",
      "name": "Example Studio",
      "url": "https://example.com/",
      "logo": "https://example.com/logo.png",
      "sameAs": [
        "https://www.linkedin.com/company/example-studio"
      ]
    },
    {
      "@type": "WebSite",
      "@id": "https://example.com/#website",
      "url": "https://example.com/",
      "name": "Example Studio",
      "publisher": {
        "@id": "https://example.com/#org"
      }
    }
  ]
}
</script>

And this one is for a blog post:

<script type="application/ld+json">
{
  "@context": "https://schema.org",
  "@type": "Article",
  "headline": "How to Fix Uneven Card Heights",
  "image": [
    "https://example.com/images/cards.jpg"
  ],
  "datePublished": "2026-11-05T09:00:00+00:00",
  "dateModified": "2026-11-05T09:00:00+00:00",
  "author": {
    "@type": "Person",
    "name": "Jane Doe",
    "url": "https://example.com/about/jane/"
  }
}
</script>

Swap in your own details. If you don’t want to type it by hand, a free schema markup generator gives you a starting block.

The one rule you can’t skip: mark up only what people can see. Google’s structured data guidelines say the same thing. If the JSON-LD says 4.8 stars, those stars must be on the page.

Step 2: Where to Put JSON-LD (Head or Body?)

Both work. Google reads JSON-LD in the <head> or the <body>, so pick whatever your platform makes easy. I prefer the head because it’s tidy, but body placement is fine when a template only gives you that spot.

Before you paste anything, check what’s already there. Open your page, press Ctrl+U to view the source, and search for ld+json. Your theme or SEO plugin may already print Article or Organization markup, and that’s how pages end up with two versions of the same thing.

You can use one block with @graph or several separate blocks. Both are valid. What matters is that the same business isn’t described twice with different details.

You might also like: Page Builders vs Custom Code in WordPress

Step 3: Add JSON-LD Schema Markup on Your Platform (No Plugin)

This is the part most guides skip, so here’s each platform in turn.

Photo by Christopher Gower on Unsplash

1. Plain HTML Sites

Paste the block just before the closing </head> tag of the page, then upload the file. That’s the whole job.

2. WordPress (functions.php)

Add this to your child theme’s functions.php. Using a child theme means a theme update won’t wipe it. Back up first, because a PHP typo here can take the site down.

add_action( 'wp_head', function () {
	if ( ! is_single() ) {
		return;
	}

	$id     = get_queried_object_id();
	$schema = array(
		'@context'      => 'https://schema.org',
		'@type'         => 'Article',
		'headline'      => wp_strip_all_tags( get_post_field( 'post_title', $id ) ),
		'datePublished' => get_the_date( 'c', $id ),
		'dateModified'  => get_the_modified_date( 'c', $id ),
		'author'        => array(
			'@type' => 'Person',
			'name'  => get_the_author_meta( 'display_name', get_post_field( 'post_author', $id ) ),
		),
	);

	$image = get_the_post_thumbnail_url( $id, 'full' );
	if ( $image ) {
		$schema['image'] = array( $image );
	}

	$flags = JSON_HEX_TAG | JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE;
	echo '<script type="application/ld+json">' . wp_json_encode( $schema, $flags ) . '</script>' . "\n";
} );

Every post now gets its own title, dates, author and image automatically. If Yoast or Rank Math already prints Article markup, don’t add this as well. Use the hook for a type your plugin doesn’t cover.

3. Shopify

Go to Online Store, then Themes, then Edit code. Many themes already print product markup, so check the source first. If yours doesn’t, add Shopify’s structured data filter to your product section:

<script type="application/ld+json">  {{ product | structured_data }}</script>

For a custom block, pass values through the json filter. It adds the quotes and escapes the text for you, so a product title with a quote mark won’t break your code:

"name": {{ product.title | json }},

4. Webflow, Wix and Squarespace

You don’t need code access here. Each one has a box for it.

PlatformWhere to paste itGood to know
WebflowPage settings, Custom code, Inside head tagNeeds a paid Site or Workspace plan
WixPages & Menu, SEO basics, Advanced SEO, Structured Data MarkupUnder 7,000 characters, up to five per page
SquarespacePage settings, Advanced, Page Header Code InjectionCore plan or higher, plus some legacy plans

5. Next.js

Render a normal script tag inside your page component. The Next.js JSON-LD guide recommends this approach, and the replace part matters. JSON.stringify alone doesn’t protect you from a script injection if your data contains HTML.

export default async function Page({ params }) {
  const { slug } = await params
  const post = await getPost(slug)

  const jsonLd = {
    '@context': 'https://schema.org',
    '@type': 'Article',
    headline: post.title,
    datePublished: post.publishedAt,
  }

  return (
    <article>
      <script
        type="application/ld+json"
        dangerouslySetInnerHTML={{
          __html: JSON.stringify(jsonLd).replace(/</g, '\\u003c'),
        }}
      />
      <h1>{post.title}</h1>
    </article>
  )
}

6. Google Tag Manager

Stuck with a platform you can’t edit? Add a Custom HTML tag, paste your block, and publish the container. Google documents this method and suggests using variables to read values from the page, so the markup can’t drift away from your content.

Treat it as a backup. The markup only exists after JavaScript runs, and Google warns that generated Product markup can make Shopping crawls less frequent and less reliable. For stores, put it in the HTML.

Step 4: Keep It Dynamic, Not Hard-Coded

A hard-coded block is fine for your home page. On a product or blog post, it goes stale fast. You change a price, the JSON-LD still shows the old one, and now your markup doesn’t match your page.

The fix is to pull values from the same place the page gets them. That’s what the examples above do: WordPress functions, Liquid objects, your Next.js data and GTM variables. Change the content once and both update together.

Dates need the ISO 8601 format, like 2026-11-05T09:00:00+00:00. Use absolute URLs too, not paths like /logo.png.

Step 5: Test Your JSON-LD

Never trust markup you haven’t tested. I run three checks, and each one catches something different:

  1. Google’s Rich Results Test: shows which rich results the live page can get. Test the URL, not only the code, because it also shows you markup added by your theme.
  2. Schema Markup Validator: checks all schema.org types, including ones Google has no rich result for.
  3. A quick paste check: while I’m still writing a block, I use this free schema validator we built at Soft Learn Hub. It flags syntax errors, misspelled properties and missing required fields, and pasted code stays in your browser.

The Article example from Step 1 in the validator: 0 errors, 0 warnings.

After it goes live, watch the rich result reports in Google Search Console. They’ll tell you if a later change breaks something.

8 Common JSON-LD Mistakes and Quick Fixes

I’ve made a few of these myself, including number four. One site-wide business block on my site used two properties that don’t exist on that type, and a single audit flagged 134 pages because of it. Hand-written code needs testing too.

MistakeQuick fix
1. Marking up things visitors can’t seeAdd it to the page or remove it from the markup
2. Plugin and manual code both print the same typeKeep one, and switch off the other
3. A trailing comma or curly quotes from WordWrite it in a code editor and run a validator
4. Properties that don’t exist on your typeCheck the type’s page on schema.org
5. Required properties missingRead Google’s page for that feature
6. Made-up ratings or reviewsUse real ones or leave them out
7. Relative URLs or wrong date formatsUse full URLs and ISO 8601 dates
8. Prices and dates that never updatePull values from your CMS

Does JSON-LD Help in AI Search?

Honestly, less than many people claim.

Google’s AI guide says structured data isn’t required for its generative AI features, and there’s no special schema to add. It still recommends structured data for rich results. Microsoft sounds warmer. Search Engine Land reported in 2025 that Bing’s Fabrice Canel said schema helps its LLMs understand content.

Photo by Shubham Dhage on Unsplash

My take: JSON-LD won’t get you cited on its own. It removes guesswork about who you are and what the page is, and that’s useful. But clear answers on the page do far more. If that’s your goal, read this guide on AI search visibility next.

You might also like: SEO in 2026: How to Get Website Traffic

Result

After you’ve done this, your site should have:

  • Markup that matches what’s on each page
  • No duplicate items from your theme or plugins
  • Values that update when your content does
  • No plugin in the way when you need something custom

It’s a small job, but it gives you control over how your site describes itself.

FAQ

What is JSON-LD schema markup?

It’s structured data written as JSON inside a script tag. It uses the schema.org vocabulary to tell search engines what a page is about, such as an article, product or business, without changing how the page looks.

Can I add JSON-LD without a plugin?

Yes. JSON-LD is only a script block, so you can paste it into your HTML, a theme file, a platform’s custom code box, or a Google Tag Manager tag. No plugin is needed on any platform.

Should JSON-LD go in the head or the body?

Either works for Google. The head is tidier, but the body is fine if that’s the only spot your template gives you.

Does JSON-LD improve rankings?

Not directly. Structured data makes a page eligible for rich results and helps search engines understand it. It’s not a ranking shortcut, and Google doesn’t guarantee a rich result.

Is FAQ schema still worth adding?

Not for Google rich results, because they stopped on 7 May 2026. FAQPage is still valid schema.org markup, so it does no harm when the questions are visible on the page. Just don’t expect a rich result from it.

Conclusion

You don’t need a plugin to add JSON-LD schema markup. Decide what the page is, write a small block that matches it, paste it in the right spot for your platform, and test the live URL.

Start with one page today. Your home page is a good choice, because the Organization example above only takes a few minutes to adapt.

Dewebkiller newsletter

Oh hi there 👋
It’s nice to meet you.

Sign up to receive awesome content in your inbox, every month.

We don’t spam! Read our privacy policy for more info.

About Zubair Shahzad

Zubair Shahzad Founder & Digital Strategist at Soft Learn Hub. Multidisciplinary digital growth expert helping businesses scale, combining high-performance web development with data-driven marketing. Expertise spans technical and on-page SEO, intuitive UI/UX design, business creatives, and managing high-converting Google and Meta ad campaigns.