diff --git a/_posts/2024-06-04-playground-for-hare.md b/_posts/2024-06-04-playground-for-hare.md
new file mode 100644
index 0000000..cf7871d
--- /dev/null
+++ b/_posts/2024-06-04-playground-for-hare.md
@@ -0,0 +1,135 @@
+---
+permalink: "/{{ year }}/{{ month }}/{{ day }}/playground-for-hare"
+title: "A playground for Hare"
+published_date: "2024-06-04 22:59:00 +0200"
+layout: post.liquid
+data:
+ route: blog
+excerpt: |
+ I built an online for the programming language Hare in Hare.
+ Why? Because I wanted to do something fun and learn Hare.
+ How? By using some existing libraries and writing the rest myself.
+---
+
+I built a thing:
+
+
+
+### [Hare Playground][playground]
+
+
+
+And this is what it looks like:[^1]
+
+![Screenshot of the Hare Playground, the default code example on the left, the out to the right](https://tmp.fnordig.de/blog/2024/hare-playground.png)
+
+It's an online playground for the [Hare programming language][harelang].
+Code is sent to the server for compilation and execution.
+It responds with the standard and error output serialized into JSON, which gets rendered in the output box in the frontend.
+This works just the same as [other](https://go.dev/play/) [playgrounds](https://play.rust-lang.org/).
+
+It's a bit slow and might crash on you, but it works (if it doesn't: reload).
+
+## Why?
+
+Because I wanted to do something fun and learn Hare.
+Hare is a rather new systems programming language (started in 2020) that's inspired by C,
+but promises to do few things better.
+The original blog post [Hare's advances compared to C][advances-on-c] has a good overview on that.
+
+This project gave me the opportunity to explore a couple of areas in Hare,
+read through the documentation and the Hare codebase and even fix a few bugs in existing code.
+
+I might write another more detailed blog post on my impressions.
+For now I can say that it was a few fun nights learning and exploring a new language.
+
+## How?
+
+The whole codebase is [in the hare-playground repository][hare-playground].
+In about 500 lines of my own code plus 3 external libraries I implemented the webserver part,
+including routing and static file serving.
+I bet it has memory leaks.
+
+```c
+fn route_request(buf: *io::stream, serv_req: *http::server_request) (void | http_err) = {
+ let request = &serv_req.request;
+ switch (request.method) {
+ case "GET" =>
+ switch (request.target.path) {
+ case "/" => handle_index(buf, serv_req);
+ case =>
+ handle_file(buf, serv_req)?;
+ return;
+ };
+ case "POST" =>
+ switch (request.target.path) {
+ case "/v1/exec" => handle_exec(buf, serv_req)?;
+ case => return notfound;
+ };
+ case "OPTIONS" =>
+ handle_cors(serv_req);
+ return;
+ case => return notfound;
+ };
+};
+```
+> The "router" part of the webserver[^2]
+
+The external libraries I pulled in are:
+1. [hare-logfmt] for formatted logging messages (though I only log the minimum).
+1. [hare-json] for parsing from and serializing to JSON (unmodified from upstream).
+1. [hare-http] for the webserver parts: listening on a socket, parsing HTTP, creating the request and response objects.
+I added a couple of commits to fix some issues (available in [my fork](https://git.fnordig.de/jer/hare-http/commits/branch/host-in-uri), I'll upstream them).
+
+I also wrote a [small wrapper around pthread](https://git.fnordig.de/jer/hare-playground/src/branch/main/vendor/hare-thread/thread/thread.ha),
+just so my server can handle more than one request at a time.
+
+To run the user-submitted Hare code the server launches `hare` in a [bubblewrap][] sandbox.
+This should make it somewhat safe to deal with arbitrary input.
+The whole thing runs in a VM on [fly.io],
+so even if a sandbox escape is possible the worst an attacker can do is break the VM and ruin the playground for others.
+
+The whole backend even works on macOS (without the sandbox, _do not run in production!_),
+thanks to the [Darwin port of Hare](https://github.com/hshq/harelang) (and some of [my own fixes on top](https://github.com/hshq/harelang/compare/master...badboy:harelang:master)).
+I wrapped that in a [Nix flake](https://git.fnordig.de/jer/hare-nix) for easy installation.
+`nix develop` is all you need in the playground repository.
+
+The frontend is some basic HTML[^3], a couple of lines of JavaScript and [htmx].
+The code editor is [Codejar], a small one-file editor implementation.
+Code highlighting is handled by [highlight.js]
+No JavaScript transpiler or bundler needed.
+And yes, I use htmx, but still return JSON from the server and add it to the DOM using JavaScript in the right places.
+I'd rather not do the whole HTML escape in Hare right now server-side.
+Initially I built this using the JavaScript parts of [codapi],
+but I ended up rolling it myself using htmx,
+as that gives me more freedom placing & styling the button elements and controlling the output.
+
+## Production when?
+
+I will keep the playground running on Fly (for now).
+I do not plan to work on it much further.
+This is after all a playground for me to learn the language a bit and not a more serious long-term project.
+The code is open-source ([MPL licensed](https://git.fnordig.de/jer/hare-playground/src/branch/main/COPYING)).
+
+[playground]: https://hare-exec.fly.dev/
+[harelang]: https://harelang.org/
+[advances-on-c]: https://harelang.org/blog/2021-02-09-hare-advances-on-c/
+[hare-playground]: https://git.fnordig.de/jer/hare-playground
+[bubblewrap]: https://github.com/containers/bubblewrap
+[fly.io]: https://fly.io/
+[hare-nix]: https://git.fnordig.de/jer/hare-nix
+[htmx]: https://htmx.org/
+[codapi]: https://codapi.org/
+[hare-http]: https://git.sr.ht/~sircmpwn/hare-http
+[hare-json]: https://git.sr.ht/~sircmpwn/hare-json/
+[hare-logfmt]: https://git.sr.ht/~blainsmith/hare-logfmt
+[codejar]: https://medv.io/codejar/
+[highlight.js]: https://highlightjs.org/
+
+---
+
+_Footnotes:_
+
+[^1]: Sorry, no dark mode yet.
+[^2]: The syntax highlighter on this site doesn't know about hare, so this code is tagged as C.
+[^3]: Thanks to [Dennis](https://overengineer.dev/) for showing me how simple Flexbox is to use.