Skip to content

proxima812/Astro-ts-mastery

Folders and files

NameName
Last commit message
Last commit date

Latest commit

ย 

History

5 Commits
ย 
ย 

Repository files navigation

import { getCollection, type CollectionEntry } from "astro:content"; import GithubSlugger from "github-slugger"; import slugify from "slugify"; import { marked } from "marked";

/* --------------------------------- slug --------------------------------- */

const RU_REGEX = /[ะฐ-ัั‘]/i; const slugger = new GithubSlugger();

export const customSlugify = (value = ""): string => { if (!value) return "";

if (RU_REGEX.test(value)) { return slugify(value, { lower: true, strict: true, locale: "ru", trim: true, }); }

return slugger.slug(value); };

/* ------------------------------ collections ------------------------------ */

export const getSinglePage = async ( collection: string ): Promise<CollectionEntry[]> => { const pages = await getCollection(collection);

return pages.filter( (p) => !p.data?.draft && !p.id.startsWith("-") ); };

export const getTaxonomy = async ( collection: string, field: string ): Promise<string[]> => { const pages = await getSinglePage(collection);

return [ ...new Set( pages .flatMap((p) => p.data?.[field] ?? []) .filter(Boolean) .map(customSlugify) ), ]; };

/* -------------------------------- markdown ------------------------------- */

export const markdownify = (content = ""): string => { if (!content) return ""; return marked.parseInline(content); };

/* -------------------------------- humanize ------------------------------- */

export const humanize = (value = ""): string => { if (!value) return "";

const cleaned = value .trim() .replace(/[_\s]+/g, " ");

return cleaned.charAt(0).toUpperCase() + cleaned.slice(1); };

/* -------------------------------- plainify ------------------------------- */

export const plainify = (html = ""): string => { if (!html) return "";

const text = html .replace(/</?[^>]+>/g, "") .replace(/\s+/g, " ") .trim();

return decodeHTMLEntities(text); };

const decodeHTMLEntities = (str: string): string => str.replace( /&(nbsp|amp|lt|gt|quot|#39);/g, (m) => ({ "ย ": " ", "&": "&", "<": "<", ">": ">", """: '"', "'": "'", } as Record<string, string>)[m] ?? m );

/* ------------------------------ reading time ------------------------------ */

const WORDS_PER_MINUTE = 275;

const readingTime = (content = "", locale: "en" | "ru" = "en"): string => { if (!content) return "0 min";

const words = content.match(/\p{L}+/gu)?.length ?? 0; const images = (content.match(/<img\b/gi) ?? []).length;

const imageSeconds = images ? images * 3 + Math.min(images, 10) * 1 : 0;

const minutes = Math.max( 1, Math.ceil(words / WORDS_PER_MINUTE + imageSeconds / 60) );

if (locale === "ru") { return ${minutes} ะผะธะฝ ั‡ั‚ะตะฝะธั; }

return ${minutes} min read; };

export default readingTime;

About

๐Ÿš€ utils and libs for Astro.js projects.

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors