fix(nx-dev): OG image meta tag (#27195)
This commit is contained in:
parent
adbb861d8c
commit
edf065115b
@ -1,5 +1,5 @@
|
|||||||
import { readFileSync, readdirSync } from 'fs';
|
import { readFileSync, readdirSync, accessSync, constants } from 'fs';
|
||||||
import { join, basename } from 'path';
|
import { join, basename, parse, resolve } from 'path';
|
||||||
import { extractFrontmatter } from '@nx/nx-dev/ui-markdoc';
|
import { extractFrontmatter } from '@nx/nx-dev/ui-markdoc';
|
||||||
import { sortPosts } from './blog.util';
|
import { sortPosts } from './blog.util';
|
||||||
import { BlogPostDataEntry } from './blog.model';
|
import { BlogPostDataEntry } from './blog.model';
|
||||||
@ -42,6 +42,8 @@ export class BlogApi {
|
|||||||
const content = await readFile(filePath, 'utf8');
|
const content = await readFile(filePath, 'utf8');
|
||||||
const frontmatter = extractFrontmatter(content);
|
const frontmatter = extractFrontmatter(content);
|
||||||
const slug = this.calculateSlug(filePath, frontmatter);
|
const slug = this.calculateSlug(filePath, frontmatter);
|
||||||
|
const { image, type } = this.determineOgImage(frontmatter.cover_image);
|
||||||
|
|
||||||
const post = {
|
const post = {
|
||||||
content,
|
content,
|
||||||
title: frontmatter.title ?? null,
|
title: frontmatter.title ?? null,
|
||||||
@ -56,6 +58,8 @@ export class BlogApi {
|
|||||||
tags: frontmatter.tags ?? [],
|
tags: frontmatter.tags ?? [],
|
||||||
reposts: frontmatter.reposts ?? [],
|
reposts: frontmatter.reposts ?? [],
|
||||||
pinned: frontmatter.pinned ?? false,
|
pinned: frontmatter.pinned ?? false,
|
||||||
|
ogImage: image,
|
||||||
|
ogImageType: type,
|
||||||
filePath,
|
filePath,
|
||||||
slug,
|
slug,
|
||||||
};
|
};
|
||||||
@ -81,6 +85,7 @@ export class BlogApi {
|
|||||||
const content = readFileSync(filePath, 'utf8');
|
const content = readFileSync(filePath, 'utf8');
|
||||||
const frontmatter = extractFrontmatter(content);
|
const frontmatter = extractFrontmatter(content);
|
||||||
const slug = this.calculateSlug(filePath, frontmatter);
|
const slug = this.calculateSlug(filePath, frontmatter);
|
||||||
|
const { image, type } = this.determineOgImage(frontmatter.cover_image);
|
||||||
const post = {
|
const post = {
|
||||||
content,
|
content,
|
||||||
title: frontmatter.title ?? null,
|
title: frontmatter.title ?? null,
|
||||||
@ -95,6 +100,8 @@ export class BlogApi {
|
|||||||
tags: frontmatter.tags ?? [],
|
tags: frontmatter.tags ?? [],
|
||||||
reposts: frontmatter.reposts ?? [],
|
reposts: frontmatter.reposts ?? [],
|
||||||
pinned: frontmatter.pinned ?? false,
|
pinned: frontmatter.pinned ?? false,
|
||||||
|
ogImage: image,
|
||||||
|
ogImageType: type,
|
||||||
filePath,
|
filePath,
|
||||||
slug,
|
slug,
|
||||||
};
|
};
|
||||||
@ -143,4 +150,50 @@ export class BlogApi {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fileExists(filePath: string): boolean {
|
||||||
|
try {
|
||||||
|
accessSync(filePath, constants.F_OK);
|
||||||
|
return true;
|
||||||
|
} catch (error) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private determineOgImage(imagePath: string): {
|
||||||
|
image: string;
|
||||||
|
type: string;
|
||||||
|
} {
|
||||||
|
const allowedExtensions = ['.png', '.webp', '.jpg', '.jpeg'];
|
||||||
|
const defaultImage = 'https://nx.dev/socials/nx-media.png';
|
||||||
|
const defaultType = 'png';
|
||||||
|
|
||||||
|
if (!imagePath) {
|
||||||
|
return { image: defaultImage, type: defaultType };
|
||||||
|
}
|
||||||
|
const { ext } = parse(imagePath);
|
||||||
|
|
||||||
|
if (!allowedExtensions.includes(ext)) {
|
||||||
|
const foundExt = allowedExtensions.find((allowedExt) => {
|
||||||
|
const ogImagePath = imagePath.replace(ext, allowedExt);
|
||||||
|
return this.fileExists(
|
||||||
|
join(
|
||||||
|
'public',
|
||||||
|
'documentation',
|
||||||
|
resolve(this.options.blogRoot, ogImagePath)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!foundExt) {
|
||||||
|
return { image: defaultImage, type: defaultType };
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
image: imagePath.replace(ext, foundExt),
|
||||||
|
type: foundExt.replace('.', ''),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return { image: imagePath, type: ext.replace('.', '') };
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -11,6 +11,8 @@ export type BlogPostDataEntry = {
|
|||||||
pinned?: boolean;
|
pinned?: boolean;
|
||||||
filePath: string;
|
filePath: string;
|
||||||
slug: string;
|
slug: string;
|
||||||
|
ogImage: string;
|
||||||
|
ogImageType: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export type BlogAuthor = {
|
export type BlogAuthor = {
|
||||||
|
|||||||
@ -62,6 +62,8 @@ function createPost(data: {
|
|||||||
title: data.title,
|
title: data.title,
|
||||||
description: '',
|
description: '',
|
||||||
authors: [],
|
authors: [],
|
||||||
|
ogImage: '',
|
||||||
|
ogImageType: '',
|
||||||
cover_image: '',
|
cover_image: '',
|
||||||
tags: [],
|
tags: [],
|
||||||
reposts: [],
|
reposts: [],
|
||||||
|
|||||||
@ -2,7 +2,7 @@ import type { Metadata, ResolvingMetadata } from 'next';
|
|||||||
import { blogApi } from '../../../lib/blog.api';
|
import { blogApi } from '../../../lib/blog.api';
|
||||||
import { BlogDetails } from '@nx/nx-dev/ui-blog';
|
import { BlogDetails } from '@nx/nx-dev/ui-blog';
|
||||||
import { DefaultLayout } from '@nx/nx-dev/ui-common';
|
import { DefaultLayout } from '@nx/nx-dev/ui-common';
|
||||||
import { parse } from 'path';
|
|
||||||
interface BlogPostDetailProps {
|
interface BlogPostDetailProps {
|
||||||
params: { slug: string };
|
params: { slug: string };
|
||||||
}
|
}
|
||||||
@ -14,9 +14,6 @@ export async function generateMetadata(
|
|||||||
const post = await blogApi.getBlogPostBySlug(slug);
|
const post = await blogApi.getBlogPostBySlug(slug);
|
||||||
const previousImages = (await parent).openGraph?.images ?? [];
|
const previousImages = (await parent).openGraph?.images ?? [];
|
||||||
|
|
||||||
const postCoverImage = post?.cover_image || 'nx-media';
|
|
||||||
const ogImage = `${parse(postCoverImage).name}.png`;
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
title: `${post.title} | Nx Blog`,
|
title: `${post.title} | Nx Blog`,
|
||||||
description: 'Latest news from the Nx & Nx Cloud core team',
|
description: 'Latest news from the Nx & Nx Cloud core team',
|
||||||
@ -26,11 +23,11 @@ export async function generateMetadata(
|
|||||||
description: post.description,
|
description: post.description,
|
||||||
images: [
|
images: [
|
||||||
{
|
{
|
||||||
url: ogImage,
|
url: post.ogImage,
|
||||||
width: 800,
|
width: 800,
|
||||||
height: 421,
|
height: 421,
|
||||||
alt: 'Nx: Smart, Fast and Extensible Build System',
|
alt: 'Nx: Smart, Fast and Extensible Build System',
|
||||||
type: 'image/png',
|
type: `image/${post.ogImageType}`,
|
||||||
},
|
},
|
||||||
...previousImages,
|
...previousImages,
|
||||||
],
|
],
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user