Mercurial
comparison markdown_converter/tests/test_wasm.js @ 156:cd35e600ae34
[MarkDown Converter] Fixed few things and made a test
| author | June Park <parkjune1995@gmail.com> |
|---|---|
| date | Mon, 12 Jan 2026 15:20:39 -0800 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 155:3bb45eb67906 | 156:cd35e600ae34 |
|---|---|
| 1 /** | |
| 2 * Test suite for markdown_to_html WASM module | |
| 3 */ | |
| 4 const fs = require('fs'); | |
| 5 // TODO: Fix the rules so that it can do relative import. | |
| 6 const wasm = fs.readFileSync('markdown_converter/wasm/markdown_to_html_wasm.wasm'); | |
| 7 | |
| 8 let testsPassed = 0; | |
| 9 let testsFailed = 0; | |
| 10 | |
| 11 function assertEqual(actual, expected, testName) { | |
| 12 if (actual === expected) { | |
| 13 console.log(`✓ ${testName}`); | |
| 14 testsPassed++; | |
| 15 } else { | |
| 16 console.log(`✗ ${testName}`); | |
| 17 console.log(` Expected: ${expected}`); | |
| 18 console.log(` Actual: ${actual}`); | |
| 19 testsFailed++; | |
| 20 } | |
| 21 } | |
| 22 | |
| 23 function assertContains(actual, expected, testName) { | |
| 24 if (actual.includes(expected)) { | |
| 25 console.log(`✓ ${testName}`); | |
| 26 testsPassed++; | |
| 27 } else { | |
| 28 console.log(`✗ ${testName}`); | |
| 29 console.log(` Expected to contain: ${expected}`); | |
| 30 console.log(` Actual: ${actual}`); | |
| 31 testsFailed++; | |
| 32 } | |
| 33 } | |
| 34 | |
| 35 async function runTests() { | |
| 36 const module = await WebAssembly.instantiate(wasm, { env: {} }); | |
| 37 const { malloc, heap_reset, markdown_to_html, memory } = module.instance.exports; | |
| 38 | |
| 39 function writeString(str) { | |
| 40 const encoder = new TextEncoder(); | |
| 41 const bytes = encoder.encode(str + '\0'); | |
| 42 const ptr = malloc(bytes.length); | |
| 43 new Uint8Array(memory.buffer).set(bytes, ptr); | |
| 44 return ptr; | |
| 45 } | |
| 46 | |
| 47 function readString(ptr) { | |
| 48 const mem = new Uint8Array(memory.buffer); | |
| 49 let end = ptr; | |
| 50 while (mem[end] !== 0) end++; | |
| 51 return new TextDecoder().decode(mem.slice(ptr, end)); | |
| 52 } | |
| 53 | |
| 54 function convert(md) { | |
| 55 heap_reset(); | |
| 56 const inputPtr = writeString(md); | |
| 57 const outputPtr = markdown_to_html(inputPtr); | |
| 58 return readString(outputPtr); | |
| 59 } | |
| 60 | |
| 61 console.log('Running markdown_to_html WASM tests...\n'); | |
| 62 | |
| 63 // Test: Headings | |
| 64 console.log('--- Headings ---'); | |
| 65 assertEqual(convert('# Hello'), '<h1>Hello</h1>', 'H1 heading'); | |
| 66 assertEqual(convert('## World'), '<h2>World</h2>', 'H2 heading'); | |
| 67 assertEqual(convert('### Level 3'), '<h3>Level 3</h3>', 'H3 heading'); | |
| 68 assertEqual(convert('###### Level 6'), '<h6>Level 6</h6>', 'H6 heading'); | |
| 69 | |
| 70 // Test: Inline formatting | |
| 71 console.log('\n--- Inline Formatting ---'); | |
| 72 assertEqual(convert('**bold**'), '<p><strong>bold</strong></p>', 'Bold with **'); | |
| 73 assertEqual(convert('__bold__'), '<p><strong>bold</strong></p>', 'Bold with __'); | |
| 74 assertEqual(convert('*italic*'), '<p><em>italic</em></p>', 'Italic with *'); | |
| 75 assertEqual(convert('_italic_'), '<p><em>italic</em></p>', 'Italic with _'); | |
| 76 assertEqual(convert('~~strike~~'), '<p><del>strike</del></p>', 'Strikethrough'); | |
| 77 assertEqual(convert('`code`'), '<p><code>code</code></p>', 'Inline code'); | |
| 78 | |
| 79 // Test: Links and Images | |
| 80 console.log('\n--- Links and Images ---'); | |
| 81 assertEqual(convert('[link](http://example.com)'), '<p><a href="http://example.com">link</a></p>', 'Link'); | |
| 82 assertEqual(convert(''), '<p><img src="http://img.png" alt="alt"></p>', 'Image'); | |
| 83 | |
| 84 // Test: Lists | |
| 85 console.log('\n--- Lists ---'); | |
| 86 assertEqual(convert('- item1\n- item2'), '<ul><li>item1</li><li>item2</li></ul>', 'Unordered list with -'); | |
| 87 assertEqual(convert('* item1\n* item2'), '<ul><li>item1</li><li>item2</li></ul>', 'Unordered list with *'); | |
| 88 assertEqual(convert('1. first\n2. second'), '<ol><li>first</li><li>second</li></ol>', 'Ordered list'); | |
| 89 | |
| 90 // Test: Code block | |
| 91 console.log('\n--- Code Block ---'); | |
| 92 const codeBlock = '```\nfunction test() {\n return 42;\n}\n```'; | |
| 93 assertContains(convert(codeBlock), '<pre><code>', 'Code block opens'); | |
| 94 assertContains(convert(codeBlock), '</code></pre>', 'Code block closes'); | |
| 95 | |
| 96 // Test: Blockquote | |
| 97 console.log('\n--- Blockquote ---'); | |
| 98 assertEqual(convert('> quote'), '<blockquote>quote </blockquote>', 'Blockquote'); | |
| 99 | |
| 100 // Test: Horizontal rule | |
| 101 console.log('\n--- Horizontal Rule ---'); | |
| 102 assertEqual(convert('---'), '<hr>', 'HR with ---'); | |
| 103 assertEqual(convert('***'), '<hr>', 'HR with ***'); | |
| 104 assertEqual(convert('___'), '<hr>', 'HR with ___'); | |
| 105 | |
| 106 // Test: Tables | |
| 107 console.log('\n--- Tables ---'); | |
| 108 const table = '| Name | Age |\n|------|-----|\n| Alice | 30 |\n| Bob | 25 |'; | |
| 109 const tableHtml = convert(table); | |
| 110 assertContains(tableHtml, '<table>', 'Table opens'); | |
| 111 assertContains(tableHtml, '</table>', 'Table closes'); | |
| 112 assertContains(tableHtml, '<thead>', 'Table has thead'); | |
| 113 assertContains(tableHtml, '<tbody>', 'Table has tbody'); | |
| 114 assertContains(tableHtml, '<th>Name</th>', 'Table header cell'); | |
| 115 assertContains(tableHtml, '<td>Alice</td>', 'Table body cell'); | |
| 116 | |
| 117 // Test: Complex table with inline formatting | |
| 118 console.log('\n--- Table with Inline Formatting ---'); | |
| 119 const complexTable = '| Feature | Status |\n|---------|--------|\n| **Bold** | *done* |'; | |
| 120 const complexTableHtml = convert(complexTable); | |
| 121 assertContains(complexTableHtml, '<strong>Bold</strong>', 'Bold in table cell'); | |
| 122 assertContains(complexTableHtml, '<em>done</em>', 'Italic in table cell'); | |
| 123 | |
| 124 // Test: HTML escaping | |
| 125 console.log('\n--- HTML Escaping ---'); | |
| 126 assertContains(convert('<script>'), '<script>', 'Escapes < and >'); | |
| 127 assertContains(convert('a & b'), '&', 'Escapes &'); | |
| 128 | |
| 129 // Test: Mixed content | |
| 130 console.log('\n--- Mixed Content ---'); | |
| 131 const mixed = '# Title\n\nSome **bold** text.\n\n- item 1\n- item 2'; | |
| 132 const mixedHtml = convert(mixed); | |
| 133 assertContains(mixedHtml, '<h1>Title</h1>', 'Mixed: heading'); | |
| 134 assertContains(mixedHtml, '<strong>bold</strong>', 'Mixed: bold'); | |
| 135 assertContains(mixedHtml, '<ul>', 'Mixed: list'); | |
| 136 | |
| 137 // Summary | |
| 138 console.log('\n========================================'); | |
| 139 console.log(`Tests passed: ${testsPassed}`); | |
| 140 console.log(`Tests failed: ${testsFailed}`); | |
| 141 | |
| 142 if (testsFailed > 0) { | |
| 143 process.exit(1); | |
| 144 } | |
| 145 } | |
| 146 | |
| 147 runTests().catch(err => { | |
| 148 console.error('Test error:', err); | |
| 149 process.exit(1); | |
| 150 }); |