@podlite/schema 0.0.33 → 0.0.35

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 (46) hide show
  1. package/CHANGELOG.podlite +142 -0
  2. package/esm/blocks-helpers.d.ts +1 -1
  3. package/esm/blocks-helpers.js +2 -2
  4. package/esm/blocks-helpers.js.map +1 -1
  5. package/esm/exportHtml.js +11 -5
  6. package/esm/exportHtml.js.map +1 -1
  7. package/esm/exportMarkdown.d.ts +15 -0
  8. package/esm/exportMarkdown.js +341 -0
  9. package/esm/exportMarkdown.js.map +1 -0
  10. package/esm/grammar.js +3 -3
  11. package/esm/grammar.js.map +1 -1
  12. package/esm/grammarfc.js +2 -2
  13. package/esm/index.d.ts +2 -0
  14. package/esm/index.js +24 -0
  15. package/esm/index.js.map +1 -1
  16. package/esm/pluggableParser.d.ts +1 -0
  17. package/esm/pluggableParser.js +5 -0
  18. package/esm/pluggableParser.js.map +1 -1
  19. package/esm/plugin-group-items.js +8 -5
  20. package/esm/plugin-group-items.js.map +1 -1
  21. package/esm/plugin-items.js +23 -0
  22. package/esm/plugin-items.js.map +1 -1
  23. package/esm/types.d.ts +2 -0
  24. package/esm/writerMarkdown.d.ts +11 -0
  25. package/esm/writerMarkdown.js +20 -0
  26. package/esm/writerMarkdown.js.map +1 -0
  27. package/lib/blocks-helpers.d.ts +1 -1
  28. package/lib/blocks-helpers.js +2 -2
  29. package/lib/exportHtml.js +11 -5
  30. package/lib/exportMarkdown.d.ts +15 -0
  31. package/lib/exportMarkdown.js +346 -0
  32. package/lib/grammar.js +3 -3
  33. package/lib/grammarfc.js +2 -2
  34. package/lib/index.d.ts +2 -0
  35. package/lib/index.js +27 -1
  36. package/lib/pluggableParser.d.ts +1 -0
  37. package/lib/pluggableParser.js +5 -0
  38. package/lib/plugin-group-items.js +8 -5
  39. package/lib/plugin-items.js +23 -0
  40. package/lib/types.d.ts +2 -0
  41. package/lib/writerMarkdown.d.ts +11 -0
  42. package/lib/writerMarkdown.js +25 -0
  43. package/package.json +23 -8
  44. package/schema/AstTree.json +12 -0
  45. package/schema/PodliteDocument.json +12 -0
  46. package/CHANGELOG.md +0 -126
@@ -0,0 +1,346 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ const exportAny_1 = __importDefault(require("./exportAny"));
7
+ const handlers_1 = require("./helpers/handlers");
8
+ const makeTransformer_1 = require("./helpers/makeTransformer");
9
+ const config_1 = __importDefault(require("./helpers/config"));
10
+ const writerMarkdown_1 = __importDefault(require("./writerMarkdown"));
11
+ const plugin_clean_location_1 = __importDefault(require("./plugin-clean-location"));
12
+ const rules = {
13
+ ':text': (writer, processor) => (node, ctx, interator) => {
14
+ if (node.value) {
15
+ writer.write(node.value);
16
+ }
17
+ else {
18
+ interator(node.content, ctx);
19
+ }
20
+ },
21
+ // Formatting codes
22
+ 'A<>': (writer, processor) => (node, ctx, interator) => {
23
+ if (!(ctx.alias && ctx.alias.hasOwnProperty(node.content))) {
24
+ writer.writeRaw(`A<${node.content}>`);
25
+ }
26
+ else {
27
+ const src = ctx.alias[node.content].join('\n');
28
+ const tree_1 = processor(src);
29
+ const tree = (0, plugin_clean_location_1.default)()(tree_1);
30
+ if (tree[0].type === 'para') {
31
+ interator(tree[0].content, ctx);
32
+ }
33
+ else {
34
+ interator(tree, ctx);
35
+ }
36
+ }
37
+ },
38
+ 'C<>': (0, handlers_1.wrapContent)('`', '`'),
39
+ 'D<>': (writer, processor) => (node, ctx, interator) => {
40
+ if (!writer.hasOwnProperty('DEFINITIONS')) {
41
+ writer.DEFINITIONS = [];
42
+ }
43
+ writer.DEFINITIONS.push({ definition: [node.content[0]] });
44
+ writer.writeRaw('**');
45
+ interator(node.content, ctx);
46
+ writer.writeRaw('**');
47
+ },
48
+ 'B<>': (0, handlers_1.wrapContent)('**', '**'),
49
+ 'I<>': (0, handlers_1.wrapContent)('*', '*'),
50
+ 'R<>': (0, handlers_1.wrapContent)('*', '*'),
51
+ 'K<>': (0, handlers_1.wrapContent)('`', '`'),
52
+ 'L<>': (0, handlers_1.setFn)((node, ctx) => {
53
+ let { meta } = node;
54
+ if (meta === null) {
55
+ meta = node.content;
56
+ }
57
+ return (0, handlers_1.wrapContent)(`[`, `](${meta})`);
58
+ }),
59
+ 'N<>': (writer, processor) => {
60
+ writer.addListener('end', () => {
61
+ if (!writer.hasOwnProperty('FOOTNOTES')) {
62
+ return;
63
+ }
64
+ const footnotes = writer.FOOTNOTES;
65
+ if (footnotes.length < 1) {
66
+ return;
67
+ }
68
+ writer.writeRaw('\n\n---\n\n');
69
+ footnotes.map(footnote => {
70
+ writer.writeRaw(`[^${footnote.gid}]: `);
71
+ footnote.make();
72
+ writer.writeRaw('\n');
73
+ });
74
+ });
75
+ return (node, ctx, interator) => {
76
+ if (node.content.length < 1) {
77
+ return;
78
+ }
79
+ if (!writer.hasOwnProperty('gid')) {
80
+ writer.gid = 1;
81
+ }
82
+ const gid = writer.gid++;
83
+ writer.writeRaw(`[^${gid}]`);
84
+ if (!writer.hasOwnProperty('FOOTNOTES')) {
85
+ writer.FOOTNOTES = [];
86
+ }
87
+ writer.FOOTNOTES.push({
88
+ gid,
89
+ fnRefId: `fnref:${gid}`,
90
+ fnId: `fn:${gid}`,
91
+ make: () => {
92
+ interator(node.content, ctx);
93
+ },
94
+ });
95
+ };
96
+ },
97
+ 'S<>': (writer, processor) => (node, ctx, interator) => {
98
+ const content = node.content || '';
99
+ // preserve spaces and newlines
100
+ writer.writeRaw(content.replace(/ /g, '&nbsp;').replace(/\n/g, ' \n'));
101
+ },
102
+ 'T<>': (0, handlers_1.wrapContent)('`', '`'),
103
+ 'U<>': (0, handlers_1.wrapContent)('', ''),
104
+ 'V<>': handlers_1.content,
105
+ 'X<>': (writer, processor) => (node, ctx, interator) => {
106
+ interator(node.content, ctx);
107
+ let { entry } = node;
108
+ if (entry === null && node.content.length > 0) {
109
+ //@ts-ignore
110
+ entry = [node.content[0]];
111
+ }
112
+ else {
113
+ return;
114
+ }
115
+ if (!writer.hasOwnProperty('INDEXTERMS')) {
116
+ writer.INDEXTERMS = [];
117
+ }
118
+ writer.INDEXTERMS.push({ entry });
119
+ },
120
+ 'Z<>': handlers_1.emptyContent,
121
+ pod: handlers_1.content,
122
+ ':code': (writer, processor) => (node, ctx, interator) => {
123
+ const conf = (0, config_1.default)(node, ctx);
124
+ const lang = conf.exists('lang') ? conf.getFirstValue('lang') : '';
125
+ writer.writeRaw('```' + lang + '\n');
126
+ // inside code blocks, write text without escaping
127
+ if (node.content) {
128
+ node.content.forEach(child => {
129
+ if (typeof child === 'string') {
130
+ writer.writeRaw(child);
131
+ }
132
+ else if (child.type === 'verbatim') {
133
+ writer.writeRaw(child.value);
134
+ }
135
+ else {
136
+ interator([child], ctx);
137
+ }
138
+ });
139
+ }
140
+ writer.writeRaw('```\n');
141
+ },
142
+ code: (0, handlers_1.handleNested)((writer, processor) => (node, ctx, interator) => {
143
+ const conf = (0, config_1.default)(node, ctx);
144
+ const lang = conf.exists('lang') ? conf.getFirstValue('lang') : '';
145
+ writer.writeRaw('```' + lang + '\n');
146
+ if (node.content) {
147
+ node.content.forEach(child => {
148
+ if (typeof child === 'string') {
149
+ writer.writeRaw(child);
150
+ }
151
+ else if (child.type === 'verbatim') {
152
+ writer.writeRaw(child.value);
153
+ }
154
+ else {
155
+ interator([child], ctx);
156
+ }
157
+ });
158
+ }
159
+ writer.writeRaw('```\n');
160
+ }),
161
+ data: handlers_1.emptyContent,
162
+ ':verbatim': (writer, processor) => (node, ctx, interator) => {
163
+ if (node.error) {
164
+ writer.emit('errors', node.location);
165
+ }
166
+ writer.writeRaw(node.value);
167
+ },
168
+ ':blankline': handlers_1.emptyContent,
169
+ ':ambient': handlers_1.emptyContent,
170
+ // Directives
171
+ ':config': (0, handlers_1.setFn)((node, ctx) => {
172
+ if (!ctx.hasOwnProperty('config'))
173
+ ctx.config = {};
174
+ ctx.config[node.name] = node.config;
175
+ return handlers_1.emptyContent;
176
+ }),
177
+ ':alias': (0, handlers_1.setFn)((node, ctx) => {
178
+ if (!ctx.hasOwnProperty('alias'))
179
+ ctx.alias = {};
180
+ ctx.alias[node.name] = node.replacement;
181
+ return handlers_1.emptyContent;
182
+ }),
183
+ // block =para
184
+ para: (0, handlers_1.handleNested)(handlers_1.content),
185
+ ':para': (writer, processor) => (node, ctx, interator) => {
186
+ if (node.content)
187
+ interator(node.content, ctx);
188
+ writer.writeRaw('\n');
189
+ },
190
+ 'head:block': (0, handlers_1.subUse)({
191
+ ':para': handlers_1.content,
192
+ }, (0, handlers_1.setFn)((node, ctx) => {
193
+ const { level } = node;
194
+ const prefix = '#'.repeat(level) + ' ';
195
+ return (writer, processor) => (node, ctx, interator) => {
196
+ writer.writeRaw(prefix);
197
+ if (node.content)
198
+ interator(node.content, ctx);
199
+ writer.writeRaw('\n');
200
+ };
201
+ })),
202
+ ':list': (0, handlers_1.setFn)((node, ctx) => {
203
+ return (writer, processor) => (node, ctx, interator) => {
204
+ // pass list type through context
205
+ const newCtx = {
206
+ ...ctx,
207
+ listType: node.list,
208
+ listCounter: { value: 1 },
209
+ listDepth: (ctx.listDepth || 0) + 1,
210
+ };
211
+ if (node.content)
212
+ interator(node.content, newCtx);
213
+ };
214
+ }),
215
+ 'item:block': (writer, processor) => (node, ctx, interator) => {
216
+ const indent = ' '.repeat(Math.max(0, (ctx.listDepth || 1) - 1));
217
+ const listType = ctx.listType || 'unordered';
218
+ let prefix;
219
+ if (listType === 'ordered') {
220
+ const counter = ctx.listCounter || { value: 1 };
221
+ prefix = `${counter.value}. `;
222
+ counter.value++;
223
+ }
224
+ else if (listType === 'variable') {
225
+ prefix = '- ';
226
+ }
227
+ else {
228
+ prefix = '- ';
229
+ }
230
+ writer.writeRaw(indent + prefix);
231
+ if (node.content)
232
+ interator(node.content, ctx);
233
+ },
234
+ 'comment:block': handlers_1.emptyContent,
235
+ defn: (writer, processor) => (node, ctx, interator) => {
236
+ if (node.content)
237
+ interator(node.content, ctx);
238
+ writer.writeRaw('\n');
239
+ },
240
+ 'term:para': (writer, processor) => (node, ctx, interator) => {
241
+ writer.writeRaw('**');
242
+ if (node.content)
243
+ interator(node.content, ctx);
244
+ writer.writeRaw(':** ');
245
+ },
246
+ nested: (0, handlers_1.handleNested)(handlers_1.content, 1),
247
+ output: (0, handlers_1.handleNested)((writer, processor) => (node, ctx, interator) => {
248
+ writer.writeRaw('```\n');
249
+ if (node.content)
250
+ interator(node.content, ctx);
251
+ writer.writeRaw('```\n');
252
+ }, 1),
253
+ input: (0, handlers_1.handleNested)((writer, processor) => (node, ctx, interator) => {
254
+ writer.writeRaw('```\n');
255
+ if (node.content)
256
+ interator(node.content, ctx);
257
+ writer.writeRaw('```\n');
258
+ }, 1),
259
+ // table section
260
+ 'table:block': (0, handlers_1.handleNested)((writer, processor) => (node, ctx, interator) => {
261
+ const conf = (0, config_1.default)(node, ctx);
262
+ if (conf.exists('caption')) {
263
+ writer.writeRaw('**');
264
+ writer.write(conf.getFirstValue('caption'));
265
+ writer.writeRaw('**\n\n');
266
+ }
267
+ // collect rows data for proper Markdown table rendering
268
+ const rows = (node.content || []).filter(child => child.name === 'table_row' || child.name === 'table_head');
269
+ if (rows.length === 0)
270
+ return;
271
+ const hasHeader = rows[0].name === 'table_head';
272
+ // render each row
273
+ rows.forEach((row, rowIndex) => {
274
+ const cells = (row.content || []).filter(c => c.name === 'table_cell');
275
+ writer.writeRaw('|');
276
+ cells.forEach(cell => {
277
+ writer.writeRaw(' ');
278
+ if (cell.content) {
279
+ cell.content.forEach(c => {
280
+ if (typeof c === 'string') {
281
+ writer.write(c.trim());
282
+ }
283
+ else {
284
+ interator([c], ctx);
285
+ }
286
+ });
287
+ }
288
+ writer.writeRaw(' |');
289
+ });
290
+ writer.writeRaw('\n');
291
+ // add separator after header row
292
+ if (rowIndex === 0 && hasHeader) {
293
+ writer.writeRaw('|');
294
+ cells.forEach(() => {
295
+ writer.writeRaw(' --- |');
296
+ });
297
+ writer.writeRaw('\n');
298
+ }
299
+ // if no header, add separator after first row
300
+ if (rowIndex === 0 && !hasHeader) {
301
+ writer.writeRaw('|');
302
+ cells.forEach(() => {
303
+ writer.writeRaw(' --- |');
304
+ });
305
+ writer.writeRaw('\n');
306
+ }
307
+ });
308
+ writer.writeRaw('\n');
309
+ }),
310
+ ':separator': handlers_1.emptyContent,
311
+ table_row: handlers_1.emptyContent,
312
+ table_cell: handlers_1.emptyContent,
313
+ table_head: handlers_1.emptyContent,
314
+ // Toc
315
+ ':toc': handlers_1.emptyContent,
316
+ ':toc-list': handlers_1.emptyContent,
317
+ ':toc-item': handlers_1.emptyContent,
318
+ ':image': (writer, processor) => (node, ctx, interator) => {
319
+ writer.writeRaw(`![${node.alt || ''}](${node.src})`);
320
+ },
321
+ };
322
+ const toMarkdown = opt => (0, exportAny_1.default)({ writer: writerMarkdown_1.default, ...opt })
323
+ .use('*', (writer, processor) => {
324
+ return (node, ctx, interator) => {
325
+ const isSemanticBlock = node => {
326
+ const name = node.name || '';
327
+ const isTypeBlock = (node.type || '') === 'block';
328
+ return isTypeBlock && name === name.toUpperCase();
329
+ };
330
+ if ((0, makeTransformer_1.isNamedBlock)(node.name)) {
331
+ return true;
332
+ }
333
+ if (isSemanticBlock(node)) {
334
+ const name = node.name;
335
+ writer.writeRaw('# ');
336
+ writer.write(name);
337
+ writer.writeRaw('\n\n');
338
+ }
339
+ if (node.hasOwnProperty('content')) {
340
+ interator(node.content, ctx);
341
+ }
342
+ };
343
+ })
344
+ .use(rules);
345
+ exports.default = toMarkdown;
346
+ //# sourceMappingURL=exportMarkdown.js.map
package/lib/grammar.js CHANGED
@@ -1,7 +1,7 @@
1
1
  /*
2
- * Generated by PEG.js 0.10.0.
2
+ * Generated by Pegmill 0.1.0
3
3
  *
4
- * http://pegjs.org/
4
+ * https://github.com/zag/pegmill
5
5
  */
6
6
  "use strict";
7
7
  function peg$subclass(child, parent) {
@@ -152,7 +152,7 @@ function peg$parse(input, options) {
152
152
  config,
153
153
  location: location()
154
154
  };
155
- }, peg$c125 = /^[+-=_|]/, peg$c126 = peg$classExpectation([["+", "="], "_", "|"], false, false), peg$c127 = function () { return { type: 'separator', text: text() }; }, peg$c128 = function () { return options.isDelimited; }, peg$c129 = function () {
155
+ }, peg$c125 = /^[\-+=_|]/, peg$c126 = peg$classExpectation(["-", "+", "=", "_", "|"], false, false), peg$c127 = function () { return { type: 'separator', text: text() }; }, peg$c128 = function () { return options.isDelimited; }, peg$c129 = function () {
156
156
  return {
157
157
  type: 'separator',
158
158
  text: text()
package/lib/grammarfc.js CHANGED
@@ -1,7 +1,7 @@
1
1
  /*
2
- * Generated by PEG.js 0.10.0.
2
+ * Generated by Pegmill 0.1.0
3
3
  *
4
- * http://pegjs.org/
4
+ * https://github.com/zag/pegmill
5
5
  */
6
6
  "use strict";
7
7
  function peg$subclass(child, parent) {
package/lib/index.d.ts CHANGED
@@ -17,6 +17,7 @@ export { podlitePluggable, Podlite, PodliteExport, cleanIds, frozenIds } from '.
17
17
  export declare function toAst(): {};
18
18
  export declare type SchemaValidationError = ErrorObject<string, Record<string, any>>;
19
19
  export declare function getTextContentFromNode(node: PodNode): string;
20
+ export declare function getPodContentFromNode(node: PodNode): string;
20
21
  export declare function validatePodliteAst(data: unknown): SchemaValidationError[];
21
22
  export declare function validateAstTree(data: unknown): SchemaValidationError[];
22
23
  export declare function validateAst(data: unknown, Name?: string): SchemaValidationError[];
@@ -75,6 +76,7 @@ export { makeTree as toTree };
75
76
  declare const parse: Function;
76
77
  export { parse as parse };
77
78
  export { default as toHtml } from './exportHtml';
79
+ export { default as toMarkdown } from './exportMarkdown';
78
80
  export { default as Writer } from './writer';
79
81
  declare const VERSION: any;
80
82
  export { VERSION as version };
package/lib/index.js CHANGED
@@ -25,7 +25,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
25
25
  return (mod && mod.__esModule) ? mod : { "default": mod };
26
26
  };
27
27
  Object.defineProperty(exports, "__esModule", { value: true });
28
- exports.version = exports.Writer = exports.toHtml = exports.parse = exports.toTree = exports.isValidateError = exports.validateAst = exports.validateAstTree = exports.validatePodliteAst = exports.getTextContentFromNode = exports.toAst = exports.frozenIds = exports.cleanIds = exports.podlitePluggable = exports.toAnyRules = exports.pluginCleanLocation = exports.makeAttrs = exports.toAny = exports.isSemanticBlock = exports.isNamedBlock = exports.makeTransformer = exports.makeInterator = void 0;
28
+ exports.version = exports.Writer = exports.toMarkdown = exports.toHtml = exports.parse = exports.toTree = exports.isValidateError = exports.validateAst = exports.validateAstTree = exports.validatePodliteAst = exports.getPodContentFromNode = exports.getTextContentFromNode = exports.toAst = exports.frozenIds = exports.cleanIds = exports.podlitePluggable = exports.toAnyRules = exports.pluginCleanLocation = exports.makeAttrs = exports.toAny = exports.isSemanticBlock = exports.isNamedBlock = exports.makeTransformer = exports.makeInterator = void 0;
29
29
  const ajv_1 = __importDefault(require("ajv"));
30
30
  const pointer = __importStar(require("json-pointer"));
31
31
  const jsonShemes = __importStar(require("../schema"));
@@ -82,6 +82,30 @@ function getTextContentFromNode(node) {
82
82
  return text;
83
83
  }
84
84
  exports.getTextContentFromNode = getTextContentFromNode;
85
+ function getPodContentFromNode(node) {
86
+ let text = '';
87
+ const rules = {
88
+ '*': (node, ctx, visiter) => {
89
+ if (node.type === 'blankline') {
90
+ text += '\n';
91
+ return;
92
+ }
93
+ if (node.text) {
94
+ text += node.text;
95
+ return;
96
+ }
97
+ text += `=${node.name} `;
98
+ if ('content' in node) {
99
+ visiter(node.content, ctx);
100
+ }
101
+ return node;
102
+ },
103
+ };
104
+ const transformer = (0, ast_inerator_1.makeInterator)(rules);
105
+ const res = transformer(node, {});
106
+ return text;
107
+ }
108
+ exports.getPodContentFromNode = getPodContentFromNode;
85
109
  function validatePodliteAst(data) {
86
110
  return validateAst(data, 'PodliteDocument');
87
111
  }
@@ -161,6 +185,8 @@ const parse = makeTree().parse;
161
185
  exports.parse = parse;
162
186
  var exportHtml_1 = require("./exportHtml");
163
187
  Object.defineProperty(exports, "toHtml", { enumerable: true, get: function () { return __importDefault(exportHtml_1).default; } });
188
+ var exportMarkdown_1 = require("./exportMarkdown");
189
+ Object.defineProperty(exports, "toMarkdown", { enumerable: true, get: function () { return __importDefault(exportMarkdown_1).default; } });
164
190
  var writer_1 = require("./writer");
165
191
  Object.defineProperty(exports, "Writer", { enumerable: true, get: function () { return __importDefault(writer_1).default; } });
166
192
  // Cannot be `import` as it's not under TS root dir
@@ -18,6 +18,7 @@ export interface Podlite {
18
18
  use: (plugin: Plugins) => Podlite;
19
19
  parse: (text: string, opt?: parseOpt) => PodliteDocument;
20
20
  toHtml: (ast: PodliteDocument) => PodliteExport;
21
+ toMarkdown: (ast: PodliteDocument) => PodliteExport;
21
22
  toAst: (ast: PodliteDocument) => PodliteDocument;
22
23
  getPlugins: () => Array<Plugins>;
23
24
  }
@@ -5,6 +5,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.podlitePluggable = exports.frozenIds = exports.cleanIds = void 0;
7
7
  const _1 = require(".");
8
+ const exportMarkdown_1 = __importDefault(require("./exportMarkdown"));
8
9
  const ids_1 = __importDefault(require("./helpers/ids"));
9
10
  const corePlugins_1 = __importDefault(require("./helpers/corePlugins"));
10
11
  var ids_2 = require("./helpers/ids");
@@ -69,6 +70,10 @@ const podlitePluggable = ({ plugins = {} } = {}) => {
69
70
  const toHtmlPlugins = (0, _1.toAnyRules)('toHtml', instance.getPlugins());
70
71
  return (0, _1.toHtml)({}).use(toHtmlPlugins).run(ast, null);
71
72
  };
73
+ instance.toMarkdown = ast => {
74
+ const toMarkdownPlugins = (0, _1.toAnyRules)('toMarkdown', instance.getPlugins());
75
+ return (0, exportMarkdown_1.default)({}).use(toMarkdownPlugins).run(ast, null);
76
+ };
72
77
  instance.getPlugins = () => _plugins;
73
78
  // init core plugins
74
79
  instance.use(corePlugins_1.default);
@@ -10,8 +10,10 @@ exports.default = () => tree => {
10
10
  (n1.name === 'item' || n1.name === 'defn') &&
11
11
  n2.name === n1.name &&
12
12
  n1['level'] === n2.level &&
13
- isNumbered(n1) === isNumbered(n2);
13
+ isNumbered(n1) === isNumbered(n2) &&
14
+ isChecked(n1) === isChecked(n2);
14
15
  const isNumbered = node => Boolean((0, config_1.default)(node, {}).exists('numbered'));
16
+ const isChecked = node => node.checked !== undefined;
15
17
  const group = (a, level = 1) => {
16
18
  const isInListMode = a => {
17
19
  return a.length > 0 && a[a.length - 1].type === 'list';
@@ -32,14 +34,15 @@ exports.default = () => tree => {
32
34
  (!isInListMode(a) ||
33
35
  // different type of list and item
34
36
  // at the same level
35
- (i.level === level && getList(a).list !== (isNumbered(i) ? 'ordered' : 'itemized')))) {
37
+ (Number(i.level) === level &&
38
+ getList(a).list !== (isNumbered(i) ? 'ordered' : isChecked(i) ? 'task' : 'itemized')))) {
36
39
  // create empty list
37
40
  // list = ['ordered', 'variable', 'itemized']
38
41
  a.push({
39
42
  type: 'list',
40
43
  level: i.level,
41
44
  content: [],
42
- list: isNumbered(i) ? 'ordered' : 'itemized',
45
+ list: isNumbered(i) ? 'ordered' : isChecked(i) ? 'task' : 'itemized',
43
46
  });
44
47
  }
45
48
  // main logic
@@ -57,12 +60,12 @@ exports.default = () => tree => {
57
60
  * { type = 'list',
58
61
  * ordered = [true, false]
59
62
  * content = [ .... ]
60
- * list = ['ordered', 'variable', 'itemized']
63
+ * list = ['ordered', 'variable', 'task', 'itemized']
61
64
  */
62
65
  return result.map(item => {
63
66
  // process any item with content ( except formatting codes)
64
67
  if (item.content && item.type !== 'fcode') {
65
- item.content = group(item.content, item.level + 1);
68
+ item.content = group(item.content, Number(item.level || 0) + 1);
66
69
  }
67
70
  return item;
68
71
  });
@@ -13,9 +13,32 @@ exports.default = () => tree => {
13
13
  if (matchItem) {
14
14
  node.name = 'item';
15
15
  node.level = matchItem[1] || 1;
16
+ // Check :checked / :!checked config attribute
17
+ const checkedConfig = (node.config || []).find(c => c.name === 'checked');
18
+ if (checkedConfig) {
19
+ node.checked = checkedConfig.value !== false && checkedConfig.value !== 0 && checkedConfig.value !== '0';
20
+ }
16
21
  if (node.content[0]) {
17
22
  const startText = node.content[0];
18
23
  if (startText.text) {
24
+ // Check for checkbox syntax [x] or [ ] at start of text
25
+ if (!checkedConfig) {
26
+ const checkboxRe = /^\[( |x)\]\s*/;
27
+ const checkboxMatch = checkboxRe.exec(startText.text);
28
+ if (checkboxMatch) {
29
+ node.checked = checkboxMatch[1] === 'x';
30
+ startText.text = startText.text.replace(checkboxRe, '');
31
+ if (startText.type === 'para') {
32
+ startText.content = [startText.text];
33
+ }
34
+ node.config = node.config || [];
35
+ node.config.push({
36
+ name: 'checked',
37
+ value: node.checked,
38
+ type: 'boolean',
39
+ });
40
+ }
41
+ }
19
42
  let re = /^(\s*#\s*)/;
20
43
  const match = re.exec(startText.text);
21
44
  if (match) {
package/lib/types.d.ts CHANGED
@@ -100,6 +100,7 @@ export interface Image {
100
100
  export interface Toc {
101
101
  type: 'toc';
102
102
  title?: string;
103
+ foldedLevels?: Record<number, boolean>;
103
104
  content: TocList;
104
105
  }
105
106
  export interface TocList {
@@ -304,6 +305,7 @@ export interface BlockItem extends Block {
304
305
  name: 'item';
305
306
  content: Array<Node>;
306
307
  level: string | number;
308
+ checked?: boolean;
307
309
  }
308
310
  export interface BlockOutput extends Block {
309
311
  name: 'output';
@@ -0,0 +1,11 @@
1
+ /**
2
+ * Markdown writer
3
+ */
4
+ import Writer from './writer';
5
+ declare class WriterMarkdown extends Writer {
6
+ constructor(output?: any);
7
+ escape(string: any): string;
8
+ _add_nesting(n: any): void;
9
+ _remove_nesting(n: any): void;
10
+ }
11
+ export default WriterMarkdown;
@@ -0,0 +1,25 @@
1
+ "use strict";
2
+ /**
3
+ * Markdown writer
4
+ */
5
+ var __importDefault = (this && this.__importDefault) || function (mod) {
6
+ return (mod && mod.__esModule) ? mod : { "default": mod };
7
+ };
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ const writer_1 = __importDefault(require("./writer"));
10
+ class WriterMarkdown extends writer_1.default {
11
+ constructor(output) {
12
+ super(output);
13
+ }
14
+ escape(string) {
15
+ return (string + '').replace(/([\\`*_\[\]#|])/g, '\\$1');
16
+ }
17
+ _add_nesting(n) {
18
+ this.writeRaw('> '.repeat(n));
19
+ }
20
+ _remove_nesting(n) {
21
+ // no closing tag needed for Markdown blockquotes
22
+ }
23
+ }
24
+ exports.default = WriterMarkdown;
25
+ //# sourceMappingURL=writerMarkdown.js.map
package/package.json CHANGED
@@ -1,8 +1,17 @@
1
1
  {
2
2
  "name": "@podlite/schema",
3
- "version": "0.0.33",
4
- "description": "AST tools for Podlite markup language",
3
+ "version": "0.0.35",
4
+ "description": "AST tools and schema for Podlite markup language — validate, traverse, and transform document trees",
5
5
  "main": "lib/index.js",
6
+ "homepage": "https://podlite.org",
7
+ "bugs": {
8
+ "url": "https://github.com/podlite/podlite/issues"
9
+ },
10
+ "repository": {
11
+ "type": "git",
12
+ "url": "https://github.com/podlite/podlite.git",
13
+ "directory": "packages/podlite-schema"
14
+ },
6
15
  "license": "MIT",
7
16
  "funding": {
8
17
  "type": "opencollective",
@@ -31,16 +40,22 @@
31
40
  "build": "run-s build:pegjs build_lib build:ast ",
32
41
  "build_lib": "yarn g:build",
33
42
  "build:ast": "ts-node scripts/make-ast-scheme.ts",
34
- "build:pegjs": "pegjs -o src/grammar.js src/grammar.pegjs && pegjs -o src/grammarfc.js src/grammarfc.pegjs",
43
+ "build:pegjs": "pegmill -o src/grammar.js src/grammar.pegjs && pegmill -o src/grammarfc.js src/grammarfc.pegjs",
35
44
  "watch": "npx nodemon -e js,ts --exec 'yarn' build",
36
- "watch:pegjs": "npx nodemon -e pegjs --exec 'yarn' build:pegjs",
45
+ "watch:pegjs": "npx nodemon -e pegmill --exec 'yarn' build:pegjs",
37
46
  "test": "yarn g:jest --passWithNoTests"
38
47
  },
39
48
  "keywords": [
40
- "markdown",
41
49
  "podlite",
42
- "markup",
43
- "markup-language"
50
+ "schema",
51
+ "ast",
52
+ "syntax-tree",
53
+ "markup-language",
54
+ "transform",
55
+ "visitor",
56
+ "parser",
57
+ "markdown",
58
+ "tree"
44
59
  ],
45
60
  "dependencies": {
46
61
  "ajv": "^7.2.3",
@@ -53,7 +68,7 @@
53
68
  "@types/node": "^17.0.7",
54
69
  "glob": "^7.2.0",
55
70
  "npm-run-all": "^4.1.5",
56
- "pegjs": "^0.10.0",
71
+ "pegmill": "0.1.0",
57
72
  "ts-node": "^9.1.1",
58
73
  "typescript": "4.5.5",
59
74
  "typescript-json-schema": "0.53.0"