@docusaurus/plugin-content-docs 2.0.0-beta.ff31de0ff → 2.0.0-rc.1

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.
Files changed (231) hide show
  1. package/lib/categoryGeneratedIndex.d.ts +12 -0
  2. package/lib/categoryGeneratedIndex.js +37 -0
  3. package/lib/cli.d.ts +3 -2
  4. package/lib/cli.js +62 -72
  5. package/lib/client/docsClientUtils.d.ts +9 -28
  6. package/lib/client/docsClientUtils.js +35 -51
  7. package/lib/client/index.d.ts +81 -0
  8. package/lib/client/index.js +67 -0
  9. package/lib/constants.d.ts +4 -0
  10. package/lib/constants.js +4 -1
  11. package/lib/docs.d.ts +35 -8
  12. package/lib/docs.js +211 -78
  13. package/{src/__tests__/__fixtures__/site-with-autogenerated-sidebar/partialAutogeneratedSidebars2.js → lib/frontMatter.d.ts} +4 -10
  14. package/lib/frontMatter.js +53 -0
  15. package/lib/globalData.d.ts +3 -3
  16. package/lib/globalData.js +35 -6
  17. package/lib/index.d.ts +3 -3
  18. package/lib/index.js +137 -146
  19. package/lib/lastUpdate.d.ts +4 -6
  20. package/lib/lastUpdate.js +22 -26
  21. package/lib/markdown/index.d.ts +3 -6
  22. package/lib/markdown/index.js +3 -3
  23. package/lib/markdown/linkify.d.ts +1 -1
  24. package/lib/markdown/linkify.js +7 -4
  25. package/lib/numberPrefix.d.ts +1 -1
  26. package/lib/numberPrefix.js +16 -21
  27. package/lib/options.d.ts +3 -5
  28. package/lib/options.js +57 -29
  29. package/lib/props.d.ts +7 -2
  30. package/lib/props.js +87 -16
  31. package/lib/routes.d.ts +29 -0
  32. package/lib/routes.js +96 -0
  33. package/lib/server-export.d.ts +9 -0
  34. package/lib/server-export.js +25 -0
  35. package/lib/{sidebarItemsGenerator.d.ts → sidebars/generator.d.ts} +1 -6
  36. package/lib/sidebars/generator.js +209 -0
  37. package/lib/sidebars/index.d.ts +13 -0
  38. package/lib/sidebars/index.js +92 -0
  39. package/lib/sidebars/normalization.d.ts +13 -0
  40. package/lib/sidebars/normalization.js +59 -0
  41. package/lib/sidebars/postProcessor.d.ts +11 -0
  42. package/lib/sidebars/postProcessor.js +81 -0
  43. package/lib/sidebars/processor.d.ts +10 -0
  44. package/lib/sidebars/processor.js +79 -0
  45. package/lib/sidebars/types.d.ts +183 -0
  46. package/{types.d.ts → lib/sidebars/types.js} +2 -7
  47. package/lib/sidebars/utils.d.ts +55 -0
  48. package/lib/sidebars/utils.js +259 -0
  49. package/lib/sidebars/validation.d.ts +11 -0
  50. package/lib/sidebars/validation.js +143 -0
  51. package/lib/slug.d.ts +5 -4
  52. package/lib/slug.js +29 -19
  53. package/{src/__tests__/__fixtures__/sidebars/sidebars-first-level-not-category.js → lib/tags.d.ts} +3 -14
  54. package/lib/tags.js +21 -0
  55. package/lib/translations.d.ts +3 -3
  56. package/lib/translations.js +100 -93
  57. package/lib/types.d.ts +13 -172
  58. package/lib/versions/files.d.ts +50 -0
  59. package/lib/versions/files.js +141 -0
  60. package/lib/versions/index.d.ts +36 -0
  61. package/lib/versions/index.js +154 -0
  62. package/lib/versions/validation.d.ts +17 -0
  63. package/lib/versions/validation.js +71 -0
  64. package/package.json +44 -29
  65. package/src/categoryGeneratedIndex.ts +60 -0
  66. package/src/cli.ts +94 -114
  67. package/src/client/docsClientUtils.ts +47 -84
  68. package/src/client/index.ts +158 -0
  69. package/src/constants.ts +4 -2
  70. package/src/docs.ts +294 -78
  71. package/src/frontMatter.ts +63 -0
  72. package/src/globalData.ts +57 -7
  73. package/src/index.ts +200 -204
  74. package/src/lastUpdate.ts +27 -34
  75. package/src/markdown/index.ts +10 -16
  76. package/src/markdown/linkify.ts +8 -5
  77. package/src/numberPrefix.ts +19 -26
  78. package/src/options.ts +61 -43
  79. package/src/plugin-content-docs.d.ts +575 -78
  80. package/src/props.ts +128 -23
  81. package/src/routes.ts +159 -0
  82. package/src/server-export.ts +26 -0
  83. package/src/sidebars/README.md +10 -0
  84. package/src/sidebars/generator.ts +292 -0
  85. package/src/sidebars/index.ts +118 -0
  86. package/src/sidebars/normalization.ts +91 -0
  87. package/src/sidebars/postProcessor.ts +112 -0
  88. package/src/sidebars/processor.ts +123 -0
  89. package/src/sidebars/types.ts +280 -0
  90. package/src/sidebars/utils.ts +393 -0
  91. package/src/sidebars/validation.ts +179 -0
  92. package/src/slug.ts +42 -23
  93. package/src/tags.ts +20 -0
  94. package/src/translations.ts +155 -124
  95. package/src/types.ts +17 -234
  96. package/src/versions/files.ts +216 -0
  97. package/src/versions/index.ts +246 -0
  98. package/src/versions/validation.ts +115 -0
  99. package/lib/.tsbuildinfo +0 -4673
  100. package/lib/docFrontMatter.d.ts +0 -21
  101. package/lib/docFrontMatter.js +0 -33
  102. package/lib/sidebarItemsGenerator.js +0 -211
  103. package/lib/sidebars.d.ts +0 -42
  104. package/lib/sidebars.js +0 -309
  105. package/lib/theme/hooks/useDocs.d.ts +0 -20
  106. package/lib/theme/hooks/useDocs.js +0 -72
  107. package/lib/versions.d.ts +0 -16
  108. package/lib/versions.js +0 -287
  109. package/src/__tests__/__fixtures__/bad-id-site/docs/invalid-id.md +0 -5
  110. package/src/__tests__/__fixtures__/bad-slug-on-doc-home-site/docs/docWithSlug.md +0 -5
  111. package/src/__tests__/__fixtures__/empty-site/docusaurus.config.js +0 -16
  112. package/src/__tests__/__fixtures__/empty-site/sidebars.json +0 -1
  113. package/src/__tests__/__fixtures__/sidebars/sidebars-category-shorthand.js +0 -34
  114. package/src/__tests__/__fixtures__/sidebars/sidebars-category-wrong-items.json +0 -11
  115. package/src/__tests__/__fixtures__/sidebars/sidebars-category-wrong-label.json +0 -11
  116. package/src/__tests__/__fixtures__/sidebars/sidebars-category.js +0 -44
  117. package/src/__tests__/__fixtures__/sidebars/sidebars-collapsed-first-level.json +0 -20
  118. package/src/__tests__/__fixtures__/sidebars/sidebars-collapsed.json +0 -21
  119. package/src/__tests__/__fixtures__/sidebars/sidebars-doc-id-not-string.json +0 -10
  120. package/src/__tests__/__fixtures__/sidebars/sidebars-link-wrong-href.json +0 -11
  121. package/src/__tests__/__fixtures__/sidebars/sidebars-link-wrong-label.json +0 -11
  122. package/src/__tests__/__fixtures__/sidebars/sidebars-link.json +0 -11
  123. package/src/__tests__/__fixtures__/sidebars/sidebars-unknown-type.json +0 -14
  124. package/src/__tests__/__fixtures__/sidebars/sidebars-wrong-field.json +0 -20
  125. package/src/__tests__/__fixtures__/sidebars/sidebars.json +0 -20
  126. package/src/__tests__/__fixtures__/simple-site/docs/foo/bar.md +0 -69
  127. package/src/__tests__/__fixtures__/simple-site/docs/foo/baz.md +0 -67
  128. package/src/__tests__/__fixtures__/simple-site/docs/headingAsTitle.md +0 -1
  129. package/src/__tests__/__fixtures__/simple-site/docs/hello.md +0 -52
  130. package/src/__tests__/__fixtures__/simple-site/docs/ipsum.md +0 -5
  131. package/src/__tests__/__fixtures__/simple-site/docs/lorem.md +0 -6
  132. package/src/__tests__/__fixtures__/simple-site/docs/rootAbsoluteSlug.md +0 -5
  133. package/src/__tests__/__fixtures__/simple-site/docs/rootRelativeSlug.md +0 -5
  134. package/src/__tests__/__fixtures__/simple-site/docs/rootResolvedSlug.md +0 -5
  135. package/src/__tests__/__fixtures__/simple-site/docs/rootTryToEscapeSlug.md +0 -5
  136. package/src/__tests__/__fixtures__/simple-site/docs/slugs/absoluteSlug.md +0 -5
  137. package/src/__tests__/__fixtures__/simple-site/docs/slugs/relativeSlug.md +0 -5
  138. package/src/__tests__/__fixtures__/simple-site/docs/slugs/resolvedSlug.md +0 -5
  139. package/src/__tests__/__fixtures__/simple-site/docs/slugs/tryToEscapeSlug.md +0 -5
  140. package/src/__tests__/__fixtures__/simple-site/docusaurus.config.js +0 -14
  141. package/src/__tests__/__fixtures__/simple-site/sidebars.json +0 -23
  142. package/src/__tests__/__fixtures__/simple-site/wrong-sidebars.json +0 -7
  143. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/0-getting-started.md +0 -3
  144. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/1-installation.md +0 -3
  145. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/00_api-overview.md +0 -3
  146. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/01_Core APIs/0 --- Client API.md +0 -1
  147. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/01_Core APIs/1 --- Server API.md +0 -1
  148. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/02_Extension APIs/0. Plugin API.md +0 -1
  149. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/02_Extension APIs/1. Theme API.md +0 -1
  150. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/02_Extension APIs/_category_.yml +0 -1
  151. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/03_api-end.md +0 -3
  152. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/3-API/_category_.json +0 -3
  153. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/0-guide2.5.md +0 -8
  154. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/02-guide2.md +0 -7
  155. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/_category_.json +0 -3
  156. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/a-guide4.md +0 -7
  157. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/b-guide5.md +0 -7
  158. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/guide3.md +0 -8
  159. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docs/Guides/z-guide1.md +0 -8
  160. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/docusaurus.config.js +0 -14
  161. package/src/__tests__/__fixtures__/site-with-autogenerated-sidebar/partialAutogeneratedSidebars.js +0 -23
  162. package/src/__tests__/__fixtures__/site-with-doc-label/docs/hello-1.md +0 -7
  163. package/src/__tests__/__fixtures__/site-with-doc-label/docs/hello-2.md +0 -8
  164. package/src/__tests__/__fixtures__/site-with-doc-label/docusaurus.config.js +0 -14
  165. package/src/__tests__/__fixtures__/site-with-doc-label/sidebars.json +0 -14
  166. package/src/__tests__/__fixtures__/versioned-site/community/team.md +0 -1
  167. package/src/__tests__/__fixtures__/versioned-site/community_sidebars.json +0 -3
  168. package/src/__tests__/__fixtures__/versioned-site/community_versioned_docs/version-1.0.0/team.md +0 -1
  169. package/src/__tests__/__fixtures__/versioned-site/community_versioned_sidebars/version-1.0.0-sidebars.json +0 -3
  170. package/src/__tests__/__fixtures__/versioned-site/community_versions.json +0 -1
  171. package/src/__tests__/__fixtures__/versioned-site/docs/foo/bar.md +0 -4
  172. package/src/__tests__/__fixtures__/versioned-site/docs/hello.md +0 -1
  173. package/src/__tests__/__fixtures__/versioned-site/docs/slugs/absoluteSlug.md +0 -5
  174. package/src/__tests__/__fixtures__/versioned-site/docs/slugs/relativeSlug.md +0 -5
  175. package/src/__tests__/__fixtures__/versioned-site/docs/slugs/resolvedSlug.md +0 -5
  176. package/src/__tests__/__fixtures__/versioned-site/docs/slugs/tryToEscapeSlug.md +0 -5
  177. package/src/__tests__/__fixtures__/versioned-site/docusaurus.config.js +0 -18
  178. package/src/__tests__/__fixtures__/versioned-site/i18n/en/docusaurus-plugin-content-docs/version-1.0.0/hello.md +0 -1
  179. package/src/__tests__/__fixtures__/versioned-site/i18n/en/docusaurus-plugin-content-docs-community/current/team.md +0 -5
  180. package/src/__tests__/__fixtures__/versioned-site/i18n/fr/docusaurus-plugin-content-docs/version-1.0.0/hello.md +0 -1
  181. package/src/__tests__/__fixtures__/versioned-site/sidebars.json +0 -10
  182. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-1.0.0/foo/bar.md +0 -4
  183. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-1.0.0/foo/baz.md +0 -1
  184. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-1.0.0/hello.md +0 -1
  185. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-1.0.1/foo/bar.md +0 -1
  186. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-1.0.1/hello.md +0 -1
  187. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/rootAbsoluteSlug.md +0 -5
  188. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/rootRelativeSlug.md +0 -5
  189. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/rootResolvedSlug.md +0 -5
  190. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/rootTryToEscapeSlug.md +0 -5
  191. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/slugs/absoluteSlug.md +0 -5
  192. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/slugs/relativeSlug.md +0 -5
  193. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/slugs/resolvedSlug.md +0 -5
  194. package/src/__tests__/__fixtures__/versioned-site/versioned_docs/version-withSlugs/slugs/tryToEscapeSlug.md +0 -5
  195. package/src/__tests__/__fixtures__/versioned-site/versioned_sidebars/version-1.0.0-sidebars.json +0 -11
  196. package/src/__tests__/__fixtures__/versioned-site/versioned_sidebars/version-1.0.1-sidebars.json +0 -10
  197. package/src/__tests__/__fixtures__/versioned-site/versioned_sidebars/version-withSlugs-sidebars.json +0 -5
  198. package/src/__tests__/__fixtures__/versioned-site/versions.json +0 -5
  199. package/src/__tests__/__snapshots__/cli.test.ts.snap +0 -90
  200. package/src/__tests__/__snapshots__/index.test.ts.snap +0 -1907
  201. package/src/__tests__/__snapshots__/sidebars.test.ts.snap +0 -218
  202. package/src/__tests__/__snapshots__/translations.test.ts.snap +0 -487
  203. package/src/__tests__/cli.test.ts +0 -333
  204. package/src/__tests__/docFrontMatter.test.ts +0 -204
  205. package/src/__tests__/docs.test.ts +0 -875
  206. package/src/__tests__/index.test.ts +0 -1831
  207. package/src/__tests__/lastUpdate.test.ts +0 -68
  208. package/src/__tests__/numberPrefix.test.ts +0 -199
  209. package/src/__tests__/options.test.ts +0 -232
  210. package/src/__tests__/sidebarItemsGenerator.test.ts +0 -336
  211. package/src/__tests__/sidebars.test.ts +0 -638
  212. package/src/__tests__/slug.test.ts +0 -109
  213. package/src/__tests__/translations.test.ts +0 -159
  214. package/src/__tests__/versions.test.ts +0 -718
  215. package/src/client/__tests__/docsClientUtils.test.ts +0 -372
  216. package/src/docFrontMatter.ts +0 -53
  217. package/src/markdown/__tests__/__fixtures__/docs/doc-localized.md +0 -1
  218. package/src/markdown/__tests__/__fixtures__/docs/doc1.md +0 -13
  219. package/src/markdown/__tests__/__fixtures__/docs/doc2.md +0 -12
  220. package/src/markdown/__tests__/__fixtures__/docs/doc4.md +0 -19
  221. package/src/markdown/__tests__/__fixtures__/docs/doc5.md +0 -6
  222. package/src/markdown/__tests__/__fixtures__/docs/subdir/doc3.md +0 -3
  223. package/src/markdown/__tests__/__fixtures__/versioned_docs/version-1.0.0/doc2.md +0 -7
  224. package/src/markdown/__tests__/__fixtures__/versioned_docs/version-1.0.0/subdir/doc1.md +0 -3
  225. package/src/markdown/__tests__/__snapshots__/linkify.test.ts.snap +0 -82
  226. package/src/markdown/__tests__/linkify.test.ts +0 -190
  227. package/src/sidebarItemsGenerator.ts +0 -307
  228. package/src/sidebars.ts +0 -489
  229. package/src/theme/hooks/useDocs.ts +0 -99
  230. package/src/versions.ts +0 -511
  231. package/tsconfig.json +0 -9
@@ -1,190 +0,0 @@
1
- /**
2
- * Copyright (c) Facebook, Inc. and its affiliates.
3
- *
4
- * This source code is licensed under the MIT license found in the
5
- * LICENSE file in the root directory of this source tree.
6
- */
7
-
8
- import fs from 'fs-extra';
9
- import path from 'path';
10
- import {linkify} from '../linkify';
11
- import {
12
- DocsMarkdownOption,
13
- SourceToPermalink,
14
- VersionMetadata,
15
- BrokenMarkdownLink,
16
- } from '../../types';
17
- import {VERSIONED_DOCS_DIR, CURRENT_VERSION_NAME} from '../../constants';
18
-
19
- function createFakeVersion({
20
- versionName,
21
- contentPath,
22
- contentPathLocalized,
23
- }: {
24
- versionName: string;
25
- contentPath: string;
26
- contentPathLocalized: string;
27
- }): VersionMetadata {
28
- return {
29
- versionName,
30
- versionLabel: 'Any',
31
- versionPath: 'any',
32
- contentPath,
33
- contentPathLocalized,
34
- sidebarFilePath: 'any',
35
- routePriority: undefined,
36
- isLast: false,
37
- };
38
- }
39
-
40
- const siteDir = path.join(__dirname, '__fixtures__');
41
-
42
- const versionCurrent = createFakeVersion({
43
- versionName: CURRENT_VERSION_NAME,
44
- contentPath: path.join(siteDir, 'docs'),
45
- contentPathLocalized: path.join(
46
- siteDir,
47
- 'i18n',
48
- 'fr',
49
- 'docusaurus-plugin-content-docs',
50
- CURRENT_VERSION_NAME,
51
- ),
52
- });
53
-
54
- const version100 = createFakeVersion({
55
- versionName: '1.0.0',
56
- contentPath: path.join(siteDir, VERSIONED_DOCS_DIR, 'version-1.0.0'),
57
- contentPathLocalized: path.join(
58
- siteDir,
59
- 'i18n',
60
- 'fr',
61
- 'docusaurus-plugin-content-docs',
62
- 'version-1.0.0',
63
- ),
64
- });
65
-
66
- const sourceToPermalink: SourceToPermalink = {
67
- '@site/docs/doc1.md': '/docs/doc1',
68
- '@site/docs/doc2.md': '/docs/doc2',
69
- '@site/docs/subdir/doc3.md': '/docs/subdir/doc3',
70
- '@site/docs/doc4.md': '/docs/doc4',
71
- '@site/versioned_docs/version-1.0.0/doc2.md': '/docs/1.0.0/doc2',
72
- '@site/versioned_docs/version-1.0.0/subdir/doc1.md':
73
- '/docs/1.0.0/subdir/doc1',
74
-
75
- '@site/i18n/fr/docusaurus-plugin-content-docs/current/doc-localized.md':
76
- '/fr/doc-localized',
77
- '@site/docs/doc-localized': '/doc-localized',
78
- };
79
-
80
- function createMarkdownOptions(
81
- options?: Partial<DocsMarkdownOption>,
82
- ): DocsMarkdownOption {
83
- return {
84
- sourceToPermalink,
85
- onBrokenMarkdownLink: () => {},
86
- versionsMetadata: [versionCurrent, version100],
87
- siteDir,
88
- ...options,
89
- };
90
- }
91
-
92
- const transform = (filepath: string, options?: Partial<DocsMarkdownOption>) => {
93
- const markdownOptions = createMarkdownOptions(options);
94
- const content = fs.readFileSync(filepath, 'utf-8');
95
- const transformedContent = linkify(content, filepath, markdownOptions);
96
- return [content, transformedContent];
97
- };
98
-
99
- test('transform nothing', () => {
100
- const doc1 = path.join(versionCurrent.contentPath, 'doc1.md');
101
- const [content, transformedContent] = transform(doc1);
102
- expect(transformedContent).toMatchSnapshot();
103
- expect(content).toEqual(transformedContent);
104
- });
105
-
106
- test('transform to correct links', () => {
107
- const doc2 = path.join(versionCurrent.contentPath, 'doc2.md');
108
- const [content, transformedContent] = transform(doc2);
109
- expect(transformedContent).toMatchSnapshot();
110
- expect(transformedContent).toContain('](/docs/doc1');
111
- expect(transformedContent).toContain('](/docs/doc2');
112
- expect(transformedContent).toContain('](/docs/subdir/doc3');
113
- expect(transformedContent).toContain('](/fr/doc-localized');
114
- expect(transformedContent).not.toContain('](doc1.md)');
115
- expect(transformedContent).not.toContain('](./doc2.md)');
116
- expect(transformedContent).not.toContain('](subdir/doc3.md)');
117
- expect(transformedContent).not.toContain('](/doc-localized');
118
- expect(content).not.toEqual(transformedContent);
119
- });
120
-
121
- test('transform relative links', () => {
122
- const doc3 = path.join(versionCurrent.contentPath, 'subdir', 'doc3.md');
123
-
124
- const [content, transformedContent] = transform(doc3);
125
- expect(transformedContent).toMatchSnapshot();
126
- expect(transformedContent).toContain('](/docs/doc2');
127
- expect(transformedContent).not.toContain('](../doc2.md)');
128
- expect(content).not.toEqual(transformedContent);
129
- });
130
-
131
- test('transforms reference links', () => {
132
- const doc4 = path.join(versionCurrent.contentPath, 'doc4.md');
133
- const [content, transformedContent] = transform(doc4);
134
- expect(transformedContent).toMatchSnapshot();
135
- expect(transformedContent).toContain('[doc1]: /docs/doc1');
136
- expect(transformedContent).toContain('[doc2]: /docs/doc2');
137
- expect(transformedContent).not.toContain('[doc1]: doc1.md');
138
- expect(transformedContent).not.toContain('[doc2]: ./doc2.md');
139
- expect(content).not.toEqual(transformedContent);
140
- });
141
-
142
- test('report broken markdown links', () => {
143
- const doc5 = path.join(versionCurrent.contentPath, 'doc5.md');
144
- const onBrokenMarkdownLink = jest.fn();
145
- const [content, transformedContent] = transform(doc5, {
146
- onBrokenMarkdownLink,
147
- });
148
- expect(transformedContent).toEqual(content);
149
- expect(onBrokenMarkdownLink).toHaveBeenCalledTimes(4);
150
- expect(onBrokenMarkdownLink).toHaveBeenNthCalledWith(1, {
151
- filePath: doc5,
152
- link: 'docNotExist1.md',
153
- contentPaths: versionCurrent,
154
- } as BrokenMarkdownLink);
155
- expect(onBrokenMarkdownLink).toHaveBeenNthCalledWith(2, {
156
- filePath: doc5,
157
- link: './docNotExist2.mdx',
158
- contentPaths: versionCurrent,
159
- } as BrokenMarkdownLink);
160
- expect(onBrokenMarkdownLink).toHaveBeenNthCalledWith(3, {
161
- filePath: doc5,
162
- link: '../docNotExist3.mdx',
163
- contentPaths: versionCurrent,
164
- } as BrokenMarkdownLink);
165
- expect(onBrokenMarkdownLink).toHaveBeenNthCalledWith(4, {
166
- filePath: doc5,
167
- link: './subdir/docNotExist4.md',
168
- contentPaths: versionCurrent,
169
- } as BrokenMarkdownLink);
170
- });
171
-
172
- test('transforms absolute links in versioned docs', () => {
173
- const doc2 = path.join(version100.contentPath, 'doc2.md');
174
- const [content, transformedContent] = transform(doc2);
175
- expect(transformedContent).toMatchSnapshot();
176
- expect(transformedContent).toContain('](/docs/1.0.0/subdir/doc1');
177
- expect(transformedContent).toContain('](/docs/1.0.0/doc2#existing-docs');
178
- expect(transformedContent).not.toContain('](subdir/doc1.md)');
179
- expect(transformedContent).not.toContain('](doc2.md#existing-docs)');
180
- expect(content).not.toEqual(transformedContent);
181
- });
182
-
183
- test('transforms relative links in versioned docs', () => {
184
- const doc1 = path.join(version100.contentPath, 'subdir', 'doc1.md');
185
- const [content, transformedContent] = transform(doc1);
186
- expect(transformedContent).toMatchSnapshot();
187
- expect(transformedContent).toContain('](/docs/1.0.0/doc2');
188
- expect(transformedContent).not.toContain('](../doc2.md)');
189
- expect(content).not.toEqual(transformedContent);
190
- });
@@ -1,307 +0,0 @@
1
- /**
2
- * Copyright (c) Facebook, Inc. and its affiliates.
3
- *
4
- * This source code is licensed under the MIT license found in the
5
- * LICENSE file in the root directory of this source tree.
6
- */
7
-
8
- import {
9
- SidebarItem,
10
- SidebarItemDoc,
11
- SidebarItemCategory,
12
- SidebarItemsGenerator,
13
- SidebarItemsGeneratorDoc,
14
- } from './types';
15
- import {sortBy, take, last, orderBy} from 'lodash';
16
- import {addTrailingSlash, posixPath} from '@docusaurus/utils';
17
- import {Joi} from '@docusaurus/utils-validation';
18
- import chalk from 'chalk';
19
- import path from 'path';
20
- import fs from 'fs-extra';
21
- import Yaml from 'js-yaml';
22
- import {DefaultCategoryCollapsedValue} from './sidebars';
23
-
24
- const BreadcrumbSeparator = '/';
25
-
26
- export const CategoryMetadataFilenameBase = '_category_';
27
- export const CategoryMetadataFilenamePattern = '_category_.{json,yml,yaml}';
28
-
29
- export type CategoryMetadatasFile = {
30
- label?: string;
31
- position?: number;
32
- collapsed?: boolean;
33
-
34
- // TODO should we allow "items" here? how would this work? would an "autogenerated" type be allowed?
35
- // This mkdocs plugin do something like that: https://github.com/lukasgeiter/mkdocs-awesome-pages-plugin/
36
- // cf comment: https://github.com/facebook/docusaurus/issues/3464#issuecomment-784765199
37
- };
38
-
39
- type WithPosition = {position?: number};
40
- type SidebarItemWithPosition = SidebarItem & WithPosition;
41
-
42
- const CategoryMetadatasFileSchema = Joi.object<CategoryMetadatasFile>({
43
- label: Joi.string(),
44
- position: Joi.number(),
45
- collapsed: Joi.boolean(),
46
- });
47
-
48
- // TODO I now believe we should read all the category metadata files ahead of time: we may need this metadata to customize docs metadata
49
- // Example use-case being able to disable number prefix parsing at the folder level, or customize the default route path segment for an intermediate directory...
50
- // TODO later if there is `CategoryFolder/index.md`, we may want to read the metadata as yaml on it
51
- // see https://github.com/facebook/docusaurus/issues/3464#issuecomment-818670449
52
- async function readCategoryMetadatasFile(
53
- categoryDirPath: string,
54
- ): Promise<CategoryMetadatasFile | null> {
55
- function validateCategoryMetadataFile(
56
- content: unknown,
57
- ): CategoryMetadatasFile {
58
- return Joi.attempt(content, CategoryMetadatasFileSchema);
59
- }
60
-
61
- async function tryReadFile(
62
- fileNameWithExtension: string,
63
- parse: (content: string) => unknown,
64
- ): Promise<CategoryMetadatasFile | null> {
65
- // Simpler to use only posix paths for mocking file metadatas in tests
66
- const filePath = posixPath(
67
- path.join(categoryDirPath, fileNameWithExtension),
68
- );
69
- if (await fs.pathExists(filePath)) {
70
- const contentString = await fs.readFile(filePath, {encoding: 'utf8'});
71
- const unsafeContent: unknown = parse(contentString);
72
- try {
73
- return validateCategoryMetadataFile(unsafeContent);
74
- } catch (e) {
75
- console.error(
76
- chalk.red(
77
- `The docs sidebar category metadata file looks invalid!\nPath=${filePath}`,
78
- ),
79
- );
80
- throw e;
81
- }
82
- }
83
- return null;
84
- }
85
-
86
- return (
87
- (await tryReadFile(`${CategoryMetadataFilenameBase}.json`, JSON.parse)) ??
88
- (await tryReadFile(`${CategoryMetadataFilenameBase}.yml`, Yaml.load)) ??
89
- // eslint-disable-next-line no-return-await
90
- (await tryReadFile(`${CategoryMetadataFilenameBase}.yaml`, Yaml.load))
91
- );
92
- }
93
-
94
- // [...parents, tail]
95
- function parseBreadcrumb(
96
- breadcrumb: string[],
97
- ): {parents: string[]; tail: string} {
98
- return {
99
- parents: take(breadcrumb, breadcrumb.length - 1),
100
- tail: last(breadcrumb)!,
101
- };
102
- }
103
-
104
- // Comment for this feature: https://github.com/facebook/docusaurus/issues/3464#issuecomment-818670449
105
- export const DefaultSidebarItemsGenerator: SidebarItemsGenerator = async function defaultSidebarItemsGenerator({
106
- item,
107
- docs: allDocs,
108
- version,
109
- numberPrefixParser,
110
- }): Promise<SidebarItem[]> {
111
- // Doc at the root of the autogenerated sidebar dir
112
- function isRootDoc(doc: SidebarItemsGeneratorDoc) {
113
- return doc.sourceDirName === item.dirName;
114
- }
115
-
116
- // Doc inside a subfolder of the autogenerated sidebar dir
117
- function isCategoryDoc(doc: SidebarItemsGeneratorDoc) {
118
- if (isRootDoc(doc)) {
119
- return false;
120
- }
121
-
122
- return (
123
- // autogen dir is . and doc is in subfolder
124
- item.dirName === '.' ||
125
- // autogen dir is not . and doc is in subfolder
126
- // "api/myDoc" startsWith "api/" (note "api2/myDoc" is not included)
127
- doc.sourceDirName.startsWith(addTrailingSlash(item.dirName))
128
- );
129
- }
130
-
131
- function isInAutogeneratedDir(doc: SidebarItemsGeneratorDoc) {
132
- return isRootDoc(doc) || isCategoryDoc(doc);
133
- }
134
-
135
- // autogenDir=a/b and docDir=a/b/c/d => returns c/d
136
- // autogenDir=a/b and docDir=a/b => returns .
137
- function getDocDirRelativeToAutogenDir(
138
- doc: SidebarItemsGeneratorDoc,
139
- ): string {
140
- if (!isInAutogeneratedDir(doc)) {
141
- throw new Error(
142
- 'getDocDirRelativeToAutogenDir() can only be called for subdocs of the sidebar autogen dir',
143
- );
144
- }
145
- // Is there a node API to compare 2 relative paths more easily?
146
- // path.relative() does not give good results
147
- if (item.dirName === '.') {
148
- return doc.sourceDirName;
149
- } else if (item.dirName === doc.sourceDirName) {
150
- return '.';
151
- } else {
152
- return doc.sourceDirName.replace(addTrailingSlash(item.dirName), '');
153
- }
154
- }
155
-
156
- // Get only docs in the autogen dir
157
- // Sort by folder+filename at once
158
- const docs = sortBy(allDocs.filter(isInAutogeneratedDir), (d) => d.source);
159
-
160
- if (docs.length === 0) {
161
- console.warn(
162
- chalk.yellow(
163
- `No docs found in dir ${item.dirName}: can't auto-generate a sidebar`,
164
- ),
165
- );
166
- }
167
-
168
- function createDocSidebarItem(
169
- doc: SidebarItemsGeneratorDoc,
170
- ): SidebarItemDoc & WithPosition {
171
- return {
172
- type: 'doc',
173
- id: doc.id,
174
- ...(doc.frontMatter.sidebar_label && {
175
- label: doc.frontMatter.sidebar_label,
176
- }),
177
- ...(typeof doc.sidebarPosition !== 'undefined' && {
178
- position: doc.sidebarPosition,
179
- }),
180
- };
181
- }
182
-
183
- async function createCategorySidebarItem({
184
- breadcrumb,
185
- }: {
186
- breadcrumb: string[];
187
- }): Promise<SidebarItemCategory & WithPosition> {
188
- const categoryDirPath = path.join(
189
- version.contentPath,
190
- item.dirName, // fix https://github.com/facebook/docusaurus/issues/4638
191
- breadcrumb.join(BreadcrumbSeparator),
192
- );
193
-
194
- const categoryMetadatas = await readCategoryMetadatasFile(categoryDirPath);
195
-
196
- const {tail} = parseBreadcrumb(breadcrumb);
197
-
198
- const {filename, numberPrefix} = numberPrefixParser(tail);
199
-
200
- const position = categoryMetadatas?.position ?? numberPrefix;
201
-
202
- return {
203
- type: 'category',
204
- label: categoryMetadatas?.label ?? filename,
205
- items: [],
206
- collapsed: categoryMetadatas?.collapsed ?? DefaultCategoryCollapsedValue,
207
- ...(typeof position !== 'undefined' && {position}),
208
- };
209
- }
210
-
211
- // Not sure how to simplify this algorithm :/
212
- async function autogenerateSidebarItems(): Promise<
213
- SidebarItemWithPosition[]
214
- > {
215
- const sidebarItems: SidebarItem[] = []; // mutable result
216
-
217
- const categoriesByBreadcrumb: Record<string, SidebarItemCategory> = {}; // mutable cache of categories already created
218
-
219
- async function getOrCreateCategoriesForBreadcrumb(
220
- breadcrumb: string[],
221
- ): Promise<SidebarItemCategory | null> {
222
- if (breadcrumb.length === 0) {
223
- return null;
224
- }
225
- const {parents} = parseBreadcrumb(breadcrumb);
226
- const parentCategory = await getOrCreateCategoriesForBreadcrumb(parents);
227
- const existingCategory =
228
- categoriesByBreadcrumb[breadcrumb.join(BreadcrumbSeparator)];
229
-
230
- if (existingCategory) {
231
- return existingCategory;
232
- } else {
233
- const newCategory = await createCategorySidebarItem({
234
- breadcrumb,
235
- });
236
- if (parentCategory) {
237
- parentCategory.items.push(newCategory);
238
- } else {
239
- sidebarItems.push(newCategory);
240
- }
241
- categoriesByBreadcrumb[
242
- breadcrumb.join(BreadcrumbSeparator)
243
- ] = newCategory;
244
- return newCategory;
245
- }
246
- }
247
-
248
- // Get the category breadcrumb of a doc (relative to the dir of the autogenerated sidebar item)
249
- function getRelativeBreadcrumb(doc: SidebarItemsGeneratorDoc): string[] {
250
- const relativeDirPath = getDocDirRelativeToAutogenDir(doc);
251
- if (relativeDirPath === '.') {
252
- return [];
253
- } else {
254
- return relativeDirPath.split(BreadcrumbSeparator);
255
- }
256
- }
257
-
258
- async function handleDocItem(doc: SidebarItemsGeneratorDoc): Promise<void> {
259
- const breadcrumb = getRelativeBreadcrumb(doc);
260
- const category = await getOrCreateCategoriesForBreadcrumb(breadcrumb);
261
-
262
- const docSidebarItem = createDocSidebarItem(doc);
263
- if (category) {
264
- category.items.push(docSidebarItem);
265
- } else {
266
- sidebarItems.push(docSidebarItem);
267
- }
268
- }
269
-
270
- // async process made sequential on purpose! order matters
271
- for (const doc of docs) {
272
- // eslint-disable-next-line no-await-in-loop
273
- await handleDocItem(doc);
274
- }
275
-
276
- return sidebarItems;
277
- }
278
-
279
- const sidebarItems = await autogenerateSidebarItems();
280
-
281
- return sortSidebarItems(sidebarItems);
282
- };
283
-
284
- // Recursively sort the categories/docs + remove the "position" attribute from final output
285
- // Note: the "position" is only used to sort "inside" a sidebar slice
286
- // It is not used to sort across multiple consecutive sidebar slices (ie a whole Category composed of multiple autogenerated items)
287
- function sortSidebarItems(
288
- sidebarItems: SidebarItemWithPosition[],
289
- ): SidebarItem[] {
290
- const processedSidebarItems = sidebarItems.map((item) => {
291
- if (item.type === 'category') {
292
- return {
293
- ...item,
294
- items: sortSidebarItems(item.items),
295
- };
296
- }
297
- return item;
298
- });
299
-
300
- const sortedSidebarItems = orderBy(
301
- processedSidebarItems,
302
- (item) => item.position,
303
- ['asc'],
304
- );
305
-
306
- return sortedSidebarItems.map(({position: _removed, ...item}) => item);
307
- }