mirror of
https://github.com/facebook/docusaurus.git
synced 2025-05-11 08:07:26 +02:00
fix(v2): relax URI validation (#3227)
* relax URI validation * add regex * add test * fix linting error * fix formatting * use URL rather than regex
This commit is contained in:
parent
fe281a8ebe
commit
181a6174c7
9 changed files with 44 additions and 7 deletions
|
@ -10,6 +10,7 @@ import {
|
||||||
RemarkPluginsSchema,
|
RemarkPluginsSchema,
|
||||||
RehypePluginsSchema,
|
RehypePluginsSchema,
|
||||||
AdmonitionsSchema,
|
AdmonitionsSchema,
|
||||||
|
URISchema,
|
||||||
} from '@docusaurus/utils-validation';
|
} from '@docusaurus/utils-validation';
|
||||||
|
|
||||||
export const DEFAULT_OPTIONS = {
|
export const DEFAULT_OPTIONS = {
|
||||||
|
@ -55,7 +56,7 @@ export const PluginOptionSchema = Joi.object({
|
||||||
remarkPlugins: RemarkPluginsSchema.default(DEFAULT_OPTIONS.remarkPlugins),
|
remarkPlugins: RemarkPluginsSchema.default(DEFAULT_OPTIONS.remarkPlugins),
|
||||||
rehypePlugins: RehypePluginsSchema.default(DEFAULT_OPTIONS.rehypePlugins),
|
rehypePlugins: RehypePluginsSchema.default(DEFAULT_OPTIONS.rehypePlugins),
|
||||||
admonitions: AdmonitionsSchema.default(DEFAULT_OPTIONS.admonitions),
|
admonitions: AdmonitionsSchema.default(DEFAULT_OPTIONS.admonitions),
|
||||||
editUrl: Joi.string().uri(),
|
editUrl: URISchema,
|
||||||
truncateMarker: Joi.object().default(DEFAULT_OPTIONS.truncateMarker),
|
truncateMarker: Joi.object().default(DEFAULT_OPTIONS.truncateMarker),
|
||||||
beforeDefaultRemarkPlugins: Joi.array()
|
beforeDefaultRemarkPlugins: Joi.array()
|
||||||
.items(
|
.items(
|
||||||
|
|
|
@ -10,6 +10,7 @@ import {
|
||||||
RemarkPluginsSchema,
|
RemarkPluginsSchema,
|
||||||
RehypePluginsSchema,
|
RehypePluginsSchema,
|
||||||
AdmonitionsSchema,
|
AdmonitionsSchema,
|
||||||
|
URISchema,
|
||||||
} from '@docusaurus/utils-validation';
|
} from '@docusaurus/utils-validation';
|
||||||
|
|
||||||
export const DEFAULT_OPTIONS: PluginOptions = {
|
export const DEFAULT_OPTIONS: PluginOptions = {
|
||||||
|
@ -31,7 +32,7 @@ export const DEFAULT_OPTIONS: PluginOptions = {
|
||||||
|
|
||||||
export const PluginOptionSchema = Joi.object({
|
export const PluginOptionSchema = Joi.object({
|
||||||
path: Joi.string().default(DEFAULT_OPTIONS.path),
|
path: Joi.string().default(DEFAULT_OPTIONS.path),
|
||||||
editUrl: Joi.string().uri(),
|
editUrl: URISchema,
|
||||||
routeBasePath: Joi.string().allow('').default(DEFAULT_OPTIONS.routeBasePath),
|
routeBasePath: Joi.string().allow('').default(DEFAULT_OPTIONS.routeBasePath),
|
||||||
homePageId: Joi.string().optional(),
|
homePageId: Joi.string().optional(),
|
||||||
include: Joi.array().items(Joi.string()).default(DEFAULT_OPTIONS.include),
|
include: Joi.array().items(Joi.string()).default(DEFAULT_OPTIONS.include),
|
||||||
|
|
|
@ -26,7 +26,8 @@
|
||||||
"prismjs": "^1.20.0",
|
"prismjs": "^1.20.0",
|
||||||
"prop-types": "^15.7.2",
|
"prop-types": "^15.7.2",
|
||||||
"react-router-dom": "^5.1.2",
|
"react-router-dom": "^5.1.2",
|
||||||
"react-toggle": "^4.1.1"
|
"react-toggle": "^4.1.1",
|
||||||
|
"@docusaurus/utils-validation": "^2.0.0-alpha.61"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@docusaurus/module-type-aliases": "^2.0.0-alpha.61",
|
"@docusaurus/module-type-aliases": "^2.0.0-alpha.61",
|
||||||
|
|
|
@ -6,6 +6,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
const Joi = require('@hapi/joi');
|
const Joi = require('@hapi/joi');
|
||||||
|
const {URISchema} = require('@docusaurus/utils-validation');
|
||||||
|
|
||||||
const DEFAULT_COLOR_MODE_CONFIG = {
|
const DEFAULT_COLOR_MODE_CONFIG = {
|
||||||
defaultMode: 'light',
|
defaultMode: 'light',
|
||||||
|
@ -28,7 +29,7 @@ const NavbarItemPosition = Joi.string().equal('left', 'right').default('left');
|
||||||
const DefaultNavbarItemSchema = Joi.object({
|
const DefaultNavbarItemSchema = Joi.object({
|
||||||
items: Joi.array().optional().items(Joi.link('...')),
|
items: Joi.array().optional().items(Joi.link('...')),
|
||||||
to: Joi.string(),
|
to: Joi.string(),
|
||||||
href: Joi.string().uri(),
|
href: URISchema,
|
||||||
label: Joi.string(),
|
label: Joi.string(),
|
||||||
position: NavbarItemPosition,
|
position: NavbarItemPosition,
|
||||||
activeBasePath: Joi.string(),
|
activeBasePath: Joi.string(),
|
||||||
|
@ -140,7 +141,7 @@ const ColorModeSchema = Joi.object({
|
||||||
|
|
||||||
const FooterLinkItemSchema = Joi.object({
|
const FooterLinkItemSchema = Joi.object({
|
||||||
to: Joi.string(),
|
to: Joi.string(),
|
||||||
href: Joi.string().uri(),
|
href: URISchema,
|
||||||
html: Joi.string(),
|
html: Joi.string(),
|
||||||
label: Joi.string(),
|
label: Joi.string(),
|
||||||
})
|
})
|
||||||
|
|
|
@ -59,3 +59,5 @@ exports[`validation schemas RemarkPluginsSchema: for value=3 1`] = `"\\"value\\"
|
||||||
exports[`validation schemas RemarkPluginsSchema: for value=false 1`] = `"\\"value\\" must be an array"`;
|
exports[`validation schemas RemarkPluginsSchema: for value=false 1`] = `"\\"value\\" must be an array"`;
|
||||||
|
|
||||||
exports[`validation schemas RemarkPluginsSchema: for value=null 1`] = `"\\"value\\" must be an array"`;
|
exports[`validation schemas RemarkPluginsSchema: for value=null 1`] = `"\\"value\\" must be an array"`;
|
||||||
|
|
||||||
|
exports[`validation schemas URISchema: for value="invalidURL" 1`] = `"\\"value\\" does not match any of the allowed types"`;
|
||||||
|
|
|
@ -12,6 +12,7 @@ import {
|
||||||
RehypePluginsSchema,
|
RehypePluginsSchema,
|
||||||
RemarkPluginsSchema,
|
RemarkPluginsSchema,
|
||||||
PluginIdSchema,
|
PluginIdSchema,
|
||||||
|
URISchema,
|
||||||
} from '../validationSchemas';
|
} from '../validationSchemas';
|
||||||
|
|
||||||
function createTestHelpers({
|
function createTestHelpers({
|
||||||
|
@ -106,4 +107,16 @@ describe('validation schemas', () => {
|
||||||
test('RehypePluginsSchema', () => {
|
test('RehypePluginsSchema', () => {
|
||||||
testMarkdownPluginSchemas(RehypePluginsSchema);
|
testMarkdownPluginSchemas(RehypePluginsSchema);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('URISchema', () => {
|
||||||
|
const validURL = 'https://docusaurus.io';
|
||||||
|
const doubleHash = 'https://docusaurus.io#github#/:';
|
||||||
|
const invalidURL = 'invalidURL';
|
||||||
|
const urlFromIssue = 'https://riot.im/app/#/room/#ligo-public:matrix.org';
|
||||||
|
const {testFail, testOK} = createTestHelpers({schema: URISchema});
|
||||||
|
testOK(validURL);
|
||||||
|
testOK(doubleHash);
|
||||||
|
testFail(invalidURL);
|
||||||
|
testOK(urlFromIssue);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -25,3 +25,19 @@ export const RemarkPluginsSchema = MarkdownPluginsSchema;
|
||||||
export const RehypePluginsSchema = MarkdownPluginsSchema;
|
export const RehypePluginsSchema = MarkdownPluginsSchema;
|
||||||
|
|
||||||
export const AdmonitionsSchema = Joi.object().default({});
|
export const AdmonitionsSchema = Joi.object().default({});
|
||||||
|
|
||||||
|
export const URISchema = Joi.alternatives(
|
||||||
|
Joi.string().uri(),
|
||||||
|
Joi.custom((val, helpers) => {
|
||||||
|
try {
|
||||||
|
const url = new URL(val);
|
||||||
|
if (url) {
|
||||||
|
return val;
|
||||||
|
} else {
|
||||||
|
return helpers.error('any.invalid');
|
||||||
|
}
|
||||||
|
} catch {
|
||||||
|
return helpers.error('any.invalid');
|
||||||
|
}
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
|
|
@ -107,7 +107,8 @@
|
||||||
"webpack-bundle-analyzer": "^3.6.1",
|
"webpack-bundle-analyzer": "^3.6.1",
|
||||||
"webpack-dev-server": "^3.11.0",
|
"webpack-dev-server": "^3.11.0",
|
||||||
"webpack-merge": "^4.2.2",
|
"webpack-merge": "^4.2.2",
|
||||||
"webpackbar": "^4.0.0"
|
"webpackbar": "^4.0.0",
|
||||||
|
"@docusaurus/utils-validation": "^2.0.0-alpha.61"
|
||||||
},
|
},
|
||||||
"peerDependencies": {
|
"peerDependencies": {
|
||||||
"react": "^16.8.4",
|
"react": "^16.8.4",
|
||||||
|
|
|
@ -11,6 +11,7 @@ import Joi from '@hapi/joi';
|
||||||
import {
|
import {
|
||||||
logValidationBugReportHint,
|
logValidationBugReportHint,
|
||||||
isValidationDisabledEscapeHatch,
|
isValidationDisabledEscapeHatch,
|
||||||
|
URISchema,
|
||||||
} from '@docusaurus/utils-validation';
|
} from '@docusaurus/utils-validation';
|
||||||
|
|
||||||
export const DEFAULT_CONFIG: Pick<
|
export const DEFAULT_CONFIG: Pick<
|
||||||
|
@ -55,7 +56,7 @@ const ConfigSchema = Joi.object({
|
||||||
.message('{{#label}} must be a string with a trailing `/`'),
|
.message('{{#label}} must be a string with a trailing `/`'),
|
||||||
favicon: Joi.string().required(),
|
favicon: Joi.string().required(),
|
||||||
title: Joi.string().required(),
|
title: Joi.string().required(),
|
||||||
url: Joi.string().uri().required(),
|
url: URISchema.required(),
|
||||||
onBrokenLinks: Joi.string()
|
onBrokenLinks: Joi.string()
|
||||||
.equal('ignore', 'log', 'warn', 'error', 'throw')
|
.equal('ignore', 'log', 'warn', 'error', 'throw')
|
||||||
.default(DEFAULT_CONFIG.onBrokenLinks),
|
.default(DEFAULT_CONFIG.onBrokenLinks),
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue