Do JavaScript Links Pass SEO Value?

Sometimes. Google renders JavaScript and will follow a link it finds afterwards — but only if the rendered page contains a real <a> element with an href pointing at a crawlable URL. A <span onclick="..."> or a button calling router.push() is not a link to any crawler, however it behaves for a user. Other crawlers render far less than Google.
The rule that decides everything: is there an href?
Google's own JavaScript SEO guidance is unambiguous on this point. Googlebot discovers links by looking for <a> tags with href attributes in the rendered HTML. Everything else is a formatting detail.
This means the question is never really "does JavaScript break links". It is: after your JavaScript has run, does the DOM contain an anchor with an href?
If yes, it is an ordinary link and passes value like any other. A React app whose router renders <a href="/pricing"> is completely fine, and this is what every mainstream framework does by default.
If no, the crawler sees clickable text. It cannot queue a URL it was never given.
The patterns that fail
Four of these account for nearly every broken link on a modern site.
The clickable element with no anchor. <span onclick="go('/pricing')">Pricing</span> or the same thing on a <div> or <button>. Works perfectly with a mouse, invisible to a crawler, and invisible to screen readers too — which is usually the faster way to get it fixed internally.
href="javascript:void(0)" or href="#" with a click handler. The anchor exists, but the href points nowhere. Google gets no destination URL. This pattern is extremely common in old navigation menus and in "load more" pagination.
Programmatic navigation from a button. <button onClick={() => router.push('/blog/post')}>. The framework navigates correctly, the URL updates, the page works — and no crawler ever learns the destination exists. This is the single most common cause of orphaned pages in single-page applications, which is the state described in what is an orphan page.
Links that only appear after interaction. Content behind a click — accordions that fetch on open, tabs that load their panel lazily, infinite scroll that never renders a paginated URL. Googlebot does not click, scroll or hover. It renders the page as loaded and reads what is there. Anything requiring an action to appear is not there.
The fix in every case is the same and it is small: render a real <a href> to the real destination, and attach your JavaScript behaviour to it rather than replacing it.
What Google actually does with JavaScript
Worth understanding, because it explains the delays people misdiagnose as crawl problems.
Googlebot crawls the raw HTML first, then queues the page for rendering in a headless browser, then processes the rendered result. Rendering is not instant — pages sit in a queue, and the delay ranges from minutes to considerably longer depending on the site.
Two practical consequences:
Links only present after render are discovered late. They are usually discovered eventually, but a link in the raw HTML enters the crawl queue immediately while a JavaScript-injected one waits. On a large site this compounds into a meaningful crawl budget problem.
If rendering fails, the links do not exist at all. A script blocked by robots.txt, a JavaScript error, a timeout, or a dependency that will not load means Google indexes the pre-render HTML. This is a common reason for a page not showing up on Google when it looks fine in a browser.
Non-Google crawlers render much less
This is where sites relying on JavaScript rendering get caught, and it has grown more important as AI search has grown.
Google invests heavily in rendering. Most other crawlers do not, and many read raw HTML only. That includes a large share of the bots behind AI assistants, social preview generators, and third-party SEO tools.
The consequences are concrete:
- Backlink tools may not see your outbound or inbound links if they exist only after render, which distorts your own audits.
- AI systems may miss the content entirely. If your main content is JavaScript-injected, a crawler that does not render sees a near-empty page — and an empty page is never cited in an AI answer.
- Social and messaging previews break, because those fetchers almost never execute JavaScript.
The safe posture: assume anything that matters — main content, navigation, canonical, title, links — must be present in the HTML the server sends, and treat client-side rendering as enhancement.
How to check your own site in five minutes
Four checks, quickest first.
1. Disable JavaScript and reload. In Chrome DevTools, Command Palette (Ctrl+Shift+P) → "Disable JavaScript", then reload. Whatever remains is roughly what a non-rendering crawler sees. This is blunt but it finds the worst problems instantly.
2. Read the rendered DOM, not the source. DevTools → Elements shows the DOM after JavaScript has run. Search it for the link you care about and confirm there is an <a> with a real href. Viewing source shows only the server response, so comparing the two tells you which links depend on rendering.
3. Use the URL Inspection tool in Search Console. "Test live URL" → View crawled page → HTML. This is the rendered HTML as Google actually got it, and it is the authoritative answer for Google specifically. The screenshot tab is often more revealing than the HTML — a blank screenshot is a rendering failure.
4. Fetch it the way a simple crawler would. curl -s https://yoursite.com/page | grep '<a ' returns the anchors in the raw HTML. If your navigation is not in that output, no non-rendering bot will find it.
If a backlink you earned is JavaScript-injected
This comes up when a link you were promised turns out not to count, and it is worth checking before chasing anyone.
Links delivered through third-party widgets, comment systems, review embeds and some "partner badge" scripts are frequently injected into an iframe or built in JavaScript at load time. The visible result looks like a link on the page. To a crawler it is often nothing at all, or a link from the widget provider's domain rather than from the site you negotiated with.
Check any placement you care about by loading the page, opening DevTools, and confirming the anchor is in the main document with an href to your URL — not inside an iframe and not absent from the raw HTML. It is the same discipline as checking whether a backlink is indexed, one step earlier in the chain.
Frequently asked questions
Do JavaScript links pass SEO value?
They do if, after rendering, the page contains a genuine <a href> pointing at the destination. Google renders JavaScript and follows those links normally. Clickable elements without an href — onclick handlers, buttons calling a router — pass nothing, because the crawler is never given a URL.
Does Google follow onclick links?
No. Googlebot looks for <a> elements with href attributes. An onclick handler on a span, div or button is not a link, no matter how it behaves for a user.
Is href="javascript:void(0)" bad for SEO?
It gives crawlers no destination, so the link passes nothing and the target page may go undiscovered. Point the href at the real URL and keep the JavaScript behaviour on top of it.
Do links in React or Next.js apps work for SEO?
Yes, when you use the framework's link component, which renders a real anchor with an href. Problems come from navigating with router.push() inside a button instead, which produces no crawlable link.
Does Google render every page? It renders, but not instantly — pages queue for rendering after the initial crawl. If rendering fails or a resource is blocked, Google falls back to the pre-render HTML, which is why blocking your JavaScript files in robots.txt can be quietly destructive.
Do AI crawlers execute JavaScript? Many do not, and the ones that do vary. Content and links that exist only after client-side rendering are frequently invisible to them, so anything you want quoted in an AI answer should be in the server-rendered HTML.
How do I test what a crawler sees?
Disable JavaScript in DevTools for a fast approximation, use Search Console's URL Inspection "Test live URL" for Google's actual rendered HTML, and curl the page to see the raw server response that simpler crawlers rely on.
The bottom line
The rule is one line: if it should be crawled, it must be an <a> with a real href in the HTML, ideally before JavaScript runs. Everything else about JavaScript SEO is a consequence of that. Audit your navigation and pagination first — those are where the failures orphan the most pages — and verify any earned backlink is in the main document rather than an injected widget.
Once the plumbing is sound, the links themselves still have to come from somewhere. Backlinkster matches owners of related sites for one-for-one in-content swaps, and every placement is verified live by code — a real anchor on a real page, checked continuously, so a link that quietly disappears gets caught. Five swaps a month on the free plan; see the plans.
Related: What is an orphan page in SEO? · Why is my website not showing up on Google? · What is crawl budget? · How to check if a backlink is indexed · Do image links pass SEO value? · Do popup and sticky banner links pass value?
