From b73865ddaee63c35a6df3118a08981337c85f847 Mon Sep 17 00:00:00 2001 From: Orion Reed Date: Sun, 13 Aug 2023 14:25:39 +0100 Subject: [PATCH] removed grey-matter dependency --- .github/workflows/deploy.yml | 51 ------- deps/gray-matter/gray-matter.d.ts | 104 --------------- deps/gray-matter/index.js | 213 ------------------------------ deps/gray-matter/lib/defaults.js | 16 --- deps/gray-matter/lib/engine.js | 28 ---- deps/gray-matter/lib/engines.js | 53 -------- deps/gray-matter/lib/excerpt.js | 30 ----- deps/gray-matter/lib/parse.js | 12 -- deps/gray-matter/lib/stringify.js | 55 -------- deps/gray-matter/lib/to-file.js | 41 ------ deps/gray-matter/lib/utils.js | 47 ------- deps/gray-matter/package.json | 78 ----------- package.json | 1 - src/pages/Post.tsx | 18 +-- 14 files changed, 10 insertions(+), 737 deletions(-) delete mode 100644 .github/workflows/deploy.yml delete mode 100644 deps/gray-matter/gray-matter.d.ts delete mode 100644 deps/gray-matter/index.js delete mode 100644 deps/gray-matter/lib/defaults.js delete mode 100644 deps/gray-matter/lib/engine.js delete mode 100644 deps/gray-matter/lib/engines.js delete mode 100644 deps/gray-matter/lib/excerpt.js delete mode 100644 deps/gray-matter/lib/parse.js delete mode 100644 deps/gray-matter/lib/stringify.js delete mode 100644 deps/gray-matter/lib/to-file.js delete mode 100644 deps/gray-matter/lib/utils.js delete mode 100644 deps/gray-matter/package.json diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml deleted file mode 100644 index 3fba226..0000000 --- a/.github/workflows/deploy.yml +++ /dev/null @@ -1,51 +0,0 @@ -# Simple workflow for deploying static content to GitHub Pages -name: Deploy to Pages - -on: - # Runs on pushes targeting the default branch - push: - branches: ['main'] - - # Allows you to run this workflow manually from the Actions tab - workflow_dispatch: - -# Sets the GITHUB_TOKEN permissions to allow deployment to GitHub Pages -permissions: - contents: read - pages: write - id-token: write - -# Allow one concurrent deployment -concurrency: - group: 'pages' - cancel-in-progress: true - -jobs: - # Single deploy job since we're just deploying - deploy: - environment: - name: github-pages - url: ${{ steps.deployment.outputs.page_url }} - runs-on: ubuntu-latest - steps: - - name: Checkout - uses: actions/checkout@v3 - - name: Set up Node - uses: actions/setup-node@v3 - with: - node-version: 18 - cache: 'npm' - - name: Install dependencies - run: npm install - - name: Build - run: npm run build - - name: Setup Pages - uses: actions/configure-pages@v3 - - name: Upload artifact - uses: actions/upload-pages-artifact@v1 - with: - # Upload dist repository - path: './dist' - - name: Deploy to GitHub Pages - id: deployment - uses: actions/deploy-pages@v1 diff --git a/deps/gray-matter/gray-matter.d.ts b/deps/gray-matter/gray-matter.d.ts deleted file mode 100644 index 0b28e94..0000000 --- a/deps/gray-matter/gray-matter.d.ts +++ /dev/null @@ -1,104 +0,0 @@ -/** - * Takes a string or object with `content` property, extracts - * and parses front-matter from the string, then returns an object - * with `data`, `content` and other [useful properties](#returned-object). - * - * @param {Object|String} `input` String, or object with `content` string - * @param {Object} `options` - * @return {Object} - * @api public - */ -declare function matter< - I extends matter.Input, - O extends matter.GrayMatterOption, ->(input: I | { content: I }, options?: O): matter.GrayMatterFile - -declare namespace matter { - type Input = string - interface GrayMatterOption< - I extends Input, - O extends GrayMatterOption, - > { - parser?: () => void - eval?: boolean - excerpt?: boolean | ((input: I, options: O) => string) - excerpt_separator?: string - engines?: { - [index: string]: - | ((input: string) => object) - | { - parse: (input: string) => object - stringify?: (data: object) => string - } - } - language?: string - delimiters?: string | [string, string] - } - interface GrayMatterFile { - data: { [key: string]: any } - content: string - excerpt?: string - orig: I - language: string - matter: string - stringify(lang: string): string - } - - /** - * Stringify an object to YAML or the specified language, and - * append it to the given string. By default, only YAML and JSON - * can be stringified. See the [engines](#engines) section to learn - * how to stringify other languages. - * - * @param {String|Object} `file` The content string to append to stringified front-matter, or a file object with `file.content` string. - * @param {Object} `data` Front matter to stringify. - * @param {Object} `options` [Options](#options) to pass to gray-matter and [js-yaml]. - * @return {String} Returns a string created by wrapping stringified yaml with delimiters, and appending that to the given string. - */ - export function stringify>( - file: string | { content: string }, - data: object, - options?: GrayMatterOption, - ): string - - /** - * Synchronously read a file from the file system and parse - * front matter. Returns the same object as the [main function](#matter). - * - * ```js - * var file = matter.read('./content/blog-post.md'); - * ``` - * @param {String} `filepath` file path of the file to read. - * @param {Object} `options` [Options](#options) to pass to gray-matter. - * @return {Object} Returns [an object](#returned-object) with `data` and `content` - */ - export function read>( - fp: string, - options?: GrayMatterOption, - ): matter.GrayMatterFile - - /** - * Returns true if the given `string` has front matter. - * @param {String} `string` - * @param {Object} `options` - * @return {Boolean} True if front matter exists. - */ - export function test>( - str: string, - options?: GrayMatterOption, - ): boolean - - /** - * Detect the language to use, if one is defined after the - * first front-matter delimiter. - * @param {String} `string` - * @param {Object} `options` - * @return {Object} Object with `raw` (actual language string), and `name`, the language with whitespace trimmed - */ - export function language>( - str: string, - options?: GrayMatterOption, - ): { name: string; raw: string } -} - -export = matter diff --git a/deps/gray-matter/index.js b/deps/gray-matter/index.js deleted file mode 100644 index 3ce3a1f..0000000 --- a/deps/gray-matter/index.js +++ /dev/null @@ -1,213 +0,0 @@ -import fs from 'fs'; -import sections from 'section-matter'; -import defaults from './lib/defaults'; -import stringify from './lib/stringify'; -import excerpt from './lib/excerpt'; -import engines from './lib/engines'; -import toFile from './lib/to-file'; -import parse from './lib/parse'; -import * as utils from './lib/utils'; - - -/** - * Takes a string or object with `content` property, extracts - * and parses front-matter from the string, then returns an object - * with `data`, `content` and other [useful properties](#returned-object). - * - * @param {Object|String} `input` String, or object with `content` string - * @param {Object} `options` - * @return {Object} - * @api public - */ - -export default function matter(input, options) { - if (input === '') { - return { data: {}, content: input, excerpt: '', orig: input }; - } - - let file = toFile(input); - const cached = matter.cache[file.content]; - - if (!options) { - if (cached) { - file = Object.assign({}, cached); - file.orig = cached.orig; - return file; - } - - // only cache if there are no options passed. if we cache when options - // are passed, we would need to also cache options values, which would - // negate any performance benefits of caching - matter.cache[file.content] = file; - } - - return parseMatter(file, options); -} - -/** - * Parse front matter - */ - -function parseMatter(file, options) { - const opts = defaults(options); - const open = opts.delimiters[0]; - const close = '\n' + opts.delimiters[1]; - let str = file.content; - - if (opts.language) { - file.language = opts.language; - } - - // get the length of the opening delimiter - const openLen = open.length; - if (!utils.startsWith(str, open, openLen)) { - excerpt(file, opts); - return file; - } - - // if the next character after the opening delimiter is - // a character from the delimiter, then it's not a front- - // matter delimiter - if (str.charAt(openLen) === open.slice(-1)) { - return file; - } - - // strip the opening delimiter - str = str.slice(openLen); - const len = str.length; - - // use the language defined after first delimiter, if it exists - const language = matter.language(str, opts); - if (language.name) { - file.language = language.name; - str = str.slice(language.raw.length); - } - - // get the index of the closing delimiter - let closeIndex = str.indexOf(close); - if (closeIndex === -1) { - closeIndex = len; - } - - // get the raw front-matter block - file.matter = str.slice(0, closeIndex); - - const block = file.matter.replace(/^\s*#[^\n]+/gm, '').trim(); - if (block === '') { - file.isEmpty = true; - file.empty = file.content; - file.data = {}; - } else { - - // create file.data by parsing the raw file.matter block - file.data = parse(file.language, file.matter, opts); - } - - // update file.content - if (closeIndex === len) { - file.content = ''; - } else { - file.content = str.slice(closeIndex + close.length); - if (file.content[0] === '\r') { - file.content = file.content.slice(1); - } - if (file.content[0] === '\n') { - file.content = file.content.slice(1); - } - } - - excerpt(file, opts); - - if (opts.sections === true || typeof opts.section === 'function') { - sections(file, opts.section); - } - return file; -} - -/** - * Expose engines - */ - -matter.engines = engines; - -/** - * Stringify an object to YAML or the specified language, and - * append it to the given string. By default, only YAML and JSON - * can be stringified. See the [engines](#engines) section to learn - * how to stringify other languages. - * - * @param {String|Object} `file` The content string to append to stringified front-matter, or a file object with `file.content` string. - * @param {Object} `data` Front matter to stringify. - * @param {Object} `options` [Options](#options) to pass to gray-matter and [js-yaml]. - * @return {String} Returns a string created by wrapping stringified yaml with delimiters, and appending that to the given string. - * @api public - */ - -matter.stringify = function(file, data, options) { - if (typeof file === 'string') file = matter(file, options); - return stringify(file, data, options); -}; - -/** - * Synchronously read a file from the file system and parse - * front matter. Returns the same object as the [main function](#matter). - * - * ```js - * const file = matter.read('./content/blog-post.md'); - * ``` - * @param {String} `filepath` file path of the file to read. - * @param {Object} `options` [Options](#options) to pass to gray-matter. - * @return {Object} Returns [an object](#returned-object) with `data` and `content` - * @api public - */ - -matter.read = function(filepath, options) { - const str = fs.readFileSync(filepath, 'utf8'); - const file = matter(str, options); - file.path = filepath; - return file; -}; - -/** - * Returns true if the given `string` has front matter. - * @param {String} `string` - * @param {Object} `options` - * @return {Boolean} True if front matter exists. - * @api public - */ - -matter.test = function(str, options) { - return utils.startsWith(str, defaults(options).delimiters[0]); -}; - -/** - * Detect the language to use, if one is defined after the - * first front-matter delimiter. - * @param {String} `string` - * @param {Object} `options` - * @return {Object} Object with `raw` (actual language string), and `name`, the language with whitespace trimmed - */ - -matter.language = function(str, options) { - const opts = defaults(options); - const open = opts.delimiters[0]; - - if (matter.test(str)) { - str = str.slice(open.length); - } - - const language = str.slice(0, str.search(/\r?\n/)); - return { - raw: language, - name: language ? language.trim() : '' - }; -}; - -/** - * Expose `matter` - */ - -matter.cache = {}; -matter.clearCache = function() { - matter.cache = {}; -}; \ No newline at end of file diff --git a/deps/gray-matter/lib/defaults.js b/deps/gray-matter/lib/defaults.js deleted file mode 100644 index f53fc3b..0000000 --- a/deps/gray-matter/lib/defaults.js +++ /dev/null @@ -1,16 +0,0 @@ -import engines from './engines' -import * as utils from './utils' - -export default function(options) { - const opts = Object.assign({}, options); - - // ensure that delimiters are an array - opts.delimiters = utils.arrayify(opts.delims || opts.delimiters || '---'); - if (opts.delimiters.length === 1) { - opts.delimiters.push(opts.delimiters[0]); - } - - opts.language = (opts.language || opts.lang || 'yaml').toLowerCase(); - opts.engines = Object.assign({}, engines, opts.parsers, opts.engines); - return opts; -}; diff --git a/deps/gray-matter/lib/engine.js b/deps/gray-matter/lib/engine.js deleted file mode 100644 index 85517e4..0000000 --- a/deps/gray-matter/lib/engine.js +++ /dev/null @@ -1,28 +0,0 @@ -export default function getEngine(name, options) { - let engine = options.engines[name] || options.engines[aliase(name)]; - if (typeof engine === 'undefined') { - throw new Error(`gray-matter engine "${name}" is not registered`); - } - if (typeof engine === 'function') { - engine = { parse: engine }; - } - return engine; -}; - -function aliase(name) { - switch (name.toLowerCase()) { - case 'js': - case 'javascript': - return 'javascript'; - case 'coffee': - case 'coffeescript': - case 'cson': - return 'coffee'; - case 'yaml': - case 'yml': - return 'yaml'; - default: { - return name; - } - } -} diff --git a/deps/gray-matter/lib/engines.js b/deps/gray-matter/lib/engines.js deleted file mode 100644 index f5fd27d..0000000 --- a/deps/gray-matter/lib/engines.js +++ /dev/null @@ -1,53 +0,0 @@ -import yaml from 'js-yaml'; - -/** - * Default engines - */ - -const engines = {}; -export default engines; - -/** - * YAML - */ - -engines.yaml = { - parse: yaml.safeLoad.bind(yaml), - stringify: yaml.safeDump.bind(yaml) -}; - -/** - * JSON - */ - -engines.json = { - parse: JSON.parse.bind(JSON), - stringify: function(obj, options) { - const opts = Object.assign({replacer: null, space: 2}, options); - return JSON.stringify(obj, opts.replacer, opts.space); - } -}; - -/** - * JavaScript - */ - -engines.javascript = { - parse: function parse(str, options, wrap) { - /* eslint no-eval: 0 */ - try { - if (wrap !== false) { - str = '(function() {\nreturn ' + str.trim() + ';\n}());'; - } - return eval(str) || {}; - } catch (err) { - if (wrap !== false && /(unexpected|identifier)/i.test(err.message)) { - return parse(str, options, false); - } - throw new SyntaxError(err); - } - }, - stringify: function() { - throw new Error('stringifying JavaScript is not supported'); - } -}; diff --git a/deps/gray-matter/lib/excerpt.js b/deps/gray-matter/lib/excerpt.js deleted file mode 100644 index ea3c364..0000000 --- a/deps/gray-matter/lib/excerpt.js +++ /dev/null @@ -1,30 +0,0 @@ -import defaults from './defaults'; - -export default function excerpt(file, options) { - const opts = defaults(options); - - if (file.data == null) { - file.data = {}; - } - - if (typeof opts.excerpt === 'function') { - return opts.excerpt(file, opts); - } - - const sep = file.data.excerpt_separator || opts.excerpt_separator; - if (sep == null && (opts.excerpt === false || opts.excerpt == null)) { - return file; - } - - const delimiter = typeof opts.excerpt === 'string' - ? opts.excerpt - : (sep || opts.delimiters[0]); - - // if enabled, get the excerpt defined after front-matter - const idx = file.content.indexOf(delimiter); - if (idx !== -1) { - file.excerpt = file.content.slice(0, idx); - } - - return file; -}; diff --git a/deps/gray-matter/lib/parse.js b/deps/gray-matter/lib/parse.js deleted file mode 100644 index 5a698bb..0000000 --- a/deps/gray-matter/lib/parse.js +++ /dev/null @@ -1,12 +0,0 @@ -import getEngine from './engine'; -import defaults from './defaults'; - - -export default function parse(language, str, options) { - const opts = defaults(options); - const engine = getEngine(language, opts); - if (typeof engine.parse !== 'function') { - throw new TypeError(`expected "${language}.parse" to be a function`); - } - return engine.parse(str, opts); -}; diff --git a/deps/gray-matter/lib/stringify.js b/deps/gray-matter/lib/stringify.js deleted file mode 100644 index 0b4d336..0000000 --- a/deps/gray-matter/lib/stringify.js +++ /dev/null @@ -1,55 +0,0 @@ -import typeOf from 'kind-of'; -import getEngine from './engine'; -import defaults from './defaults'; - - -export default function stringify(file, data, options) { - if (data == null && options == null) { - switch (typeOf(file)) { - case 'object': - data = file.data; - options = {}; - break; - case 'string': - return file; - default: { - throw new TypeError('expected file to be a string or object'); - } - } - } - - const str = file.content; - const opts = defaults(options); - if (data == null) { - if (!opts.data) return file; - data = opts.data; - } - - const language = file.language || opts.language; - const engine = getEngine(language, opts); - if (typeof engine.stringify !== 'function') { - throw new TypeError('expected "' + language + '.stringify" to be a function'); - } - - data = Object.assign({}, file.data, data); - const open = opts.delimiters[0]; - const close = opts.delimiters[1]; - const matter = engine.stringify(data, options).trim(); - let buf = ''; - - if (matter !== '{}') { - buf = newline(open) + newline(matter) + newline(close); - } - - if (typeof file.excerpt === 'string' && file.excerpt !== '') { - if (str.indexOf(file.excerpt.trim()) === -1) { - buf += newline(file.excerpt) + newline(close); - } - } - - return buf + newline(str); -}; - -function newline(str) { - return str.slice(-1) !== '\n' ? str + '\n' : str; -} diff --git a/deps/gray-matter/lib/to-file.js b/deps/gray-matter/lib/to-file.js deleted file mode 100644 index 5e8e7c7..0000000 --- a/deps/gray-matter/lib/to-file.js +++ /dev/null @@ -1,41 +0,0 @@ -import typeOf from 'kind-of'; -import stringify from './stringify'; -import * as utils from './utils'; - - -/** - * Normalize the given value to ensure an object is returned - * with the expected properties. - */ - -export default function toFile(file) { - if (typeOf(file) !== 'object') { - file = { content: file }; - } - - if (typeOf(file.data) !== 'object') { - file.data = {}; - } - - // if file was passed as an object, ensure that - // "file.content" is set - if (file.contents && file.content == null) { - file.content = file.contents; - } - - // set non-enumerable properties on the file object - utils.define(file, 'language', file.language || ''); - utils.define(file, 'matter', file.matter || ''); - utils.define(file, 'stringify', function(data, options) { - if (options && options.language) { - file.language = options.language; - } - return stringify(file, data, options); - }); - - // strip BOM and ensure that "file.content" is a string - file.content = utils.toString(file.content); - file.isEmpty = false; - file.excerpt = ''; - return file; -}; diff --git a/deps/gray-matter/lib/utils.js b/deps/gray-matter/lib/utils.js deleted file mode 100644 index eaf4de0..0000000 --- a/deps/gray-matter/lib/utils.js +++ /dev/null @@ -1,47 +0,0 @@ -import stripBom from 'strip-bom-string' -import typeOf from 'kind-of' - -export function define(obj, key, val) { - Reflect.defineProperty(obj, key, { - enumerable: false, - configurable: true, - writable: true, - value: val - }); -}; - -/** - * Returns true if `val` is an object - */ - -export function isObject(val) { - return typeOf(val) === 'object'; -}; - -/** - * Cast `val` to a string. - */ - -export function toString(input) { - if (typeof input !== 'string') { - throw new TypeError('expected input to be a string'); - } - return stripBom(input); -}; - -/** - * Cast `val` to an array. - */ - -export function arrayify(val) { - return val ? (Array.isArray(val) ? val : [val]) : []; -}; - -/** - * Returns true if `str` starts with `substr`. - */ - -export function startsWith(str, substr, len) { - if (typeof len !== 'number') len = substr.length; - return str.slice(0, len) === substr; -}; diff --git a/deps/gray-matter/package.json b/deps/gray-matter/package.json deleted file mode 100644 index 59eb5b4..0000000 --- a/deps/gray-matter/package.json +++ /dev/null @@ -1,78 +0,0 @@ -{ - "name": "gray-matter", - "version": "4.0.3", - "author": "Jon Schlinkert (https://github.com/jonschlinkert)", - "type":"module", - "license": "MIT", - "files": [ - "gray-matter.d.ts", - "index.js", - "lib" - ], - "main": "index.js", - "engines": { - "node": ">=6.0" - }, - "scripts": { - "test": "mocha" - }, - "dependencies": { - "js-yaml": "^3.13.1", - "kind-of": "^6.0.2", - "section-matter": "^1.0.0", - "strip-bom-string": "^1.0.0" - }, - "devDependencies": { - "ansi-green": "^0.1.1", - "benchmarked": "^2.0.0", - "coffeescript": "^2.2.3", - "delimiter-regex": "^2.0.0", - "extend-shallow": "^3.0.2", - "front-matter": "^2.3.0", - "gulp-format-md": "^1.0.0", - "minimist": "^1.2.0", - "mocha": "^6.1.4", - "toml": "^2.3.3", - "vinyl": "^2.1.0", - "write": "^1.0.3" - }, - "browser": { - "fs": false - }, - "typings": "gray-matter.d.ts", - "eslintConfig": { - "rules": { - "no-console": 0 - } - }, - "verb": { - "toc": false, - "layout": "default", - "tasks": [ - "readme" - ], - "plugins": [ - "gulp-format-md" - ], - "helpers": { - "examples": "./examples/helper.js" - }, - "lint": { - "reflinks": true - }, - "related": { - "list": [ - "assemble", - "metalsmith", - "verb" - ] - }, - "reflinks": [ - "coffe-script", - "generate", - "js-yaml", - "toml", - "update" - ] - } -} diff --git a/package.json b/package.json index 7ddd2bb..8971eb1 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,6 @@ "@mantine/hooks": "^6.0.19", "@preact/signals": "^1.2.1", "date-fns": "^2.30.0", - "gray-matter": "file:deps/gray-matter", "jsonlines": "^0.1.1", "minisearch": "^6.1.0", "preact": "^10.13.1", diff --git a/src/pages/Post.tsx b/src/pages/Post.tsx index 31a0cb9..f717462 100644 --- a/src/pages/Post.tsx +++ b/src/pages/Post.tsx @@ -7,12 +7,13 @@ import { Group, } from '@mantine/core' import Markdown from 'markdown-to-jsx' -import matter from 'gray-matter' +import fm from 'front-matter' import { readingTime } from 'reading-time-estimator' import { Header } from '@/components/Header' import { getCurrentUrl } from 'preact-router' import { useState, useEffect } from 'preact/hooks' import { friendlyDate } from '@/utils' +import { useTitle } from '@/hooks/useTitle' const useStyles = createStyles((theme) => ({ title: { @@ -34,7 +35,7 @@ const useStyles = createStyles((theme) => ({ async function getPost(name: string) { const response = await fetch(`${name}.md?raw`) - return matter(await response.text()) + return fm(await response.text()) } export default function Post() { @@ -57,16 +58,17 @@ export default function Post() { ) } else { - const readTime = readingTime(post.content).text - const date = friendlyDate(post.data.date) - const location = post.data.location + useTitle(post.attributes.title) + const readTime = readingTime(post.body).text + const date = friendlyDate(post.attributes.date) + const location = post.attributes.location return ( <>
- {post.data.title} - {post.data.subtitle} + {post.attributes.title} + {post.attributes.subtitle} {date} {location} @@ -76,7 +78,7 @@ export default function Post() { - {post.content} + {post.body}