@docsector/docsector-reader 2.3.0 → 3.0.0

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 (287) hide show
  1. package/README.md +49 -21
  2. package/bin/docsector.js +1 -1
  3. package/package.json +5 -3
  4. package/src/components/DMenu.vue +15 -8
  5. package/src/components/DPageExpandable.vue +78 -0
  6. package/src/components/DPageSection.vue +7 -572
  7. package/src/components/DPageSourceCode.vue +1 -1
  8. package/src/components/DPageTokens.vue +122 -0
  9. package/src/components/page-section-tokens.js +613 -0
  10. package/src/pages/guide/getting-started.overview.en-US.md +2 -2
  11. package/src/pages/guide/getting-started.overview.pt-BR.md +2 -2
  12. package/src/pages/guide/i18n-and-markdown.overview.en-US.md +16 -0
  13. package/src/pages/guide/i18n-and-markdown.overview.pt-BR.md +16 -0
  14. package/src/pages/guide.index.js +48 -0
  15. package/src/pages/manual/components/d-menu.overview.en-US.md +1 -1
  16. package/src/pages/manual/components/d-menu.overview.pt-BR.md +1 -1
  17. package/src/pages/manual/components/d-page-expandable.overview.en-US.md +58 -0
  18. package/src/pages/manual/components/d-page-expandable.overview.pt-BR.md +58 -0
  19. package/src/pages/manual/components/d-page-expandable.showcase.en-US.md +33 -0
  20. package/src/pages/manual/components/d-page-expandable.showcase.pt-BR.md +33 -0
  21. package/src/pages/manual.index.js +102 -0
  22. package/src/quasar.factory.js +158 -13
  23. package/src/search/book-search.js +25 -0
  24. package/public/Docsphere/flags/brazil.png +0 -0
  25. package/public/Docsphere/flags/united-states-of-america.png +0 -0
  26. package/src/i18n/tags.hjson +0 -46
  27. /package/public/{Docsphere → images}/flags/abkhazia.png +0 -0
  28. /package/public/{Docsphere → images}/flags/afghanistan.png +0 -0
  29. /package/public/{Docsphere → images}/flags/aland-islands.png +0 -0
  30. /package/public/{Docsphere → images}/flags/albania.png +0 -0
  31. /package/public/{Docsphere → images}/flags/algeria.png +0 -0
  32. /package/public/{Docsphere → images}/flags/american-samoa.png +0 -0
  33. /package/public/{Docsphere → images}/flags/andorra.png +0 -0
  34. /package/public/{Docsphere → images}/flags/angola.png +0 -0
  35. /package/public/{Docsphere → images}/flags/anguilla.png +0 -0
  36. /package/public/{Docsphere → images}/flags/antigua-and-barbuda.png +0 -0
  37. /package/public/{Docsphere → images}/flags/argentina.png +0 -0
  38. /package/public/{Docsphere → images}/flags/armenia.png +0 -0
  39. /package/public/{Docsphere → images}/flags/aruba.png +0 -0
  40. /package/public/{Docsphere → images}/flags/australia.png +0 -0
  41. /package/public/{Docsphere → images}/flags/austria.png +0 -0
  42. /package/public/{Docsphere → images}/flags/azerbaijan.png +0 -0
  43. /package/public/{Docsphere → images}/flags/azores-islands.png +0 -0
  44. /package/public/{Docsphere → images}/flags/bahamas.png +0 -0
  45. /package/public/{Docsphere → images}/flags/bahrain.png +0 -0
  46. /package/public/{Docsphere → images}/flags/balearic-islands.png +0 -0
  47. /package/public/{Docsphere → images}/flags/bangladesh.png +0 -0
  48. /package/public/{Docsphere → images}/flags/barbados.png +0 -0
  49. /package/public/{Docsphere → images}/flags/basque-country.png +0 -0
  50. /package/public/{Docsphere → images}/flags/belarus.png +0 -0
  51. /package/public/{Docsphere → images}/flags/belgium.png +0 -0
  52. /package/public/{Docsphere → images}/flags/belize.png +0 -0
  53. /package/public/{Docsphere → images}/flags/benin.png +0 -0
  54. /package/public/{Docsphere → images}/flags/bermuda.png +0 -0
  55. /package/public/{Docsphere → images}/flags/bhutan-1.png +0 -0
  56. /package/public/{Docsphere → images}/flags/bhutan.png +0 -0
  57. /package/public/{Docsphere → images}/flags/bolivia.png +0 -0
  58. /package/public/{Docsphere → images}/flags/bonaire.png +0 -0
  59. /package/public/{Docsphere → images}/flags/bosnia-and-herzegovina.png +0 -0
  60. /package/public/{Docsphere → images}/flags/botswana.png +0 -0
  61. /package/public/{Docsphere → images}/flags/british-columbia.png +0 -0
  62. /package/public/{Docsphere → images}/flags/british-indian-ocean-territory.png +0 -0
  63. /package/public/{Docsphere → images}/flags/british-virgin-islands.png +0 -0
  64. /package/public/{Docsphere → images}/flags/brunei.png +0 -0
  65. /package/public/{Docsphere → images}/flags/bulgaria.png +0 -0
  66. /package/public/{Docsphere → images}/flags/burkina-faso.png +0 -0
  67. /package/public/{Docsphere → images}/flags/burundi.png +0 -0
  68. /package/public/{Docsphere → images}/flags/cambodia.png +0 -0
  69. /package/public/{Docsphere → images}/flags/cameroon.png +0 -0
  70. /package/public/{Docsphere → images}/flags/canada.png +0 -0
  71. /package/public/{Docsphere → images}/flags/canary-islands.png +0 -0
  72. /package/public/{Docsphere → images}/flags/cape-verde.png +0 -0
  73. /package/public/{Docsphere → images}/flags/cayman-islands.png +0 -0
  74. /package/public/{Docsphere → images}/flags/central-african-republic.png +0 -0
  75. /package/public/{Docsphere → images}/flags/ceuta.png +0 -0
  76. /package/public/{Docsphere → images}/flags/chad.png +0 -0
  77. /package/public/{Docsphere → images}/flags/chile.png +0 -0
  78. /package/public/{Docsphere → images}/flags/china.png +0 -0
  79. /package/public/{Docsphere → images}/flags/christmas-island.png +0 -0
  80. /package/public/{Docsphere → images}/flags/cocos-island.png +0 -0
  81. /package/public/{Docsphere → images}/flags/colombia.png +0 -0
  82. /package/public/{Docsphere → images}/flags/comoros.png +0 -0
  83. /package/public/{Docsphere → images}/flags/cook-islands.png +0 -0
  84. /package/public/{Docsphere → images}/flags/corsica.png +0 -0
  85. /package/public/{Docsphere → images}/flags/costa-rica.png +0 -0
  86. /package/public/{Docsphere → images}/flags/croatia.png +0 -0
  87. /package/public/{Docsphere → images}/flags/cuba.png +0 -0
  88. /package/public/{Docsphere → images}/flags/curacao.png +0 -0
  89. /package/public/{Docsphere → images}/flags/cyprus.png +0 -0
  90. /package/public/{Docsphere → images}/flags/czech-republic.png +0 -0
  91. /package/public/{Docsphere → images}/flags/democratic-republic-of-congo.png +0 -0
  92. /package/public/{Docsphere → images}/flags/denmark.png +0 -0
  93. /package/public/{Docsphere → images}/flags/djibouti.png +0 -0
  94. /package/public/{Docsphere → images}/flags/dominica.png +0 -0
  95. /package/public/{Docsphere → images}/flags/dominican-republic.png +0 -0
  96. /package/public/{Docsphere → images}/flags/east-timor.png +0 -0
  97. /package/public/{Docsphere → images}/flags/ecuador.png +0 -0
  98. /package/public/{Docsphere → images}/flags/egypt.png +0 -0
  99. /package/public/{Docsphere → images}/flags/england.png +0 -0
  100. /package/public/{Docsphere → images}/flags/equatorial-guinea.png +0 -0
  101. /package/public/{Docsphere → images}/flags/eritrea.png +0 -0
  102. /package/public/{Docsphere → images}/flags/estonia.png +0 -0
  103. /package/public/{Docsphere → images}/flags/ethiopia.png +0 -0
  104. /package/public/{Docsphere → images}/flags/european-union.png +0 -0
  105. /package/public/{Docsphere → images}/flags/falkland-islands.png +0 -0
  106. /package/public/{Docsphere → images}/flags/faroe-islands.png +0 -0
  107. /package/public/{Docsphere → images}/flags/fiji.png +0 -0
  108. /package/public/{Docsphere → images}/flags/finland.png +0 -0
  109. /package/public/{Docsphere → images}/flags/france.png +0 -0
  110. /package/public/{Docsphere → images}/flags/french-polynesia.png +0 -0
  111. /package/public/{Docsphere → images}/flags/gabon.png +0 -0
  112. /package/public/{Docsphere → images}/flags/galapagos-islands.png +0 -0
  113. /package/public/{Docsphere → images}/flags/gambia.png +0 -0
  114. /package/public/{Docsphere → images}/flags/georgia.png +0 -0
  115. /package/public/{Docsphere → images}/flags/germany.png +0 -0
  116. /package/public/{Docsphere → images}/flags/ghana.png +0 -0
  117. /package/public/{Docsphere → images}/flags/gibraltar.png +0 -0
  118. /package/public/{Docsphere → images}/flags/greece.png +0 -0
  119. /package/public/{Docsphere → images}/flags/greenland.png +0 -0
  120. /package/public/{Docsphere → images}/flags/grenada.png +0 -0
  121. /package/public/{Docsphere → images}/flags/guam.png +0 -0
  122. /package/public/{Docsphere → images}/flags/guatemala.png +0 -0
  123. /package/public/{Docsphere → images}/flags/guernsey.png +0 -0
  124. /package/public/{Docsphere → images}/flags/guinea-bissau.png +0 -0
  125. /package/public/{Docsphere → images}/flags/guinea.png +0 -0
  126. /package/public/{Docsphere → images}/flags/guyana.png +0 -0
  127. /package/public/{Docsphere → images}/flags/haiti.png +0 -0
  128. /package/public/{Docsphere → images}/flags/hawaii.png +0 -0
  129. /package/public/{Docsphere → images}/flags/honduras.png +0 -0
  130. /package/public/{Docsphere → images}/flags/hong-kong.png +0 -0
  131. /package/public/{Docsphere → images}/flags/hungary.png +0 -0
  132. /package/public/{Docsphere → images}/flags/iceland.png +0 -0
  133. /package/public/{Docsphere → images}/flags/india.png +0 -0
  134. /package/public/{Docsphere → images}/flags/indonesia.png +0 -0
  135. /package/public/{Docsphere → images}/flags/iran.png +0 -0
  136. /package/public/{Docsphere → images}/flags/iraq.png +0 -0
  137. /package/public/{Docsphere → images}/flags/ireland.png +0 -0
  138. /package/public/{Docsphere → images}/flags/isle-of-man.png +0 -0
  139. /package/public/{Docsphere → images}/flags/israel.png +0 -0
  140. /package/public/{Docsphere → images}/flags/italy.png +0 -0
  141. /package/public/{Docsphere → images}/flags/ivory-coast.png +0 -0
  142. /package/public/{Docsphere → images}/flags/jamaica.png +0 -0
  143. /package/public/{Docsphere → images}/flags/japan.png +0 -0
  144. /package/public/{Docsphere → images}/flags/jersey.png +0 -0
  145. /package/public/{Docsphere → images}/flags/jordan.png +0 -0
  146. /package/public/{Docsphere → images}/flags/kazakhstan.png +0 -0
  147. /package/public/{Docsphere → images}/flags/kenya.png +0 -0
  148. /package/public/{Docsphere → images}/flags/kiribati.png +0 -0
  149. /package/public/{Docsphere → images}/flags/kosovo.png +0 -0
  150. /package/public/{Docsphere → images}/flags/kuwait.png +0 -0
  151. /package/public/{Docsphere → images}/flags/kyrgyzstan.png +0 -0
  152. /package/public/{Docsphere → images}/flags/laos.png +0 -0
  153. /package/public/{Docsphere → images}/flags/latvia.png +0 -0
  154. /package/public/{Docsphere → images}/flags/lebanon.png +0 -0
  155. /package/public/{Docsphere → images}/flags/lesotho.png +0 -0
  156. /package/public/{Docsphere → images}/flags/liberia.png +0 -0
  157. /package/public/{Docsphere → images}/flags/libya.png +0 -0
  158. /package/public/{Docsphere → images}/flags/liechtenstein.png +0 -0
  159. /package/public/{Docsphere → images}/flags/lithuania.png +0 -0
  160. /package/public/{Docsphere → images}/flags/luxembourg.png +0 -0
  161. /package/public/{Docsphere → images}/flags/macao.png +0 -0
  162. /package/public/{Docsphere → images}/flags/madagascar.png +0 -0
  163. /package/public/{Docsphere → images}/flags/madeira.png +0 -0
  164. /package/public/{Docsphere → images}/flags/malawi.png +0 -0
  165. /package/public/{Docsphere → images}/flags/malaysia.png +0 -0
  166. /package/public/{Docsphere → images}/flags/maldives.png +0 -0
  167. /package/public/{Docsphere → images}/flags/mali.png +0 -0
  168. /package/public/{Docsphere → images}/flags/malta.png +0 -0
  169. /package/public/{Docsphere → images}/flags/marshall-island.png +0 -0
  170. /package/public/{Docsphere → images}/flags/martinique.png +0 -0
  171. /package/public/{Docsphere → images}/flags/mauritania.png +0 -0
  172. /package/public/{Docsphere → images}/flags/mauritius.png +0 -0
  173. /package/public/{Docsphere → images}/flags/melilla.png +0 -0
  174. /package/public/{Docsphere → images}/flags/mexico.png +0 -0
  175. /package/public/{Docsphere → images}/flags/micronesia.png +0 -0
  176. /package/public/{Docsphere → images}/flags/moldova.png +0 -0
  177. /package/public/{Docsphere → images}/flags/monaco.png +0 -0
  178. /package/public/{Docsphere → images}/flags/mongolia.png +0 -0
  179. /package/public/{Docsphere → images}/flags/montenegro.png +0 -0
  180. /package/public/{Docsphere → images}/flags/montserrat.png +0 -0
  181. /package/public/{Docsphere → images}/flags/morocco.png +0 -0
  182. /package/public/{Docsphere → images}/flags/mozambique.png +0 -0
  183. /package/public/{Docsphere → images}/flags/myanmar.png +0 -0
  184. /package/public/{Docsphere → images}/flags/namibia.png +0 -0
  185. /package/public/{Docsphere → images}/flags/nato.png +0 -0
  186. /package/public/{Docsphere → images}/flags/nauru.png +0 -0
  187. /package/public/{Docsphere → images}/flags/nepal.png +0 -0
  188. /package/public/{Docsphere → images}/flags/netherlands.png +0 -0
  189. /package/public/{Docsphere → images}/flags/new-zealand.png +0 -0
  190. /package/public/{Docsphere → images}/flags/nicaragua.png +0 -0
  191. /package/public/{Docsphere → images}/flags/niger.png +0 -0
  192. /package/public/{Docsphere → images}/flags/nigeria.png +0 -0
  193. /package/public/{Docsphere → images}/flags/niue.png +0 -0
  194. /package/public/{Docsphere → images}/flags/norfolk-island.png +0 -0
  195. /package/public/{Docsphere → images}/flags/north-korea.png +0 -0
  196. /package/public/{Docsphere → images}/flags/northen-cyprus.png +0 -0
  197. /package/public/{Docsphere → images}/flags/northern-marianas-islands.png +0 -0
  198. /package/public/{Docsphere → images}/flags/norway.png +0 -0
  199. /package/public/{Docsphere → images}/flags/oman.png +0 -0
  200. /package/public/{Docsphere → images}/flags/orkney-islands.png +0 -0
  201. /package/public/{Docsphere → images}/flags/ossetia.png +0 -0
  202. /package/public/{Docsphere → images}/flags/pakistan.png +0 -0
  203. /package/public/{Docsphere → images}/flags/palau.png +0 -0
  204. /package/public/{Docsphere → images}/flags/palestine.png +0 -0
  205. /package/public/{Docsphere → images}/flags/panama.png +0 -0
  206. /package/public/{Docsphere → images}/flags/papua-new-guinea.png +0 -0
  207. /package/public/{Docsphere → images}/flags/paraguay.png +0 -0
  208. /package/public/{Docsphere → images}/flags/peru.png +0 -0
  209. /package/public/{Docsphere → images}/flags/philippines.png +0 -0
  210. /package/public/{Docsphere → images}/flags/pitcairn-islands.png +0 -0
  211. /package/public/{Docsphere → images}/flags/portugal.png +0 -0
  212. /package/public/{Docsphere → images}/flags/puerto-rico.png +0 -0
  213. /package/public/{Docsphere → images}/flags/qatar.png +0 -0
  214. /package/public/{Docsphere → images}/flags/rapa-nui.png +0 -0
  215. /package/public/{Docsphere → images}/flags/republic-of-macedonia.png +0 -0
  216. /package/public/{Docsphere → images}/flags/republic-of-poland.png +0 -0
  217. /package/public/{Docsphere → images}/flags/republic-of-the-congo.png +0 -0
  218. /package/public/{Docsphere → images}/flags/romania.png +0 -0
  219. /package/public/{Docsphere → images}/flags/russia.png +0 -0
  220. /package/public/{Docsphere → images}/flags/rwanda.png +0 -0
  221. /package/public/{Docsphere → images}/flags/saba-island.png +0 -0
  222. /package/public/{Docsphere → images}/flags/saint-kitts-and-nevis.png +0 -0
  223. /package/public/{Docsphere → images}/flags/salvador.png +0 -0
  224. /package/public/{Docsphere → images}/flags/samoa.png +0 -0
  225. /package/public/{Docsphere → images}/flags/san-marino.png +0 -0
  226. /package/public/{Docsphere → images}/flags/sao-tome-and-principe.png +0 -0
  227. /package/public/{Docsphere → images}/flags/sardinia.png +0 -0
  228. /package/public/{Docsphere → images}/flags/saudi-arabia.png +0 -0
  229. /package/public/{Docsphere → images}/flags/scotland.png +0 -0
  230. /package/public/{Docsphere → images}/flags/senegal.png +0 -0
  231. /package/public/{Docsphere → images}/flags/serbia.png +0 -0
  232. /package/public/{Docsphere → images}/flags/seychelles.png +0 -0
  233. /package/public/{Docsphere → images}/flags/sierra-leone.png +0 -0
  234. /package/public/{Docsphere → images}/flags/singapore.png +0 -0
  235. /package/public/{Docsphere → images}/flags/sint-eustatius.png +0 -0
  236. /package/public/{Docsphere → images}/flags/sint-maarten.png +0 -0
  237. /package/public/{Docsphere → images}/flags/slovakia.png +0 -0
  238. /package/public/{Docsphere → images}/flags/slovenia.png +0 -0
  239. /package/public/{Docsphere → images}/flags/solomon-islands.png +0 -0
  240. /package/public/{Docsphere → images}/flags/somalia.png +0 -0
  241. /package/public/{Docsphere → images}/flags/somaliland.png +0 -0
  242. /package/public/{Docsphere → images}/flags/south-africa.png +0 -0
  243. /package/public/{Docsphere → images}/flags/south-korea.png +0 -0
  244. /package/public/{Docsphere → images}/flags/south-sudan.png +0 -0
  245. /package/public/{Docsphere → images}/flags/spain.png +0 -0
  246. /package/public/{Docsphere → images}/flags/sri-lanka.png +0 -0
  247. /package/public/{Docsphere → images}/flags/st-barts.png +0 -0
  248. /package/public/{Docsphere → images}/flags/st-lucia.png +0 -0
  249. /package/public/{Docsphere → images}/flags/st-vincent-and-the-grenadines.png +0 -0
  250. /package/public/{Docsphere → images}/flags/sudan.png +0 -0
  251. /package/public/{Docsphere → images}/flags/suriname.png +0 -0
  252. /package/public/{Docsphere → images}/flags/swaziland.png +0 -0
  253. /package/public/{Docsphere → images}/flags/sweden.png +0 -0
  254. /package/public/{Docsphere → images}/flags/switzerland.png +0 -0
  255. /package/public/{Docsphere → images}/flags/syria.png +0 -0
  256. /package/public/{Docsphere → images}/flags/taiwan.png +0 -0
  257. /package/public/{Docsphere → images}/flags/tajikistan.png +0 -0
  258. /package/public/{Docsphere → images}/flags/tanzania.png +0 -0
  259. /package/public/{Docsphere → images}/flags/thailand.png +0 -0
  260. /package/public/{Docsphere → images}/flags/tibet.png +0 -0
  261. /package/public/{Docsphere → images}/flags/togo.png +0 -0
  262. /package/public/{Docsphere → images}/flags/tokelau.png +0 -0
  263. /package/public/{Docsphere → images}/flags/tonga.png +0 -0
  264. /package/public/{Docsphere → images}/flags/transnistria.png +0 -0
  265. /package/public/{Docsphere → images}/flags/trinidad-and-tobago.png +0 -0
  266. /package/public/{Docsphere → images}/flags/tunisia.png +0 -0
  267. /package/public/{Docsphere → images}/flags/turkey.png +0 -0
  268. /package/public/{Docsphere → images}/flags/turkmenistan.png +0 -0
  269. /package/public/{Docsphere → images}/flags/turks-and-caicos.png +0 -0
  270. /package/public/{Docsphere → images}/flags/tuvalu.png +0 -0
  271. /package/public/{Docsphere → images}/flags/uganda.png +0 -0
  272. /package/public/{Docsphere → images}/flags/ukraine.png +0 -0
  273. /package/public/{Docsphere → images}/flags/united-arab-emirates.png +0 -0
  274. /package/public/{Docsphere → images}/flags/united-kingdom.png +0 -0
  275. /package/public/{Docsphere → images}/flags/united-nations.png +0 -0
  276. /package/public/{Docsphere → images}/flags/uruguay.png +0 -0
  277. /package/public/{Docsphere → images}/flags/uzbekistn.png +0 -0
  278. /package/public/{Docsphere → images}/flags/vanuatu.png +0 -0
  279. /package/public/{Docsphere → images}/flags/vatican-city.png +0 -0
  280. /package/public/{Docsphere → images}/flags/venezuela.png +0 -0
  281. /package/public/{Docsphere → images}/flags/vietnam.png +0 -0
  282. /package/public/{Docsphere → images}/flags/virgin-islands.png +0 -0
  283. /package/public/{Docsphere → images}/flags/wales.png +0 -0
  284. /package/public/{Docsphere → images}/flags/western-sahara.png +0 -0
  285. /package/public/{Docsphere → images}/flags/yemen.png +0 -0
  286. /package/public/{Docsphere → images}/flags/zambia.png +0 -0
  287. /package/public/{Docsphere → images}/flags/zimbabwe.png +0 -0
@@ -0,0 +1,613 @@
1
+ import MarkdownIt from 'markdown-it'
2
+ import attrs from 'markdown-it-attrs'
3
+
4
+ const ALERT_MESSAGE_TYPES = new Set([
5
+ 'note',
6
+ 'tip',
7
+ 'important',
8
+ 'warning',
9
+ 'caution'
10
+ ])
11
+
12
+ const QUICK_LINKS_MARKER_PREFIX = '@@DOCSECTOR_QUICK_LINKS_'
13
+ const EXPANDABLE_MARKER_PREFIX = '@@DOCSECTOR_EXPANDABLE_'
14
+ const CODE_SEGMENT_MARKER_PREFIX = '@@DOCSECTOR_CODE_SEGMENT_'
15
+
16
+ const parseAlertMarker = (rawContent = '') => {
17
+ const match = String(rawContent).trim().match(/^\[!\s*([A-Za-z]+)\s*\]\s*(.*)$/s)
18
+ if (!match) {
19
+ return null
20
+ }
21
+
22
+ const type = match[1].toLowerCase()
23
+ if (!ALERT_MESSAGE_TYPES.has(type)) {
24
+ return null
25
+ }
26
+
27
+ return {
28
+ type,
29
+ content: (match[2] || '').trim()
30
+ }
31
+ }
32
+
33
+ export const parseCustomTagAttributes = (raw = '') => {
34
+ const parsed = {}
35
+ const pattern = /([\w-]+)\s*=\s*(?:"([^"]*)"|'([^']*)'|([^\s"'=<>`]+))/g
36
+
37
+ let match = pattern.exec(String(raw))
38
+ while (match !== null) {
39
+ const key = match[1]
40
+ const value = match[2] || match[3] || match[4] || ''
41
+ parsed[key] = value
42
+ match = pattern.exec(String(raw))
43
+ }
44
+
45
+ return parsed
46
+ }
47
+
48
+ const shieldInlineCodeSegments = (line = '', createMarker, codeSegmentsMap) => {
49
+ return String(line).replace(/(`+)([^`\n]*?)\1/g, (match) => {
50
+ const marker = createMarker()
51
+ codeSegmentsMap.set(marker, match)
52
+ return marker
53
+ })
54
+ }
55
+
56
+ const shieldMarkdownCodeSegments = (source = '') => {
57
+ const codeSegmentsMap = new Map()
58
+ const output = []
59
+ const lines = String(source).split(/\r?\n/)
60
+ let index = 0
61
+
62
+ const createMarker = () => `${CODE_SEGMENT_MARKER_PREFIX}${index++}@@`
63
+
64
+ for (let lineIndex = 0; lineIndex < lines.length; lineIndex++) {
65
+ const line = lines[lineIndex]
66
+ const fenceMatch = line.match(/^( {0,3})(`{3,}|~{3,})(.*)$/)
67
+
68
+ if (fenceMatch) {
69
+ const fenceToken = fenceMatch[2]
70
+ const fenceChar = fenceToken[0]
71
+ const closingPattern = new RegExp(`^( {0,3})${fenceChar}{${fenceToken.length},}\\s*$`)
72
+ const blockLines = [line]
73
+
74
+ while (lineIndex + 1 < lines.length) {
75
+ lineIndex++
76
+ const nextLine = lines[lineIndex]
77
+ blockLines.push(nextLine)
78
+
79
+ if (closingPattern.test(nextLine)) {
80
+ break
81
+ }
82
+ }
83
+
84
+ const marker = createMarker()
85
+ codeSegmentsMap.set(marker, blockLines.join('\n'))
86
+ output.push(marker)
87
+ continue
88
+ }
89
+
90
+ output.push(shieldInlineCodeSegments(line, createMarker, codeSegmentsMap))
91
+ }
92
+
93
+ return {
94
+ source: output.join('\n'),
95
+ codeSegmentsMap
96
+ }
97
+ }
98
+
99
+ const restoreShieldedCodeSegments = (source = '', codeSegmentsMap = new Map()) => {
100
+ let restored = String(source)
101
+
102
+ codeSegmentsMap.forEach((content, marker) => {
103
+ restored = restored.replaceAll(marker, content)
104
+ })
105
+
106
+ return restored
107
+ }
108
+
109
+ const extractQuickLinksBlocks = (source = '') => {
110
+ const map = new Map()
111
+ let index = 0
112
+
113
+ const blockPattern = /<d-quick-links\b([^>]*)>([\s\S]*?)<\/d-quick-links>/gi
114
+ const replaced = String(source).replace(blockPattern, (_, blockAttrsRaw, inner) => {
115
+ const blockAttrs = parseCustomTagAttributes(blockAttrsRaw)
116
+ const items = []
117
+ const itemPattern = /<d-quick-link\b([^>]*)\/?\s*>/gi
118
+
119
+ let itemMatch = itemPattern.exec(inner)
120
+ while (itemMatch !== null) {
121
+ const itemAttrs = parseCustomTagAttributes(itemMatch[1])
122
+ const title = itemAttrs.title || ''
123
+ const description = itemAttrs.description || ''
124
+ const to = itemAttrs.to || ''
125
+ const href = itemAttrs.href || ''
126
+
127
+ if (title && description && (to || href)) {
128
+ items.push({
129
+ icon: itemAttrs.icon || 'link',
130
+ title,
131
+ description,
132
+ to,
133
+ href
134
+ })
135
+ }
136
+
137
+ itemMatch = itemPattern.exec(inner)
138
+ }
139
+
140
+ const marker = `${QUICK_LINKS_MARKER_PREFIX}${index}@@`
141
+ index++
142
+
143
+ map.set(marker, {
144
+ title: blockAttrs.title || '',
145
+ items
146
+ })
147
+
148
+ return `\n${marker}\n`
149
+ })
150
+
151
+ return {
152
+ source: replaced,
153
+ quickLinksMap: map
154
+ }
155
+ }
156
+
157
+ const parseExpandableOpenState = (raw = '') => {
158
+ return ['1', 'true', 'yes', 'on'].includes(String(raw).trim().toLowerCase())
159
+ }
160
+
161
+ const extractExpandableBlocks = (source = '') => {
162
+ const map = new Map()
163
+ let index = 0
164
+
165
+ const blockPattern = /<d-expandable\b([^>]*)>([\s\S]*?)<\/d-expandable>/gi
166
+ const replaced = String(source).replace(blockPattern, (_, rawAttrs, inner) => {
167
+ const attrs = parseCustomTagAttributes(rawAttrs)
168
+ const marker = `${EXPANDABLE_MARKER_PREFIX}${index}@@`
169
+ index++
170
+
171
+ map.set(marker, {
172
+ title: attrs.title || '',
173
+ open: parseExpandableOpenState(attrs.open),
174
+ content: inner
175
+ })
176
+
177
+ return `\n${marker}\n`
178
+ })
179
+
180
+ return {
181
+ source: replaced,
182
+ expandableMap: map
183
+ }
184
+ }
185
+
186
+ const parseFenceAttributes = (raw = '') => {
187
+ const parsed = {}
188
+ const pattern = /([\w-]+)\s*=\s*(?:"([^"]*)"|'([^']*)'|([^\s;]+))/g
189
+
190
+ let match = pattern.exec(String(raw))
191
+ while (match !== null) {
192
+ const key = match[1]
193
+ const value = match[2] || match[3] || match[4] || ''
194
+ parsed[key] = value
195
+ match = pattern.exec(String(raw))
196
+ }
197
+
198
+ return parsed
199
+ }
200
+
201
+ const parseTokenAttributes = (element) => {
202
+ const parsed = {}
203
+
204
+ ;(element.attrs || []).forEach(([key, value]) => {
205
+ parsed[key] = value || ''
206
+ })
207
+
208
+ return parsed
209
+ }
210
+
211
+ const parseFenceLanguage = (raw = '') => {
212
+ const cleaned = String(raw)
213
+ .replace(/:[^;]*;/g, ' ')
214
+ .replace(/[\w-]+\s*=\s*(?:"[^"]*"|'[^']*'|[^\s;]+)/g, ' ')
215
+ .replace(/[;:]/g, ' ')
216
+ .trim()
217
+
218
+ return cleaned.split(/\s+/)[0] || ''
219
+ }
220
+
221
+ const parseFenceMeta = (element) => {
222
+ const rawInfo = String(element.info || '')
223
+ const meta = {
224
+ ...parseFenceAttributes(rawInfo),
225
+ ...parseTokenAttributes(element)
226
+ }
227
+
228
+ return {
229
+ ...meta,
230
+ language: parseFenceLanguage(rawInfo) || meta.language || 'html'
231
+ }
232
+ }
233
+
234
+ const parseBreadcrumb = (raw = '') => {
235
+ const value = String(raw).trim()
236
+
237
+ if (!value) {
238
+ return []
239
+ }
240
+
241
+ const separator = value.includes('>') ? '>' : '/'
242
+
243
+ return value
244
+ .split(separator)
245
+ .map((segment) => segment.trim())
246
+ .filter(Boolean)
247
+ }
248
+
249
+ const createSourceCodeTab = (element, meta) => ({
250
+ label: meta.tab || meta.filename || meta.language || 'Code',
251
+ language: meta.language || 'html',
252
+ text: element.content,
253
+ filename: meta.filename || '',
254
+ breadcrumbs: parseBreadcrumb(meta.breadcrumb)
255
+ })
256
+
257
+ const pushSourceCodeToken = (tokens, element, parserState) => {
258
+ const meta = parseFenceMeta(element)
259
+
260
+ if (meta.language === 'mermaid') {
261
+ tokens.push({
262
+ tag: 'mermaid',
263
+ content: element.content
264
+ })
265
+ return
266
+ }
267
+
268
+ const tab = createSourceCodeTab(element, meta)
269
+
270
+ if (meta.group) {
271
+ const previous = tokens[tokens.length - 1]
272
+
273
+ if (previous?.tag === 'code' && previous.group === meta.group && Array.isArray(previous.tabs)) {
274
+ previous.tabs.push(tab)
275
+ return
276
+ }
277
+
278
+ tokens.push({
279
+ tag: 'code',
280
+ codeIndex: parserState.codeIndex++,
281
+ group: meta.group,
282
+ content: tab.text,
283
+ info: tab.language,
284
+ filename: tab.filename,
285
+ breadcrumbs: tab.breadcrumbs,
286
+ tabs: [tab]
287
+ })
288
+ return
289
+ }
290
+
291
+ tokens.push({
292
+ tag: 'code',
293
+ codeIndex: parserState.codeIndex++,
294
+ content: tab.text,
295
+ info: tab.language,
296
+ filename: tab.filename,
297
+ breadcrumbs: tab.breadcrumbs,
298
+ tabs: []
299
+ })
300
+ }
301
+
302
+ const createMarkdownBlockParser = () => {
303
+ const markdown = new MarkdownIt({
304
+ html: true
305
+ })
306
+
307
+ markdown.use(attrs, {
308
+ leftDelimiter: ':',
309
+ rightDelimiter: ';',
310
+ allowedAttributes: ['filename', 'group', 'tab', 'breadcrumb']
311
+ })
312
+
313
+ return markdown
314
+ }
315
+
316
+ const createMarkdownInlineParser = () => {
317
+ return new MarkdownIt({
318
+ html: true
319
+ })
320
+ }
321
+
322
+ const normalizePageSectionSource = (source = '') => {
323
+ return String(source)
324
+ .replace(/&#123;/g, '{')
325
+ .replace(/&#125;/g, '}')
326
+ .replace(/&amp;/g, '&')
327
+ }
328
+
329
+ export const tokenizePageSectionSource = (source = '', options = {}) => {
330
+ const {
331
+ allowHeadingTokens = true,
332
+ parserState = { codeIndex: 0 }
333
+ } = options
334
+ const normalizedSource = normalizePageSectionSource(source)
335
+ const { source: sourceWithShieldedCode, codeSegmentsMap } = shieldMarkdownCodeSegments(normalizedSource)
336
+ const { source: sourceWithExpandables, expandableMap } = extractExpandableBlocks(sourceWithShieldedCode)
337
+
338
+ expandableMap.forEach((data, marker) => {
339
+ expandableMap.set(marker, {
340
+ ...data,
341
+ content: restoreShieldedCodeSegments(data.content, codeSegmentsMap)
342
+ })
343
+ })
344
+
345
+ const { source: sourceWithQuickLinks, quickLinksMap } = extractQuickLinksBlocks(sourceWithExpandables)
346
+ const markdown = createMarkdownBlockParser()
347
+ const markdownInline = createMarkdownInlineParser()
348
+ const markdownEnv = {}
349
+ const parsed = markdown.parse(restoreShieldedCodeSegments(sourceWithQuickLinks, codeSegmentsMap), markdownEnv)
350
+ const tokens = []
351
+
352
+ let level = 0
353
+ let tag = ''
354
+
355
+ const blockquote = {
356
+ depth: 0,
357
+ content: '',
358
+ alertType: '',
359
+ firstInline: true
360
+ }
361
+
362
+ const resetBlockquote = () => {
363
+ blockquote.content = ''
364
+ blockquote.alertType = ''
365
+ blockquote.firstInline = true
366
+ }
367
+
368
+ const flushBlockquote = () => {
369
+ const content = blockquote.content
370
+ .replace(/<p>\s*<\/p>/g, '')
371
+ .trim()
372
+
373
+ tokens.push({
374
+ tag: 'blockquote',
375
+ content,
376
+ alertType: blockquote.alertType
377
+ })
378
+
379
+ resetBlockquote()
380
+ }
381
+
382
+ const appendBlockquoteTag = (element, open) => {
383
+ if (!element.tag || element.tag === 'blockquote') {
384
+ return
385
+ }
386
+
387
+ blockquote.content += open
388
+ ? `<${element.tag}>`
389
+ : `</${element.tag}>`
390
+ }
391
+
392
+ parsed.forEach((element) => {
393
+ if (element.type === 'blockquote_open') {
394
+ if (blockquote.depth === 0) {
395
+ resetBlockquote()
396
+ }
397
+
398
+ blockquote.depth++
399
+ return
400
+ }
401
+
402
+ if (element.type === 'blockquote_close' && blockquote.depth > 0) {
403
+ blockquote.depth--
404
+
405
+ if (blockquote.depth === 0) {
406
+ flushBlockquote()
407
+ }
408
+
409
+ return
410
+ }
411
+
412
+ if (blockquote.depth > 0) {
413
+ if (element.type === 'inline') {
414
+ const rawInline = element.content
415
+
416
+ if (blockquote.firstInline) {
417
+ blockquote.firstInline = false
418
+
419
+ const alert = parseAlertMarker(rawInline)
420
+ if (alert !== null) {
421
+ blockquote.alertType = alert.type
422
+
423
+ if (alert.content !== '') {
424
+ blockquote.content += markdownInline.renderInline(alert.content, markdownEnv)
425
+ }
426
+
427
+ return
428
+ }
429
+ }
430
+
431
+ blockquote.content += markdownInline.renderInline(rawInline, markdownEnv)
432
+ return
433
+ }
434
+
435
+ if (element.type === 'fence') {
436
+ const language = parseFenceLanguage(element.info)
437
+ const escaped = String(element.content)
438
+ .replace(/&/g, '&amp;')
439
+ .replace(/</g, '&lt;')
440
+ .replace(/>/g, '&gt;')
441
+
442
+ const languageClass = language ? ` class="language-${language}"` : ''
443
+ blockquote.content += `<pre><code${languageClass}>${escaped}</code></pre>`
444
+ return
445
+ }
446
+
447
+ if (element.type.endsWith('_open')) {
448
+ appendBlockquoteTag(element, true)
449
+ return
450
+ }
451
+
452
+ if (element.type.endsWith('_close')) {
453
+ appendBlockquoteTag(element, false)
454
+ return
455
+ }
456
+
457
+ return
458
+ }
459
+
460
+ switch (element.type) {
461
+ case 'bullet_list_open':
462
+ case 'ordered_list_open':
463
+ case 'table_open':
464
+ level++
465
+ }
466
+
467
+ if (element.type === 'inline') {
468
+ element.content = markdownInline.renderInline(element.content, markdownEnv)
469
+ }
470
+
471
+ if (level === 0) {
472
+ switch (element.type) {
473
+ case 'heading_open':
474
+ tag = allowHeadingTokens ? element.tag : 'p'
475
+ break
476
+ case 'paragraph_open':
477
+ case 'list_item_open':
478
+ tag = element.tag
479
+ break
480
+ }
481
+
482
+ switch (element.type) {
483
+ case 'inline':
484
+ if (expandableMap.has(element.content.trim())) {
485
+ const data = expandableMap.get(element.content.trim())
486
+
487
+ tokens.push({
488
+ tag: 'expandable',
489
+ title: data.title,
490
+ open: data.open,
491
+ tokens: tokenizePageSectionSource(data.content, {
492
+ allowHeadingTokens: false,
493
+ parserState
494
+ })
495
+ })
496
+ break
497
+ }
498
+
499
+ if (quickLinksMap.has(element.content.trim())) {
500
+ const data = quickLinksMap.get(element.content.trim())
501
+
502
+ tokens.push({
503
+ tag: 'quick-links',
504
+ title: data.title,
505
+ items: data.items
506
+ })
507
+ break
508
+ }
509
+
510
+ tokens.push({
511
+ tag,
512
+ map: element.map,
513
+ content: element.content,
514
+ info: element.info
515
+ })
516
+ break
517
+
518
+ case 'fence':
519
+ pushSourceCodeToken(tokens, element, parserState)
520
+ break
521
+
522
+ case 'html_block':
523
+ tokens.push({
524
+ tag: 'html',
525
+ content: element.content
526
+ })
527
+ break
528
+ }
529
+ } else if (level === 1) {
530
+ const parent = tokens[tokens.length - 1]
531
+
532
+ switch (element.type) {
533
+ case 'bullet_list_open':
534
+ tokens.push({
535
+ tag: 'ul',
536
+ content: ''
537
+ })
538
+ break
539
+
540
+ case 'ordered_list_open':
541
+ tokens.push({
542
+ tag: 'ol',
543
+ content: ''
544
+ })
545
+ break
546
+
547
+ case 'table_open':
548
+ tokens.push({
549
+ tag: 'table',
550
+ content: ''
551
+ })
552
+ break
553
+
554
+ case 'list_item_open':
555
+ parent.content += '<li>'
556
+ break
557
+
558
+ case 'thead_open':
559
+ parent.content += '<thead>'
560
+ break
561
+ case 'tbody_open':
562
+ parent.content += '<tbody>'
563
+ break
564
+ case 'tr_open':
565
+ parent.content += '<tr>'
566
+ break
567
+ case 'th_open':
568
+ parent.content += '<th>'
569
+ break
570
+ case 'td_open':
571
+ parent.content += '<td>'
572
+ break
573
+
574
+ case 'inline':
575
+ parent.content += element.content
576
+ break
577
+ case 'html_inline':
578
+ case 'html_block':
579
+ parent.content += element.content
580
+ break
581
+
582
+ case 'list_item_close':
583
+ parent.content += '</li>'
584
+ break
585
+
586
+ case 'thead_close':
587
+ parent.content += '</thead>'
588
+ break
589
+ case 'tbody_close':
590
+ parent.content += '</tbody>'
591
+ break
592
+ case 'tr_close':
593
+ parent.content += '</tr>'
594
+ break
595
+ case 'th_close':
596
+ parent.content += '</th>'
597
+ break
598
+ case 'td_close':
599
+ parent.content += '</td>'
600
+ break
601
+ }
602
+ }
603
+
604
+ switch (element.type) {
605
+ case 'bullet_list_close':
606
+ case 'ordered_list_close':
607
+ case 'table_close':
608
+ level--
609
+ }
610
+ })
611
+
612
+ return tokens
613
+ }
@@ -64,7 +64,7 @@ After `init`, your project will have this structure:
64
64
  - `src/pages/guide/` — Guide-type pages (Markdown files)
65
65
  - `src/pages/manual/` — Manual-type pages (Markdown files)
66
66
  - `src/i18n/index.js` — i18n loader using `buildMessages()` from the package
67
- - `src/i18n/tags.hjson` — Search keywords per route and locale
67
+ - `src/pages/*.index.js` — Page registry plus per-page `metadata.tags` for menu search
68
68
  - `public/` — Static assets (logo, favicon, images)
69
69
 
70
70
  The rendering engine (components, layouts, router, store, composables) lives inside the `@docsector/docsector-reader` package — you only maintain your content and configuration.
@@ -74,5 +74,5 @@ The rendering engine (components, layouts, router, store, composables) lives ins
74
74
  - Configure your project branding in **docsector.config.js**
75
75
  - Define your pages in **src/pages/guide.index.js** (and other `*.index.js` registries)
76
76
  - Write your documentation in **Markdown**
77
- - Add search keywords in **src/i18n/tags.hjson**
77
+ - Add search keywords via **metadata.tags** in each page entry of **src/pages/*.index.js**
78
78
  - Customize themes and appearance
@@ -64,7 +64,7 @@ Após o `init`, seu projeto terá esta estrutura:
64
64
  - `src/pages/guide/` — Páginas tipo guia (arquivos Markdown)
65
65
  - `src/pages/manual/` — Páginas tipo manual (arquivos Markdown)
66
66
  - `src/i18n/index.js` — Loader i18n usando `buildMessages()` do pacote
67
- - `src/i18n/tags.hjson` — Palavras-chave de busca por rota e idioma
67
+ - `src/pages/*.index.js` — Registro de páginas com `metadata.tags` por página para busca no menu
68
68
  - `public/` — Assets estáticos (logo, favicon, imagens)
69
69
 
70
70
  O motor de renderização (componentes, layouts, router, store, composables) fica dentro do pacote `@docsector/docsector-reader` — você só mantém seu conteúdo e configuração.
@@ -74,5 +74,5 @@ O motor de renderização (componentes, layouts, router, store, composables) fic
74
74
  - Configure o branding do seu projeto em **docsector.config.js**
75
75
  - Defina suas páginas em **src/pages/guide.index.js** (e outros registros `*.index.js`)
76
76
  - Escreva sua documentação em **Markdown**
77
- - Adicione palavras-chave de busca em **src/i18n/tags.hjson**
77
+ - Adicione palavras-chave de busca via **metadata.tags** em cada entrada de página em **src/pages/*.index.js**
78
78
  - Personalize temas e aparência
@@ -94,6 +94,22 @@ echo "Example"
94
94
 
95
95
  `filename` is shown in the info bar for single blocks. Consecutive fences with the same `group` are rendered as tabs. `tab` sets the tab label, so filename-like labels such as `example.php` receive file icons in the tab. `breadcrumb` sets the breadcrumb segments above the active code block, and the final filename-like segment receives the same file icon.
96
96
 
97
+ ### Expandable Content
98
+
99
+ Use `<d-expandable>` to hide secondary content without removing rich Markdown features from the page:
100
+
101
+ ```markdown
102
+ <d-expandable title="More details">
103
+
104
+ Optional explanations, operational notes, or longer examples.
105
+
106
+ </d-expandable>
107
+ ```
108
+
109
+ Set `open="true"` when the block should start expanded.
110
+
111
+ The expandable body supports paragraphs, lists, alerts, code blocks, Mermaid diagrams, tables, raw HTML, and quick links. Keep headings outside the expandable block in this first version, because headings inside the body are flattened to regular paragraphs to preserve the page ToC.
112
+
97
113
  ## Adding a New Language
98
114
 
99
115
  1. Create `src/i18n/languages/xx-XX.hjson` with all UI translations
@@ -94,6 +94,22 @@ echo "Exemplo"
94
94
 
95
95
  `filename` aparece na barra de info em blocos simples. Fences consecutivos com o mesmo `group` são renderizados como abas. `tab` define o rótulo da aba, então labels que parecem arquivo, como `exemplo.php`, recebem ícones na aba. `breadcrumb` define os segmentos acima do bloco ativo, e o segmento final que parece arquivo recebe o mesmo ícone.
96
96
 
97
+ ### Conteúdo Expansível
98
+
99
+ Use `<d-expandable>` para esconder conteúdo secundário sem perder os recursos ricos de Markdown da página:
100
+
101
+ ```markdown
102
+ <d-expandable title="Mais detalhes">
103
+
104
+ Explicações opcionais, notas operacionais ou exemplos maiores.
105
+
106
+ </d-expandable>
107
+ ```
108
+
109
+ Defina `open="true"` quando o bloco precisar começar aberto.
110
+
111
+ O corpo do expansível suporta parágrafos, listas, alertas, blocos de código, diagramas Mermaid, tabelas, HTML bruto e quick links. Nesta primeira versão, mantenha títulos fora do bloco expansível, porque títulos dentro do corpo viram parágrafos comuns para preservar o ToC da página.
112
+
97
113
  ## Adicionando um Novo Idioma
98
114
 
99
115
  1. Crie `src/i18n/languages/xx-XX.hjson` com todas as traduções de UI