Upgrade Node-RED on Siemens IOT2050: Step-by-Step Guide

David Krause9 min read
Other TopicSiemensTutorial / How-to
Licensed PE Working through this on a live machine? A Maine-licensed engineer can take it from here — included with IMD hardware, by the hour for everything else. Book an engineer

Overview

The Siemens SIMATIC IOT2050 is an industrial edge device based on the SIMATIC IOT2050 hardware platform (order number 6ES7647-0BA00-0YA2). It ships with a Yocto-based example image that bundles Node-RED as a pre-installed flow-based development tool. Operators frequently need to upgrade the bundled Node-RED runtime to obtain new nodes, security patches, and protocol support, but the procedure is non-trivial because the example image pins specific Node.js and Node-RED versions, and because an existing Node-RED service often continues to hold port 1880 after an upgrade.

This reference covers the supported upgrade path, the diagnostic steps required before the upgrade, the Node.js / Node-RED compatibility matrix that determines which upgrade is even possible, and the post-upgrade verification sequence. It is written for engineers commissioning or maintaining an IOT2050 with the stock example image, and for integrators building their own Yocto image from meta-iot2050.

Critical: Node-RED 4.x requires Node.js 18 or later. The stock IOT2050 example images ship with Node.js 10. Upgrading Node-RED on these images without first upgrading Node.js will either fail outright, leave the runtime non-functional, or produce a working binary that reports the old version because the previous service never released port 1880. Read the compatibility matrix in section 4 before issuing any npm install command.

Prerequisites

  • Hardware: SIMATIC IOT2050, 6ES7647-0BA00-0YA2 (or compatible variant).
  • Image: Siemens IOT2050 example image (any 1.0.x / 1.1.x / 1.2.x release). Verify with cat /etc/os-release and cat /etc/iot2050-image-version if present.
  • Shell access: serial console, SSH, or direct keyboard/display. The example image enables dropbear on the LAN interface; root login is permitted from the console.
  • Network: outbound HTTPS to registry.npmjs.org for npm install, and to nodered.org for documentation.
  • Existing Node.js runtime: node -v and npm -v must return non-zero before proceeding. Node-RED itself is not a prerequisite for upgrading it.
  • Backup: snapshot or copy /usr/lib/node_modules/node-red, /var/lib/node-red (flows and credentials), and any systemd unit file under /etc/systemd/system/.

Pre-Upgrade Diagnostics

Before issuing any upgrade command, capture the current state. Three artifacts matter: the existing Node-RED version, the Node.js version, and the process that owns TCP port 1880.

1. Current Node-RED version

node-red --version
node -e "console.log(require('/usr/lib/node_modules/node-red/package.json').version)"

Expected output on the stock image: 1.0.2, 1.0.6, 1.1.0, or 1.2.x. Anything else indicates the image was already customized.

2. Current Node.js version

node --version
npm --version

The stock IOT2050 image bundles Node.js 10.x. This single fact determines which Node-RED versions are installable.

3. Process holding port 1880

ss -tlnp | grep 1880
ps -ef | grep -E "node-red|nodejs" | grep -v grep
systemctl list-units | grep -i node

If a Node-RED service is autostarted, it will be holding port 1880 and will block the upgraded runtime from binding. This is the most common cause of the symptom "installed V2.x but the browser still shows V1.x".

4. Autostart mechanism

systemctl status node-red.service 2>/dev/null
ls /etc/systemd/system/multi-user.target.wants/ | grep -i node
ls /etc/init.d/ | grep -i node
cat /lib/systemd/system/node-red.service 2>/dev/null

The example image typically autostarts Node-RED via a systemd unit named node-red.service running as root from /usr/bin/node-red.

Node.js / Node-RED Compatibility Matrix

Node-RED enforces a minimum Node.js version and emits deprecation warnings on EOL Node.js releases. The matrix below is derived from the official Node-RED supported Node.js versions FAQ and release notes.

Node-RED Minimum Node.js Maximum Node.js Notes
1.x (1.0 – 1.3) 8.x 14.x Pre-installed on early IOT2050 example images.
2.x (2.0 – 2.2) 12.x 16.x Drops Node.js 10. npm install succeeds with warnings on Node 10 but the runtime refuses to start.
3.x (3.0 – 3.1) 14.x 18.x Final 3.x line. LTS-safe on Node 14/16/18.
4.0 18.x 22.x Released 20 Jun 2024. Drops Node.js 14 and 16. See Version 4.0 release notes.
4.1 18.x 22.x Released 29 Jul 2025. See Version 4.1 release notes.

Because the stock IOT2050 image bundles Node.js 10, the highest Node-RED version reachable without first upgrading Node.js is Node-RED 1.3.x. Node-RED 2.x and later will install (npm ignores engine checks unless --engine-strict is set), but the new process will exit immediately on start because Node.js 10 is rejected by the version guard in red.js.

Field note: Symptom of a Node.js 10 + Node-RED 2.x mismatch — npm install -g node-red completes without hard error, the browser still shows the previous version, and /var/log/syslog or journalctl -u node-red contains "Node.js v10.x is not supported, please upgrade" followed by the previous instance's restart loop on port 1880.

Upgrade Path A — Within the Stock Image (Node.js 10)

Use this path when the example image must remain unchanged and only minor Node-RED patch updates (1.0.x → 1.0.y, 1.1.x → 1.1.y, 1.2.x → 1.2.y) are required.

Step 1 — Stop the existing instance

systemctl stop node-red.service
pkill -f node-red
sleep 3
ss -tlnp | grep 1880   # must return empty

Step 2 — Back up the user data directory

cp -a /var/lib/node-red /var/lib/node-red.bak.$(date +%Y%m%d)
cp -a /root/.node-red /root/.node-red.bak.$(date +%Y%m%d)

Step 3 — Upgrade the global package

cd /usr/lib
npm install -g --unsafe-perm node-red@^1.3

The --unsafe-perm flag is required because the install runs as root; npm otherwise refuses to drop privileges. The ^1.3 range pin keeps you on the last 1.x line that supports Node.js 10.

Step 4 — Verify the new binary

which node-red
node-red --version
ls -la /usr/lib/node_modules/node-red/package.json

Step 5 — Restart the service

systemctl daemon-reload
systemctl start node-red.service
systemctl status node-red.service

Step 6 — Verify from the browser

Open http://<iot2050-ip>:1880. The header bar must show the new version. If it still shows the old version, the old process is still binding the port; revisit Step 1.

Upgrade Path B — Upgrade Node.js First, Then Node-RED

Use this path when Node-RED 2.x, 3.x, or 4.x is required. The official Node-RED documentation recommends the global npm upgrade pattern: Running Node-RED locally.

Step 1 — Upgrade Node.js

The example image does not expose node as an apt package. Install a newer Node.js from the NodeSource repository:

curl -fsSL https://deb.nodesource.com/setup_18.x | bash -
apt-get install -y nodejs
node --version   # expect v18.x or later

Alternatively, install Node.js 20 LTS for forward compatibility with Node-RED 4.1:

curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
apt-get install -y nodejs

Step 2 — Stop Node-RED

systemctl stop node-red.service
pkill -9 -f node-red

Step 3 — Upgrade Node-RED globally

npm install -g --unsafe-perm node-red
node-red --version

For a specific major version:

npm install -g --unsafe-perm node-red@4
npm install -g --unsafe-perm node-red@3

Step 4 — Reinstall nodes that have native bindings

Nodes with native code (serialport, node-opcua, node-red-contrib-modbus, etc.) were compiled against Node.js 10's V8 ABI. They must be reinstalled:

cd ~/.node-red
rm -rf node_modules
npm install

Step 5 — Restart and verify

systemctl start node-red.service
journalctl -u node-red -f

Resolving the "Port 1880 in Use" Symptom

The most reported issue on the IOT2050 forum thread is that npm install -g node-red succeeds, but the browser at http://<ip>:1880 still shows the old version. The cause is invariably a leftover Node-RED process.

Diagnostic sequence

systemctl status node-red
ss -tlnp | grep 1880
ps -ef | grep node-red
ls -la /proc/$(pidof node-red)/cwd 2>/dev/null

Hard reset procedure

systemctl stop node-red.service
systemctl disable node-red.service
kill -9 $(pidof node-red) 2>/dev/null
sleep 5
ss -tlnp | grep 1880   # confirm port is free
node-red --safe-mode &   # start in safe mode without user flows
# verify new version in browser, then Ctrl+C
node-red &             # restart in normal mode
# re-enable autostart once satisfied
systemctl enable node-red.service
systemctl start node-red.service

Safe-mode flag

Node-RED --safe-mode starts the runtime without loading any user-installed nodes or flows. Use it whenever a bad node module prevents startup. See the Running Node-RED locally reference for the full flag list.

Resolving npm Warnings During Install

Typical warnings on the IOT2050 stock image:

  • npm WARN EBADENGINE Unsupported engine — Node-RED 2.x+ requesting Node.js ≥12 while running on Node.js 10. Downgrade the target Node-RED or upgrade Node.js.
  • npm WARN deprecated — transitive dependencies that have been replaced. Safe to ignore unless a node refuses to load.
  • gyp ERR! stack Error: not found: make — the build chain is missing. Install with apt-get install -y build-essential python3 before installing nodes with native bindings.
  • EACCES on /usr/lib/node_modules — npm invoked without root. Either run as root, prefix with sudo, or change the global prefix with npm config set prefix /usr/local and re-login.

Building a Custom Image with meta-iot2050

For production deployments where reproducibility matters, build the IOT2050 image with the desired Node-RED version baked in rather than upgrading in the field. The meta-iot2050 Yocto layer exposes an npm.bbclass that handles the install: meta-iot2050 npm.bbclass.

Recipe snippet

inherit npm

NPM_PACKAGES = "node-red"
NPM_INSTALL_EXTRA_ARGS = "--unsafe-perm"

# Pin the version
EXTRA_OENPM_append = " [email protected]"

Adjusting the recipe

Edit the recipe that owns Node-RED (typically under recipes-devtools/ or recipes-connectivity/), bump PV or use npm://node-red;version=4.1.0 in SRC_URI, then rebuild:

bitbake iot2050-image-example
ls tmp-glibc/deploy/images/iot2050/

Verifying the baked image

node-red --version   # must match the pinned version
ls /usr/lib/node_modules/node-red/package.json
systemctl status node-red.service

Version Manifest Reference

IOT2050 Image Pre-installed Node-RED Node.js Latest Compatible Node-RED
Example image V1.0.x 1.0.2 10.x 1.3.x
Example image V1.1.x 1.1.0 10.x 1.3.x
Example image V1.2.x 1.2.x 10.x 1.3.x
Custom image (Node 18+) user-defined 18 / 20 / 22 4.1.x

Post-Upgrade Verification

  1. Confirm the binary version: node-red --version matches the target version.
  2. Confirm the browser banner at http://<ip>:1880 matches the target version.
  3. Confirm port ownership: ss -tlnp | grep 1880 shows the new PID.
  4. Confirm autostart: systemctl is-enabled node-red.service returns enabled.
  5. Reboot and re-check: reboot, then after boot confirm systemctl status node-red is active (running).
  6. Load each user flow once and check the warn tab for missing nodes. If nodes are missing, cd ~/.node-red && npm install <missing-node>.
  7. Tail logs: journalctl -u node-red -f must show no "not supported" or "cannot find module" entries.

Troubleshooting Matrix

Symptom Likely Cause Fix
Browser still shows old version after install Old Node-RED still holding port 1880 systemctl stop node-red && pkill -9 node-red, then restart
Error: port 1880 in use on startup Duplicate instance Same as above, then verify with ss -tlnp
Node.js v10.x is not supported Node-RED 2.x+ on Node 10 Upgrade Node.js or pin Node-RED to 1.3.x
npm WARN EBADENGINE Engine mismatch Align Node.js and Node-RED majors per matrix
EACCES permission denied Non-root user Use sudo or --unsafe-perm as root
Custom node fails to load after upgrade Native ABI mismatch cd ~/.node-red && rm -rf node_modules && npm install
Autostart lost after upgrade npm replaced the binary; systemd unit may need refresh systemctl daemon-reload && systemctl enable node-red
Reboot leaves Node-RED down Unit disabled systemctl enable node-red.service

FAQ

Why does my browser still show Node-RED 1.x after I upgraded to 2.x?

The previous Node-RED process is still bound to TCP port 1880. Stop and disable the existing service (systemctl stop node-red && pkill -9 node-red), confirm with ss -tlnp | grep 1880, then start the new runtime.

Can I install Node-RED 4.x on the stock IOT2050 example image?

Not directly. The stock image bundles Node.js 10, but Node-RED 4.x requires Node.js 18 or later. Either upgrade Node.js via the NodeSource repository first, or rebuild the IOT2050 image from meta-iot2050 with Node.js 18/20 baked in.

Do I need --unsafe-perm when installing Node-RED on the IOT2050?

Yes when running as root. npm drops to the nobody user by default, but the IOT2050 image runs the install as root, which requires --unsafe-perm to skip the privilege drop. Without it, lifecycle scripts in native modules fail.

Where should I run npm install -g node-red?

Any directory works because of the -g flag. The conventional location is /usr/lib or simply the home directory. The global prefix is determined by npm config get prefix, which defaults to /usr on the stock image.

How do I pin a specific Node-RED version in a custom meta-iot2050 image?

Edit the recipe that inherits npm from npm.bbclass and append node-red@<version> to EXTRA_OENPM, then rebuild with bitbake iot2050-image-example. The resulting image will ship the pinned version with the systemd autostart already configured.

Back to blog