refactor: organize app extensions

Signed-off-by: Tilman Vatteroth <git@tilmanvatteroth.de>
This commit is contained in:
Tilman Vatteroth 2023-04-14 09:13:37 +02:00
parent 8cddc96881
commit 1e4709c087
209 changed files with 286 additions and 243 deletions

View file

@ -0,0 +1,43 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`Legacy shortcodes markdown extension transforms a pdf short code into an URL 1`] = `
<div>
<p>
<a
href="https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf"
>
https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf
</a>
</p>
</div>
`;
exports[`Legacy shortcodes markdown extension transforms a slideshare short code into an URL 1`] = `
<div>
<p>
<a
href="https://www.slideshare.net/example/123456789"
>
https://www.slideshare.net/example/123456789
</a>
</p>
</div>
`;
exports[`Legacy shortcodes markdown extension transforms a speakerdeck short code into an URL 1`] = `
<div>
<p>
<a
href="https://speakerdeck.com/example/123456789"
>
https://speakerdeck.com/example/123456789
</a>
</p>
</div>
`;

View file

@ -0,0 +1,43 @@
/*
* SPDX-FileCopyrightText: 2022 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import type { Linter } from '../../../components/editor-page/editor-pane/linter/linter'
import { SingleLineRegexLinter } from '../../../components/editor-page/editor-pane/linter/single-line-regex-linter'
import type { MarkdownRendererExtension } from '../../../components/markdown-renderer/extensions/_base-classes/markdown-renderer-extension'
import { AppExtension } from '../../_base-classes/app-extension'
import { LegacyShortcodesMarkdownExtension } from './legacy-shortcodes-markdown-extension'
import { legacyPdfRegex } from './replace-legacy-pdf-short-code'
import { legacySlideshareRegex } from './replace-legacy-slideshare-short-code'
import { legacySpeakerdeckRegex } from './replace-legacy-speakerdeck-short-code'
import { t } from 'i18next'
/**
* Adds support for legacy shortcodes (pdf, slideshare and speakerdeck) from HedgeDoc 1 to the markdown renderer.
*/
export class LegacyShortcodesAppExtension extends AppExtension {
buildMarkdownRendererExtensions(): MarkdownRendererExtension[] {
return [new LegacyShortcodesMarkdownExtension()]
}
buildCodeMirrorLinter(): Linter[] {
return [
new SingleLineRegexLinter(
legacySpeakerdeckRegex,
t('editor.linter.shortcode', { shortcode: 'SpeakerDeck' }),
(match: string) => `https://speakerdeck.com/${match}`
),
new SingleLineRegexLinter(
legacySlideshareRegex,
t('editor.linter.shortcode', { shortcode: 'SlideShare' }),
(match: string) => `https://www.slideshare.net/${match}`
),
new SingleLineRegexLinter(
legacyPdfRegex,
t('editor.linter.shortcode', { shortcode: 'PDF' }),
(match: string) => match
)
]
}
}

View file

@ -0,0 +1,39 @@
/*
* SPDX-FileCopyrightText: 2023 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { TestMarkdownRenderer } from '../../../components/markdown-renderer/test-utils/test-markdown-renderer'
import { LegacyShortcodesMarkdownExtension } from './legacy-shortcodes-markdown-extension'
import { render } from '@testing-library/react'
import React from 'react'
describe('Legacy shortcodes markdown extension', () => {
it('transforms a pdf short code into an URL', () => {
const view = render(
<TestMarkdownRenderer
extensions={[new LegacyShortcodesMarkdownExtension()]}
content={'{%pdf https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf %}'}
/>
)
expect(view.container).toMatchSnapshot()
})
it('transforms a slideshare short code into an URL', () => {
const view = render(
<TestMarkdownRenderer
extensions={[new LegacyShortcodesMarkdownExtension()]}
content={'{%slideshare example/123456789 %}'}
/>
)
expect(view.container).toMatchSnapshot()
})
it('transforms a speakerdeck short code into an URL', () => {
const view = render(
<TestMarkdownRenderer
extensions={[new LegacyShortcodesMarkdownExtension()]}
content={'{%speakerdeck example/123456789 %}'}
/>
)
expect(view.container).toMatchSnapshot()
})
})

View file

@ -0,0 +1,21 @@
/*
* SPDX-FileCopyrightText: 2022 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { MarkdownRendererExtension } from '../../../components/markdown-renderer/extensions/_base-classes/markdown-renderer-extension'
import { legacyPdfShortCode } from './replace-legacy-pdf-short-code'
import { legacySlideshareShortCode } from './replace-legacy-slideshare-short-code'
import { legacySpeakerdeckShortCode } from './replace-legacy-speakerdeck-short-code'
import type MarkdownIt from 'markdown-it'
/**
* Adds support for legacy shortcodes (pdf, slideshare and speakerdeck) by replacing them with anchor elements.
*/
export class LegacyShortcodesMarkdownExtension extends MarkdownRendererExtension {
public configureMarkdownIt(markdownIt: MarkdownIt): void {
legacyPdfShortCode(markdownIt)
legacySlideshareShortCode(markdownIt)
legacySpeakerdeckShortCode(markdownIt)
}
}

View file

@ -0,0 +1,24 @@
/*
* SPDX-FileCopyrightText: 2023 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { legacyPdfShortCode } from './replace-legacy-pdf-short-code'
import MarkdownIt from 'markdown-it'
describe('Legacy pdf short code', () => {
it('replaces with link', () => {
const markdownIt = new MarkdownIt('default', {
html: false,
breaks: true,
langPrefix: '',
typographer: true
})
markdownIt.use(legacyPdfShortCode)
expect(
markdownIt.renderInline('{%pdf https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf %}')
).toEqual(
`<a href="https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf">https://www.w3.org/WAI/ER/tests/xhtml/testfiles/resources/pdf/dummy.pdf</a>`
)
})
})

View file

@ -0,0 +1,23 @@
/*
* SPDX-FileCopyrightText: 2022 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import type { RegexOptions } from '../../../external-types/markdown-it-regex/interface'
import markdownItRegex from 'markdown-it-regex'
import type MarkdownIt from 'markdown-it/lib'
export const legacyPdfRegex = /^{%pdf\s+(\S*)\s*%}$/
/**
* Configure the given {@link MarkdownIt} to render legacy hedgedoc 1 pdf shortcodes as html links.
*
* @param markdownIt The {@link MarkdownIt} to configure
*/
export const legacyPdfShortCode: MarkdownIt.PluginSimple = (markdownIt) => {
markdownItRegex(markdownIt, {
name: 'legacy-pdf-short-code',
regex: legacyPdfRegex,
replace: (match) => `<a href="${match}">${match}</a>`
} as RegexOptions)
}

View file

@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2023 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { legacySlideshareShortCode } from './replace-legacy-slideshare-short-code'
import MarkdownIt from 'markdown-it'
describe('Legacy slideshare short code', () => {
it('replaces with link', () => {
const markdownIt = new MarkdownIt('default', {
html: false,
breaks: true,
langPrefix: '',
typographer: true
})
markdownIt.use(legacySlideshareShortCode)
expect(markdownIt.renderInline('{%slideshare example/123456789 %}')).toEqual(
"<a href='https://www.slideshare.net/example/123456789'>https://www.slideshare.net/example/123456789</a>"
)
})
})

View file

@ -0,0 +1,23 @@
/*
* SPDX-FileCopyrightText: 2022 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import type { RegexOptions } from '../../../external-types/markdown-it-regex/interface'
import markdownItRegex from 'markdown-it-regex'
import type MarkdownIt from 'markdown-it/lib'
export const legacySlideshareRegex = /^{%slideshare\s+(\w+\/[\w-]+)\s*%}$/
/**
* Configure the given {@link MarkdownIt} to render legacy hedgedoc 1 slideshare shortcodes as HTML links.
*
* @param markdownIt The {@link MarkdownIt} to configure
*/
export const legacySlideshareShortCode: MarkdownIt.PluginSimple = (markdownIt) => {
markdownItRegex(markdownIt, {
name: 'legacy-slideshare-short-code',
regex: legacySlideshareRegex,
replace: (match) => `<a href='https://www.slideshare.net/${match}'>https://www.slideshare.net/${match}</a>`
} as RegexOptions)
}

View file

@ -0,0 +1,22 @@
/*
* SPDX-FileCopyrightText: 2023 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import { legacySpeakerdeckShortCode } from './replace-legacy-speakerdeck-short-code'
import MarkdownIt from 'markdown-it'
describe('Legacy speakerdeck short code', () => {
it('replaces with link', () => {
const markdownIt = new MarkdownIt('default', {
html: false,
breaks: true,
langPrefix: '',
typographer: true
})
markdownIt.use(legacySpeakerdeckShortCode)
expect(markdownIt.renderInline('{%speakerdeck example/123456789 %}')).toEqual(
'<a href="https://speakerdeck.com/example/123456789">https://speakerdeck.com/example/123456789</a>'
)
})
})

View file

@ -0,0 +1,23 @@
/*
* SPDX-FileCopyrightText: 2022 The HedgeDoc developers (see AUTHORS file)
*
* SPDX-License-Identifier: AGPL-3.0-only
*/
import type { RegexOptions } from '../../../external-types/markdown-it-regex/interface'
import markdownItRegex from 'markdown-it-regex'
import type MarkdownIt from 'markdown-it/lib'
export const legacySpeakerdeckRegex = /^{%speakerdeck\s+(\w+\/[\w-]+)\s*%}$/
/**
* Configure the given {@link MarkdownIt} to render legacy hedgedoc 1 speakerdeck shortcodes as HTML links.
*
* @param markdownIt The {@link MarkdownIt} to configure
*/
export const legacySpeakerdeckShortCode: MarkdownIt.PluginSimple = (markdownIt) => {
markdownItRegex(markdownIt, {
name: 'legacy-speakerdeck-short-code',
regex: legacySpeakerdeckRegex,
replace: (match) => `<a href="https://speakerdeck.com/${match}">https://speakerdeck.com/${match}</a>`
} as RegexOptions)
}