This article demonstrates updating detect and build scripts to dynamically set the Node.js version from the package.json file.
In this article, we demonstrate how to update your detect and build scripts to dynamically set the Node.js version specified by the user in the package.json file. The package.json file includes an “engines” section where you can declare the required Node.js version. In our example, the package.json file specifies Node.js version 18.18.0.
The detect script now sets a default Node.js version and then attempts to extract the user-specified version from the package.json file by reading the “engines.node” property. Finally, it writes the appropriate “provides” and “requires” fields to the buildpack build plan, which the build script uses later to download and install the correct Node.js version.
Copy
Ask AI
if [[ -f package.json ]]; then # default version version=18.18.1 # Determine Node.js version from package.json using jq version=$(jq -r '.engines.node' "./package.json") # echo "version: ${version}" cat > "${CNB_BUILD_PLAN_PATH}" << EOLprovides = [{ name = "node-js" }]requires = [{ name = "node-js", metadata = { version = "${version}" } }]EOLfi
Ensure that your package.json file contains the “engines” section with the correct Node.js version.
To test the container state, run:
Copy
Ask AI
docker ps
Expected output for docker ps:
Copy
Ask AI
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES28f480564d5e myapp "/cnb/process/web" 2 seconds ago Up 2 seconds 0.0.0.0:8000->8080/tcp, [::]:8000->8080/tcp eager
Previously, the build script hardcoded Node.js version 18.18.1. In the updated script, a default Node.js version (18.18.0) is defined, and the desired version is later retrieved from the build plan. This retrieved version is then used to dynamically construct the download URL for the appropriate Node.js tarball.Below is the revised build script:
Copy
Ask AI
#!/usr/bin/env bashset -euo pipefailecho "Building image using my-js-buildpack buildpack"default_node_js_version="18.18.0"echo "--> Downloading and extracting NodeJS"node_js_url=https://nodejs.org/dist/v18.18.1/node-v18.18.1-linux-x64.tar.xzwget -q -O - "${node_js_url}" | tar -xJf - --strip-components 1export PATH="./bin:$PATH"pwdls -laecho "--> Installing Application Dependencies"
After building, you can check the container status with:
Copy
Ask AI
docker ps
Expected output:
Copy
Ask AI
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES28f480564d5e myapp "/cnb/process/web" 2 seconds ago Up 2 seconds 0.0.0.0:8000->8080/tcp, [::]:8000->8080/tcp eager
The build script is now updated to dynamically include the user-specified Node.js version. After retrieving the version from the build plan, the script prints the version for verification and constructs the download URL based on that version. The snippet below shows the modified section:
The console output during the build might resemble:
Copy
Ask AI
[analyzer] Restoring data for SBOM from previous image==> DETECTING[detector] my-js-buildpack 0.0.1==> RESTORING[builder] Building image using my-js-buildpack buildpack[builder] nodejs version: 18.18.0==> Downloading and extracting NodeJS[builder] workspaceTotal 812[builder] drwxr-xr-x 1 root root 4096 Nov 4 04:42 ..
After confirming this output, delete the old container and rebuild the image. The build output will then verify that the correct Node.js version is used.To test the dynamic version retrieval, update the package.json “engines.node” value to 18.18.1 and rebuild the image. The build logs should now indicate that Node.js version 18.18.1 is installed:
[exporter] Reusing layer 'buildpacksio/lifecycle:process-types'[exporter] Adding label 'io.buildpacks.lifecycle.metadata'[exporter] Adding label 'io.buildpacks.build.metadata'[exporter] Setting default process type 'web'[exporter] Saving myapp...[exporter] *** Images (5d6facb4612d):myappSuccessfully built image myapp
And later:
Copy
Ask AI
[exporter] Reusing layer 'buildpacksio/lifecycle:process-types'[exporter] Adding label 'io.buildpacks.lifecycle.metadata'[exporter] Adding label 'io.buildpacks.build.metadata'[exporter] Adding label 'io.buildpacks.project.metadata'[exporter] Setting default process type 'web'[exporter] Saving myapp...[exporter] *** Images (56dfacb4612d):[exporter] myappSuccessfully built image myapproot in ubuntu-s-4vcpu-8gb-nyc1-01 in ~/buildpack-demo took 20s
This confirms that the buildpack now successfully supports dynamic Node.js version selection based on the user’s specification in package.json.Happy building!