From ce57e48fec78c13d458bba703ab5447a58b16453 Mon Sep 17 00:00:00 2001 From: Malte2036 Date: Wed, 22 Jan 2025 12:16:01 +0100 Subject: [PATCH] :sparkles: Implement structured JSON-LD data for QuizHead, FAQ, and Quiz listing pages to enhance SEO and accessibility. Update metadata generation with dynamic content and improve question answer formatting for better clarity. This refactor ensures consistent structured data across the application. --- src/lib/quiz/QuizHead.svelte | 55 ++++++++++++++++++- src/routes/(main)/faq/+page.svelte | 11 +--- .../(main)/quiz/[type]/listing/+page.svelte | 38 +++++++++++++ 3 files changed, 95 insertions(+), 9 deletions(-) diff --git a/src/lib/quiz/QuizHead.svelte b/src/lib/quiz/QuizHead.svelte index c8fb8ff..6c00af2 100644 --- a/src/lib/quiz/QuizHead.svelte +++ b/src/lib/quiz/QuizHead.svelte @@ -1,5 +1,6 @@ @@ -71,4 +121,7 @@ name="keywords" content="THW, THW Prüfungsfragen, Grundausbildung, Atemschutz, CBRN, Sprechfunk, Online-Quiz, Theorie-Quiz, Prüfung, THW-Tools, Feuerwehr, Ausbildung, Training" /> + {#if jsonLd} + {@html ``} + {/if} diff --git a/src/routes/(main)/faq/+page.svelte b/src/routes/(main)/faq/+page.svelte index 3c77cad..0d82e10 100644 --- a/src/routes/(main)/faq/+page.svelte +++ b/src/routes/(main)/faq/+page.svelte @@ -6,6 +6,7 @@ import InstallPwaDialog from '$lib/InstallPWADialog.svelte'; import FeedbackDialog from '$lib/FeedbackDialog.svelte'; import { version } from '$app/environment'; + import { formatDate } from '$lib/utils'; export let data: PageData; @@ -20,20 +21,14 @@ $: jsonLd = { '@context': 'https://schema.org', '@type': 'FAQPage', - name: 'THW-Tools FAQ', - description: - 'Häufig gestellte Fragen zu THW-Tools: Prüfungsfragen, Finnentest, Spannungsfall und mehr', - url: 'https://thw-tools.de/faq', inLanguage: 'de', - dateModified: version, + dateModified: new Date(+version).toISOString().split('T')[0], mainEntity: data.faqs.map((faq) => ({ '@type': 'Question', name: faq.question, acceptedAnswer: { '@type': 'Answer', - text: faq.text.replace(/\{\{link\}\}/g, ''), - url: - 'https://thw-tools.de/faq#faq-' + faq.question.toLowerCase().replace(/[^a-z0-9]+/g, '-') + text: faq.text.replace(/\{\{link\}\}/g, '') } })), publisher: { diff --git a/src/routes/(main)/quiz/[type]/listing/+page.svelte b/src/routes/(main)/quiz/[type]/listing/+page.svelte index f5c1707..c65a916 100644 --- a/src/routes/(main)/quiz/[type]/listing/+page.svelte +++ b/src/routes/(main)/quiz/[type]/listing/+page.svelte @@ -8,6 +8,7 @@ import QuestionsStatistics from '$lib/quiz/question/QuestionsStatistics.svelte'; import { getQuestionStatsCountForType } from '$lib/api/api'; import { getQuizTypeName } from '$lib/quiz/quizUtils'; + import { version } from '$app/environment'; export let data: PageData; @@ -41,10 +42,47 @@ return `Das Quiz besteht aus ${count} Fragen für die Ausbildung im Technischen Hilfswerk.`; } } + + $: jsonLd = { + '@context': 'https://schema.org', + '@type': 'ItemList', + name: getQuizTypeName(data.questionType), + description: getDescriptionForQuestionType(data.questionType), + inLanguage: 'de', + dateModified: new Date(+version).toISOString(), + numberOfItems: data.allQuestions.length, + itemListElement: data.allQuestions + .slice(0, 50) // Limit to first 50 items for better performance + .map((question, index) => ({ + '@type': 'ListItem', + position: index + 1, + url: `https://thw-tools.de/quiz/${data.questionType}/${question.number}` + })), + about: { + '@type': 'Thing', + name: getQuizTypeName(data.questionType), + description: getDescriptionForQuestionType(data.questionType) + }, + publisher: { + '@type': 'Organization', + name: 'THW-Tools', + url: 'https://thw-tools.de', + logo: { + '@type': 'ImageObject', + url: 'https://thw-tools.de/_app/immutable/assets/thw-mzgw.24176eee.webp', + width: '512', + height: '512' + } + } + }; + + {@html ``} + +

{getQuizTypeName(data.questionType)}