diff --git a/core/modules/parsers/wikiparser/rules/fnprocdef.js b/core/modules/parsers/wikiparser/rules/fnprocdef.js index a4259e574..82c4b6217 100644 --- a/core/modules/parsers/wikiparser/rules/fnprocdef.js +++ b/core/modules/parsers/wikiparser/rules/fnprocdef.js @@ -104,8 +104,8 @@ exports.serialize = function(tree, serialize) { }).join(","); // Definition text var definition = tree.attributes.value.value; - // Construct the serialized string - return "\\" + type + " " + name + "(" + params + ")\n" + definition + "\n\\end"; + // Construct the serialized string, concat the children because pragma rule wrap everything below it as children + return "\\" + type + " " + name + "(" + params + ")\n" + definition + "\n\\end\n\n" + serialize(tree.children) + "\n"; }; })(); diff --git a/core/modules/parsers/wikiparser/rules/hardlinebreaks.js b/core/modules/parsers/wikiparser/rules/hardlinebreaks.js index 39ef6fc5c..9f26c3d95 100644 --- a/core/modules/parsers/wikiparser/rules/hardlinebreaks.js +++ b/core/modules/parsers/wikiparser/rules/hardlinebreaks.js @@ -53,23 +53,22 @@ exports.parse = function() { } } } while(match && !match[1]); - // Return the nodes + // Mark first and last node, and return the nodes + if(tree[0]) tree[0].isRuleStart = true; + if(tree[tree.length-1]) tree[tree.length-1].isRuleEnd = true; return tree; }; exports.serialize = function(tree,serialize) { - // Serialized text with hard line breaks - var serialized = '"""\n'; - // Serialize each node in the tree - tree.forEach(function(node) { - if(node.type === "element" && node.tag === "br") { - serialized += "\n"; - } else { - serialized += serialize([node]).join(''); - } - }); - serialized += '\n"""'; - return serialized; + // we get each of element on tree from `parse` one by one here. + var text = tree.tag === 'br' ? '\n' : tree.text; + if(tree.isRuleStart) { + return '"""\n' + text; + } + if(tree.isRuleEnd) { + return text + '"""'; + } + return text; }; })(); diff --git a/core/modules/parsers/wikiparser/rules/heading.js b/core/modules/parsers/wikiparser/rules/heading.js index 79df971e5..67470c9c5 100644 --- a/core/modules/parsers/wikiparser/rules/heading.js +++ b/core/modules/parsers/wikiparser/rules/heading.js @@ -47,14 +47,11 @@ exports.parse = function() { }; exports.serialize = function(tree, serialize) { - // Heading level - var headingLevel = tree.tag.length - 1; - // Classes + // Get heading level from number after `h` + var headingLevel = parseInt(tree.tag.substr(1),10); var classes = tree.attributes.class ? tree.attributes.class.value.split(" ").join(".") : ""; - // Serialized heading text - var headingText = serialize(tree.children).join(''); - // Construct the serialized string - return Array(headingLevel + 1).join("!") + (classes ? "." + classes : "") + " " + headingText; + var headingText = serialize(tree.children); + return Array(headingLevel + 1).join("!") + (classes ? "." + classes : "") + " " + headingText + "\n"; }; })(); diff --git a/core/modules/parsers/wikiparser/rules/html.js b/core/modules/parsers/wikiparser/rules/html.js index 656759ed8..1e3f9865b 100644 --- a/core/modules/parsers/wikiparser/rules/html.js +++ b/core/modules/parsers/wikiparser/rules/html.js @@ -199,7 +199,7 @@ exports.serialize = function(tree, serialize) { var tag = tree.tag; var attributes = Object.keys(tree.attributes).map(function(key) { return key + '="' + tree.attributes[key].value + '"'; - }); + }).join(''); // Children var children = tree.children ? serialize(tree.children) : ''; // Self-closing tag diff --git a/core/modules/parsers/wikiparser/rules/image.js b/core/modules/parsers/wikiparser/rules/image.js index 8591e544e..33454f46e 100644 --- a/core/modules/parsers/wikiparser/rules/image.js +++ b/core/modules/parsers/wikiparser/rules/image.js @@ -131,16 +131,14 @@ exports.parseImage = function(source,pos) { }; exports.serialize = function(tree) { - // Width attribute + // DEBUG: console tree + console.warn(`tree`, JSON.stringify(tree, null, ' ')); var width = tree.attributes.width ? " width=" + tree.attributes.width.value : ""; - // Height attribute var height = tree.attributes.height ? " height=" + tree.attributes.height.value : ""; - // Tooltip attribute + var padSpace = width || height ? " " : ""; var tooltip = tree.attributes.tooltip ? tree.attributes.tooltip.value + "|" : ""; - // Source attribute var source = tree.attributes.source.value; - // Construct the serialized string - return "[img" + width + height + " [" + tooltip + source + "]]"; + return "[img" + width + height + padSpace + "[" + tooltip + source + "]]"; }; })(); diff --git a/editions/test/tiddlers/tests/test-wikitext-serialize.js b/editions/test/tiddlers/tests/test-wikitext-serialize.js index d3ab4dc04..69800a81f 100644 --- a/editions/test/tiddlers/tests/test-wikitext-serialize.js +++ b/editions/test/tiddlers/tests/test-wikitext-serialize.js @@ -7,7 +7,7 @@ Tests the wikitext inverse-rendering from Wiki AST. \*/ -describe('WikiAST serialization tests', function () { +describe('WikiAST serialization unit tests', function () { var wiki = new $tw.Wiki(); wiki.addTiddler({ @@ -64,35 +64,35 @@ describe('WikiAST serialization tests', function () { expect(serialized).toBe(wiki.getTiddlerText('UnderscoreEmphasisTest').trimEnd()); }); - wiki.addTiddler({ title: 'TiddlerOne', text: 'The quick brown fox' }); + wiki.addTiddler({ title: 'SimpleTextTest', text: 'The quick brown fox' }); it('should render tiddlers with no special markup as-is', function () { // `trimEnd` because when we handle `p` element when parsing block rules, we always add a newline. But original text that may not have a trailing newline, will still be recognized as a block. - expect($tw.utils.serializeParseTree(wiki.parseTiddler('TiddlerOne').tree).trimEnd()).toBe( - wiki.getTiddlerText('TiddlerOne') + expect($tw.utils.serializeParseTree(wiki.parseTiddler('SimpleTextTest').tree).trimEnd()).toBe( + wiki.getTiddlerText('SimpleTextTest') ); }); - wiki.addTiddler({ title: 'TiddlerTwo', text: 'The rain in Spain\nfalls mainly on the plain' }); + wiki.addTiddler({ title: 'SoftLineBreakTest', text: 'The rain in Spain\nfalls mainly on the plain' }); it('should preserve single new lines', function () { - expect($tw.utils.serializeParseTree(wiki.parseTiddler('TiddlerTwo').tree).trimEnd()).toBe( - wiki.getTiddlerText('TiddlerTwo') + expect($tw.utils.serializeParseTree(wiki.parseTiddler('SoftLineBreakTest').tree).trimEnd()).toBe( + wiki.getTiddlerText('SoftLineBreakTest') ); }); - wiki.addTiddler({ title: 'TiddlerThree', text: 'The speed of sound\n\nThe light of speed' }); + wiki.addTiddler({ title: 'BlockRule', text: 'The speed of sound\n\nThe light of speed' }); it('should preserve double new lines to create paragraphs', function () { - expect($tw.utils.serializeParseTree(wiki.parseTiddler('TiddlerThree').tree).trimEnd()).toBe( - wiki.getTiddlerText('TiddlerThree') + expect($tw.utils.serializeParseTree(wiki.parseTiddler('BlockRule').tree).trimEnd()).toBe( + wiki.getTiddlerText('BlockRule') ); }); wiki.addTiddler({ - title: 'TiddlerFour', + title: 'CodeBlockTest', text: 'Simple `JS` and complex\n\n---\n\n```js\nvar match = reEnd.exec(this.parser.source)\n```\nend', }); it('should render inline code and block code', function () { - expect($tw.utils.serializeParseTree(wiki.parseTiddler('TiddlerFour').tree).trimEnd()).toBe( - wiki.getTiddlerText('TiddlerFour') + expect($tw.utils.serializeParseTree(wiki.parseTiddler('CodeBlockTest').tree).trimEnd()).toBe( + wiki.getTiddlerText('CodeBlockTest') ); }); @@ -177,7 +177,6 @@ describe('WikiAST serialization tests', function () { var serialized = $tw.utils.serializeParseTree(wiki.parseTiddler('FunctionDefinition').tree).trimEnd(); expect(serialized).toBe(wiki.getTiddlerText('FunctionDefinition').trimEnd()); }); - return; wiki.addTiddler({ title: 'HardLineBreaksTest', @@ -214,6 +213,7 @@ describe('WikiAST serialization tests', function () { var serialized = $tw.utils.serializeParseTree(wiki.parseTiddler('ImageTest').tree).trimEnd(); expect(serialized).toBe(wiki.getTiddlerText('ImageTest').trimEnd()); }); + return; wiki.addTiddler({ title: 'ImportTest',