Merge branch 'master' into feat/open-graph

feat/open-graph
Kamran Ahmed 8 months ago committed by GitHub
commit a7238171fa
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
  1. 3
      src/data/authors/kamran.md
  2. 2
      src/data/roadmaps/sql/content/107-sub-queries/index.md
  3. 2
      src/data/roadmaps/typescript/content/101-typescript-types/104-undefined.md
  4. 5
      src/layouts/BaseLayout.astro
  5. 4
      src/lib/author.ts
  6. 45
      src/pages/authors/[authorId].astro

@ -1,6 +1,9 @@
--- ---
name: 'Kamran Ahmed' name: 'Kamran Ahmed'
imageUrl: '/authors/kamran.jpeg' imageUrl: '/authors/kamran.jpeg'
employment:
title: 'Founder'
company: 'roadmap.sh'
social: social:
linkedin: 'https://www.linkedin.com/in/kamrify' linkedin: 'https://www.linkedin.com/in/kamrify'
twitter: 'https://twitter.com/kamrify' twitter: 'https://twitter.com/kamrify'

@ -33,7 +33,7 @@ WHERE column_name OPERATOR
WHERE roll_id = (SELECT roll_id FROM student WHERE name='John'); WHERE roll_id = (SELECT roll_id FROM student WHERE name='John');
``` ```
2. **Row subquery**: It returns single row of two or more values. 2. **Row subquery**: It returns a single row or multiple rows of two or more values.
```sql ```sql
SELECT * FROM student SELECT * FROM student

@ -1,6 +1,6 @@
# undefined # undefined
JavaScript has two primitive values used to signal absent or uninitialized value: `null` (absent) and `undefined` (unintialized). JavaScript has two primitive values used to signal absent or uninitialized value: `null` (absent) and `undefined` (uninitialized).
TypeScript has two corresponding _types_ by the same names. How these types behave depends on whether you have the `strictNullChecks` option on. TypeScript has two corresponding _types_ by the same names. How these types behave depends on whether you have the `strictNullChecks` option on.

@ -145,7 +145,10 @@ const gaPageIdentifier = Astro.url.pathname
<slot name='after-header' /> <slot name='after-header' />
{ {
jsonLd.length > 0 && ( jsonLd.length > 0 && (
<script type='application/ld+json' set:html={JSON.stringify(jsonLd)} /> <script
type='application/ld+json'
set:html={JSON.stringify(jsonLd.length === 1 ? jsonLd[0] : jsonLd)}
/>
) )
} }
</head> </head>

@ -3,6 +3,10 @@ import type { MarkdownFileType } from './file';
export interface AuthorFrontmatter { export interface AuthorFrontmatter {
name: string; name: string;
imageUrl: string; imageUrl: string;
employment?: {
title: string;
company: string;
};
social: { social: {
twitter: string; twitter: string;
github: string; github: string;

@ -20,6 +20,8 @@ export async function getStaticPaths() {
const { authorId } = Astro.params; const { authorId } = Astro.params;
const author = await getAuthorById(authorId); const author = await getAuthorById(authorId);
const authorFrontmatter = author.frontmatter;
const guides = await getGuidesByAuthor(authorId); const guides = await getGuidesByAuthor(authorId);
const videos = await getVideosByAuthor(authorId); const videos = await getVideosByAuthor(authorId);
--- ---
@ -28,16 +30,37 @@ const videos = await getVideosByAuthor(authorId);
permalink={`/author/${author.id}`} permalink={`/author/${author.id}`}
title={`${author.frontmatter.name} - Author at roadmap.sh`} title={`${author.frontmatter.name} - Author at roadmap.sh`}
briefTitle={author.frontmatter.name} briefTitle={author.frontmatter.name}
ogImageUrl={`https://roadmap.sh/${author.frontmatter.imageUrl}`} ogImageUrl={`https://roadmap.sh/${authorFrontmatter.imageUrl}`}
description={`${author.frontmatter.name} has written ${guides.length} articles on roadmap.sh on a variety of topics.`} description={`${author.frontmatter.name} has written ${guides.length} articles on roadmap.sh on a variety of topics.`}
noIndex={false} noIndex={false}
jsonLd={[
{
'@context': 'https://schema.org/',
'@type': 'Person',
name: authorFrontmatter.name,
url: `https://roadmap.sh/authors/${authorId}`,
image: authorFrontmatter.imageUrl.startsWith('http')
? authorFrontmatter.imageUrl
: `https://roadmap.sh${authorFrontmatter.imageUrl}`,
sameAs: authorFrontmatter.social
? Object.values(authorFrontmatter.social)
: [],
...(authorFrontmatter.employment && {
jobTitle: authorFrontmatter.employment?.title,
worksFor: {
'@type': 'Organization',
name: authorFrontmatter.employment.company,
},
}),
},
]}
> >
<div class='container pb-0 pt-4 md:pb-16 md:pt-8'> <div class='container pb-0 pt-4 md:pb-16 md:pt-8'>
<div class=''> <div class=''>
<div class='mb-5 flex items-center gap-8 rounded-3xl py-0 md:py-8'> <div class='mb-5 flex items-center gap-8 rounded-3xl py-0 md:py-8'>
<div class='flex-grow'> <div class='flex-grow'>
<h1 class='text-2xl font-bold md:text-3xl'> <h1 class='text-2xl font-bold md:text-3xl'>
{author.frontmatter.name} {authorFrontmatter.name}
</h1> </h1>
<div <div
class='mb-4 mt-1 flex flex-col gap-3 leading-normal text-gray-800 md:mb-6 md:mt-4 [&>p>a]:font-semibold [&>p>a]:underline' class='mb-4 mt-1 flex flex-col gap-3 leading-normal text-gray-800 md:mb-6 md:mt-4 [&>p>a]:font-semibold [&>p>a]:underline'
@ -48,9 +71,9 @@ const videos = await getVideosByAuthor(authorId);
<div class='flex items-center justify-between'> <div class='flex items-center justify-between'>
<div class='flex items-center gap-1.5'> <div class='flex items-center gap-1.5'>
{ {
author.frontmatter.social?.github && ( authorFrontmatter.social?.github && (
<a <a
href={author.frontmatter.social.github} href={authorFrontmatter.social.github}
target='_blank' target='_blank'
class='text-gray-500 transition-colors hover:text-gray-800' class='text-gray-500 transition-colors hover:text-gray-800'
> >
@ -59,9 +82,9 @@ const videos = await getVideosByAuthor(authorId);
) )
} }
{ {
author.frontmatter.social.twitter && ( authorFrontmatter.social.twitter && (
<a <a
href={author.frontmatter.social.twitter} href={authorFrontmatter.social.twitter}
target='_blank' target='_blank'
class='text-gray-500 transition-colors hover:text-gray-800' class='text-gray-500 transition-colors hover:text-gray-800'
> >
@ -70,9 +93,9 @@ const videos = await getVideosByAuthor(authorId);
) )
} }
{ {
author.frontmatter.social.linkedin && ( authorFrontmatter.social.linkedin && (
<a <a
href={author.frontmatter.social.linkedin} href={authorFrontmatter.social.linkedin}
target='_blank' target='_blank'
class='text-gray-500 transition-colors hover:text-gray-800' class='text-gray-500 transition-colors hover:text-gray-800'
> >
@ -81,9 +104,9 @@ const videos = await getVideosByAuthor(authorId);
) )
} }
{ {
author.frontmatter.social.website && ( authorFrontmatter.social.website && (
<a <a
href={author.frontmatter.social.website} href={authorFrontmatter.social.website}
target='_blank' target='_blank'
class='text-gray-500 transition-colors hover:text-gray-800' class='text-gray-500 transition-colors hover:text-gray-800'
> >
@ -98,7 +121,7 @@ const videos = await getVideosByAuthor(authorId);
<img <img
alt="Kamran Ahmed's profile picture" alt="Kamran Ahmed's profile picture"
class='block h-[175px] w-[175px] rounded-full bg-gray-100' class='block h-[175px] w-[175px] rounded-full bg-gray-100'
src={author.frontmatter.imageUrl} src={authorFrontmatter.imageUrl}
/> />
</div> </div>
</div> </div>

Loading…
Cancel
Save