link-integrity
Skill2 starsChanged 25 days agoApache-2.0View on GitHub
Use when links, buttons, and route targets across a site must actually resolve: navigation, footer, CTAs, content links, canonical and sitemap targets, mailto and tel links, form actions, and external references. It separates confirmed broken routes from transient network failures and repairs internal links safely. Do not use it to declare an external site broken from a single timeout, to crawl a site you do not have permission to test, or to replace browser testing of client-side interactions.
We split this skill into the rules it gives an agent
4 rules. About 0 are common, 2 are distinctive, and 2 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈2
Distinctive · estimate
This author's own choices. Worth a look.
2
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Very specific: line 17
Before launch, after a routing/rename/migration, or when links look wrong.
- Distinctive: line 19
Not for behaviors that need JavaScript interaction only (clicking a menu).
- Very specific: line 23
Run the checker (paths relative to this skill's folder).
- Distinctive: line 73
All internal targets resolve and any unverified ones are explained.
≈ “Common” is an estimate: at least 1 in 5 of the 308,232 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
link-integrity
Broken links in the nav or footer are the fastest way to look abandoned. But a flaky external server is not a broken link, and # is not a destination. This skill makes those distinctions with evidence.
Activate when
- Before launch, after a routing/rename/migration, or when links look wrong.
launch-all/trust-all/discoverability-allroute here for checks 22, 23 (dead hrefs), or 17 (dev/staging hosts in links).- Not for behaviors that need JavaScript interaction only (clicking a menu); check those in a browser.
Inspect
Run the checker (paths relative to this skill's folder). Serve a local build if none is running; add --render for client-rendered apps, and --external to also check outbound links:
node scripts/check-links.mjs --url http://localhost:3000 --render
node scripts/check-links.mjs --url https://staging.example --external
node scripts/check-links.mjs --dir ./dist # static only; client-routed links are reported UNVERIFIEDWhat it checks and how to read it:
| Finding | Meaning | Confidence |
LINK_BROKEN (nav/footer/CTA = HIGH) | internal route returns 404/410 after a retry | confirmed |
LINK_SOFT_404 | returns 200 but the page says not found | confirmed behavior; fix status too (error-pages) |
LINK_UNVERIFIED | timeout, DNS, 5xx, 401/403/429/999 from the target | unknown; not evidence of breakage; retry later or verify by hand |
LINK_DEAD_HREF | #, empty, javascript: | source-indicated: a script may handle it; verify in browser |
LINK_FRAGMENT_MISSING | #section has no matching id | observed on that page |
LINK_PLACEHOLDER_TARGET | example.com, placeholder mailto/tel/form action | observed |
LINK_DEV_HOST | localhost/staging host in a link or form action | observed (HIGH) |
SITEMAP_URL_BROKEN, CANONICAL_TARGET_BROKEN | sitemap/canonical targets do not resolve | observed |
LINK_REDIRECT_CHAIN / LINK_INSECURE_SCHEME | > 2 redirects; http:// external | observed, low |
Then think beyond the tool: important external links (docs, social profiles, app-store, payment, calendar) by hand; email links (templates) for localhost/staging hosts; buttons implemented as <button onClick> that navigate (the checker cannot see them; read the code); dynamic routes and locale prefixes; links that need auth (401/403 is protected, not broken).
Evidence that counts
Label each claim OBSERVED, SOURCE-INDICATED, DECLARED, INFERRED, UNKNOWN, or REVIEW REQUIRED. UNKNOWN is never a pass and never a failure.
- Confirmed broken requires an HTTP 404/410 (or a static build lacking the file with no SPA fallback) after retry. Timeouts, TLS errors, bot-blocking codes, and 5xx are UNKNOWN.
- Static-directory mode cannot see client-side routing: those links stay UNKNOWN. Serve the build and use
--url --render. - Coverage is limited to crawled pages (
--max-pages): state how many.
May change
Fix internal links to the correct existing route; add a redirect when a route moved; restore a deleted page only if it should exist; replace placeholder targets with owner-supplied ones; remove links that lead nowhere with no intended destination (and say so); correct localhost/staging hosts to the confirmed production origin; add rel="noopener noreferrer" to external target="_blank" links. Do not guess a target for a dead CTA: ask the owner what it should do.
Must not claim
"No broken links" (say "0 confirmed broken among N pages crawled, M links unverified"). Do not report unreachable external sites as broken from one failure.
Verify
Re-run the same command. Pass = zero LINK_BROKEN, zero LINK_DEV_HOST, zero placeholder targets, dead hrefs either fixed or explained, sitemap/canonical targets resolve. Retry LINK_UNVERIFIED items once later; leave them labeled if still unknown.
Escalate
Links to legal pages that do not exist (legal-navigation, privacy-policy, terms-of-service); payment/auth flows behind broken links (HIGH, production-all); large-scale route changes needing a redirect map.
No change is valid when
All internal targets resolve and any unverified ones are explained. Do not remove working external links because a single check timed out.
In this repository54 other files it gives its agents.
- wcag-readinessSkill
- admin-audit-logSkill
- admin-authorizationSkill
- admin-dashboardSkill
- payments-readinessSkill
- subscription-readinessSkill
- ai-features-readinessSkill
- analytics-privacySkill
- consent-managementSkill
- consumer-protection-readinessSkill
- cookie-and-storage-auditSkill
- data-flow-mappingSkill
- data-rightsSkill
- email-complianceSkill
- jurisdiction-applicabilitySkill
- legal-identity-noticesSkill
- minors-readinessSkill
- policy-consistencySkill
- privacy-policySkill
- privacy-readinessSkill
- regulated-domain-triggersSkill
- terms-of-serviceSkill
- third-party-privacySkill
- user-content-safetySkill
- compliance-allSkill
- compliance-diffSkill
- design-system-reconnaissanceSkill
- discoverability-allSkill
- launch-allSkill
- launch-verificationSkill
- production-allSkill
- quality-allSkill
- site-reconnaissanceSkill
- trust-allSkill
- search-console-readinessSkill
- seo-readinessSkill
- social-sharingSkill
- structured-dataSkill
- multilingual-readinessSkill
- rtl-readinessSkill
- content-trustSkill
- error-pagesSkill
- failure-resilienceSkill
- faq-readinessSkill
- forms-readinessSkill
- launch-identitySkill
- legal-navigationSkill
- mobile-readinessSkill
- performance-readinessSkill
- public-supportSkill
- dependency-securitySkill
- deployment-cleanupSkill
- security-headersSkill
- web-securitySkill
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

