自分はプログラミングする時、特に制約事項がない場合は Node.js を使います。サーバーサイドアプリだけでなく、CLI 系のコマンドラインアプリも作れるし、React を併用してフロンドエンドアプリも作れます。HTML 内で JavaScript を使うケースも含めると JavaScript 系の言語は使い道が幅広くて便利、と思ってます。
そんな自分が最近作った CLI アプリ(コマンドラインアプリ)がそこそこ便利だったので公開したかったのですが、Node.js アプリは Node.js がインストールされた環境で動くのです。ある意味で当たり前のことを言っているのですが、プログラミングなどに詳しくない人からすると「プログラミング言語をインストールしないと動かない」というのはハードルが高いものです。なんとかして「ダウンロード→即実行可能」な形にできないかと調べてみました。今回のブログエントリはそんな経緯をまとめたものです。
ランタイムが Node.js の場合、このようなアプリケーションのパッケージ化ツールには nexe はじめ、いくつかの選択肢があるようですが、今回自分が使ったのは pkg というツールです※
※ Git リポジトリは現在アーカイブされているので、今後のアップデートはされない可能性が高いと思っています。逆に言うと、良くも悪くも今後の変更はほぼないものだと思って使ってください。
自分が Linux(WSL2) で作った CLI アプリが Linux および Windows 向けにクロスコンパイルして実行可能バイナリ化できる所まで確認しました。自分の用途としてはここまでできれば実用的と言えるので、今後はこれを使っていこうかな、と考えています。
【pkg のインストール】
既に Node.js が導入済みの環境であれば、pkg のインストールは以下のコマンドを実行するだけなので超簡単です:
npm で pkg をグローバルインストールします。これで pkg コマンドが使えるようになります。
【pkg の使い方】
例えば 64bit Linux(WSL2) で app.js というファイル名の CLI アプリを作ったとします。この CLI アプリは Node.js を使う場合は以下のように実行できるものとします:
ここに pkg をインストールして、3つの環境(64bit Linux, 64bit MacOS, 64bit Windows)向けの実行可能バイナリを作る場合は以下のコマンドを(特にオプションを付けずに)実行します:
この場合は同じフォルダに app-linux, app-macos, app-win.exe という3つのファイルが生成され、それぞれ 64bit Linux, 64bit MacOS, 64bit Windows 向け実行可能バイナリになっています。
現在の環境と同じ環境(64bit Linux)向けの実行可能バイナリ(app)を作るのであれば、以下のコマンドを実行します("-o" オプションで出力する実行可能バイナリファイル名を指定します):
出力するファイルをクロスコンパイルしたい場合、つまり現在の環境とは異なる環境(例えば 64bit Windows)向けの実行可能バイナリ(app.exe)を作る場合は "-t" オプションでクロスコンパイル先の対象プラットフォームを指定します("node16" は "Node.js v16 でコンパイルする" の意味です):
対象プラットフォームは node16 までは使えることを確認したのですが(ドキュメントも node16 までは書かれているのですが)、これ以上のバージョンがサポートされているかどうかは未確認です。
この pkg を使って作った実行可能バイナリは小規模なアプリでも 30MB 以上になります。私が作ったアプリも package.json には2つのライブラリしか登録していないのですが、それでも 45MB ほどになりました。おそらく node 本体とライブラリを全部まとめてパッケージングしてるんだろうな・・・と想像しています。
そんな自分が最近作った CLI アプリ(コマンドラインアプリ)がそこそこ便利だったので公開したかったのですが、Node.js アプリは Node.js がインストールされた環境で動くのです。ある意味で当たり前のことを言っているのですが、プログラミングなどに詳しくない人からすると「プログラミング言語をインストールしないと動かない」というのはハードルが高いものです。なんとかして「ダウンロード→即実行可能」な形にできないかと調べてみました。今回のブログエントリはそんな経緯をまとめたものです。
ランタイムが Node.js の場合、このようなアプリケーションのパッケージ化ツールには nexe はじめ、いくつかの選択肢があるようですが、今回自分が使ったのは pkg というツールです※
※ Git リポジトリは現在アーカイブされているので、今後のアップデートはされない可能性が高いと思っています。逆に言うと、良くも悪くも今後の変更はほぼないものだと思って使ってください。
自分が Linux(WSL2) で作った CLI アプリが Linux および Windows 向けにクロスコンパイルして実行可能バイナリ化できる所まで確認しました。自分の用途としてはここまでできれば実用的と言えるので、今後はこれを使っていこうかな、と考えています。
【pkg のインストール】
既に Node.js が導入済みの環境であれば、pkg のインストールは以下のコマンドを実行するだけなので超簡単です:
$ sudo npm install -g pkg
npm で pkg をグローバルインストールします。これで pkg コマンドが使えるようになります。
【pkg の使い方】
例えば 64bit Linux(WSL2) で app.js というファイル名の CLI アプリを作ったとします。この CLI アプリは Node.js を使う場合は以下のように実行できるものとします:
$ node app.js
ここに pkg をインストールして、3つの環境(64bit Linux, 64bit MacOS, 64bit Windows)向けの実行可能バイナリを作る場合は以下のコマンドを(特にオプションを付けずに)実行します:
$ pkg app.js
この場合は同じフォルダに app-linux, app-macos, app-win.exe という3つのファイルが生成され、それぞれ 64bit Linux, 64bit MacOS, 64bit Windows 向け実行可能バイナリになっています。
現在の環境と同じ環境(64bit Linux)向けの実行可能バイナリ(app)を作るのであれば、以下のコマンドを実行します("-o" オプションで出力する実行可能バイナリファイル名を指定します):
$ pkg -o app app.js
出力するファイルをクロスコンパイルしたい場合、つまり現在の環境とは異なる環境(例えば 64bit Windows)向けの実行可能バイナリ(app.exe)を作る場合は "-t" オプションでクロスコンパイル先の対象プラットフォームを指定します("node16" は "Node.js v16 でコンパイルする" の意味です):
$ pkg -t node16-win-x64 -o app.exe app.js
対象プラットフォームは node16 までは使えることを確認したのですが(ドキュメントも node16 までは書かれているのですが)、これ以上のバージョンがサポートされているかどうかは未確認です。
この pkg を使って作った実行可能バイナリは小規模なアプリでも 30MB 以上になります。私が作ったアプリも package.json には2つのライブラリしか登録していないのですが、それでも 45MB ほどになりました。おそらく node 本体とライブラリを全部まとめてパッケージングしてるんだろうな・・・と想像しています。