npm package: @sissijs/muh
Description: Muh (say: Moo!) stands for 'mustached hypertext' and is a template language for static site generators
Author: Lea Rosema
Latest version: 2.0.0

# Muh

Muh (say: Moo!) stands for "mustached hypertext" and is the template language that runs [Sissi](https://sissi.js.org), the static site generator. It is put into a single package so it can be re-used in other projects as well.

## Flavors

Muh comes in 2 flavors. Both of them live in the `@sissijs/muh` package.

`@sissijs/muh` includes everything. A full-fledged `processTemplateFile` function that supports SmolYAML/JSON frontmatter, layout files, basic preprocessing such as (a minimal) markdown, handling css imports and resolving `<html-include src="">` directives. In roughly 10KB of JavaScript.

`@sissijs/muh/template` is just the `template` function that implements the mustache syntax. It also provides the built-in filters for formatting dates/numbers, and built-in helper functions. The helper functions provided are small wrappers around fetch, namely `fetchText()` and `fetchJson()`. All that is contained in roughly 4KB of JavaScript.

Sizes are measured with minification and without compression.

TypeScript declarations and API documentation are autogenerated from JSDoc.

## Syntax

The syntax is `{{ moo }}` where `moo` can be any arbitrary JavaScript. JavaScript is evaluated in a safe context. The only globals it can access are the ones you provide, plus a few built-ins.

When the evaluated expression is a promise, it is automatically resolved (or rejected). When the evaluated expression is a function, it is automatically invoked without parameters.

Under the hood, it uses `node:vm`, which makes it a node-only library (for now). It should work in Deno 2, as it provides some backwards-compatibility to node.js.

## Filters

You can apply filters to your mustache expressions using the pipe notation. There are a few built-in filters:

```js
{{ content | safe }} // dont escape html
{{ promise | async }} // resolve promises
{{ result | json }} // print json
{{ article.date | date: 'de' }} // 25.12.2024 (for first Christmas Day 2024)
{{ price | currency: 'de', 'euro' }}  // 1.234,56 €
{{ fetchJson('/api/articles') | async | limit: 5 | each: templateFunction }} 
{{ include('article.html', {title: 'Article Title'}) | safe }}
{{ '<' | htmlentities }} // &lt;
{{ ' ' | urlencode }} // %20
```

## Helpers

There are a few built-in helper functions:

```js
{{ fetchJson('https://yesno.wtf/api') | async | json }}
{{ fetchText('https://some-html.api/api/weather') | async }}

{{ include('partial.html', {title: 'some additional data'}) }}
```

## Additional Syntaxes

HTML-files can use `<html-include src="partial.html" title="some additional data"/>` directives.
Additional attributes are passed to the include's data.

There is a basic markdown processor for markdown files involved.
Markdown files also interprete the `<html-include>` directive.

Also, CSS import directives are resolved.

All file types mentioned above can also work with the mustache syntax.

## Usage

```js
const result = await processTemplateFile(
  '<h1>{{ title }}</h1>',
  'index.html', 
  {title: 'Test'}
);

console.log(result) // <h1>Test</h1>
```