DESK-MX9-L-AN-0002: Using node.js for Embedded applications

From DAVE Developer's Wiki
Jump to: navigation, search
Info Box


200px-Emblem-important.svg.png

This application note has been validated using the kit version in the History table.


History
Issue Date Notes
2024/09/04 DESK-MX9-L 5.x.x


Introduction[edit | edit source]

Nowadays several designs are based on the latest Javascript technologies available for implementing advanced (Industrial) Graphical User Interface easily.

This Technical Note illustrates how to use the AURA for installing the well-known node.js runtime application framework.

node.js allows the creation of desktop applications in JavaScript, HTML, and CSS.

node.js[edit | edit source]

node runtime can be easily installed in the target root file system using the nvm node version manager:

root@desk-mx93-rev1:~# wget -qO- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.0/install.sh | bash
wget: note: TLS certificate validation not implemented
=> Downloading nvm from git to '/home/root/.nvm'
=> Cloning into '/home/root/.nvm'...
remote: Enumerating objects: 376, done.
remote: Counting objects: 100% (376/376), done.
remote: Compressing objects: 100% (324/324), done.
remote: Total 376 (delta 43), reused 168 (delta 25), pack-reused 0 (from 0)
Receiving objects: 100% (376/376), 374.67 KiB | 976.00 KiB/s, done.
Resolving deltas: 100% (43/43), done.
* (HEAD detached at FETCH_HEAD)
  master
=> Compressing and cleaning up git repository

=> Appending nvm source string to /home/root/.profile
=> bash_completion source string already in /home/root/.profile
=> You currently have modules installed globally with `npm`. These will no
=> longer be linked to the active version of Node when you install a new node
=> with `nvm`; and they may (depending on how you construct your `$PATH`)
=> override the binaries of modules installed with `nvm`:

/usr/lib
+-- corepack@0.18.0
+-- n@9.2.3
=> If you wish to uninstall them at a later point (or re-install them under your
=> `nvm` Nodes), you can remove them from the system Node as follows:

     $ nvm use system
     $ npm uninstall -g a_module

=> Close and reopen your terminal to start using nvm or run the following to use it now:

export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"  # This loads nvm
root@desk-mx93-rev1:~#

Once nvm is installed, simply ask it for installing the latest LTS version of node.js:

root@desk-mx93-rev1:~# exit
logout

NXP i.MX Release Distro 6.1-mickledore desk-mx93-rev1 ttyLP0

desk-mx93-rev1 login: root
Last login: Wed Sep  4 09:41:48 UTC 2024 on ttyLP0
root@desk-mx93-rev1:~# nvm install --lts
Installing latest LTS version.
Downloading and installing node v20.17.0...
od: ../lib/systemd/systemd: No such file or directory
Downloading https://nodejs.org/dist/v20.17.0/node-v20.17.0-linux-arm64.tar.xz...
##################################################################################################################################### 100.0%
Computing checksum with sha256sum
Checksums matched!
Now using node v20.17.0 (npm v10.8.2)
Creating default alias: default -> lts/* (-> v20.17.0)
root@desk-mx93-rev1:~#

The installed version can be checked:

root@desk-mx93-rev1:~# node --version
v20.17.0
root@desk-mx93-rev1:~#

node-red[edit | edit source]

Installing Node-RED is a quite easy operation using npm, see the nodered.org website:

npm install -g --unsafe-perm node-red
root@desk-mx93-rev1:~# npm install -g --unsafe-perm node-red

added 312 packages in 29s

60 packages are looking for funding
  run `npm fund` for details
root@desk-mx93-rev1:~#

In this way, it is possible to start the Node-RED instance locally which runs on top of nodejs:

root@desk-mx93-rev1:~# node-red
6 Sep 14:24:45 - [info]

Welcome to Node-RED
===================

6 Sep 14:24:45 - [info] Node-RED version: v4.0.2
6 Sep 14:24:45 - [info] Node.js  version: v20.17.0
6 Sep 14:24:45 - [info] Linux 6.1.55-desk-mx9-l-5.1.0+geededa2c10f6 arm64 LE
6 Sep 14:24:46 - [info] Loading palette nodes
6 Sep 14:24:49 - [info] Settings file  : /home/root/.node-red/settings.js
6 Sep 14:24:49 - [info] Context store  : 'default' [module=memory]
6 Sep 14:24:49 - [info] User directory : /home/root/.node-red
6 Sep 14:24:49 - [warn] Projects disabled : editorTheme.projects.enabled=false
6 Sep 14:24:49 - [info] Flows file     : /home/root/.node-red/flows.json
6 Sep 14:24:49 - [info] Creating new flow file
6 Sep 14:24:49 - [warn]

---------------------------------------------------------------------
Your flow credentials file is encrypted using a system-generated key.

If the system-generated key is lost for any reason, your credentials
file will not be recoverable, you will have to delete it and re-enter
your credentials.

You should set your own key using the 'credentialSecret' option in
your settings file. Node-RED will then re-encrypt your credentials
file using your chosen key the next time you deploy a change.
---------------------------------------------------------------------

6 Sep 14:24:49 - [info] Server now running at http://127.0.0.1:1880/
6 Sep 14:24:49 - [warn] Encrypted credentials not found
6 Sep 14:24:49 - [info] Starting flows
6 Sep 14:24:49 - [info] Started flows

Opening the related website, it is possible to see the Node-RED editor:

Node-RED editor via web browser

gpio[edit | edit source]

As a usage example, it is possible to access a GPIO. For this purpose, the node-libgpiod native nodejs binding for libgpiod is used.

node-libgpiod can be installed with npm, but it requires libgpiod-1.x version while the default DESK-MX9-L BSP include the libgpiod-2.x version which is not compatible. For using node-libgpiod it is enough to build the related libgpiod package forcing the PREFERRED_VERSION:

PREFERRED_VERSION_libgpiod ?= "1.6.4"

which is compatible with mickledore Yocto layer

Once built, it is possible to install the related packages in the target:

root@desk-mx93-rev1:~# dpkg -i libgpiod-dev_1.6.4-r0_arm64.deb
dpkg: warning: downgrading libgpiod-dev from 2.0-r0 to 1.6.4-r0
(Reading database ... 65030 files and directories currently installed.)
Preparing to unpack libgpiod-dev_1.6.4-r0_arm64.deb ...
Unpacking libgpiod-dev (1.6.4-r0) over (2.0-r0) ...
Setting up libgpiod-dev (1.6.4-r0) ...
root@desk-mx93-rev1:~# dpkg -i libgpiod2_1.6.4-r0_arm64.deb
Selecting previously unselected package libgpiod2.
(Reading database ... 65014 files and directories currently installed.)
Preparing to unpack libgpiod2_1.6.4-r0_arm64.deb ...
Unpacking libgpiod2 (1.6.4-r0) ...
Setting up libgpiod2 (1.6.4-r0) ...
root@desk-mx93-rev1:~# 

and install node-libgpiod using npm:

npm install node-libgpiod 
root@desk-mx93-rev1:~# npm install node-libgpiod

added 1 package, and audited 8 packages in 41s

found 0 vulnerabilities
root@desk-mx93-rev1:~#

In this way, it is possible to create a Javascript code blink.js which toggle/blink a LED (see code here):

const { version, Chip, Line } = require("node-libgpiod");

global.chip = new Chip(0);
global.line = new Line(chip, 3); // led on gpio3 GPIO2_IO03 - LED0
let count = 10;

console.log(version());
console.log("Blink LED0");
line.requestOutputMode();

const blink = () => {
          if(count){
                      line.setValue(count-- % 2);
                      setTimeout(blink,1000);
          } // else line.release();
          // not needed, libgpiod releases resources on process exit
};

setTimeout(blink,1000);

Running the code, LED0 (gpio3) blinks/toggles every 1s and after 10s it stops:

root@desk-mx93-rev1:~# node blink.js
1.6.4
Blink LED0
root@desk-mx93-rev1:~#

This hardware adapter has been used in the AURA Evaluation Kit for having 4 leds and 4 pushbuttons available.

Simple web server[edit | edit source]

Using the nodejs Javascript runtime it is possible to easily create an embedded webserver with few lines of code:

root@desk-mx6:~# cat server.mjs
// server.mjs
import { createServer } from 'node:http';

const server = createServer((req, res) => {
  res.writeHead(200, { 'Content-Type': 'text/plain' });
  res.end('Hello World!\n');
});

// starts a simple http server locally on port 3000
server.listen(3000, '192.168.0.91', () => {
  console.log('Listening on 192.168.0.91:3000');
});

// run with `node server.mjs`
root@desk-mx6:~# node server.mjs
Listening on 192.168.0.91:3000

and the web server can be contacted from the network at its IP address:

node.js web server