Skip to main content
Redhat Developers  Logo
  • Products

    Featured

    • Red Hat Enterprise Linux
      Red Hat Enterprise Linux Icon
    • Red Hat OpenShift AI
      Red Hat OpenShift AI
    • Red Hat Enterprise Linux AI
      Linux icon inside of a brain
    • Image mode for Red Hat Enterprise Linux
      RHEL image mode
    • Red Hat OpenShift
      Openshift icon
    • Red Hat Ansible Automation Platform
      Ansible icon
    • Red Hat Developer Hub
      Developer Hub
    • View All Red Hat Products
    • Linux

      • Red Hat Enterprise Linux
      • Image mode for Red Hat Enterprise Linux
      • Red Hat Universal Base Images (UBI)
    • Java runtimes & frameworks

      • JBoss Enterprise Application Platform
      • Red Hat build of OpenJDK
    • Kubernetes

      • Red Hat OpenShift
      • Microsoft Azure Red Hat OpenShift
      • Red Hat OpenShift Virtualization
      • Red Hat OpenShift Lightspeed
    • Integration & App Connectivity

      • Red Hat Build of Apache Camel
      • Red Hat Service Interconnect
      • Red Hat Connectivity Link
    • AI/ML

      • Red Hat OpenShift AI
      • Red Hat Enterprise Linux AI
    • Automation

      • Red Hat Ansible Automation Platform
      • Red Hat Ansible Lightspeed
    • Developer tools

      • Red Hat Trusted Software Supply Chain
      • Podman Desktop
      • Red Hat OpenShift Dev Spaces
    • Developer Sandbox

      Developer Sandbox
      Try Red Hat products and technologies without setup or configuration fees for 30 days with this shared Openshift and Kubernetes cluster.
    • Try at no cost
  • Technologies

    Featured

    • AI/ML
      AI/ML Icon
    • Linux
      Linux Icon
    • Kubernetes
      Cloud icon
    • Automation
      Automation Icon showing arrows moving in a circle around a gear
    • View All Technologies
    • Programming Languages & Frameworks

      • Java
      • Python
      • JavaScript
    • System Design & Architecture

      • Red Hat architecture and design patterns
      • Microservices
      • Event-Driven Architecture
      • Databases
    • Developer Productivity

      • Developer productivity
      • Developer Tools
      • GitOps
    • Secure Development & Architectures

      • Security
      • Secure coding
    • Platform Engineering

      • DevOps
      • DevSecOps
      • Ansible automation for applications and services
    • Automated Data Processing

      • AI/ML
      • Data Science
      • Apache Kafka on Kubernetes
      • View All Technologies
    • Start exploring in the Developer Sandbox for free

      sandbox graphic
      Try Red Hat's products and technologies without setup or configuration.
    • Try at no cost
  • Learn

    Featured

    • Kubernetes & Cloud Native
      Openshift icon
    • Linux
      Rhel icon
    • Automation
      Ansible cloud icon
    • Java
      Java icon
    • AI/ML
      AI/ML Icon
    • View All Learning Resources

    E-Books

    • GitOps Cookbook
    • Podman in Action
    • Kubernetes Operators
    • The Path to GitOps
    • View All E-books

    Cheat Sheets

    • Linux Commands
    • Bash Commands
    • Git
    • systemd Commands
    • View All Cheat Sheets

    Documentation

    • API Catalog
    • Product Documentation
    • Legacy Documentation
    • Red Hat Learning

      Learning image
      Boost your technical skills to expert-level with the help of interactive lessons offered by various Red Hat Learning programs.
    • Explore Red Hat Learning
  • Developer Sandbox

    Developer Sandbox

    • Access Red Hat’s products and technologies without setup or configuration, and start developing quicker than ever before with our new, no-cost sandbox environments.
    • Explore Developer Sandbox

    Featured Developer Sandbox activities

    • Get started with your Developer Sandbox
    • OpenShift virtualization and application modernization using the Developer Sandbox
    • Explore all Developer Sandbox activities

    Ready to start developing apps?

    • Try at no cost
  • Blog
  • Events
  • Videos

How to troubleshoot Node.js images in OpenShift

March 5, 2025
Francisco De Melo Junior
Related topics:
JavaNode.js
Related products:
Red Hat build of Node.js

Share:

    Red Hat build of Node.js is a fully supported product within our portfolio and allows the deployment of JavaScript applications outside of a browser. Inside a container, it provides several features including an I/O model based on events and non-blocking operations for performant applications. Red Hat currently provides support for Node.js 20 links for Red Hat build of Node.js 20 LTS Component Details, Red Hat build of Node.js Supported Configurations, and Node.js Runtime Guide, which is an excellent guide. 

    This article discusses how to troubleshoot build or deployment of Node.js in Red Hat OpenShift. However, I will not cover any advanced topics such as FIPS, OpenSSL, garbage collection tuning, or extensive Node.js manipulation.

    I will present examples of Node.js build using a Dockerfile or a Source-to-Image (S2I) framework.

    Node.js deployment via Dockerfile

    Given the following hello.js file:

    $ cat lib/hello.js 
    console.log("Hello, Red Hat Developer Program World from Node " + process.version)

    This is an example container file (Dockerfile) that can be used to build a container that runs the application when the container starts as follows:

    FROM registry.access.redhat.com/ubi9/nodejs-20:1-24
    COPY lib/hello.js /opt/app-root/src/hello.js
    ENTRYPOINT ["node", "/opt/app-root/src/hello.js"]

    When running the following, you will get the HelloWorld output:

    $ podman run --rm -it  localhost/nodejs:app
    Hello, Red Hat Developer Program World from Node v20.9.0

    This is a less trivial example:

    var http = require('http');
    var port = 8000;
    var laddr = '0.0.0.0';
    http.createServer(function (req, res) {
        res.writeHead(200, {'Content-Type': 'text/plain'});
        res.end('Hello, Red Hat Developer Program World from ' +
            process.version + '!\n');
        console.log('Processed request for '+ req.url);
    }).listen(port, laddr);
    console.log('Server running at http://' + laddr + ':' + port + '/');

    These examples do not take advantage of Source-to-Image, but rely directly on the injection of the application directly as entrypoint. 

    Node.js Source-to-Image example

    Here is a trivial application deployed by taking advantage of oc new-app command:

    $ oc new-app nodejs:latest~https://github.com/sclorg/nodejs-ex.git
        Node.js 16 
        ---------- 
        Node.js 16 available as container is a base platform for building and running various Node.js 16 applications and frameworks. Node.js is a platform built on Chrome's JavaScript runtime for easily building fast, scalable network applications. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient, perfect for data-intensive real-time applications that run across distributed devices.
        Tags: builder, nodejs, nodejs16
        * A source build using source code from https://github.com/sclorg/nodejs-ex.git will be created
          * The resulting image will be pushed to image stream tag "nodejs-ex:latest"
          * Use 'oc start-build' to trigger a new build
    --> Creating resources ...
        imagestream.image.openshift.io "nodejs-ex" created
        buildconfig.build.openshift.io "nodejs-ex" created
        deployment.apps "nodejs-ex" created
        service "nodejs-ex" created
    --> Success
        Build scheduled, use 'oc logs -f buildconfig/nodejs-ex' to track its progress.

    This oc client command uses the image Node.js tag latest, passing this GitHub path as an argument which will create a build in one container and then deploy the Node.js application in another. In this case, it is a create, read, update, delete (CRUD) application.

    Going into a bit more in detail, for the Source-to-Image build process to happen, Red Hat provides a Node.js S2I builder image that assembles the application source plus the dependencies for a new Node.js container. What I mean by "builder image" is that the image will have the builder tag and the assemble and run scripts (Figure 1).

    Node.js 20 builder image
    Figure 1: Node.js builder image.
    $ podman run --entrypoint=/bin/bash --rm -it  registry.redhat.io/rhel9/nodejs-20:1-48
    bash-5.1$ cd /usr/libexec/s2i/
    bash-5.1$ ls
    assemble  run  save-artifacts  usage
    ...
    ...
    bash-5.1$ cat assemble 
    #!/bin/bash
    # Prevent running assemble in builders different than official STI image.
    # The official nodejs:8-onbuild already run npm install and use different
    # application folder.
    [ -d "/usr/src/app" ] && exit 0
    set -e

    Troubleshooting Node.js issues

    There are numerous issues that can happen with Node.js deployment. They can be divided into two segments: building and deployment (runtime) issues.

    Build issues

    For this type of issue, collect the inspect file if the build is inside Red Hat OpenShift Container Platform (RHOCP) 4 or build resources such as Dockerfile if the build is done in Podman. Depending on the context, package.json could be useful as well.

    Examples of issues that can occur during the OpenShift build include the Source-to-Image build process or image retrieval failures. Although the OpenShift 4 BuildConfig is quite common, there can be complex scenarios with Jenkins agents, the GitLab Runner Operator, and OpenShift sandboxed containers (OSC). That's because depending on the build, the runtime, the CPU number, and availability might change, and this impacts builds. 

    Examples of issues with Podman builds could also include the Node.js using Source-to-Image, and the injection of the applications in which the container would need to be built with an entry point that will start the application, such as the previous examples. 

    There may also be issues with the Node Package Manager (NPM) installation and operations, such as installation libraries via NPM in this category. For instance, there may be issues with dependencies and profiles (which would be done via environment variables) usually done via NODE_ENV or declarative instruction RUN npm install --include=dev. For issues occurring during the NPM install process, package.json file can be useful to verify. 

    Finally, in terms of deployment, Node.js applications often use some environment variables for their operations, and the building and/or deployment method might overwrite those variables.

    bash-5.1$ echo $DESCRIPTION 
    Node.js 20 available as container is a base platform for building and running various Node.js 20 applications and frameworks. Node.js is a platform built on Chrome's JavaScript runtime for easily building fast, scalable network applications. Node.js uses an event-driven, non-blocking I/O model that makes it lightweight and efficient, perfect for data-intensive real-time applications that run across distributed devices.
    bash-5.1$ echo $SUMMARY   
    Platform for building and running Node.js 20 applications
    bash-5.1$ echo $NPM_RUN
    start
    bash-5.1$ echo $NPM_CONFIG_PREFIX 
    /opt/app-root/src/.npm-global

    This is slightly specific to the Next.js framework, but also related to environment variables; and therefore might be mistakenly overwritten on the build as the NEXT_PUBLIC and  NEXT_PUBLIC_VAR environment variables.

    You can find more example issues here and here.

    Deployment issues

    For this deployment issues, collecting the inspect file and/or specific resources such as garbage collection data can be useful. For example, in the case of CPU discrepancies, the output of /proc/stat can be useful, as this will bring CPU utilization from the container.

    For memory issues, collecting the garbage collection logs can be useful. To collect garbage collection logs, start the application with --trace-gc as follows:

     ENTRYPOINT ["node", "--trace-gc", "/opt/app-root/src/hello.js"] <-- to allow trace-gc

    When investigating memory consumption, another option in terms of memory issues is the capture of heap snapshots. There are several options for taking a heap snapshot, for instance, via external signal and command line flag. For heap snapshot refer to this guide. Evidently for containers, triggering via signal such as kill -USR1 $PID is very useful.

    After collecting the heap snapshot, to analyze heap snapshots, open the Chromium base browser Dev tools and navigate to the Memory tab. This browser can also be useful for comparing different snapshots. There is a feature on the browser to do so (Figure 2).

    Heap snapshot
    Figure 2: A snapshot of the heap.

    To diagnose a real leak, one must increase the memory a few times and wait for the increase. I would suggest increasing the memory to 50% or even 100%, rather than 10% as suggested on the upstream documentation until you start seeing the OOM again:

    FATAL ERROR: Reached heap limit Allocation failed - JavaScript heap out of memory [...]

    In terms of memory usage, it can come in handy to diagnose issues such as increasing or reducing --max-old-space-size in terms of memory consumption or leaks. 

    In the case of an upgraded OpenShift cluster that has a different performance, by changing the number of requests, it is interesting to have networking data or performance data. 

    Finally, having an agent for collecting data can be very useful. In this example of requests, some agents might be able to see what the bulk of the requests are during a certain period.

    In terms of OpenShift Container Platform 4 build and deployment, collecting the inspect can be a good alternative, given that it will provide logs and YAMLs for both build and deployment resources, such as pod YAML/deployment YAML. inspect is useful for most middleware issues in general. 

    Read the article, Using OpenShift 4's inspect for middleware troubleshooting and note the namespace's inspect won't bring workload data, but rather the collection of OpenShift Container Platform 4 deployment YAMLs, which need the specific deployment and pod names.

    For builds outside OpenShift Container Platform via Podman/Docker, the Dockerfile and the logs will be needed as mentioned.

    Finally, the Runtime Guide brings details on debugging the Node.js application using the native debugger. 

    Note that Node.js inspect command (node inspect EXAMPLE.js) is different from OpenShift inspect bundle ($ oc adm inspect ns/NAMESPACE). Node.js inspect concerns a command-line debugging utility that is started with inspect command, whereas OpenShift Inspect is the bundle that contains runtime resources. 

    Additional resources

    In summation, Node.js is based on Google's V8 JavaScript and allows server-side JavaScript applications. Red Hat's build of Node.js containerized image enables those features in a container, which is easy to use and scale, and also allows container deployment features in OpenShift 4, such as HorizontalPodAutoscaler and container settings via cgroups.

    Although not extensive, this article sheds light on the matter of troubleshooting and clarifying relevant data to be collected and how to collect it. In the future, I plan to dive into garbage collection logs and tuning in Node.js.

    To learn more about Node.js see the Node.js Runtime Guide and upstream pages. Also, the GitHub page is a good reference, covering topics from building good containers to debugging, mostly agnostic from Red Hat-specific implementation. In terms of tracing/debugging, there is the Observability for Node.js applications in OpenShift series.

    For any other specific inquiries, please open a case with Red Hat support. Our global team of experts will be glad to help you with any issues.

    Special thanks to Alexander Barbosa for the excellent review and Michael Dawson for his great input and collaboration for Node.js issues in OpenShift throughout the years.

    Related Posts

    • Monitor Node.js applications on Red Hat OpenShift with Prometheus

    • Deploying Node.js applications to Kubernetes with Nodeshift and Minikube

    • Add standardized support information to your Node.js modules

    • Get started with Node.js 14 on Red Hat OpenShift

    • Deploying serverless Node.js applications on Red Hat OpenShift, Part 1

    Recent Posts

    • GuideLLM: Evaluate LLM deployments for real-world inference

    • Unleashing multimodal magic with RamaLama

    • Integrate Red Hat AI Inference Server & LangChain in agentic workflows

    • Streamline multi-cloud operations with Ansible and ServiceNow

    • Automate dynamic application security testing with RapiDAST

    What’s up next?

    This cheat sheet covers tips for making the most of Node.js JavaScript applications on Red Hat OpenShift, using UBI Containers.

    Get the cheat sheet
    Red Hat Developers logo LinkedIn YouTube Twitter Facebook

    Products

    • Red Hat Enterprise Linux
    • Red Hat OpenShift
    • Red Hat Ansible Automation Platform

    Build

    • Developer Sandbox
    • Developer Tools
    • Interactive Tutorials
    • API Catalog

    Quicklinks

    • Learning Resources
    • E-books
    • Cheat Sheets
    • Blog
    • Events
    • Newsletter

    Communicate

    • About us
    • Contact sales
    • Find a partner
    • Report a website issue
    • Site Status Dashboard
    • Report a security problem

    RED HAT DEVELOPER

    Build here. Go anywhere.

    We serve the builders. The problem solvers who create careers with code.

    Join us if you’re a developer, software engineer, web designer, front-end designer, UX designer, computer scientist, architect, tester, product manager, project manager or team lead.

    Sign me up

    Red Hat legal and privacy links

    • About Red Hat
    • Jobs
    • Events
    • Locations
    • Contact Red Hat
    • Red Hat Blog
    • Inclusion at Red Hat
    • Cool Stuff Store
    • Red Hat Summit

    Red Hat legal and privacy links

    • Privacy statement
    • Terms of use
    • All policies and guidelines
    • Digital accessibility

    Report a website issue