seo: drop tag archives from sitemap, add hreflang and BlogPosting schema - #25
Merged
Conversation
Three measured problems, verified against a local build of Hugo 0.163.3 (the version pages.yml pins) before and after. 1. Tag archives dominated the sitemap. EN sitemap held 1392 URLs, of which 916 (66%) were tag term pages against 449 real content URLs. LT held 346. On a site with ~93 referring domains that spends most of Googlebot's crawl allowance re-reading near-empty archives instead of discovering new posts. layouts/sitemap.xml now filters term and taxonomy pages for the tags taxonomy. Categories (22) and series (5) are curated and stay listed. Tag pages remain crawlable and indexable, they are only delisted, so any tag page already earning traffic keeps it. Measured: EN 1392 -> 476, LT 346 -> 99. No /tags/ URL leaks through. The xhtml:link hreflang alternates the embedded template emits are preserved deliberately, they were the site's only hreflang signal. 2. No hreflang in the HTML head. The site ships EN and LT for every post and declared alternates only inside the sitemap. Head tags are what Google treats as authoritative for a page reached by internal link, backlink or share. Added reciprocal alternates plus x-default resolved from hugo.Sites.Default rather than hardcoded. 3. No Article schema anywhere. Every URL emitted only Person + WebSite, so no page ever declared a headline, publish date, modified date, author or section. Added BlogPosting for article pages with datePublished, dateModified, wordCount, articleSection, series as CreativeWorkSeries, and keywords. Built with dict + jsonify rather than hand-written JSON so quotes and non-ASCII escape correctly. Verified the LT output parses and that Lithuanian diacritics land as valid \u escapes. Used .Language.Locale over the .Language.LanguageCode the embedded template uses, since that was deprecated in 0.158. Build is warning-clean.
|
Bugbot is not enabled for your account, so this pull request was not reviewed. Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs. |
This was referenced Aug 16, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Three technical SEO fixes, each measured against a local build of Hugo 0.163.3 (the version
pages.ymlpins) before and after. No content changes — titles and copy are handled separately.1. Tag archives were 66% of the sitemap
The EN sitemap carried 1392 URLs, of which 916 were tag term pages against 449 real content URLs. LT carried 346. On a site with ~93 referring domains, that spends most of Googlebot's crawl allowance re-reading near-empty archives instead of finding new posts.
blog/layouts/sitemap.xmlnow filterstermandtaxonomypages belonging to thetagstaxonomy. Categories (22) and series (5) are curated, so they stay listed.Tag pages remain crawlable and indexable — they are only delisted from the sitemap, so any tag page that already earns traffic keeps it. (
/tags/diffraction-grating/currently ranks, so a blanketnoindexwas deliberately not used.)Verified no
/tags/URL leaks through. Thexhtml:linkhreflang alternates that Hugo's embedded template emits are preserved deliberately — they were the site's only hreflang signal, and dropping them while rewriting the template would have been a silent regression.2. No hreflang in the HTML head
Every post ships EN and LT, but alternates were declared only inside the sitemap. Head tags are what Google treats as authoritative for a page reached by internal link, backlink or share.
Added reciprocal alternates plus
x-default, with the default language resolved fromhugo.Sites.Defaultrather than hardcoded toen. Verified both language versions emit an identical, reciprocal set:3. No Article schema anywhere
Every URL on the site emitted only
Person+WebSite. No page ever declared a headline, publish date, modified date, author or section — Google had to infer all of it from rendered HTML. That also left the site ineligible for article rich results and gave no explicit freshness signal for a series that gets revised.Added
BlogPostingfor article pages withdatePublished,dateModified,wordCount,articleSection,keywords, and series asCreativeWorkSeries. Excluded from taxonomy pages (verified: tag pages emit noBlogPosting).Built with
dict+jsonifyrather than hand-written JSON so quotes and non-ASCII escape correctly instead of producing invalid JSON-LD. Verified the LT output parses and Lithuanian diacritics land as valid\uescapes.Notes
.Language.Localeinstead of the.Language.LanguageCodethe embedded template uses, since that was deprecated in Hugo 0.158. Build is warning-clean; before this change the build emitted three deprecation warnings.