dumi 2.0.9 → 2.0.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/assetParsers/atom.d.ts +3 -1
- package/dist/assetParsers/atom.js +50 -36
- package/dist/assetParsers/block.js +4 -3
- package/dist/client/theme-api/types.d.ts +4 -1
- package/dist/client/theme-api/useNavData.d.ts +3 -1
- package/dist/client/theme-api/useNavData.js +5 -2
- package/dist/features/assets.js +1 -1
- package/dist/features/autoAlias.js +9 -9
- package/dist/features/parser.js +3 -3
- package/dist/loaders/markdown/transformer/remarkEmbed.js +30 -1
- package/dist/service/service.js +2 -2
- package/package.json +2 -2
- package/theme-default/slots/Features/index.js +16 -3
- package/theme-default/slots/Features/index.less +6 -0
|
@@ -4,12 +4,14 @@ declare class AtomAssetsParser {
|
|
|
4
4
|
private resolveDir;
|
|
5
5
|
private unresolvedFiles;
|
|
6
6
|
private parser;
|
|
7
|
-
private
|
|
7
|
+
private parseDeferrer;
|
|
8
8
|
private watcher;
|
|
9
9
|
private cbs;
|
|
10
|
+
private resolveFilter;
|
|
10
11
|
constructor(opts: {
|
|
11
12
|
entryFile: string;
|
|
12
13
|
resolveDir: string;
|
|
14
|
+
resolveFilter?: AtomAssetsParser['resolveFilter'];
|
|
13
15
|
unpkgHost?: string;
|
|
14
16
|
watch?: boolean;
|
|
15
17
|
});
|
|
@@ -35,6 +35,7 @@ var AtomAssetsParser = class {
|
|
|
35
35
|
this.watcher = null;
|
|
36
36
|
this.cbs = [];
|
|
37
37
|
this.resolveDir = opts.resolveDir;
|
|
38
|
+
this.resolveFilter = opts.resolveFilter || (() => true);
|
|
38
39
|
this.entryDir = import_path.default.relative(opts.resolveDir, import_path.default.dirname(opts.entryFile));
|
|
39
40
|
this.parser = new import_parser.SchemaParser({
|
|
40
41
|
entryPath: opts.entryFile,
|
|
@@ -43,45 +44,58 @@ var AtomAssetsParser = class {
|
|
|
43
44
|
});
|
|
44
45
|
}
|
|
45
46
|
async parse() {
|
|
46
|
-
if (!this.
|
|
47
|
-
this.
|
|
47
|
+
if (!this.parseDeferrer || this.unresolvedFiles.length) {
|
|
48
|
+
this.parseDeferrer = (async () => {
|
|
48
49
|
await this.parser.patch(this.unresolvedFiles.splice(0));
|
|
49
|
-
|
|
50
|
+
const resolver = new import_parser.SchemaResolver(await this.parser.parse());
|
|
51
|
+
const result = {
|
|
52
|
+
components: {},
|
|
53
|
+
functions: {}
|
|
54
|
+
};
|
|
55
|
+
const fallbackProps = { type: "object", properties: {} };
|
|
56
|
+
const fallbackSignature = { arguments: [] };
|
|
57
|
+
resolver.componentList.forEach((id) => {
|
|
58
|
+
const needResolve = this.resolveFilter({
|
|
59
|
+
id,
|
|
60
|
+
type: "COMPONENT",
|
|
61
|
+
ids: resolver.componentList
|
|
62
|
+
});
|
|
63
|
+
let propsConfig = needResolve ? resolver.getComponent(id).props : fallbackProps;
|
|
64
|
+
const size = Buffer.byteLength(JSON.stringify(propsConfig));
|
|
65
|
+
if (size > MAX_PARSE_SIZE) {
|
|
66
|
+
propsConfig = fallbackProps;
|
|
67
|
+
import_plugin_utils.logger.warn(`Parsed component ${id} props size ${size} exceeds 512KB, skip it.`);
|
|
68
|
+
}
|
|
69
|
+
result.components[id] = {
|
|
70
|
+
type: "COMPONENT",
|
|
71
|
+
id,
|
|
72
|
+
title: id,
|
|
73
|
+
propsConfig
|
|
74
|
+
};
|
|
75
|
+
});
|
|
76
|
+
resolver.functionList.forEach((id) => {
|
|
77
|
+
const needResolve = this.resolveFilter({
|
|
78
|
+
id,
|
|
79
|
+
type: "FUNCTION",
|
|
80
|
+
ids: resolver.functionList
|
|
81
|
+
});
|
|
82
|
+
let signature = needResolve ? resolver.getFunction(id).signature : fallbackSignature;
|
|
83
|
+
const size = Buffer.byteLength(JSON.stringify(signature));
|
|
84
|
+
if (size > MAX_PARSE_SIZE) {
|
|
85
|
+
signature = fallbackSignature;
|
|
86
|
+
import_plugin_utils.logger.warn(`Parsed function ${id} signature size ${size} exceeds 512KB, skip it.`);
|
|
87
|
+
}
|
|
88
|
+
result.functions[id] = {
|
|
89
|
+
type: "FUNCTION",
|
|
90
|
+
id,
|
|
91
|
+
title: id,
|
|
92
|
+
signature
|
|
93
|
+
};
|
|
94
|
+
});
|
|
95
|
+
return result;
|
|
50
96
|
})();
|
|
51
97
|
}
|
|
52
|
-
return this.
|
|
53
|
-
const components = {};
|
|
54
|
-
const functions = {};
|
|
55
|
-
resolver.componentList.forEach((id) => {
|
|
56
|
-
let propsConfig = resolver.getComponent(id).props;
|
|
57
|
-
const size = Buffer.byteLength(JSON.stringify(propsConfig));
|
|
58
|
-
if (size > MAX_PARSE_SIZE) {
|
|
59
|
-
propsConfig = { type: "object", properties: {} };
|
|
60
|
-
import_plugin_utils.logger.warn(`Parsed component ${id} props size ${size} exceeds 512KB, skip it.`);
|
|
61
|
-
}
|
|
62
|
-
components[id] = {
|
|
63
|
-
type: "COMPONENT",
|
|
64
|
-
id,
|
|
65
|
-
title: id,
|
|
66
|
-
propsConfig
|
|
67
|
-
};
|
|
68
|
-
});
|
|
69
|
-
resolver.functionList.forEach((id) => {
|
|
70
|
-
let signature = resolver.getFunction(id).signature;
|
|
71
|
-
const size = Buffer.byteLength(JSON.stringify(signature));
|
|
72
|
-
if (size > MAX_PARSE_SIZE) {
|
|
73
|
-
signature = { arguments: [] };
|
|
74
|
-
import_plugin_utils.logger.warn(`Parsed function ${id} signature size ${size} exceeds 512KB, skip it.`);
|
|
75
|
-
}
|
|
76
|
-
functions[id] = {
|
|
77
|
-
type: "FUNCTION",
|
|
78
|
-
id,
|
|
79
|
-
title: id,
|
|
80
|
-
signature
|
|
81
|
-
};
|
|
82
|
-
});
|
|
83
|
-
return { components, functions };
|
|
84
|
-
});
|
|
98
|
+
return this.parseDeferrer;
|
|
85
99
|
}
|
|
86
100
|
watch(cb) {
|
|
87
101
|
this.cbs.push(cb);
|
|
@@ -63,9 +63,10 @@ async function parseBlockAsset(opts) {
|
|
|
63
63
|
cwd: resolved
|
|
64
64
|
});
|
|
65
65
|
if (pkgJsonPath) {
|
|
66
|
-
|
|
66
|
+
const pkg = require(pkgJsonPath);
|
|
67
|
+
asset.dependencies[pkg.name] = {
|
|
67
68
|
type: "NPM",
|
|
68
|
-
value:
|
|
69
|
+
value: pkg.version
|
|
69
70
|
};
|
|
70
71
|
}
|
|
71
72
|
return { path: args.path, external: true };
|
|
@@ -87,7 +88,7 @@ async function parseBlockAsset(opts) {
|
|
|
87
88
|
".json"
|
|
88
89
|
].includes(ext);
|
|
89
90
|
const isEntryPoint = args.pluginData.kind === "entry-point";
|
|
90
|
-
const filename = isEntryPoint ? `index${ext}` : (0, import_plugin_utils.winPath)(import_path.default.relative(import_path.default.dirname(opts.fileAbsPath), args.path));
|
|
91
|
+
const filename = isEntryPoint ? `index${ext}` : (0, import_plugin_utils.winPath)(import_path.default.relative(import_path.default.dirname(opts.fileAbsPath), args.path)).replace(/^(\.?\.\/)+/g, "");
|
|
91
92
|
if (isModule || isPlainText) {
|
|
92
93
|
asset.dependencies[filename] = {
|
|
93
94
|
type: "FILE",
|
|
@@ -74,6 +74,7 @@ export interface IRouteMeta {
|
|
|
74
74
|
features?: {
|
|
75
75
|
emoji?: string;
|
|
76
76
|
title?: string;
|
|
77
|
+
link?: string;
|
|
77
78
|
description?: string;
|
|
78
79
|
[key: string]: any;
|
|
79
80
|
}[];
|
|
@@ -156,7 +157,9 @@ export interface IThemeConfig {
|
|
|
156
157
|
logo?: string;
|
|
157
158
|
nav?: (INavItem & {
|
|
158
159
|
children?: INavItem[];
|
|
159
|
-
})[]
|
|
160
|
+
})[] | Record<string, (INavItem & {
|
|
161
|
+
children?: INavItem[];
|
|
162
|
+
})[]>;
|
|
160
163
|
sidebar?: Record<string, ISidebarGroup[]>;
|
|
161
164
|
footer?: string;
|
|
162
165
|
[key: string]: any;
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
function _typeof(obj) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (obj) { return typeof obj; } : function (obj) { return obj && "function" == typeof Symbol && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }, _typeof(obj); }
|
|
2
|
+
|
|
1
3
|
function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
|
|
2
4
|
|
|
3
5
|
function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
|
|
@@ -10,7 +12,7 @@ function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Sy
|
|
|
10
12
|
|
|
11
13
|
function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
|
|
12
14
|
|
|
13
|
-
import { useFullSidebarData, useSiteData } from 'dumi';
|
|
15
|
+
import { useFullSidebarData, useLocale, useSiteData } from 'dumi';
|
|
14
16
|
import { useState } from 'react';
|
|
15
17
|
import { pickRouteSortMeta, useLocaleDocRoutes, useRouteDataComparer } from "./utils";
|
|
16
18
|
/**
|
|
@@ -18,6 +20,7 @@ import { pickRouteSortMeta, useLocaleDocRoutes, useRouteDataComparer } from "./u
|
|
|
18
20
|
*/
|
|
19
21
|
|
|
20
22
|
export var useNavData = function useNavData() {
|
|
23
|
+
var locale = useLocale();
|
|
21
24
|
var routes = useLocaleDocRoutes();
|
|
22
25
|
|
|
23
26
|
var _useSiteData = useSiteData(),
|
|
@@ -28,7 +31,7 @@ export var useNavData = function useNavData() {
|
|
|
28
31
|
|
|
29
32
|
var _useState = useState(function () {
|
|
30
33
|
// use user config first
|
|
31
|
-
if (themeConfig.nav) return themeConfig.nav; // fallback to generate nav data from sidebar data
|
|
34
|
+
if (themeConfig.nav) return _typeof(themeConfig.nav) === 'object' ? themeConfig.nav[locale.id] : themeConfig.nav; // fallback to generate nav data from sidebar data
|
|
32
35
|
|
|
33
36
|
var data = Object.entries(sidebar).map(function (_ref) {
|
|
34
37
|
var _ref2 = _slicedToArray(_ref, 2),
|
package/dist/features/assets.js
CHANGED
|
@@ -69,7 +69,7 @@ var assets_default = (api) => {
|
|
|
69
69
|
return await api.applyPlugins({
|
|
70
70
|
key: "modifyAssetsMetadata",
|
|
71
71
|
initialValue: {
|
|
72
|
-
name: api.config.themeConfig.
|
|
72
|
+
name: api.config.themeConfig.name || api.pkg.name,
|
|
73
73
|
npmPackageName: api.pkg.name,
|
|
74
74
|
version: api.pkg.version,
|
|
75
75
|
description: api.pkg.description,
|
|
@@ -36,27 +36,27 @@ var autoAlias_default = (api) => {
|
|
|
36
36
|
},
|
|
37
37
|
enableBy: ({ userConfig }) => userConfig.autoAlias !== false
|
|
38
38
|
});
|
|
39
|
-
api.
|
|
40
|
-
var _a;
|
|
39
|
+
api.modifyConfig(async (memo) => {
|
|
40
|
+
var _a, _b, _c;
|
|
41
41
|
let entryDir = "";
|
|
42
|
-
if ((_a =
|
|
43
|
-
entryDir = import_path.default.resolve(api.cwd,
|
|
42
|
+
if ((_a = memo.resolve) == null ? void 0 : _a.entryFile) {
|
|
43
|
+
entryDir = import_path.default.resolve(api.cwd, memo.resolve.entryFile);
|
|
44
44
|
} else if (import_fs.default.existsSync(import_path.default.join(api.cwd, "src"))) {
|
|
45
45
|
entryDir = import_path.default.join(api.cwd, "src");
|
|
46
46
|
}
|
|
47
47
|
if (entryDir && api.pkg.name) {
|
|
48
48
|
const fatherConfigs = await (0, import_utils.tryFatherBuildConfigs)(api.cwd);
|
|
49
49
|
fatherConfigs.sort((a, b) => {
|
|
50
|
-
var _a2,
|
|
50
|
+
var _a2, _b2;
|
|
51
51
|
const aLevel = (((_a2 = a.output) == null ? void 0 : _a2.path) || a.output).split("/").length;
|
|
52
|
-
const bLevel = (((
|
|
52
|
+
const bLevel = (((_b2 = b.output) == null ? void 0 : _b2.path) || b.output).split("/").length;
|
|
53
53
|
return bLevel - aLevel;
|
|
54
54
|
});
|
|
55
55
|
fatherConfigs.forEach((item) => {
|
|
56
|
-
var _a2;
|
|
57
|
-
memo.alias[`${api.pkg.name}/${((_a2 = item.output) == null ? void 0 : _a2.path) || item.output}`] = import_path.default.join(api.cwd, item.entry || item.input);
|
|
56
|
+
var _a2, _b2, _c2;
|
|
57
|
+
(_b2 = memo.alias)[_c2 = `${api.pkg.name}/${((_a2 = item.output) == null ? void 0 : _a2.path) || item.output}`] ?? (_b2[_c2] = import_path.default.join(api.cwd, item.entry || item.input));
|
|
58
58
|
});
|
|
59
|
-
memo.alias[api.pkg.name] = entryDir;
|
|
59
|
+
(_b = memo.alias)[_c = api.pkg.name] ?? (_b[_c] = entryDir);
|
|
60
60
|
}
|
|
61
61
|
return memo;
|
|
62
62
|
});
|
package/dist/features/parser.js
CHANGED
|
@@ -45,9 +45,8 @@ var parser_default = (api) => {
|
|
|
45
45
|
}
|
|
46
46
|
});
|
|
47
47
|
api.modifyDefaultConfig((memo) => {
|
|
48
|
-
var _a
|
|
48
|
+
var _a;
|
|
49
49
|
(0, import_assert.default)((_a = api.userConfig.resolve) == null ? void 0 : _a.entryFile, "`resolve.entryFile` must be configured when `apiParser` enable");
|
|
50
|
-
(0, import_assert.default)((_b = api.pkg.devDependencies) == null ? void 0 : _b["typescript"], "typescript must be installed when `apiParser` enable");
|
|
51
50
|
return memo;
|
|
52
51
|
});
|
|
53
52
|
api.onStart(async () => {
|
|
@@ -57,7 +56,8 @@ var parser_default = (api) => {
|
|
|
57
56
|
api.service.atomParser = new AtomAssetsParser({
|
|
58
57
|
entryFile: api.config.resolve.entryFile,
|
|
59
58
|
resolveDir: api.cwd,
|
|
60
|
-
unpkgHost: api.config.apiParser.unpkgHost
|
|
59
|
+
unpkgHost: api.config.apiParser.unpkgHost,
|
|
60
|
+
resolveFilter: api.config.apiParser.resolveFilter
|
|
61
61
|
});
|
|
62
62
|
if (api.env === "development") {
|
|
63
63
|
api.service.atomParser.watch(writeAtomsMetaFile);
|
|
@@ -29,6 +29,7 @@ var import_utils = require("../../../utils");
|
|
|
29
29
|
var import_enhanced_resolve = __toESM(require("enhanced-resolve"));
|
|
30
30
|
var import_fs = __toESM(require("fs"));
|
|
31
31
|
var import_path = __toESM(require("path"));
|
|
32
|
+
var import_plugin_utils = require("umi/plugin-utils");
|
|
32
33
|
var import_url = __toESM(require("url"));
|
|
33
34
|
var EMBED_OPEN_TAG = "<embed ";
|
|
34
35
|
var EMBED_CLOSE_TAG = "</embed>";
|
|
@@ -46,6 +47,31 @@ var visit;
|
|
|
46
47
|
({ default: remarkDirective } = await import("remark-directive"));
|
|
47
48
|
({ default: remarkGfm } = await import("remark-gfm"));
|
|
48
49
|
})();
|
|
50
|
+
function remarkReplaceSrc(opts) {
|
|
51
|
+
function getEmbedRltPath(value) {
|
|
52
|
+
const { fileAbsPath, parentAbsPath } = opts;
|
|
53
|
+
const absPath = import_path.default.resolve(fileAbsPath, "..", value);
|
|
54
|
+
return (0, import_plugin_utils.winPath)(import_path.default.relative(import_path.default.dirname(parentAbsPath), absPath)).replace(/^([^.])/, "./$1");
|
|
55
|
+
}
|
|
56
|
+
return (ast) => {
|
|
57
|
+
visit(ast, ["html", "image", "link"], (node) => {
|
|
58
|
+
switch (node.type) {
|
|
59
|
+
case "html":
|
|
60
|
+
if (/^<(code|img|a)[^>]+(src|href)=('|")\.\.?\//.test(node.value)) {
|
|
61
|
+
node.value = node.value.replace(/(src|href)=("|')([^]+?)\2/, (_, tag, quote, value) => `${tag}=${quote}${getEmbedRltPath(value)}${quote}`);
|
|
62
|
+
}
|
|
63
|
+
break;
|
|
64
|
+
case "image":
|
|
65
|
+
case "link":
|
|
66
|
+
if (/^\.\.?\//.test(node.url)) {
|
|
67
|
+
node.url = getEmbedRltPath(node.url);
|
|
68
|
+
}
|
|
69
|
+
break;
|
|
70
|
+
default:
|
|
71
|
+
}
|
|
72
|
+
});
|
|
73
|
+
};
|
|
74
|
+
}
|
|
49
75
|
function remarkRawAST() {
|
|
50
76
|
this.Compiler = function Compiler(ast) {
|
|
51
77
|
visit(ast, "yaml", (node, ancestors) => {
|
|
@@ -83,7 +109,10 @@ function remarkEmbed(opts) {
|
|
|
83
109
|
const {
|
|
84
110
|
result: mdast,
|
|
85
111
|
data: { embeds }
|
|
86
|
-
} = unified().use(remarkParse).use(remarkEmbed, { ...opts, fileAbsPath: absPath }).use(remarkFrontmatter).use(remarkDirective).use(remarkGfm).use(
|
|
112
|
+
} = unified().use(remarkParse).use(remarkEmbed, { ...opts, fileAbsPath: absPath }).use(remarkFrontmatter).use(remarkDirective).use(remarkGfm).use(remarkReplaceSrc, {
|
|
113
|
+
fileAbsPath: absPath,
|
|
114
|
+
parentAbsPath: opts.fileAbsPath
|
|
115
|
+
}).use(remarkRawAST).processSync(content);
|
|
87
116
|
if (!node.value.endsWith(EMBED_CLOSE_TAG)) {
|
|
88
117
|
for (let j = i; j < parent.children.length; j++) {
|
|
89
118
|
const sibling = parent.children[j];
|
package/dist/service/service.js
CHANGED
|
@@ -41,10 +41,10 @@ var DumiService = class extends import_umi.Service {
|
|
|
41
41
|
var _a;
|
|
42
42
|
const cwd = this.cwd;
|
|
43
43
|
const absSrcPath = ((_a = this.userConfig.alias) == null ? void 0 : _a["@"]) ?? cwd;
|
|
44
|
-
const absPagesPath = winJoin(
|
|
44
|
+
const absPagesPath = winJoin(cwd, `.${import_constants.FRAMEWORK_NAME}`, "pages");
|
|
45
45
|
const absApiRoutesPath = winJoin(absSrcPath, "api");
|
|
46
46
|
const tmp = this.env === import_core.Env.development ? `tmp` : `tmp-${this.env}`;
|
|
47
|
-
const absTmpPath = winJoin(
|
|
47
|
+
const absTmpPath = winJoin(cwd, `.${import_constants.FRAMEWORK_NAME}`, tmp);
|
|
48
48
|
const absNodeModulesPath = winJoin(cwd, "node_modules");
|
|
49
49
|
const absOutputPath = winJoin(cwd, "dist");
|
|
50
50
|
return {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dumi",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.11",
|
|
4
4
|
"description": "📖 Documentation Generator of React Component",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"generator",
|
|
@@ -84,7 +84,7 @@
|
|
|
84
84
|
"animated-scroll-to": "^2.3.0",
|
|
85
85
|
"codesandbox": "^2.2.3",
|
|
86
86
|
"deepmerge": "^4.2.2",
|
|
87
|
-
"dumi-afx-deps": "^1.0.0-alpha.
|
|
87
|
+
"dumi-afx-deps": "^1.0.0-alpha.6",
|
|
88
88
|
"dumi-assets-types": "2.0.0-alpha.0",
|
|
89
89
|
"enhanced-resolve": "^5.10.0",
|
|
90
90
|
"estree-util-to-js": "^1.1.0",
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { useRouteMeta } from 'dumi';
|
|
1
|
+
import { Link, useRouteMeta } from 'dumi';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
import "./index.less";
|
|
4
4
|
|
|
@@ -17,11 +17,24 @@ var Features = function Features() {
|
|
|
17
17
|
}, frontmatter.features.map(function (_ref) {
|
|
18
18
|
var title = _ref.title,
|
|
19
19
|
description = _ref.description,
|
|
20
|
-
emoji = _ref.emoji
|
|
20
|
+
emoji = _ref.emoji,
|
|
21
|
+
link = _ref.link;
|
|
22
|
+
var titleWithLink;
|
|
23
|
+
|
|
24
|
+
if (link) {
|
|
25
|
+
titleWithLink = /^(\w+:)\/\/|^(mailto|tel):/.test(link) ? /*#__PURE__*/React.createElement("a", {
|
|
26
|
+
href: link,
|
|
27
|
+
target: "_blank",
|
|
28
|
+
rel: "noreferrer"
|
|
29
|
+
}, title) : /*#__PURE__*/React.createElement(Link, {
|
|
30
|
+
to: link
|
|
31
|
+
}, title);
|
|
32
|
+
}
|
|
33
|
+
|
|
21
34
|
return /*#__PURE__*/React.createElement("div", {
|
|
22
35
|
key: title,
|
|
23
36
|
className: "dumi-default-features-item"
|
|
24
|
-
}, emoji && /*#__PURE__*/React.createElement("i", null, emoji), title && /*#__PURE__*/React.createElement("h3", null, title), description && /*#__PURE__*/React.createElement("p", {
|
|
37
|
+
}, emoji && /*#__PURE__*/React.createElement("i", null, emoji), title && /*#__PURE__*/React.createElement("h3", null, titleWithLink || title), description && /*#__PURE__*/React.createElement("p", {
|
|
25
38
|
dangerouslySetInnerHTML: {
|
|
26
39
|
__html: description
|
|
27
40
|
}
|