<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0"><channel><title>Pulumi Blog: Publishing</title><link>https://www.pulumi.com/blog/tag/publishing/</link><description>Pulumi blog posts: Publishing.</description><language>en-us</language><pubDate>Tue, 13 Sep 2022 00:00:00 +0000</pubDate><item><title>Node.js Native Binary Compilation Using vercel/pkg</title><link>https://www.pulumi.com/blog/nodejs-binaries-with-pkg/</link><pubDate>Tue, 13 Sep 2022 00:00:00 +0000</pubDate><guid>https://www.pulumi.com/blog/nodejs-binaries-with-pkg/</guid><description>
&lt;img src="https://www.pulumi.com/images/generated/blog/nodejs-binaries-with-pkg/index.png" /&gt;
&lt;p&gt;In Pulumi&amp;rsquo;s engineering department, we often build and distribute tools as native binaries to avoid the need for additional dependencies on user machines. Most of these tools are written in Go, which has good support for building self-contained binaries that target modern operating systems.&lt;/p&gt;
&lt;p&gt;While other Pulumi-supported languages like Node.js, Python, and .NET require additional runtime dependencies, it&amp;rsquo;s possible to bundle dependencies with the program. In this article, we&amp;rsquo;ll show you how to do that for a Node.js program.&lt;/p&gt;
&lt;p&gt;This is a problem that can be solved using &lt;a href="https://github.com/vercel/pkg"&gt;vercel/pkg&lt;/a&gt; command line tool. Here&amp;rsquo;s the summary from their readme.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;This command line interface enables you to package your Node.js project into an executable that can be run even on devices without Node.js installed.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Let&amp;rsquo;s take a look at how to use &lt;code&gt;pkg&lt;/code&gt; and some issues we encountered on the way.&lt;/p&gt;
&lt;h2 id="setting-up-pkg"&gt;Setting up &lt;code&gt;pkg&lt;/code&gt;&lt;/h2&gt;
&lt;h3 id="1---install"&gt;1 - Install&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;pkg&lt;/code&gt; is distributed as an npm package which can be installed into your “devDependencies” using:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;npm install -D pkg
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;or&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;yarn add -D pkg
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;or run without installing with npx:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;npx pkg &lt;span class="o"&gt;[&lt;/span&gt;args&lt;span class="o"&gt;]&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id="2---set-bin-in-packagejson"&gt;2 - Set &lt;code&gt;bin&lt;/code&gt; in &lt;code&gt;package.json&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;pkg&lt;/code&gt; will use &lt;a href="https://docs.npmjs.com/cli/v6/configuring-npm/package-json#bin"&gt;the bin field from your package.json&lt;/a&gt; to find the entry point so you just have to specify a path to the directory containing your &lt;code&gt;package.json&lt;/code&gt;.&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-json" data-lang="json"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="p"&gt;{&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="nt"&gt;&amp;#34;name&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;&amp;#34;my-program&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="s2"&gt;&amp;#34;bin&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;&amp;#34;bin/index.js&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="err"&gt;...&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;If no target is specified, then a set of defaults will be chosen for you. If the output path is not specified, &lt;code&gt;pkg&lt;/code&gt; will infer the name from the package.json “name” field and write to the current working directory.&lt;/p&gt;
&lt;h3 id="3---execute"&gt;3 - Execute&lt;/h3&gt;
&lt;p&gt;The main inputs that &lt;code&gt;pkg&lt;/code&gt; needs is:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;The entry point to your program for packaging&lt;/li&gt;
&lt;li&gt;The target machine to build for&lt;/li&gt;
&lt;li&gt;The output path to write the finished binary&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Here’s an example of building the project in the current directory using node v18 for macOS ARM architectures:&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c1"&gt;# pkg [options] &amp;lt;input&amp;gt;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c1"&gt;# -t, --targets comma-separated list of targets&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c1"&gt;# -o, --output output file name or template for several files&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;pkg -t node18-macos-arm64 -o bin/my-program .
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;It&amp;rsquo;s possible to specify multiple targets in a comma-separated list to build them all at the same time, but it does come with the limitation where the output file names follow a fixed pattern. Instead, we chose to just run the &lt;code&gt;pkg&lt;/code&gt; command multiple times with different arguments from our makefile in parallel as this fits with our existing workflows well.&lt;/p&gt;
&lt;h2 id="issues-encountered"&gt;Issues encountered&lt;/h2&gt;
&lt;h3 id="inspector-not-available"&gt;“Inspector Not Available”&lt;/h3&gt;
&lt;p&gt;As soon as we started executing the provider we started seeing some interesting warnings printed to the console stating “Inspector is not available” (here’s our &lt;a href="https://github.com/pulumi/pulumi-awsx/issues/848"&gt;tracking issue&lt;/a&gt; and some &lt;a href="https://github.com/vercel/pkg/issues/93"&gt;&lt;code&gt;pkg&lt;/code&gt; discussion&lt;/a&gt;). This is because we use the Node.js Inspector API as part of our automatic closure serialization, however this is not available by default when packaging with &lt;code&gt;pkg&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;code&gt;pkg&lt;/code&gt; provides an option to fix this by building your own base image with custom Node.js flags set to enable debugging. However, on investigation, these issues were caused by the Pulumi Typescript SDK creating and caching an inspector instance at the point of being imported even though we never actually call this code in our plugin. Therefore, we opted to make this eager singleton creation to be lazy – only created on first use, as we’re not using in our providers at this time.&lt;/p&gt;
&lt;h3 id="unrunnable-macos-arm-binaries"&gt;Unrunnable MacOS ARM binaries&lt;/h3&gt;
&lt;p&gt;When trying to use the binaries produced by our CI, we found that &lt;a href="https://github.com/pulumi/pulumi-awsx/issues/850"&gt;the binaries weren’t runnable on MacOS ARM architectures&lt;/a&gt; - and were forcibly killed by the operating system.&lt;/p&gt;
&lt;p&gt;This led me down quite a bit of a rabbit hole investigating signing of binaries, but it was actually resolved by simply installing the ‘ldid’ tool on our linux CI environments. The ldid source is available via &lt;a href="git://git.saurik.com/ldid.git"&gt;git.saurik.com/ldid&lt;/a&gt; and binaries are available from various sources. Our solution was to use the &lt;a href="https://github.com/marketplace/actions/install-ldid"&gt;“Install Ldid” GitHub Action&lt;/a&gt; to install the ldid binary and add it to the PATH in our CI workflow. My learning here is that sometimes reading the warnings in logs more carefully can save you lots of time!&lt;/p&gt;
&lt;h3 id="static-binaries"&gt;Static Binaries&lt;/h3&gt;
&lt;p&gt;One adjustment to our configuration came from a &lt;a href="https://github.com/pulumi/pulumi-awsx/pull/862"&gt;community contribution by @afreakk&lt;/a&gt; where the provider was being used in a nixos environment. Nixos adds the requirement for all binaries to be static rather than dynamic - so there’s no requirement for the operating system to dynamically map link functions from system libraries at runtime. Statically compiled programs sometimes result in a larger size, but avoid any possible issues with different versions of the libraries it depends on.&lt;/p&gt;
&lt;p&gt;To resolve this issue, it’s as simple as changing the ‘linux’ targets to ‘linuxstatic’. E.g. &lt;code&gt;node18-linux-amd64&lt;/code&gt; becomes &lt;code&gt;node18-linuxstatic-amd64&lt;/code&gt;.&lt;/p&gt;
&lt;div class="rounded-lg bg-violet-50 p-6 my-8"&gt;
&lt;p class="heading-4 m-0 mb-3 flex items-center gap-1.5"&gt;Build infrastructure with Node.js&lt;/p&gt;
&lt;div class="body-base m-0 text-gray-950"&gt;Pulumi lets you define, deploy, and manage cloud infrastructure using TypeScript and JavaScript, with the same npm packages and tooling you already rely on. Start building your first stack in Pulumi Cloud.&lt;/div&gt;
&lt;a href="https://app.pulumi.com/signup" data-track="blog-body-cta" class="btn btn-primary mt-4"&gt;
Get started
&lt;svg xmlns="http://www.w3.org/2000/svg" class="ph-icon ph-icon--regular size-4" fill="currentColor" aria-hidden="true" focusable="false"&gt;&lt;use href="https://www.pulumi.com/icons/sprite.21047dcd83825f0caafb78a6fd28628a694219e6b6824f6b3e24ee3147bac331.svg#p-arrow-right-regular"/&gt;&lt;/svg&gt;
&lt;/a&gt;
&lt;/div&gt;
&lt;h2 id="multi-platform-builds-with-a-makefile"&gt;Multi-platform builds with a makefile&lt;/h2&gt;
&lt;p&gt;We use makefiles to build our providers, so here&amp;rsquo;s a brief outline of how we build for multiple platforms using GNU Make.&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-make" data-lang="make"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# Set the correct pkg TARGET for each binary we build
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# when building for linux-amd64, set the pkg target to node18-linuxstatic-x64
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/linux-amd64/my-program&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;TARGET&lt;/span&gt; := &lt;span class="n"&gt;node&lt;/span&gt;18-&lt;span class="n"&gt;linuxstatic&lt;/span&gt;-&lt;span class="n"&gt;x&lt;/span&gt;64
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# output binary file ^ ^ variable ^ pkg target
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/linux-arm64/my-program&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;TARGET&lt;/span&gt; := &lt;span class="n"&gt;node&lt;/span&gt;18-&lt;span class="n"&gt;linuxstatic&lt;/span&gt;-&lt;span class="n"&gt;arm&lt;/span&gt;64
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/darwin-amd64/my-program&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;TARGET&lt;/span&gt; := &lt;span class="n"&gt;node&lt;/span&gt;18-&lt;span class="n"&gt;macos&lt;/span&gt;-&lt;span class="n"&gt;x&lt;/span&gt;64
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/darwin-arm64/my-program&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;TARGET&lt;/span&gt; := &lt;span class="n"&gt;node&lt;/span&gt;18-&lt;span class="n"&gt;macos&lt;/span&gt;-&lt;span class="n"&gt;arm&lt;/span&gt;64
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/windows-amd64/my-program.exe&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;TARGET&lt;/span&gt; := &lt;span class="n"&gt;node&lt;/span&gt;18-&lt;span class="n"&gt;win&lt;/span&gt;-&lt;span class="n"&gt;x&lt;/span&gt;64
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# Wildcard rule to build any of binary outputs
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# &amp;#34;To build any bin file, ensure node_modules are up to date...&amp;#34;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bin/%&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;node_modules&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="c1"&gt;# &amp;#34;... then run pkg for actual output name &amp;amp; target&amp;#34;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; yarn run pkg . --target &lt;span class="si"&gt;${&lt;/span&gt;&lt;span class="nv"&gt;TARGET&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt; --output &lt;span class="nv"&gt;$@&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="c1"&gt;# &amp;#34;TARGET&amp;#34; is the variable defined above, depending on the output&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; &lt;span class="c1"&gt;# &amp;#34;$@&amp;#34; is the current makefile target - e.g. &amp;#39;bin/linux-amd64/my-program&amp;#39;&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# Running `make bins` will build all the listed outputs
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bins&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bin&lt;/span&gt;/&lt;span class="n"&gt;linux&lt;/span&gt;-&lt;span class="n"&gt;amd&lt;/span&gt;64/&lt;span class="n"&gt;my&lt;/span&gt;-&lt;span class="n"&gt;program&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bins&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bin&lt;/span&gt;/&lt;span class="n"&gt;linux&lt;/span&gt;-&lt;span class="n"&gt;arm&lt;/span&gt;64/&lt;span class="n"&gt;my&lt;/span&gt;-&lt;span class="n"&gt;program&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bins&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bin&lt;/span&gt;/&lt;span class="n"&gt;darwin&lt;/span&gt;-&lt;span class="n"&gt;amd&lt;/span&gt;64/&lt;span class="n"&gt;my&lt;/span&gt;-&lt;span class="n"&gt;program&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bins&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bin&lt;/span&gt;/&lt;span class="n"&gt;darwin&lt;/span&gt;-&lt;span class="n"&gt;arm&lt;/span&gt;64/&lt;span class="n"&gt;my&lt;/span&gt;-&lt;span class="n"&gt;program&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;bins&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bin&lt;/span&gt;/&lt;span class="n"&gt;windows&lt;/span&gt;-&lt;span class="n"&gt;amd&lt;/span&gt;64/&lt;span class="n"&gt;my&lt;/span&gt;-&lt;span class="n"&gt;program&lt;/span&gt;.&lt;span class="n"&gt;exe&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="c"&gt;# Let Make know that `bins` doesn&amp;#39;t really exist (is phony) - it&amp;#39;s just a helpful shortcut
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nf"&gt;.PHONY&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;bins&lt;/span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;In summary the above code does the following:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Define each output file we need
&lt;ul&gt;
&lt;li&gt;Set the correct &lt;code&gt;pkg&lt;/code&gt; &lt;code&gt;TARGET&lt;/code&gt; for each output&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Define a rule for building any binary output:
&lt;ul&gt;
&lt;li&gt;Ensure module_modules are up-to-date (this is another make target not shown here).&lt;/li&gt;
&lt;li&gt;Run &lt;code&gt;pkg&lt;/code&gt; with the &lt;code&gt;$TARGET&lt;/code&gt; set in (1) and the name of the current output (&lt;code&gt;$@&lt;/code&gt;).&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Define &lt;code&gt;bins&lt;/code&gt; &amp;ldquo;phony target&amp;rdquo; which builds all listed bins.&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="note note-tip"&gt;
&lt;div class="icon-and-line"&gt;
&lt;svg xmlns="http://www.w3.org/2000/svg" class="ph-icon ph-icon--fill" fill="currentColor" aria-hidden="true" focusable="false"&gt;&lt;use href="https://www.pulumi.com/icons/sprite.21047dcd83825f0caafb78a6fd28628a694219e6b6824f6b3e24ee3147bac331.svg#p-lightbulb-fill"/&gt;&lt;/svg&gt;
&lt;div class="line"&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;div class="content"&gt;
&lt;p&gt;&lt;strong&gt;You might also like:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://www.pulumi.com/blog/benchmarking-python-performance/"&gt;
Benchmarking Python Performance
&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://www.pulumi.com/blog/amazing-performance/"&gt;
Achieving Amazing Performance in the Pulumi CLI
&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;h2 id="recap"&gt;Recap&lt;/h2&gt;
&lt;p&gt;I hope this gives you a good overview of the vercel/pkg tool and how you can use it to create standalone programs using Node.js.&lt;/p&gt;
&lt;h3 id="historical-note"&gt;Historical Note&lt;/h3&gt;
&lt;p&gt;We used to do a similar process using the &lt;a href="https://github.com/nexe/nexe"&gt;nexe project&lt;/a&gt;, but there’s been no releases since 2017 and therefore no support for newer versions of Node.js and we therefore consider this package as unmaintained at this point in time.&lt;/p&gt;</description><author>Daniel Bradley</author><category>engineering</category><category>nodejs</category><category>publishing</category><category>providers</category></item></channel></rss>