Compiling pwgen to WebAssembly
Wednesday, 29 January 2020
While there are many ways to generate strong passwords, I’ve been a fan of using pwgen for systems that I stand up. It’s usually been an “apt-get install” away, but there have been times while away from a Linux machine where I couldn’t access it like I normally would; right on the cli.
After coming across a Docker image that sets up most of the environment to compile a C/C++ project using Emscripten, it got me thinking that it might be easier than I thought to build a Wasm version of the original pwgen. It progressed something like this, “I can currently use it on the Linux command line—but with WebAssembly on Node.js and Wasmer, I could run it on Mac OS X, Windows, and really anywhere a runtime is—I think I can wrap this in a custom element.”
So, I gave it a shot, and I couldn’t be more pleased with how easy the results are to use and in how many environments it runs on. Does the system already have a recent setup of npm/npx installed? Start generating passwords with the command below (wapm is similar), or pass “‐‐help” for additional options to be printed.
npx pwgen
What about from the browser?
The PWA works offline, includes a minimal view for displaying passwords, some sliders to adjust the settings, and the x-pwgen Web Component that wraps up everything. At first I was a bit surprised that the JavaScript wrapper that Emscripten provides to load the module is larger than the Wasm itself, but it still loads fast. To use it in React, Angular or anywhere else HTML likes to hide out, declare the following:
<x-pwgen></x-pwgen> <script type="module"> import 'https://unpkg.com/pwgen' </script>
Finally, I felt like this was a good opportunity to investigate Web Bundles [1 ,2] seeing how the hosted version is a just a set of static files. If you use Chrome 80 or higher and want to test it, set your browser’s chrome://flags/#web-bundles
flag to enabled
, download the pwgen.wbn file, and then drag and drop it onto a Chrome window.
Checkout the project at Github, or browse some demos [1, 2] to find out more.