惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

I
InfoQ
Last Week in AI
Last Week in AI
大猫的无限游戏
大猫的无限游戏
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
V
V2EX
D
Darknet – Hacking Tools, Hacker News & Cyber Security
WordPress大学
WordPress大学
H
Help Net Security
P
Proofpoint News Feed
B
Blog
腾讯CDC
博客园 - 司徒正美
Recorded Future
Recorded Future
酷 壳 – CoolShell
酷 壳 – CoolShell
S
Security Archives - TechRepublic
N
News and Events Feed by Topic
T
The Exploit Database - CXSecurity.com
www.infosecurity-magazine.com
www.infosecurity-magazine.com
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
O
OpenAI News
GbyAI
GbyAI
Attack and Defense Labs
Attack and Defense Labs
T
Troy Hunt's Blog
IntelliJ IDEA : IntelliJ IDEA – the Leading IDE for Professional Development in Java and Kotlin | The JetBrains Blog
IntelliJ IDEA : IntelliJ IDEA – the Leading IDE for Professional Development in Java and Kotlin | The JetBrains Blog
F
Future of Privacy Forum
V
Vulnerabilities – Threatpost
T
Threatpost
The Cloudflare Blog
Recent Announcements
Recent Announcements
爱范儿
爱范儿
S
Schneier on Security
Blog — PlanetScale
Blog — PlanetScale
Cyberwarzone
Cyberwarzone
T
The Blog of Author Tim Ferriss
T
True Tiger Recordings
P
Proofpoint News Feed
S
Secure Thoughts
F
Fox-IT International blog
aimingoo的专栏
aimingoo的专栏
阮一峰的网络日志
阮一峰的网络日志
M
Microsoft Research Blog - Microsoft Research
F
Full Disclosure
Google Online Security Blog
Google Online Security Blog
T
Threat Research - Cisco Blogs
S
Securelist
罗磊的独立博客
L
Lohrmann on Cybersecurity
博客园 - 三生石上(FineUI控件)
T
Tailwind CSS Blog
MongoDB | Blog
MongoDB | Blog

DEV Community

Laravel Waiting Request AI Travel Assistant Powered by Gemma 4; With Streaming, Image Input, and Visual Recommendation Cards Microsoft tried to kill the printer driver. Healthcare said no. The Blueprint Beneath the Blueprint: Designing Data Model and Choosing Its Database REST APIs vs Webhooks in Telecom Billing - Which One Actually Makes Sense? Accounting Made Simple: AI-Powered Financial Insights of Japanese Companies with Gemma 4 The append-only AST trick that makes Flutter AI chat actually smooth Designing the Future of Payments — Why XML Still Matters in the Age of APIs From Legacy to Live — Reviving XMLPayments with GitHub Copilot Two Weeks Into Learning Solana XMLPayments — The Hidden Backbone of Modern Financial Orchestration AI Agents in Practice — Read from the beginning Reviving My Gemma Agentic Framework: From Prototype to Polished Repo Smart Contracts Demand Better Infrastructure: Building on contract.dev Self-Hosted LLM Tool Calling: Forge and the Build-vs-Buy Decision ORA-00072 오류 원인과 해결 방법 완벽 가이드 OpenWA for CTOs: Self-Hosted WhatsApp Gateway Trade-Offs NotebookLM Automation With notebooklm-py: Useful, But Classify Data First Docker v29.5.x Operator Upgrade Checklist Coding-Agent Instruction Design: The CLAUDE.md File That Prevents Rework When I Finally Realized My Runtime Was Holding Me Back GnokeOps: Host Your Own AI House Party The Death of Static Rate Limiters: Why Your Java Virtual Threads Need BBR-Style Adaptive Concurrency AI Agents in Practice — Part 2: What Makes Something an Agent Stop scattering LLM SDK/API calls across your codebase. Here is the 2-file rule that fixed mine Beyond Prompts: Structuring AI Workflows for Real Frontend Engineering From an Abandoned Hackathon Project to an AI Study Workspace 🚀 Terraform with AI: Build AWS Infra (Cursor + MCP) What If AI Didn’t Need the Internet? 750,000 Chips, 140 Trillion Tokens: The Math Behind DeepSeek's Permanent Price Cut You're Renting Someone Else's Compute — And It's Costing You More Than You Think CSS :has() Selector: The Layout Trick I Wish I Knew 5 Years Ago Five Clusters. Five Lessons. One Production System. Synaptic: A Local-First AI Dev Companion That Remembers How You Think Revolutionizing Edge MedTech: Building a Sovereign Sleep Apnea Companion ("XiHan Snore Coach") with Gemma 4 HDD Eksternal Tiba-Tiba Tidak Bisa Diakses di Windows? Ini Tiga Lapis Fix-nya DMARC p=none vs p=quarantine vs p=reject: what to use and when DSA Application in Real Life: How Git Diff Works: LCS Intuition, Myers Algorithm, and Real Code Changes I solo-built a reputation layer for AI agents on NEAR — and here's what I learned I built an AI faceless video generator in 2 months — here's the stack Diffusion Language Models: How NVIDIA Nemotron-Labs Diffusion Shatters the Autoregressive Speed Ceiling llm-nano-vm v0.8.0 — deterministic FSM runtime for LLM pipelines, now with output validation and per-step timeouts From the Renaissance to the Quantum Dawn: AI, Computation, and the Next Paradigm Shift How I Built a Review Site with 800+ Articles Using AI I Built a Smart Kitchen AI with Gemma 4 That Turns Fridge Photos Into Recipes Why your vulnerability dashboard is lying to you (and how to fix it) From Abandoned Prototype to Smart AI System: Reviving Trafiq AI with GitHub Copilot Why Country/State/City Pickers Are Weirdly Hard Node.js 22 LTS — EOL Date, Support Timeline, and What Comes Next The 7-Layer Memory Architecture Behind Modern AI Agents I Imagined Hermes Agent Running an Entire Smart City — And It Changed How I See AI One backend, four products: why we bet on platform-per-brand AI's tech debt is invisible — even to AI. I solved it at the architecture layer. Why ROAS 300% Can Still Mean Losses — Gross Margin in 5 Ecommerce Verticals You Don’t Need to Try Every AI Tool to Keep Up NovelPilot: A Novel Writing Agent Powered by Gemma 4 BoxAgnts is an Out-Of-The-Box Secure AI Agent ToolBox in a WASM SandBox Gemma 4 deep dive: why a 1.5 GB model scores 37.5% on competition mathematics, how the MoE routing actually works, and which model fits your hardware. Full breakdown inside. BeeLlama v0.2.0: 164 tok/s on a 27B model, one RTX 3090 Google Just Declared the Chat-Log Interface Dead. Here's What Neural Expressive Actually Signals for Developers. ARCHITECTURE SPECIFICATION & FORMAL SYSTEM REPORT: k501-AIONARC Notes from a Hammock What's Google Antigravity 2.0 ? Here's What the Agent Harness Actually Changes for Developers. Building an E2EE Chat App in Flask - Part 3: Keeping File Uploads Safe Google's Gemini Spark. Here's What It Actually Does for Developers. Microsoft Just Shipped MCP Governance for .NET. Here's What It Actually Enforces. How I Built a Pakistan Internet Speed Test Platform at 16 How to Build a Supervisor Agent Architecture Without Frameworks I Built My Own Corner of the Internet — Here's What It Looks Like How does VuReact compile Vue 3's defineExpose() to React? Neo-VECTR's Rift Ascent Idempotency Keys: The API Safety Net You Probably Aren't Using Building E-Commerce Sites for Niche Products: Technical Lessons from Specialty Outdoor Retailers Audit Logs: The Silent Guardian of Every Serious System Open-source SDS tooling for Japanese MHLW compliance: the gap nobody filled BetAGracevI I Built a Post-Quantum Cryptographic Identity SDK for AI Agents — Here's Why It Needs to Exist Running Claude Code across multiple repos without losing context There Are Cameras in Every Room of My House. I Put Them There. Why your AI agent loops forever (and how to break the cycle) How does VuReact compile Vue 3's defineSlots() to React? Building a Privacy-First Resume Editor with Typst WASM and React One Soul, Any Model: Portable Memory for Open-Source Agents with .klickd From Pixels to Prescriptions: Building an Autonomous Healthcare Booking Agent with LangGraph MonoGame - A Game Engine for Those Who Love Reinventing the Wheel # Day 24: In Solana, Everything is an Account Mastering Node.js HTTP Module: Build Servers, REST APIs, and Handle Requests Mastering Node.js HTTP Module: Build Servers, REST APIs, and Handle Requests RP2040 Wristwatch Tells Time With a Vintage VU Meter Needle observations about models / 2026, may From Video Transcripts to Source-Grounded AI Notes: A Practical Look at Notesnip AI Agent Dev Environment Guide — Real Experience from an AI Living Inside a Server How I Run 7 AI Models 24/7: Multi-Agent Architecture in Practice What exactly changes with the Claude Max plan? I Revived a Broken MLOps Platform — Now It's Self-Service, Policy-Guarded, and Operationally Credible OpenAI's $2M-tokens-for-equity YC deal, decoded Why DMX Infrastructure is Still Stuck in the 90s Agent Series (2): ReAct — The Most Important Agent Reasoning Paradigm Open Source Project (No.73): Sub2API - All-in-One Claude/OpenAI/Gemini Subscription-to-API Relay I Made the Wrong Bet on Event Streaming in Our Treasure Hunt Engine
Why Google Can't See Your React Breadcrumbs (And the 4-Line Fix)
Mitu Das · 2026-05-23 · via DEV Community

I wasted an entire afternoon wondering why Google Search Console kept showing zero rich results for my React app. The breadcrumbs looked perfect in the browser. Users could see them. But Google? Completely blind. The problem wasn't my breadcrumb component it was that I'd never told Google what those breadcrumbs actually were. Structured data. Four lines of JSON-LD. That was it. Here's everything I learned, so you don't lose the same afternoon.

Why React Breadcrumbs Are Invisible to Google

React apps render in the browser. Google's crawler is getting better at parsing JavaScript, but structured data embedded in client-rendered markup is still unreliable for rich results. The gold standard for breadcrumb rich results in Google Search is JSON-LD schema markup injected into <head> not your visible DOM breadcrumb trail.

The two things are completely separate:

  • Your breadcrumb UI component what users see
  • Breadcrumb Schema markup what search engines read

Most tutorials show you how to build the UI. Almost none explain the schema side. That's why your breadcrumbs look fine to you but don't show up as rich results in Google.

Here's what a valid BreadcrumbList schema looks like, per Schema.org:

{
  "@context": "https://schema.org",
  "@type": "BreadcrumbList",
  "itemListElement": [
    {
      "@type": "ListItem",
      "position": 1,
      "name": "Home",
      "item": "https://example.com"
    },
    {
      "@type": "ListItem",
      "position": 2,
      "name": "Blog",
      "item": "https://example.com/blog"
    },
    {
      "@type": "ListItem",
      "position": 3,
      "name": "My Article",
      "item": "https://example.com/blog/my-article"
    }
  ]
}

Enter fullscreen mode Exit fullscreen mode

Your job is to get exactly this into a <script type="application/ld+json"> tag in <head> on every page that has breadcrumbs.

The Manual Approach: A Custom React Hook

If you're not using any SEO library, here's a clean, copy-paste hook that builds and injects breadcrumb schema based on your current route.

// hooks/useBreadcrumbSchema.js
import { useEffect } from "react";

export function useBreadcrumbSchema(crumbs) {
  useEffect(() => {
    const schema = {
      "@context": "https://schema.org",
      "@type": "BreadcrumbList",
      itemListElement: crumbs.map((crumb, index) => ({
        "@type": "ListItem",
        position: index + 1,
        name: crumb.label,
        item: crumb.url,
      })),
    };

    const script = document.createElement("script");
    script.type = "application/ld+json";
    script.id = "breadcrumb-schema";
    script.textContent = JSON.stringify(schema);

    // Remove any existing breadcrumb schema before inserting
    document.getElementById("breadcrumb-schema")?.remove();
    document.head.appendChild(script);

    return () => {
      document.getElementById("breadcrumb-schema")?.remove();
    };
  }, [crumbs]);
}

Enter fullscreen mode Exit fullscreen mode

Then in your page component:

// pages/BlogPost.jsx
import { useBreadcrumbSchema } from "../hooks/useBreadcrumbSchema";

export default function BlogPost({ post }) {
  useBreadcrumbSchema([
    { label: "Home", url: "https://example.com" },
    { label: "Blog", url: "https://example.com/blog" },
    { label: post.title, url: `https://example.com/blog/${post.slug}` },
  ]);

  return <article>{/* your content */}</article>;
}

Enter fullscreen mode Exit fullscreen mode

Result: Every time the component mounts, the correct JSON-LD block is injected into <head> and cleaned up on unmount. Paste it into Google's Rich Results Test and you'll see a green checkmark.

One caveat: if you're using SSR (Next.js, Remix, etc.), this useEffect approach only runs client-side. For SSR, you need to render the script tag server-side which brings us to the next section.

The SSR Problem: Getting Schema Into <head> at Build Time

With Next.js, you can't rely on useEffect for schema that needs to be in the initial HTML response. The fix is rendering a <script> tag directly in your component using next/head or the App Router's <Head>:

// app/blog/[slug]/page.jsx (Next.js App Router)
import Head from "next/head";

function buildBreadcrumbSchema(crumbs) {
  return {
    "@context": "https://schema.org",
    "@type": "BreadcrumbList",
    itemListElement: crumbs.map((crumb, i) => ({
      "@type": "ListItem",
      position: i + 1,
      name: crumb.label,
      item: crumb.url,
    })),
  };
}

export default function BlogPost({ params }) {
  const crumbs = [
    { label: "Home", url: "https://example.com" },
    { label: "Blog", url: "https://example.com/blog" },
    { label: "My Post", url: `https://example.com/blog/${params.slug}` },
  ];

  const schema = buildBreadcrumbSchema(crumbs);

  return (
    <>
      <Head>
        <script
          type="application/ld+json"
          dangerouslySetInnerHTML={{ __html: JSON.stringify(schema) }}
        />
      </Head>
      <article>{/* your content */}</article>
    </>
  );
}

Enter fullscreen mode Exit fullscreen mode

Now the schema is part of the server-rendered HTML Google sees it immediately, no JavaScript execution required.

Using a Library: When Manual Gets Tedious

The manual approach is fine for one or two page types. But if your app has ten different page templates (product pages, category pages, blog posts, docs), you'll end up copy-pasting and slightly mangling that schema builder everywhere. That's where a dedicated library helps.

I tried a few options and ended up using @power-seo because it handles breadcrumb schema, OpenGraph, and canonical tags from a single config object which matched how I was already thinking about per-page SEO.

npm install @power-seo

Enter fullscreen mode Exit fullscreen mode

import { SEO } from "@power-seo";

export default function BlogPost({ post }) {
  return (
    <>
      <SEO
        breadcrumbs={[
          { label: "Home", url: "https://example.com" },
          { label: "Blog", url: "https://example.com/blog" },
          { label: post.title, url: `https://example.com/blog/${post.slug}` },
        ]}
        title={post.title}
        canonical={`https://example.com/blog/${post.slug}`}
      />
      <article>{/* your content */}</article>
    </>
  );
}

Enter fullscreen mode Exit fullscreen mode

It generates the same JSON-LD output as the manual approach no magic, just less repetition. Whether that's worth a dependency is your call. For small projects, the hook above is plenty.

What I Learned

  • Your visible breadcrumb UI and your breadcrumb schema are two separate things. One is for users, one is for search engines. Both need to exist.
  • useEffect-injected schema works for CSR apps, but for SSR/SSG (Next.js, Remix), render the <script> tag server-side inside <head> to guarantee it's in the initial HTML.
  • Always validate with Google's Rich Results Test (search.google.com/test/rich-results) before assuming it works. It'll show you exactly what schema Google can parse.
  • Keep your schema in sync with your actual URLs. Stale or mismatched item values in your schema are a silent SEO killer Google will ignore the breadcrumb entirely if the URLs don't resolve.

If you want to see how the full implementation looks in a real Next.js blog (including dynamic route handling), here's a detailed walkthrough: https://ccbd.dev/blog/how-to-implement-breadcrumb-schema-in-react-using-power-seo

What's your setup?

Are you handling structured data manually, using a library, or just skipping it entirely and hoping for the best? I'm curious how other React devs are solving this especially on large apps with lots of page templates. Drop your approach in the comments. If you've found a cleaner pattern than what I've shown here, I genuinely want to know.