Title Tag and Meta Description in Server-Rendered HTML
Issue No: 212
Category: JavaScript SEO Rendering
Issue type: Issue
Priority: CRITICAL
Description
This audit verifies that the page title and meta description are present in the raw server-rendered HTML response and are not injected only after JavaScript execution. If metadata is JS-only, crawlers may miss or inconsistently process key snippet signals.
How do we capture it
- Send an HTTP GET request to the canonical page URL with a crawler-style user agent and store status code, final URL, headers, and raw response bytes.
- Follow redirects up to configured cap and evaluate metadata only on the final HTML URL.
- Validate that the final response is HTML-like content using Content-Type header and initial payload inspection.
- Decode response bytes using declared charset (fallback UTF-8) and parse raw HTML text only.
- Extract the first title element text from the head section and normalize whitespace.
- Extract the first meta description candidate where name="description" (case-insensitive on attribute names) and read content value.
- Record presence booleans, extracted values, and normalized length metrics for both fields.
- Detect malformed metadata states: empty title text, empty meta description content, duplicate conflicting meta description tags, or description outside expected head context.
- Apply trigger rules to determine whether metadata is missing, empty, or likely JS-only from raw HTML evidence.
- Persist capture and trigger diagnostics to Postgres for scoring, reporting, and remediation traceability.
Constraint: The crawler must not execute JavaScript or render DOM for this issue. Only the raw HTTP response and raw HTML are authoritative for evaluation.
What to store
| Field | Type | Comment |
|---|---|---|
http_status_code | INTEGER | Final HTTP status code used for metadata validation. |
final_url | TEXT | Final URL after redirects where raw HTML was inspected. |
content_type | TEXT | Response Content-Type captured for HTML validation diagnostics. |
is_html_response | BOOLEAN DEFAULT FALSE | Indicates whether the final payload is HTML and eligible for this audit. |
raw_html_has_title_tag | BOOLEAN DEFAULT FALSE | True if a title element exists in raw HTML. |
raw_html_has_meta_description | BOOLEAN DEFAULT FALSE | True if a meta description tag exists in raw HTML. |
title_text | TEXT | Normalized title text extracted from raw HTML. |
meta_description_text | TEXT | Normalized meta description content extracted from raw HTML. |
title_length | INTEGER DEFAULT 0 | Character length of extracted title text after normalization. |
meta_description_length | INTEGER DEFAULT 0 | Character length of extracted meta description after normalization. |
meta_description_tag_count | INTEGER DEFAULT 0 | Number of meta description tags found for duplicate/conflict diagnostics. |
meta_in_head_section | BOOLEAN DEFAULT FALSE | True if metadata was found inside the head section. |
metadata_ssr_issue | BOOLEAN DEFAULT FALSE | Final issue boolean indicating metadata not reliably present in SSR HTML. |
trigger_reason | TEXT | Primary rule reason code for why the issue was triggered. |
capture_error_detail | TEXT | Parsing/fetch diagnostics for triage when capture is partial or failed. |
Condition for trigger
Trigger this issue when title or meta description is missing, empty, malformed, or otherwise not reliably present in raw server-rendered HTML.
-
Trigger Rule 1: Missing Title in SSR HTML
- Target Field:
metadata_ssr_issue - Evaluation Logic:
raw_html_has_title_tag = FALSE AND is_html_response = TRUE - Severity: CRITICAL
- Diagnostic Message: "Title tag is missing from server-rendered HTML response."
- Target Field:
-
Trigger Rule 2: Missing Meta Description in SSR HTML
- Target Field:
metadata_ssr_issue - Evaluation Logic:
raw_html_has_meta_description = FALSE AND is_html_response = TRUE - Severity: CRITICAL
- Diagnostic Message: "Meta description is missing from server-rendered HTML response."
- Target Field:
-
Trigger Rule 3: Empty Title Value
- Target Field:
metadata_ssr_issue - Evaluation Logic:
raw_html_has_title_tag = TRUE AND title_length = 0 - Severity: CRITICAL
- Diagnostic Message: "Title tag exists but contains no meaningful text in SSR HTML."
- Target Field:
-
Trigger Rule 4: Empty Meta Description Value
- Target Field:
metadata_ssr_issue - Evaluation Logic:
raw_html_has_meta_description = TRUE AND meta_description_length = 0 - Severity: CRITICAL
- Diagnostic Message: "Meta description exists but content is empty in SSR HTML."
- Target Field:
-
Trigger Rule 5: Duplicate Meta Description Tags
- Target Field:
metadata_ssr_issue - Evaluation Logic:
meta_description_tag_count > 1 - Severity: WARNING
- Diagnostic Message: "Multiple meta description tags detected; crawlers may interpret conflicting snippet signals."
- Target Field:
-
Trigger Rule 6: Metadata Outside Head
- Target Field:
metadata_ssr_issue - Evaluation Logic:
meta_in_head_section = FALSE AND (raw_html_has_title_tag = TRUE OR raw_html_has_meta_description = TRUE) - Severity: WARNING
- Diagnostic Message: "Metadata found outside head section; crawler processing reliability may be reduced."
- Target Field:
-
Trigger Rule 7: Final Issue State
- Target Field:
metadata_ssr_issue - Evaluation Logic:
metadata_ssr_issue = TRUE - Severity: CRITICAL
- Diagnostic Message: "Title/meta are not reliably available in server-rendered HTML and may be missed by crawlers."
- Target Field:
Sources
- Google Search Central: Control your title links in search results: https://developers.google.com/search/docs/appearance/title-link
- Google Search Central: Snippet controls (meta description guidance): https://developers.google.com/search/docs/appearance/snippet
- Google Search Central: JavaScript SEO basics: https://developers.google.com/search/docs/crawling-indexing/javascript/javascript-seo-basics
- HTML Living Standard (Document metadata): https://html.spec.whatwg.org/multipage/semantics.html#the-head-element
- RFC 9110 HTTP Semantics: https://www.rfc-editor.org/rfc/rfc9110
Long description
Title and meta description are core metadata signals used by search engines for document understanding and snippet generation. If these values are absent from raw server-rendered HTML and appear only after client-side JavaScript execution, crawler reliability drops, especially under resource limits, deferred execution, or partial rendering conditions.
This audit evaluates only what is present in the direct HTML response body delivered by the server after redirects. That makes the result deterministic for crawler-visible SSR output and avoids false confidence from browser-only DOM states.
When metadata is unstable, missing, duplicated, or misplaced, indexing systems may generate poor snippets, reduce relevance confidence, or select fallback text from page body content that is less representative.
Common failure scenarios checked by the crawler:
- Metadata is injected only in client hydration and not present in initial HTML.
- Title exists but is empty or whitespace-only in SSR output.
- Meta description tag exists with empty content.
- Multiple meta description tags create conflicting signals.
- Metadata is incorrectly emitted outside head region due to template defects.
- Non-HTML responses are returned for crawlable URLs because of routing or edge misconfiguration.
How to Fix
- Ensure title and meta description are emitted directly in server-rendered HTML for every indexable page.
- Keep exactly one meaningful meta description per page and avoid duplicate conflicting tags.
- Validate template/layout pipelines so metadata is placed inside the head section.
- Avoid relying on client-side JavaScript to inject essential metadata.
- Add CI checks that fetch raw HTML and assert title and meta description presence and non-empty values.
- Re-crawl affected URLs and confirm issue recovery with metadata present in raw SSR HTML.