What is a JS Executable?
.bin file (or no extension on macOS).
It has been possible to create executables for Node.js applications using community projects like node-windows/mac/linux, pkg, or nexe for a while, so the concept isn’t entirely new. These are all efforts maintained by the community (userland). While these types of efforts haven’t gone unrecognized, it’s always been more of an “add-on” experience.
Compiling With Deno 1.6.0
Deno 1.6.0 is/was scheduled for release on December 8th, 2020. It is notable for the inclusion of
The Impact of Executables
This has particularly important ramifications for the creation of developer tooling and commercial software. Being able to ship a single executable can be a much simpler process than requiring users to have software pre-installed.
Consider the use case for Docker and containers. Containerization is a solid approach to development, but it still requires a runtime like Docker, podman, etc. That is a manageable hurdle for IT departments installing software on their servers, but it’s far more challenging for developers who ship software to individuals working on a workstation. It’s difficult to ship that great new FinTech app to your users if they also need Node or Docker installed to use it.
Developing Applications as Executables
For applications like these, an executable is a slimmer and more manageable way to deliver software.
Developing CLI Applications
CLI (Command Line Interpreter) applications are a natural fit for the executable format. These types of applications are one of the purest forms of function, meaning they do something very specific.
With Deno 1.6.0, developers can create their own tooling without worrying much about runtime dependencies. Remember, executables are self-contained, so it does not matter if the runtime changes. For example, updating to a new version of Node.js (or downgrading) will not change the executable. End users do not need to do anything special to install prerequisites. They just download and run the application.
- First, users do not always update their executables as frequently as developers would like. There are ways to administer automatic updates, but it is the responsibility of developers to create such a mechanism.
- Generating an executable is not a substitute for security. Do not make the mistake of thinking code which is compiled is impervious to malicious use.
- Installers can be hard to create. In a world where
npm installhas felt normal, developers will need a different way to distribute executables. Tools like homebrew and choco help, but distribution of commercial applications still have the same installation challenges.
- Runtimes like Node.js and Deno bridge many cross-platform gaps, but not all of them. Generating an executable does not alleviate these problems.
The announcement of
deno compile is a big step forward for the use of executables. There will undoubtedly be some challenges for early adopters, but there will also be many benefits.
Update (Feb 20, 2023)
Node.js 19.7.0 ships this week with single executable application support (SEA). Node developers will now be able to produce binary applications from their scripts/projects.
Personal Use Cases
Articles like these can come across vague, advocating some so-called new way of doing things without much real life experience to support it. For a change of pace, I’d like to share some of what I’m working on and why I’m excited to work with the new
deno compile feature.
As a quick caveat, CLI’s and executables definitely aren’t a new concept. They’re one of the oldest forms of computing. What’s new is the tooling used to create them. Most of my work with JS executables is a result of “back to basics” thinking, using proven fundamentals in practical modern ways.
CLI First Development
I’m excited by the
deno compile feature because it aligns with my own flavor of modern software development, a CLI-First Development Strategy.
My explorations in this concept have led to the use of runtime-agnostic libraries, such as author/shell (a cross-runtime library for building CLI tools). This library helps bring an “executable-like” CLI experience to web applications, while still being able to rapidly produce Node-based CLI tools using the same/similar code base.
The net affect of this approach is the ability to port application logic to different runtimes. Different experiences can be built upon the same core logic, even across different runtimes.
Historically, the challenge has always been working with build processes. A build process is required to produce the executable. As mentioned earlier, there have been ways to do this, but it usually required a separate DevOps build process of some kind. The
deno compile feature brings this to the runtime, reducing the overhead for releasing a project and the “CLI First” strategy I’ve become fond of.
The Deno commitment to executables has provided an opportunity to rethink the architecture of non-web projects.
The most notable experience I recall is thinking about the original design of NVM for Windows, a version manager for Node.js. In the beginning, there were version managers which relied upon Node. This felt illogical, because the approach requires Node in order to install Node.
How JS executables changed my thinking…
Remember to clap if you want to see more articles like these.