From 4f2eaad1047258706179399ba8ddd676b733cc4a Mon Sep 17 00:00:00 2001 From: Joe Pea Date: Mon, 3 Jul 2023 01:27:22 -0700 Subject: [PATCH] chore: update miscellaneous parts of the source to reasonably modern language alternatives, remove polyfills, improve some JSDoc comments, remove traces of IE BREAKING: In a minority of cases syntax updates may break apps running in very old browsers (such as Internet Explorer), or apps that build Docsify in a custom way with old build tools. To upgrade, build Docsify for older browsers in a custom way, or update existing build tools to handle newer syntax. DEPRECATED: `$docsify.themeColor` is deprecated and will be eventually removed, use a `--theme-color` CSS variable in your style sheet. --- .github/PULL_REQUEST_TEMPLATE.md | 1 - README.md | 1 - build/build.js | 13 +- build/cover.js | 12 +- build/css.js | 7 +- build/emoji.js | 24 ++-- docs/README.md | 1 - docs/_media/example.js | 18 +-- docs/configuration.md | 35 +++--- docs/index.html | 22 ++-- docs/language-highlight.md | 2 +- docs/markdown.md | 14 +-- docs/plugins.md | 6 +- docs/pwa.md | 4 +- docs/quickstart.md | 1 - docs/themes.md | 8 +- docs/write-a-plugin.md | 76 +++++------ index.html | 7 +- src/core/Docsify.js | 2 +- src/core/config.js | 45 +++++-- src/core/event/index.js | 9 +- src/core/event/scroll.js | 7 +- src/core/fetch/ajax.js | 46 ++++--- src/core/fetch/index.js | 18 +-- src/core/render/compiler.js | 14 +-- src/core/render/compiler/code.js | 2 +- src/core/render/compiler/headline.js | 2 +- src/core/render/compiler/image.js | 10 +- src/core/render/compiler/link.js | 2 +- src/core/render/compiler/paragraph.js | 2 +- src/core/render/compiler/taskListItem.js | 4 +- src/core/render/embed.js | 119 +++++++++--------- src/core/render/emojify.js | 4 +- src/core/render/gen-tree.js | 2 +- src/core/render/index.js | 16 +-- src/core/render/progressbar.js | 6 +- src/core/render/slugify.js | 4 +- src/core/render/tpl.js | 103 ++++++++------- src/core/router/history/base.js | 4 +- src/core/router/history/hash.js | 3 +- src/core/router/index.js | 3 +- src/core/router/util.js | 5 +- src/core/util/core.js | 33 +---- src/core/util/dom.js | 14 +-- src/core/util/env.js | 18 --- src/core/util/polyfill/css-vars.js | 36 ------ src/core/util/str.js | 8 -- src/core/virtual-routes/exact-match.js | 14 +-- src/core/virtual-routes/index.js | 2 +- src/plugins/disqus.js | 8 +- src/plugins/emoji.js | 6 +- src/plugins/external-script.js | 11 +- src/plugins/front-matter/index.js | 3 +- src/plugins/front-matter/parser.js | 22 ++-- src/plugins/front-matter/yaml.js | 33 +---- src/plugins/ga.js | 4 +- src/plugins/gitalk.js | 6 +- src/plugins/gtag.js | 4 +- src/plugins/matomo.js | 5 +- src/plugins/search/component.js | 21 ++-- src/plugins/search/index.js | 3 +- src/plugins/search/search.js | 14 ++- src/plugins/zoom-image.js | 14 +-- test/config/server.js | 22 ++-- test/e2e/configuration.test.js | 13 +- test/e2e/plugins.test.js | 32 ++--- test/e2e/virtual-routes.test.js | 6 +- test/e2e/vue.test.js | 12 +- test/helpers/docsify-init.js | 28 ++++- .../__snapshots__/docs.test.js.snap | 20 ++- test/integration/emoji.test.js | 6 +- test/integration/render.test.js | 2 +- test/unit/render-util.test.js | 2 +- 73 files changed, 514 insertions(+), 592 deletions(-) delete mode 100644 src/core/util/polyfill/css-vars.js diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md index 4c0bc84680..4e6fad009e 100644 --- a/.github/PULL_REQUEST_TEMPLATE.md +++ b/.github/PULL_REQUEST_TEMPLATE.md @@ -62,4 +62,3 @@ If yes, please describe the impact and migration path for existing applications: - [ ] Firefox - [ ] Safari - [ ] Edge -- [ ] IE diff --git a/README.md b/README.md index 2941927239..a4e73eec12 100644 --- a/README.md +++ b/README.md @@ -46,7 +46,6 @@ - Smart full-text search plugin - Multiple themes - Useful plugin API -- Compatible with IE11 - Support embedded files ## Quick start diff --git a/build/build.js b/build/build.js index ca50d4e1ff..6a3726ed52 100644 --- a/build/build.js +++ b/build/build.js @@ -26,14 +26,15 @@ async function build(opts) { await rollup .rollup({ input: opts.input, - plugins: (opts.plugins || []).concat([ + plugins: [ + ...(opts.plugins || []), commonjs(), nodeResolve(), replace({ __VERSION__: version, }) - ]), - onwarn: function (message) { + ], + onwarn(message) { if (message.code === 'UNRESOLVED_IMPORT') { throw new Error( `Could not resolve module ` + @@ -44,8 +45,8 @@ async function build(opts) { } } }) - .then(function (bundle) { - var dest = 'lib/' + (opts.output || opts.input) + .then(bundle => { + const dest = 'lib/' + (opts.output || opts.input) console.log(dest) return bundle.write({ @@ -77,7 +78,7 @@ async function buildCore() { } async function buildAllPlugin() { - var plugins = [ + const plugins = [ {name: 'search', input: 'search/index.js'}, {name: 'ga', input: 'ga.js'}, {name: 'gtag', input: 'gtag.js'}, diff --git a/build/cover.js b/build/cover.js index 996e525697..9d64aebedd 100644 --- a/build/cover.js +++ b/build/cover.js @@ -1,17 +1,17 @@ import fs from 'fs'; import { relative } from './util.js'; -var read = fs.readFileSync; -var write = fs.writeFileSync; +const read = fs.readFileSync; +const write = fs.writeFileSync; const pkgPath = relative(import.meta, '..', 'package.json'); const pkg = JSON.parse(read(pkgPath).toString()); -var version = process.env.VERSION || pkg.version; +const version = process.env.VERSION || pkg.version; -var file = relative(import.meta, '..', 'docs', '_coverpage.md'); -var cover = read(file, 'utf8').toString(); +const file = relative(import.meta, '..', 'docs', '_coverpage.md'); +let cover = read(file, 'utf8').toString(); console.log('Replace version number in cover page...'); cover = cover.replace( /(\S+)?<\/small>/g, - '' + version + '' + /* html */ `${version}` ); write(file, cover); diff --git a/build/css.js b/build/css.js index baf9816287..1047c58680 100644 --- a/build/css.js +++ b/build/css.js @@ -11,17 +11,16 @@ fs.readdir(relative('../src/themes'), (err, files) => { } files.map(async (file) => { if (/\.styl/g.test(file)) { - var stylusCMD; const stylusBin = ['node_modules', 'stylus', 'bin', 'stylus'].join(path.sep) - var cmdargs = [ + let cmdargs = [ stylusBin, `src/themes/${file}`, '-u', 'autoprefixer-stylus' ] - cmdargs = cmdargs.concat(args) + cmdargs = [...cmdargs, ...args] - stylusCMD = spawn('node', cmdargs, { shell: true }) + const stylusCMD = spawn('node', cmdargs, { shell: true }) stylusCMD.stdout.on('data', (data) => { console.log(`[Stylus Build ] stdout: ${data}`); diff --git a/build/emoji.js b/build/emoji.js index f9d5d0aa2e..0dc41dc3b1 100644 --- a/build/emoji.js +++ b/build/emoji.js @@ -93,17 +93,15 @@ function writeEmojiJS(emojiData) { } } -(async () => { - console.info('Build emoji'); - - try { - const emojiData = await getEmojiData(); - - if (emojiData) { - writeEmojiPage(emojiData); - writeEmojiJS(emojiData); - } - } catch (err) { - console.warn(`- Error: ${err.message}`); +console.info('Build emoji'); + +try { + const emojiData = await getEmojiData(); + + if (emojiData) { + writeEmojiPage(emojiData); + writeEmojiJS(emojiData); } -})(); +} catch (err) { + console.warn(`- Error: ${err.message}`); +} diff --git a/docs/README.md b/docs/README.md index f9d03d8749..f85aa72ab9 100644 --- a/docs/README.md +++ b/docs/README.md @@ -16,7 +16,6 @@ See the [Quick start](quickstart.md) guide for more details. - Multiple themes - Useful plugin API - Emoji support -- Compatible with IE11 ## Examples diff --git a/docs/_media/example.js b/docs/_media/example.js index 8cad2d7306..33bdf862c5 100644 --- a/docs/_media/example.js +++ b/docs/_media/example.js @@ -1,16 +1,16 @@ -import fetch from 'fetch' +import fetch from 'fetch'; -const URL = 'https://example.com' -const PORT = 8080 +const URL = 'https://example.com'; +const PORT = 8080; /// [demo] const result = fetch(`${URL}:${PORT}`) - .then(function (response) { - return response.json() - }) - .then(function (myJson) { - console.log(JSON.stringify(myJson)) + .then(response => { + return response.json(); }) + .then(myJson => { + console.log(JSON.stringify(myJson)); + }); /// [demo] -result.then(console.log).catch(console.error) +result.then(console.log).catch(console.error); diff --git a/docs/configuration.md b/docs/configuration.md index 61c3a9b3e8..83b9956d21 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -244,7 +244,7 @@ See https://github.com/lukeed/tinydate#patterns window.$docsify = { formatUpdated: '{MM}/{DD} {HH}:{mm}', - formatUpdated: function (time) { + formatUpdated(time) { // ... return time; @@ -341,14 +341,14 @@ window.$docsify = { markdown: { smartypants: true, renderer: { - link: function () { + link() { // ... }, }, }, // function - markdown: function (marked, renderer) { + markdown(marked, renderer) { // ... return marked; }, @@ -689,18 +689,17 @@ window.$docsify = { '/foo': '# Custom Markdown', // RegEx match w/ synchronous function - '/bar/(.*)': function (route, matched) { + '/bar/(.*)'(route, matched) { return '# Custom Markdown'; }, // RegEx match w/ asynchronous function - '/baz/(.*)': function (route, matched, next) { - // Requires `fetch` polyfill for legacy browsers (https://github.github.io/fetch/) + '/baz/(.*)'(route, matched, next) { fetch('/api/users?id=12345') - .then(function (response) { + .then(response => { next('# Custom Markdown'); }) - .catch(function (err) { + .catch(err => { // Handle error... }); }, @@ -714,7 +713,7 @@ Other than strings, route functions can return a falsy value (`null` \ `undefine window.$docsify = { routes: { // accepts everything other than dogs (synchronous) - '/pets/(.+)': function(route, matched) { + '/pets/(.+)'(route, matched) { if (matched[0] === 'dogs') { return null; } else { @@ -723,7 +722,7 @@ window.$docsify = { } // accepts everything other than cats (asynchronous) - '/pets/(.*)': function(route, matched, next) { + '/pets/(.*)'(route, matched, next) { if (matched[0] === 'cats') { next(); } else { @@ -741,12 +740,12 @@ Finally, if you have a specific path that has a real markdown file (and therefor window.$docsify = { routes: { // if you look up /pets/cats, docsify will skip all routes and look for "pets/cats.md" - '/pets/cats': function(route, matched) { + '/pets/cats'(route, matched) { return false; } // but any other pet should generate dynamic content right here - '/pets/(.+)': function(route, matched) { + '/pets/(.+)'(route, matched) { const pet = matched[0]; return `your pet is ${pet} (but not a cat)`; } @@ -777,11 +776,19 @@ If you have a link to the homepage in the sidebar and want it to be shown as act For more details, see [#1131](https://github.com/docsifyjs/docsify/issues/1131). -## themeColor +## themeColor (_deprecated_) + +> **Warning** Deprecated. Use the CSS var `--theme-color` in your ` - Type: `String` -Customize the theme color. Use [CSS3 variables](https://developer.mozilla.org/en-US/docs/Web/CSS/Using_CSS_variables) feature and polyfill in older browsers. +Customize the theme color. ```js window.$docsify = { diff --git a/docs/index.html b/docs/index.html index db07743553..2eaeb3acb4 100644 --- a/docs/index.html +++ b/docs/index.html @@ -8,7 +8,6 @@ name="google-site-verification" content="6t0LoIeFksrjF4c9sqUEsVXiQNxLp2hgoqo0KryT-sE" /> - -var num = 0; +let num = 0; mermaid.initialize({ startOnLoad: false }); window.$docsify = { markdown: { renderer: { - code: function(code, lang) { + code(code, lang) { if (lang === "mermaid") { - return ( - '
' + mermaid.render('mermaid-svg-' + num++, code) + "
" - ); + return /* html */ ` +
${mermaid.render('mermaid-svg-' + num++, code)}
+ `; } return this.origin.code.apply(this, arguments); } diff --git a/docs/plugins.md b/docs/plugins.md index dce1f4e645..ee0c0967d9 100644 --- a/docs/plugins.md +++ b/docs/plugins.md @@ -63,11 +63,7 @@ By default, the hyperlink on the current page is recognized and the content is s ``` -This plugin ignores diacritical marks when performing a full text search (e.g., "cafe" will also match "café"). Legacy browsers like IE11 require the following [String.normalize()](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/normalize) polyfill to ignore diacritical marks: - -```html - -``` +This plugin ignores diacritical marks when performing a full text search (e.g., "cafe" will also match "café"). ## Google Analytics diff --git a/docs/pwa.md b/docs/pwa.md index 3caca11221..464f0c5be2 100644 --- a/docs/pwa.md +++ b/docs/pwa.md @@ -29,8 +29,8 @@ const HOSTNAME_WHITELIST = [ // The Util Function to hack URLs of intercepted requests const getFixedUrl = (req) => { - var now = Date.now() - var url = new URL(req.url) + const now = Date.now() + const url = new URL(req.url) // 1. fixed http URL // Just keep syncing with location.protocol diff --git a/docs/quickstart.md b/docs/quickstart.md index 149afd1088..032e306466 100644 --- a/docs/quickstart.md +++ b/docs/quickstart.md @@ -44,7 +44,6 @@ If you don't like `npm` or have trouble installing the tool, you can manually cr - ${match} `; diff --git a/test/e2e/configuration.test.js b/test/e2e/configuration.test.js index f54c0dede4..561249bdd4 100644 --- a/test/e2e/configuration.test.js +++ b/test/e2e/configuration.test.js @@ -1,3 +1,4 @@ +/* global fail */ import docsifyInit from '../helpers/docsify-init.js'; import { test, expect } from './fixtures/docsify-init-fixture.js'; @@ -13,11 +14,8 @@ test.describe('Configuration options', () => { catchPluginErrors: true, plugins: [ function (hook, vm) { - hook.init(function () { - // eslint-disable-next-line no-undef - fail(); - }); - hook.beforeEach(function (markdown) { + hook.init(fail); + hook.beforeEach(markdown => { return `${markdown}\n\nbeforeEach`; }); }, @@ -48,10 +46,7 @@ test.describe('Configuration options', () => { catchPluginErrors: false, plugins: [ function (hook, vm) { - hook.ready(function () { - // eslint-disable-next-line no-undef - fail(); - }); + hook.ready(fail); }, ], }, diff --git a/test/e2e/plugins.test.js b/test/e2e/plugins.test.js index 8944462bc4..ebf6d3ca94 100644 --- a/test/e2e/plugins.test.js +++ b/test/e2e/plugins.test.js @@ -21,43 +21,43 @@ test.describe('Plugins', () => { config: { plugins: [ function (hook, vm) { - hook.init(function () { + hook.init(() => { console.log('init'); }); - hook.mounted(function () { + hook.mounted(() => { console.log('mounted'); }); - hook.beforeEach(function (markdown, next) { - setTimeout(function () { + hook.beforeEach((markdown, next) => { + setTimeout(() => { console.log('beforeEach-async'); next(markdown); }, 100); }); - hook.beforeEach(function (markdown) { + hook.beforeEach(markdown => { console.log('beforeEach'); return markdown; }); - hook.afterEach(function (html, next) { - setTimeout(function () { + hook.afterEach((html, next) => { + setTimeout(() => { console.log('afterEach-async'); next(html); }, 100); }); - hook.afterEach(function (html) { + hook.afterEach(html => { console.log('afterEach'); return html; }); - hook.doneEach(function () { + hook.doneEach(() => { console.log('doneEach'); }); - hook.ready(function () { + hook.ready(() => { console.log('ready'); }); }, @@ -77,7 +77,7 @@ test.describe('Plugins', () => { config: { plugins: [ function (hook, vm) { - hook.beforeEach(function (markdown) { + hook.beforeEach(markdown => { return 'beforeEach'; }); }, @@ -94,8 +94,8 @@ test.describe('Plugins', () => { config: { plugins: [ function (hook, vm) { - hook.beforeEach(function (markdown, next) { - setTimeout(function () { + hook.beforeEach((markdown, next) => { + setTimeout(() => { next('beforeEach'); }, 100); }); @@ -116,7 +116,7 @@ test.describe('Plugins', () => { config: { plugins: [ function (hook, vm) { - hook.afterEach(function (html) { + hook.afterEach(html => { return '

afterEach

'; }); }, @@ -136,8 +136,8 @@ test.describe('Plugins', () => { config: { plugins: [ function (hook, vm) { - hook.afterEach(function (html, next) { - setTimeout(function () { + hook.afterEach((html, next) => { + setTimeout(() => { next('

afterEach

'); }, 100); }); diff --git a/test/e2e/virtual-routes.test.js b/test/e2e/virtual-routes.test.js index ba31adcb08..b84ca30cab 100644 --- a/test/e2e/virtual-routes.test.js +++ b/test/e2e/virtual-routes.test.js @@ -101,9 +101,7 @@ test.describe('Virtual Routes - Generate Dynamic Content via Config', () => { page, }) => { const routes = { - '/pets/(.*)': function (route) { - return `# Route: /pets/dog`; - }, + '/pets/(.*)': route => `# Route: /pets/dog`, }; await docsifyInit({ @@ -122,7 +120,7 @@ test.describe('Virtual Routes - Generate Dynamic Content via Config', () => { page, }) => { const routes = { - '/pets/(.*)': function (_, matched) { + '/pets/(.*)'(_, matched) { return `# Pets Page (${matched[1]})`; }, }; diff --git a/test/e2e/vue.test.js b/test/e2e/vue.test.js index fde2dcd8c1..0edbb43d57 100644 --- a/test/e2e/vue.test.js +++ b/test/e2e/vue.test.js @@ -24,16 +24,14 @@ test.describe('Vue.js Compatibility', () => { }, }, vueGlobalOptions: { - data: function () { - return { - counter: 0, - msg: 'vueglobaloptions', - }; - }, + data: () => ({ + counter: 0, + msg: 'vueglobaloptions', + }), }, vueMounts: { '#vuemounts': { - data: function () { + data() { return { counter: 0, msg: 'vuemounts', diff --git a/test/helpers/docsify-init.js b/test/helpers/docsify-init.js index a645856916..3441046eaf 100644 --- a/test/helpers/docsify-init.js +++ b/test/helpers/docsify-init.js @@ -225,11 +225,29 @@ async function docsifyInit(options = {}) { await page.evaluate(config => { // Restore config functions from strings - const configObj = JSON.parse(config, (key, val) => - /^__FN__/.test(val) - ? new Function(`return ${val.split('__FN__')[1]}`)() - : val - ); + const configObj = JSON.parse(config, (key, val) => { + if (/^__FN__/.test(val)) { + let source = val.split('__FN__')[1]; + + // f.e. `foo() {}` or `'bar!?'() {}` without the `function ` prefix + const isConcise = + !source.includes('function') && !source.includes('=>'); + + if (isConcise) { + source = `{ ${source} }`; + } else { + source = `{ _: ${source} }`; + } + + return new Function(/* js */ ` + const o = ${source} + const keys = Object.keys(o) + return o[keys[0]] + `)(); + } else { + return val; + } + }); window.$docsify = configObj; }, configString); diff --git a/test/integration/__snapshots__/docs.test.js.snap b/test/integration/__snapshots__/docs.test.js.snap index ffe44b777b..2e620b9dd9 100644 --- a/test/integration/__snapshots__/docs.test.js.snap +++ b/test/integration/__snapshots__/docs.test.js.snap @@ -1,12 +1,26 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP exports[`Docs Site coverpage renders and is unchanged 1`] = ` -"

\\"logo\\"

docsify 4.13.0

+"
+
+

\\"logo\\"

docsify 4.13.0

A magical documentation site generator.

  • Simple and lightweight
  • No statically built html files
  • Multiple themes

GitHub -Getting Started

" +Getting Started

+
" `; exports[`Docs Site navbar renders and is unchanged 1`] = `""`; -exports[`Docs Site sidebar renders and is unchanged 1`] = `""`; +exports[`Docs Site sidebar renders and is unchanged 1`] = ` +"" +`; diff --git a/test/integration/emoji.test.js b/test/integration/emoji.test.js index b448347cae..cae95a1d67 100644 --- a/test/integration/emoji.test.js +++ b/test/integration/emoji.test.js @@ -137,7 +137,7 @@ describe('Emoji', function () { test('Ignores emoji shorthand codes in html attributes', async () => { await docsifyInit({ markdown: { - homepage: ` `, + homepage: /* html */ ` `, }, // _logHTML: true, }); @@ -150,7 +150,7 @@ describe('Emoji', function () { test('Ignores emoji shorthand codes in style url() values', async () => { await docsifyInit({ markdown: { - homepage: ``, + homepage: /* html */ ``, }, // _logHTML: true, }); @@ -163,7 +163,7 @@ describe('Emoji', function () { test('Ignores emoji shorthand codes in code, pre, script, and template tags', async () => { await docsifyInit({ markdown: { - homepage: ` + homepage: /* html */ `
:100:
:100: diff --git a/test/integration/render.test.js b/test/integration/render.test.js index d2b12527e2..8b65f11ca0 100644 --- a/test/integration/render.test.js +++ b/test/integration/render.test.js @@ -104,7 +104,7 @@ describe('render', function () { const output = window.marked('![alt text](http://imageUrl)'); expect(output).toMatchInlineSnapshot( - `"

\\"alt

"` + `"

\\"alt

"` ); }); diff --git a/test/unit/render-util.test.js b/test/unit/render-util.test.js index d416079ce0..46e4395e6c 100644 --- a/test/unit/render-util.test.js +++ b/test/unit/render-util.test.js @@ -122,7 +122,7 @@ describe('core/render/tpl', () => { ]); expect(result).toBe( - `
` + /* html */ `` ); }); });