nextui/apps/docs/libs/contentlayer.ts
աӄա 765dac53cf
refactor(docs): dx improvement in accordion (#3856)
* refactor: improve dx for writing a docs component (#2544)

* refactor: improve dx for write a docs component

Signed-off-by: Innei <i@innei.in>

* refactor(docs): switch to contentlayer2

* chore(docs): rename to avoid conflict

* refactor(docs): switch to next-contentlayer2

* refactor(docs): revise docs lib

* chore(deps): bump docs related dependencies

* fix(use-aria-multiselect): type issue due to ts version bump

---------

Signed-off-by: Innei <i@innei.in>
Co-authored-by: WK Wong <wingkwong.code@gmail.com>

* refactor(docs): accordion codes

* feat(docs): declare module `*.jsx?raw`

* feat(docs): include `**/*.jsx`

* fix(docs): incorrect content

* chore(docs): add new lines

* refactor(docs): lint

---------

Signed-off-by: Innei <i@innei.in>
Co-authored-by: Innei <tukon479@gmail.com>
2024-10-20 00:54:13 +08:00

104 lines
2.5 KiB
TypeScript

import type {Document, MDX} from "contentlayer2/core";
import {slug} from "github-slugger";
export type MDXDocument = Document & {body: MDX};
export type MDXDocumentDate = MDXDocument & {
date: string;
};
export type MDXBlog = MDXDocumentDate & {
tags?: string[];
draft?: boolean;
};
export type MDXAuthor = MDXDocument & {
name: string;
};
export function dateSortDesc(a: string, b: string) {
if (a > b) return -1;
if (a < b) return 1;
return 0;
}
export function sortedBlogPost(allBlogs: MDXDocumentDate[]) {
return allBlogs.sort((a, b) => dateSortDesc(a.date, b.date));
}
type ConvertUndefined<T> = OrNull<{
[K in keyof T as undefined extends T[K] ? K : never]-?: T[K];
}>;
type OrNull<T> = {[K in keyof T]: Exclude<T[K], undefined> | null};
type PickRequired<T> = {
[K in keyof T as undefined extends T[K] ? never : K]: T[K];
};
type ConvertPick<T> = ConvertUndefined<T> & PickRequired<T>;
/**
* A typesafe omit helper function
* @example pick(content, ['title', 'description'])
*
* @param {Obj} obj
* @param {Keys[]} keys
* @return {*} {ConvertPick<{ [K in Keys]: Obj[K] }>}
*/
export const pick = <Obj, Keys extends keyof Obj>(
obj: Obj,
keys: Keys[],
): ConvertPick<{[K in Keys]: Obj[K]}> => {
return keys.reduce((acc, key) => {
acc[key] = obj[key] ?? null;
return acc;
}, {} as any);
};
/**
* A typesafe omit helper function
* @example omit(content, ['body', '_raw', '_id'])
*
* @param {Obj} obj
* @param {Keys[]} keys
* @return {*} {Omit<Obj, Keys>}
*/
export const omit = <Obj, Keys extends keyof Obj>(obj: Obj, keys: Keys[]): Omit<Obj, Keys> => {
const result = Object.assign({}, obj);
keys.forEach((key) => {
delete result[key];
});
return result;
};
export type CoreContent<T> = Omit<T, "body" | "_raw" | "_id">;
export function coreContent<T extends MDXDocument>(content: T) {
return omit(content, ["body", "_raw", "_id"]);
}
export function allCoreContent<T extends MDXDocument>(contents: T[]) {
return contents.map((c) => coreContent(c)).filter((c) => !("draft" in c && c.draft === true));
}
export async function getAllTags(allBlogs: MDXBlog[]) {
const tagCount: Record<string, number> = {};
allBlogs.forEach((file) => {
if (file.tags && file.draft !== true) {
file.tags.forEach((tag) => {
const formattedTag = slug(tag);
if (formattedTag in tagCount) {
tagCount[formattedTag] += 1;
} else {
tagCount[formattedTag] = 1;
}
});
}
});
return tagCount;
}