Creating a Node.js execution environment

Problem

You want to run Node.js content on a Posit Connect server configured for off-host execution.

The stock posit-dev/images-connect images do not include Node.js, so you must register a Node.js-bearing image as an execution environment before publishers can deploy Node.js content.

Solution

Prerequisites

Node.js content support must be enabled. The Connect configuration file must set NodeJs.Enabled to true.

Running Node.js content requires the Advanced license tier. See License requirements for details.

Choose a Node.js image

The official Docker node image places the Node.js binary at /usr/local/bin/node and is suitable for most Node.js content.

We recommend using a full major.minor.patch tag, for example, node:24.16.0, to avoid version mismatch errors. Major version tags like node:24 are mutable and receive newer Node.js releases over time. If the Node.js version inside the image stops matching the version registered in Connect, content builds fail with an error like Expected Node.js 24.16.0 but found 24.17.0 until an administrator updates the execution environment.

Some content depends on system libraries that the official image does not include. Examples include libvips for sharp and Cairo for canvas. For those cases, build a custom image that adds the required libraries to a Node.js base.

Register the execution environment

Administrators can register the environment through the Connect UI or by calling the environments API. The UI is the most convenient path for one-off setup. The API is useful for scripting and automation.

Through the Connect UI

  1. Sign in to Connect as an administrator.
  2. Click System in the top menu, then click the Environments tab.
  3. Click + Add Environment.
  4. In the Add Environment dialog:
    • Title: A human-readable name, for example, Node.js 24.16.0.
    • Image name: The container image reference, for example, node:24.16.0.
    • Under Installations, click + Add Installation, select Node.js as the type, and enter the Node.js version (for example, 24.16.0) and the absolute path to the node binary (for example, /usr/local/bin/node).
  5. (Optional) Click Advanced if you want to restrict the environment so it is only used when content explicitly requests it. The default matching strategy any lets Connect select this environment automatically. Switch to exact for environments you only want addressed by name.
  6. Click Save.

The new environment appears in the Environments table and is available for content deployment.

Through the environments API

from posit import connect

client = connect.Client()

client.post(
    "v1/environments",
    json={
        "title": "Node.js 24.16.0",
        "description": "Official Docker node:24.16.0 image",
        "cluster_name": "Kubernetes",
        "name": "node:24.16.0",
        "matching": "any",
        "nodejs": {
            "installations": [
                {"version": "24.16.0", "path": "/usr/local/bin/node"}
            ]
        },
    },
)
library(connectapi)
library(jsonlite)

client <- connect()

json_payload <- toJSON(list(
  title = "Node.js 24.16.0",
  description = "Official Docker node:24.16.0 image",
  cluster_name = "Kubernetes",
  name = "node:24.16.0",
  matching = "any",
  nodejs = list(
    installations = list(
      list(version = "24.16.0", path = "/usr/local/bin/node")
    )
  )
), auto_unbox = TRUE, pretty = TRUE)

client$POST("/v1/environments", json_payload)

After the request returns, list execution environments and confirm the new entry includes a populated nodejs.installations field:

environments = client.get("v1/environments").json()
print([e for e in environments if e["name"] == "node:24.16.0"])
environments <- client$GET("/v1/environments")
print(Filter(function(e) e$name == "node:24.16.0", environments))

Discussion

Once the environment is registered, Connect selects it for Node.js content based on the engines.node constraint declared in the bundle’s package.json. If the constraint matches multiple environments, Connect picks the one with the highest matching version. If no environment matches, the deploy fails with an error listing the Node.js versions available across configured environments.

To support multiple Node.js major versions side-by-side, register a separate execution environment for each major version (for example, one using node:22.22.3 and another using node:24.16.0). Connect routes each bundle to the environment whose Node.js installation satisfies its engines.node constraint.

See also