New feature: full file conversion support for .md files using showdown
Tags: opensource, beginners, webdev
Published: 2023-10-30 00:28:18

**New feature**
New feature of file conversion from `.md` to `.html` was implemented using [showdown](https://github.com/showdownjs/showdown).
You can check out the [issue](https://github.com/avelynhc/til_tracker/issues/23) here.

**Before**
Previous implementations required parsing the `.md` file first and manually converting some of the `.md` syntax to `.html` syntax using regular expressions, as shown below. As you can see, the syntax conversion was fairly limited and did not fully support file conversion between the two formats.

```typescript
...
export function fileHandler(inputPath: string, cssLink: string, selectedLang: string, outputFolder: string) {
fileHandler(inputPath: string, cssLink: string, selectedLang: st
        if (isTextFile(inputPath)) {
            body = parseTextFileContent(data);
        } else if (isMarkdownFile(inputPath)) {
            body = parseMarkdownFileContent(data);
        } else {
            parseTextFileContent(content: string): string {
        .map((para: string) =>
            `<p>${para.replace(/\r?\n/, ' ')}</p>`)
        .join('\n');
}

// Parses the content of a markdown file
function parseMarkdownFileContent(content: string): string {
    return content
        .replace(/(\r?\n){1}/, ' ') // Aggregate text at gaps of single newlines
        .split(/\r?\n/)
        .filter(line => line?.length > 0) // Remove empty lines
        .map((line: string) => {
            return formatHtmlForMarkdownLine(line)
        })
        .join('\n'); // Join all the generated tags
}

function formatHtmlForMarkdownLine(line: string) {
    return line
        .replace(/^#\s(.+)$/gm, '<h1>$1</h1>') // heading 1
        .replace(/^##\s(.+)$/gm, '<h2>$1</h2>') // heading 2
        .replace(/^###\s(.+)$/gm, '<h3>$1</h3>') // heading 3
        .replace(/^####\s(.+)$/gm, '<h4>$1</h4>') // heading 4
        .replace(/^#####\s(.+)$/gm, '<h5>$1</h5>') // heading 5
        .replace(/^######\s(.+)$/gm, '<h6>$1</h6>') // heading 6
        .replace(/^(?!<h[1-6]>|<ul>|<ol>|<li>|<a>).+$/gm, '<p>$&</p>') // paragraph
        .replace(/\[(.+?)\]\((.+?)\)/g, '<a href=$2>$1</a>') //  link
        .replace(/\*\*(.*?)\*\*/g, '<b>$1</b>') // bold
        .replace(/\*(.*?)\*/g, '<i>$1</i>') // italic
}
```

**After**
```typescript
...
const showdown = require('showdown');
const converter = new showdown.Converter()
let body: string = '';

export function fileHandler(inputPath: string, cssLink: string, selectedLang: string, outputFolder: string) {
fileHandler(inputPath: string, cssLink: string, selectedLang: st
        if (isTextFile(inputPath)) {
            body = parseTextFileContent(data);
        } else if (isMarkdownFile(inputPath)) {
            body = converter.makeHtml(data);
        } else {
            parseTextFileContent(content: string): string {
            .map((para: string) =>
                `<p>${para.replace(/\r?\n/, ' ')}</p>`)
            .join('\n');
}
```

You can check out the [pr](https://github.com/avelynhc/til_tracker/pull/24/files) for the entire code change.

**Inspiration from Docusaurus**
[Markdown Frontmatter](https://docusaurus.io/docs/api/plugins/@docusaurus/plugin-content-docs#markdown-frontmatter) inspired me to dig deeper into the support for `.md` files. Since Docusaurus employs it to enrich markdown files with metadata, I was thinking why not extend full support for converting from `.md` to `.html`, as the current implementation for this purpose is somewhat limited. While Docusaurus did use the `Joi` library to validate the metadata, I opted to use only the `showdown` library, as I wasn't planning to add any metadata for now.

You can find the full blog post about the code review I did for Docusaurus [here](https://dev.to/avelynhc/reading-docusaurus-code-1a7l-temp-slug-8411288?preview=ba219f0b2c1090b7086c3d64d22ba52781709ea010edfeb169fde31c7516c6f0e22f6ab893499ba8b4f264891c2c53f40ab86905f66eb06f590f0bb0).

**Next step**
There are several cool features that Docusaurus utilizes, including Search Engine Optimization (SEO), incorporating meta tags in the HTML head, and improved accessibility of generated HTML, among others. I will continue to create issues for other features and submit pull requests for those. If anyone is interested in participating, please ping me in [any opened issues](https://github.com/avelynhc/til_tracker/issues). Thank you!