Install node in Dockerfile?
Asked Answered
A

13

104

I am user of AWS elastic beanstalk, and I have a little problem. I want to build my CSS files with less+node. But I don`t know how to install node in my dockerfile, when building with jenkins.

Here is installation packages what I am using in my docker. I will be glad for any suggestions.

FROM php:5.6-apache


# Install PHP5 and modules along with composer binary
RUN apt-get update
RUN apt-get -y install \
    curl \
    default-jdk \
    git \
    libcurl4-openssl-dev \
    libpq-dev \
    libmcrypt-dev \
    libpq5 \
    npm \
    node \
    zlib1g-dev \
    libfreetype6-dev \
    libjpeg62-turbo-dev \
    libpng12-dev

RUN docker-php-ext-configure gd --with-freetype-dir=/usr/include/ --with-jpeg-dir=/usr/include/

RUN docker-php-ext-install curl json mbstring opcache pdo_mysql zip gd exif sockets mcrypt

# Install pecl
RUN pecl install -o -f memcache-beta \
    && rm -rf /tmp/pear \
    && echo 'extension=memcache.so' > /usr/local/etc/php/conf.d/memcache.ini

After this I am runing my entrypoint.sh with code

#!/usr/bin/env sh

composer run-script post-install-cmd --no-interaction

chmod 0777 -R /var/app/app/cache
chmod 0777 -R /var/app/app/logs

exec apache2-foreground

But then I`ve got this error

 Error Output: [2016-04-04 11:23:44] assetic.ERROR: The template ":tmp:module.html.twig" contains an error: A template that extends another one cannot have a body in ":tmp:module.ht  
  ml.twig" at line 7.     

But when I install inside the Docker container node this way

apt-get install git-core curl build-essential openssl libssl-dev
 git clone https://github.com/nodejs/node.git
 cd node
 ./configure
 make
 sudo make install
 node -v

I can build my CSS. So question is..how this installation above make install inside my Dockerfile when I am building it with Jenkins?

Anuska answered 4/4, 2016 at 10:10 Comment(1)
Whatever you are hoping to accomplish, chmod 777 is wrong and dangerous. You absolutely do not want to grant write access to executable or system files to all users under any circumstances. You will want to revert to sane permissions ASAP (for your use case, probably simply make sure the files have the correct owner, and stick to 0755) and learn about the Unix permissions model before you try to use it again. If this happened on a system with Internet access, check whether an intruder could have exploited this to escalate their privileges.Fantasia
W
38

Running apt-get install node does not install Node.js, because that's not the package you're asking for.

If you run apt-cache info node you can see that what you are installing is a "Amateur Packet Radio Node program (transitional package)"

You should follow the Node.js install instructions to install via package manager.

Or if you like building from git, you can just do that inside Docker:

RUN apt-get install -y git-core curl build-essential openssl libssl-dev \
 && git clone https://github.com/nodejs/node.git \
 && cd node \
 && ./configure \
 && make \
 && sudo make install
Waterer answered 4/4, 2016 at 11:12 Comment(1)
If you are looking for a more recent answer have a look at this one below https://mcmap.net/q/1778983/-install-node-in-dockerfile His/her/their idea work just fine as well and does not require sudo which you may not want or have in your docker image.Leatherleaf
C
176

I think this works slightly better.

ENV NODE_VERSION=16.13.0
RUN apt install -y curl
RUN curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.0/install.sh | bash
ENV NVM_DIR=/root/.nvm
RUN . "$NVM_DIR/nvm.sh" && nvm install ${NODE_VERSION}
RUN . "$NVM_DIR/nvm.sh" && nvm use v${NODE_VERSION}
RUN . "$NVM_DIR/nvm.sh" && nvm alias default v${NODE_VERSION}
ENV PATH="/root/.nvm/versions/node/v${NODE_VERSION}/bin/:${PATH}"
RUN node --version
RUN npm --version

Note that nvm is a version manager for node.js, designed to be installed per-user, and invoked per-shell. nvm works on any POSIX-compliant shell (sh, dash, ksh, zsh, bash), in particular on these platforms: unix, macOS, and windows WSL.

Cheery answered 18/8, 2019 at 15:59 Comment(11)
Why do you think so?Darrow
This seems like a better answer, as it lets you easily specify the Node version, and the docker build is much faster with nvm, versus building from source within dockerManifestative
To add how fast: Answer from Nathaniel took 5 minutes before I quit the build to try this one. This one took around 15 secs.Kabob
FYI, for anyone else wanting to put the NVM_DIR in some non-standard location, the ENV NVM_DIR=/somewhere-else/.nvm line must go before the "curl | bash" line in order to be respected by the install script.Catania
FYI, the NVM_DIR was giving an error that the path does not exists. So I had mkdir the path before curl lineSouvenir
line 3 should be RUN curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.0/install.sh | bash *the path has an extra /install.sh at the endJacquesjacquet
Thank you for this answer this works like charm. Many other answers I found on other questions did not work.Bellerophon
This was awesome. Just a small add. It would probably be better if the ENV line said: ENV PATH="$NVM_DIR/versions/node/v${NODE_VERSION}/bin/:${PATH}". That way it dynamically changes the path if you use a different $NVM_DIR.Drug
Just a note, if you replaced 16.13.0 with 20, like me, it won't work. You need to specify 20.11.0Greyhen
Works slightly better is an understatement, thxSmelter
RUN node --version throws an error => ERROR [ 9/11] RUN node --version 0.3s ------ > [ 9/11] RUN node --version: 0.303 /bin/sh: 1: node: not found Could anyone help me out why node is not getting detected for meDiastyle
L
45

According to the following answer, I would suggest using npm via the n package, that lets you choose the nodejs version, or use the latest tag or the lts tag. For example for latest:

RUN apt-get update && apt-get install -y \
    software-properties-common \
    npm
RUN npm install npm@latest -g && \
    npm install n -g && \
    n latest
Levenson answered 11/5, 2021 at 17:22 Comment(6)
Great answer! Short, to the point and it just works. Nice! To use LTS just replace latest with lts in the code snippet of the answer.Leatherleaf
Another small suggestion -- depending on the base image you have, you may have to install curl or wget for n to fetch a node binary. apt-get install -y curlMyrticemyrtie
i get error : 0.379 node: /lib/x86_64-linux-gnu/libm.so.6: version `GLIBC_2.27' not found (required by node) 0.379 node: /lib/x86_64-linux-gnu/libc.so.6: version `GLIBC_2.25' not found (required by node) 0.379 node: /lib/x86_64-linux-gnu/libc.so.6: version `GLIBC_2.28' not found (required by node) actualy i get this error for all solutions :)Vanmeter
Error: engine Not compatible with your version of node/npm: [email protected]Campeche
why wouldnt 'npm@latest' not be the latest? seeems redundant. this whole thing seems like we're installing npm 3 timesFundamentalism
@Fundamentalism npm install npm@latest will install the latest npm, npm install n -g will install n, and n latest will install the latest version of nodejs.Levenson
G
39

Just 2 lines

RUN curl -sL https://deb.nodesource.com/setup_12.x | bash - 
RUN apt-get install -y nodejs
Glut answered 9/8, 2021 at 11:52 Comment(4)
This line gives me following error message: debconf: unable to initialize frontend: Dialog debconf: (TERM is not set, so the dialog frontend is not usable.) debconf: falling back to frontend: Readline debconf: unable to initialize frontend: Readline debconf: (This frontend requires a controlling tty.) debconf: falling back to frontend: Teletype dpkg-preconfigure: unable to re-open stdin:Spam
@Spam set ARG DEBIAN_FRONTEND=noninteractive in your Dockerfile, that should solve the issuePrivy
Is it better than accepted answer from @Nathan, which installs nvm first?Seafarer
This script, located at deb.nodesource.com/setup_X, used to install Node.js is deprecated now and will eventually be made inactive.Blindworm
W
38

Running apt-get install node does not install Node.js, because that's not the package you're asking for.

If you run apt-cache info node you can see that what you are installing is a "Amateur Packet Radio Node program (transitional package)"

You should follow the Node.js install instructions to install via package manager.

Or if you like building from git, you can just do that inside Docker:

RUN apt-get install -y git-core curl build-essential openssl libssl-dev \
 && git clone https://github.com/nodejs/node.git \
 && cd node \
 && ./configure \
 && make \
 && sudo make install
Waterer answered 4/4, 2016 at 11:12 Comment(1)
If you are looking for a more recent answer have a look at this one below https://mcmap.net/q/1778983/-install-node-in-dockerfile His/her/their idea work just fine as well and does not require sudo which you may not want or have in your docker image.Leatherleaf
F
32

Get the node image and put it at the top of your dockerfile:

FROM node:[tag_name] AS [alias_name]

Verify the version by adding following code:

RUN echo "NODE Version:" && node --version
RUN echo "NPM Version:" && npm --version

Then add the following code every time you need to use nodejs in a container:

COPY --from=[alias_name] . .


From the codes above, replace the following with:

[tag_name] - the tag value of the node image you want to use. Visit https://hub.docker.com/_/node?tab=tags for the list of available tags.

[alias_name] - your preferred image name to use in your dockerfile.


Example:

FROM node:latest AS node_base

RUN echo "NODE Version:" && node --version
RUN echo "NPM Version:" && npm --version


FROM php:5.6-apache

COPY --from=node_base . .

### OTHER CODE GOES HERE
Faun answered 6/4, 2020 at 6:40 Comment(7)
For me it did not work with COPY --from=node_base . ., but rather with COPY --from=node_base / /Macassar
Error: cannot copy to non-directory: /var/lib/docker/overlay2/oscikzv9ow4kfi4x1dmvw8dmn/merged/usr/include/mysqlLymphadenitis
I find this solution more elegant, and it also took less time than installing nodejs for meReena
This also works: COPY --from=node:18.16.0-slim /usr/local/bin /usr/local/bin if you just want the node binaryAcidimeter
I had to also add COPY --from=node:18.16.0-slim /usr/local/lib/node_modules/npm /usr/local/lib/node_modules/npm because npm is symlinked to that folderClaviform
This is the answer I really needed but didn't find it until I went back here to create my own answer about multi-stage docker files. Only learned about those after trying the 'manual' node install from one of the other answers and later stumbling onto the multi-stage build section in the docker docs. This needs to be higher, thank you mister.Teniacide
NOTE: You might get away with doing whatever you need with node and then copying over just the outcome - not the whole file system (i.e. build project, copy the build)Teniacide
F
19

Binary download without any compilation

FROM ubuntu

RUN apt-get update && apt-get install -y \
  ca-certificates \
  curl

ARG NODE_VERSION=14.16.0
ARG NODE_PACKAGE=node-v$NODE_VERSION-linux-x64
ARG NODE_HOME=/opt/$NODE_PACKAGE

ENV NODE_PATH $NODE_HOME/lib/node_modules
ENV PATH $NODE_HOME/bin:$PATH

RUN curl https://nodejs.org/dist/v$NODE_VERSION/$NODE_PACKAGE.tar.gz | tar -xzC /opt/

# comes with npm
# RUN npm install -g typescript
Freytag answered 26/2, 2021 at 17:21 Comment(2)
Hi, I like your approach but it is not compatible with ARM chips.Carping
Emanuel: use proper arm binary url: s/x64/arm64/Freytag
D
9

I am using following Dockerfile to setup node version 8.10.0.

Here I have used NVM (Node Version Manager ), so we can choose which node version should be installed on that container. Please use absolute path of npm when installing node modules (eg: /root/.nvm/versions/node/v${NODE_VERSION}/bin/npm install leasot@latest -g)

   FROM ubuntu:18.04
   ENV NODE_VERSION=8.10.0
   RUN apt-get update && \
       apt-get install wget curl ca-certificates rsync -y
   RUN wget -qO- https://raw.githubusercontent.com/creationix/nvm/v0.33.2/install.sh | bash
   ENV NVM_DIR=/root/.nvm
   RUN . "$NVM_DIR/nvm.sh" && nvm install ${NODE_VERSION}
   RUN . "$NVM_DIR/nvm.sh" &&  nvm use v${NODE_VERSION}
   RUN . "$NVM_DIR/nvm.sh" && nvm alias default v${NODE_VERSION}
   RUN cp /root/.nvm/versions/node/v${NODE_VERSION}/bin/node /usr/bin/
   RUN cp /root/.nvm/versions/node/v${NODE_VERSION}/bin/npm /usr/bin/
   RUN /root/.nvm/versions/node/v${NODE_VERSION}/bin/npm install  leasot@latest -g

Note: This is a cropped Dockerfile.

Dowser answered 27/2, 2019 at 7:37 Comment(0)
Y
5

Directly into /usr/local so it's already in your $PATH

ARG NODE_VERSION=8.10.0
RUN curl https://nodejs.org/dist/v$NODE_VERSION/node-v$NODE_VERSION-linux-x64.tar.gz | tar -xz -C /usr/local --strip-components 1
Yolande answered 17/11, 2021 at 18:24 Comment(0)
E
4

The short answer, for example, install v14.17.1

ENV PATH="/opt/node-v14.17.1-linux-x64/bin:${PATH}"
RUN curl https://nodejs.org/dist/v14.17.1/node-v14.17.1-linux-x64.tar.gz |tar xzf - -C /opt/ 

list of all available versions can be found here -> https://nodejs.org/dist/

Evacuate answered 21/6, 2021 at 16:50 Comment(0)
R
2

The accepted answer gives the link to the installation instructions for all systems, but it won't run out of the box since you often (e.g. for ubuntu) don't have all required dependencies installed (namely curl and sudo).

So here's for example how you'd do it for ubuntu:

FROM ubuntu

# Core dependencies
RUN apt-get update && apt-get install -y curl sudo

# Node
# Uncomment your target version
# RUN curl -fsSL https://deb.nodesource.com/setup_10.x | sudo -E bash -
# RUN curl -fsSL https://deb.nodesource.com/setup_12.x | sudo -E bash -
# RUN curl -fsSL https://deb.nodesource.com/setup_14.x | sudo -E bash -
# RUN curl -fsSL https://deb.nodesource.com/setup_16.x | sudo -E bash -
RUN sudo apt-get install -y nodejs
RUN echo "NODE Version:" && node --version
RUN echo "NPM Version:" && npm --version

then build with

docker build . --progress=plain

to see the output of the echo statements. Of course you could also leave away the echo statements and run it regularly with docker build ., after you've made sure everything is working as intended.

You can also leave away the installation of sudo, but then you'll have to get rid of the sudo occurrences in the script.

Runin answered 22/4, 2021 at 11:56 Comment(0)
V
2
FROM ubuntu:20.04

# all necessaries for next RUN
RUN set -e; \
    apt-get update && \
    apt-get install -qqy --no-install-recommends \
    curl wget nano gnupg2 software-properties-common && \
    rm -rf /var/lib/apt/lists;

RUN curl -sL https://deb.nodesource.com/setup_14.x | bash -

# uncomment for checking versions
  # Step 4/10 : RUN apt-cache show nodejs | grep Version;return 1;
  #  ---> Running in xxxxxxxxx
  # Version: 14.18.2-deb-1nodesource1
  # Version: 10.19.0~dfsg-3ubuntu1
#RUN apt-cache show nodejs | grep Version;return 1;

RUN set -e; \
    apt-get update && \
    apt-get install -qqy \
    nodejs && \
    rm -rf /var/lib/apt/lists;

# uncomment for check
# RUN node  -v
Viral answered 29/12, 2021 at 14:17 Comment(0)
O
2

This worked for me

RUN curl -sL https://deb.nodesource.com/setup_14.x | bash - && \
    apt-get update && apt-get install -y nodejs npm
Oospore answered 4/3 at 0:11 Comment(0)
I
1

Nowadays, you can simply install the npm package via apt, and it'll come with npm 9.x and node 18.x, which are not the LTS versions, but are at least one of the latest ones.

RUN apt-get update && apt-get install -y npm

Additionally, if you wanna install a more recent version of node and npm, you can do similarly what was pointed out in this answer. Just use the 'n' package:

RUN npm i -g n && n lts && npm i -g npm@latest
Intelligentsia answered 1/11, 2023 at 12:20 Comment(1)
this results in: node:internal/modules/cjs/loader:1148Fundamentalism

© 2022 - 2024 — McMap. All rights reserved.