feat(knowledge): add markdown rendering (KNOW-004)

- Install marked, marked-highlight, marked-gfm-heading-id, sanitize-html
- Create markdown utility with GFM support (tables, task lists, strikethrough)
- Add code syntax highlighting with highlight.js
- Implement XSS sanitization for security
- Update knowledge service to use markdown renderer
- Add comprehensive test suite (34 tests, all passing)
- Generate IDs for headers for deep linking
- Cache rendered HTML in database for performance
This commit is contained in:
Jason Woltje
2026-01-29 16:57:57 -06:00
parent 4881d0698f
commit 287a0e2556
6 changed files with 839 additions and 12 deletions
+121
View File
@@ -0,0 +1,121 @@
# Knowledge Module Utilities
## Markdown Rendering
### Overview
The `markdown.ts` utility provides secure markdown rendering with GFM (GitHub Flavored Markdown) support, syntax highlighting, and XSS protection.
### Features
- **GFM Support**: Tables, task lists, strikethrough, autolinks
- **Syntax Highlighting**: Code blocks with language detection via highlight.js
- **XSS Protection**: HTML sanitization using sanitize-html
- **Header IDs**: Automatic ID generation for headers (for linking)
- **Security**: Blocks dangerous HTML (scripts, iframes, event handlers)
### Usage
```typescript
import { renderMarkdown, markdownToPlainText } from './utils/markdown';
// Render markdown to HTML (async)
const html = await renderMarkdown('# Hello **World**');
// Result: <h1 id="hello-world">Hello <strong>World</strong></h1>
// Extract plain text (for search indexing)
const plainText = await markdownToPlainText('# Hello **World**');
// Result: "Hello World"
```
### Supported Markdown Features
#### Basic Formatting
- **Bold**: `**text**` or `__text__`
- *Italic*: `*text*` or `_text_`
- ~~Strikethrough~~: `~~text~~`
- `Inline code`: `` `code` ``
#### Headers
```markdown
# H1
## H2
### H3
```
#### Lists
```markdown
- Unordered list
- Nested item
1. Ordered list
2. Another item
```
#### Task Lists
```markdown
- [ ] Unchecked task
- [x] Completed task
```
#### Tables
```markdown
| Header 1 | Header 2 |
|----------|----------|
| Cell 1 | Cell 2 |
```
#### Code Blocks
````markdown
```typescript
const greeting: string = "Hello";
console.log(greeting);
```
````
#### Links and Images
```markdown
[Link text](https://example.com)
![Alt text](https://example.com/image.png)
```
#### Blockquotes
```markdown
> This is a quote
> Multi-line quote
```
### Security
The renderer implements multiple layers of security:
1. **HTML Sanitization**: Only allows safe HTML tags and attributes
2. **URL Validation**: Blocks `javascript:` and other dangerous protocols
3. **External Links**: Automatically adds `target="_blank"` and `rel="noopener noreferrer"`
4. **Task Lists**: Checkboxes are disabled to prevent interaction
5. **No Event Handlers**: Blocks `onclick`, `onload`, etc.
6. **No Dangerous Tags**: Blocks `<script>`, `<iframe>`, `<object>`, `<embed>`
### Testing
Comprehensive test suite covers:
- Basic markdown rendering
- GFM features (tables, task lists, strikethrough)
- Code syntax highlighting
- Security (XSS prevention)
- Edge cases (unicode, long content, nested structures)
Run tests:
```bash
pnpm test --filter=@mosaic/api -- markdown.spec.ts
```
### Integration
The markdown renderer is integrated into the Knowledge Entry service:
1. **On Create**: Renders `content` to `contentHtml`
2. **On Update**: Re-renders if content changes
3. **Caching**: HTML is stored in database for performance
See `knowledge.service.ts` for implementation details.