computer-scienceangular-roadmapbackend-roadmapblockchain-roadmapdba-roadmapdeveloper-roadmapdevops-roadmapfrontend-roadmapgo-roadmaphactoberfestjava-roadmapjavascript-roadmapnodejs-roadmappython-roadmapqa-roadmapreact-roadmaproadmapstudy-planvue-roadmapweb3-roadmap
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
131 lines
3.7 KiB
131 lines
3.7 KiB
--- |
|
import FAQs, { type FAQType } from '../../components/FAQs/FAQs.astro'; |
|
import FrameRenderer from '../../components/FrameRenderer/FrameRenderer.astro'; |
|
import RelatedRoadmaps from '../../components/RelatedRoadmaps.astro'; |
|
import RoadmapHeader from '../../components/RoadmapHeader.astro'; |
|
import ShareIcons from '../../components/ShareIcons/ShareIcons.astro'; |
|
import { TopicDetail } from '../../components/TopicDetail/TopicDetail'; |
|
import UpcomingForm from '../../components/UpcomingForm.astro'; |
|
import { UserProgressModal } from '../../components/UserProgress/UserProgressModal'; |
|
import BaseLayout from '../../layouts/BaseLayout.astro'; |
|
import { |
|
generateArticleSchema, |
|
generateFAQSchema, |
|
} from '../../lib/jsonld-schema'; |
|
import { getOpenGraphImageUrl } from '../../lib/open-graph'; |
|
import { type RoadmapFrontmatter, getRoadmapIds } from '../../lib/roadmap'; |
|
|
|
export async function getStaticPaths() { |
|
const roadmapIds = await getRoadmapIds(); |
|
|
|
return roadmapIds.map((roadmapId) => ({ |
|
params: { roadmapId }, |
|
})); |
|
} |
|
|
|
interface Params extends Record<string, string | undefined> { |
|
roadmapId: string; |
|
} |
|
|
|
const { roadmapId } = Astro.params as Params; |
|
const roadmapFile = await import( |
|
`../../data/roadmaps/${roadmapId}/${roadmapId}.md` |
|
); |
|
const { faqs: roadmapFAQs = [] } = await import( |
|
`../../data/roadmaps/${roadmapId}/faqs.astro` |
|
); |
|
const roadmapData = roadmapFile.frontmatter as RoadmapFrontmatter; |
|
|
|
let jsonLdSchema = []; |
|
|
|
if (roadmapData.schema) { |
|
const roadmapSchema = roadmapData.schema; |
|
jsonLdSchema.push( |
|
generateArticleSchema({ |
|
url: `https://roadmap.sh/${roadmapId}`, |
|
headline: roadmapSchema.headline, |
|
description: roadmapSchema.description, |
|
datePublished: roadmapSchema.datePublished, |
|
dateModified: roadmapSchema.dateModified, |
|
imageUrl: roadmapSchema.imageUrl, |
|
}), |
|
); |
|
} |
|
|
|
if (roadmapFAQs.length) { |
|
jsonLdSchema.push(generateFAQSchema(roadmapFAQs as unknown as FAQType[])); |
|
} |
|
|
|
const ogImageUrl = |
|
roadmapData?.seo?.ogImageUrl || |
|
getOpenGraphImageUrl({ |
|
group: 'roadmaps', |
|
resourceId: roadmapId, |
|
}); |
|
--- |
|
|
|
<BaseLayout |
|
permalink={`/${roadmapId}`} |
|
title={roadmapData?.seo?.title} |
|
briefTitle={roadmapData.briefTitle} |
|
ogImageUrl={ogImageUrl} |
|
description={roadmapData.seo.description} |
|
keywords={roadmapData.seo.keywords} |
|
noIndex={roadmapData.isUpcoming} |
|
jsonLd={jsonLdSchema} |
|
resourceId={roadmapId} |
|
resourceType='roadmap' |
|
> |
|
<!-- Preload the font being used in the renderer --> |
|
<link |
|
rel='preload' |
|
href='/fonts/balsamiq.woff2' |
|
as='font' |
|
type='font/woff2' |
|
crossorigin |
|
slot='after-header' |
|
/> |
|
|
|
<RoadmapHeader |
|
title={roadmapData.title} |
|
description={roadmapData.description} |
|
note={roadmapData.note} |
|
tnsBannerLink={roadmapData.tnsBannerLink} |
|
roadmapId={roadmapId} |
|
hasTopics={roadmapData.hasTopics} |
|
isUpcoming={roadmapData.isUpcoming} |
|
isForkable={roadmapData.isForkable} |
|
question={roadmapData.question} |
|
/> |
|
|
|
<div class='bg-gray-50 pt-4 sm:pt-12'> |
|
{ |
|
!roadmapData.isUpcoming && ( |
|
<div class='container relative !max-w-[1000px]'> |
|
<ShareIcons |
|
description={roadmapData.briefDescription} |
|
pageUrl={`https://roadmap.sh/${roadmapId}`} |
|
/> |
|
<TopicDetail client:idle canSubmitContribution={true} /> |
|
|
|
<FrameRenderer |
|
resourceType={'roadmap'} |
|
resourceId={roadmapId} |
|
dimensions={roadmapData.dimensions} |
|
/> |
|
</div> |
|
) |
|
} |
|
|
|
{roadmapData.isUpcoming && <UpcomingForm />} |
|
<UserProgressModal |
|
resourceId={roadmapId} |
|
resourceType='roadmap' |
|
client:only='react' |
|
/> |
|
|
|
<FAQs faqs={roadmapFAQs as unknown as FAQType[]} /> |
|
|
|
<RelatedRoadmaps roadmap={roadmapData} /> |
|
</div> |
|
</BaseLayout>
|
|
|