A small, no bloat, minimalist static site generator using sh as a templating language.


We provide statically compiled binaries for Linux or OpenBSD. It can also run on Windows via the Windows Subsystem for Linux for other UNIX like operating systems, you can build from sources.

Install mkws

On a Linux machine, just download the archive from https://mkws.sh/mkws@4.0.8.tgz or in the terminal, assuming wget is installed, type:

wget -O - https://mkws.sh/mkws@4.0.8.tgz | tar -xzvf -

File Hierarchy

Inside the downloaded archive you will find the following file structure:

|-- bin
|   |-- lmt
|   |-- mkws
|   `-- pp
`-- share
    |-- l.upphtml
    |-- man
    |   `-- man1
    |       |-- lmt.1
    |       |-- mkws.1
    |       `-- pp.1
    |-- s.uppcss
    `-- sitemap.uppxml

Generate the Static Site

Rename the directory you unarchived earlier to your site's name:

mv ws.sh example.com && cd example.com

Create your first template named index.upphtml, this is required by mkws:

cat <<EOF > index.upphtml
echo hello, world

Run mkws:

./bin/mkws https://example.com

You just generated your first static site with mkws. You will now have an index.html file in your . root directory containing the following code:

<!doctype html>
<html lang=en>


<title>My website</title>

<meta charset=UTF-8>
<meta name=viewport content='width=device-width'>

<link rel=icon href=favicon.ico type=image/x-icon>
<link rel=stylesheet



hello, world



To create new pages, just add new *.upphtml files in the . root directory, mkws automatically scans for them. You can create an aboutus.upphtml or a contact.upphtml file for example to generate an aboutus.html or a contact.html page.

For further customizations you can always modify your ./bin/mkws or ./share/l.upphtml files, in fact, it's recommended.


mkws uses *.upphtml files as templates which are processed via pp, a preprocessor that allows embedding sh code in files of any type by nesting it inside the #!\n token, where \n is a new line.

As an example, for the following code:

while test $i -le 10
if test $((i % 2)) -eq 0
	<li class=even>$i</li>
	<li class=odd>$i</li>
i=$((i + 1))

pp outputs:

        <li class=odd>1</li>
        <li class=even>2</li>
        <li class=odd>3</li>
        <li class=even>4</li>
        <li class=odd>5</li>
        <li class=even>6</li>
        <li class=odd>7</li>
        <li class=even>8</li>
        <li class=odd>9</li>
        <li class=even>10</li>

This means you can script your templates in any way you prefer using preferably, standard UNIX tools for portability reasons.


Because pp uses sh internally, double quotes (") must be escaped in templates, so to get an actual double quote (") you have to write \".

This isn't a problem for HTML because quoting attribute values is optional and double quotes and single quotes are interchangeable. We recommend not quoting attribute values and using single quotes (') in special cases.

So instead of:

<!doctype html>
<html lang="en">


<title>My website</title>

<meta charset="UTF-8">
<meta name="viewport" content="width=device-width">

you would write:

<!doctype html>
<html lang=en>


<title>My website</title>

<meta charset=UTF-8>
<meta name=viewport content='width=device-width'>



The package contains a Linux amd64 pp statically compiled binary, the mkws sh script, the base theme and lmt from lts. mkws-openbsd@4.0.8.tgz. is the OpenBSD binary version.

Deploy to Netlify Deploy to Vercel


The main mkws sh script
Base files for a theme, you can use it to make your own theme
pp, the POSIX sh preprocessor
File time data