Node container image - это реализация легковесной сборки ЯП Node.js на базе Astra Linux
Присоединяйтесь к нашим социальным сетям:
- Docker >= 28.1.1 (возможно работает в предыдущих версиях, но мы не можем это гарантировать)
OS | Node.js | Status |
---|---|---|
✅ Fully supported | ||
✅ Fully supported |
Node.js — это программная платформа для масштабируемых серверных и сетевых приложений. Приложения Node.js написаны на JavaScript и могут быть запущены в среде выполнения Node.js на Mac OS X, Windows и Linux без изменений. Приложения Node.js разработаны для максимизации пропускной способности и эффективности, используя неблокирующий ввод-вывод и асинхронные события. Приложения Node.js работают в однопоточном режиме, хотя Node.js использует несколько потоков для файловых и сетевых событий. Node.js обычно используется для приложений реального времени из-за его асинхронной природы.
Node.js внутренне использует движок Google V8 JavaScript для выполнения кода; большой процент базовых модулей написан на JavaScript. Node.js содержит встроенную библиотеку асинхронного ввода-вывода для файловой, сокетной и HTTP-связи. Поддержка HTTP и сокетов позволяет Node.js выступать в качестве веб-сервера без дополнительного программного обеспечения, такого как Apache. Образ построен на основе отечественной ОС Astra Linux
Для начала работы необходимо установить pre-commit и хуки
$ pip install pre-commit
$ pre-commit --version
pre-commit 4.2.0
$ pre-commit install
pre-commit installed at .git/hooks/pre-commit
pre-commit installed at .git/hooks/commit-msg
pre-commit installed at .git/hooks/pre-push
Warning
Чтобы проверить свои изменения, воспользуйтесь командой pre-commit run --all-files
.
Чтобы проверить конкретную задачу, воспользуетесь командой pre-commit run <target> --all-files
.
Если Вы понимаете что творите и хотите пропустить проверку pre-commit
-ом воспользуйтесь --no-verify
, пример git commit -m "Добавил изменения и не хочу проверки" --no-verify
Существует несколько способов как можно взаимодействовать со сборкой образа. Благодаря скрипту1 может существовать 3 способа передачи аргумента в Dockerfile
:
-
Передача 'примерной' версии. В результате передачи данной строки, скрипт попытается найти точную версии, если таковой нет, то будет возвращена пустая строка
## Export Node.js version for 1.7.5 $ export NODEJS_VERSION='10.24-astra1.7.5-slim' ## Node.js image: 194MB docker build \ --progress=plain \ --build-arg node_identity=10.24 \ --build-arg image_version=1.7.5-slim \ -t node:"${NODEJS_VERSION}" \ . .. build ...
-
Передача точной версии
## Export Node.js version for 1.8.2 $ export NODEJS_VERSION='18.19-astra1.8.2-slim' ## Node.js build utils image: 314MB docker build \ --progress=plain \ --build-arg node_identity='18.19.0+dfsg-6~deb12u1+ci2+b1' \ --build-arg image_version=1.8.2-slim \ -t node:"${NODEJS_VERSION}" \ . .. build ...
-
Передача ссылки, на заранее собранный из исходников Node.js
## Export Node.js version for 1.8.2 $ export NODEJS_VERSION='20.18-astra1.8.2-slim' ## Node.js build utils image: 198MB docker build \ --progress=plain \ --build-arg node_identity=https://example-registry.com/repository/node/node-v20.18.0-linux-amd64.tar.gz \ --build-arg image_version=1.8.2-slim \ -t node:"${NODEJS_VERSION}" \ . .. build ...
Tip
Проверка доступных версий приложения -
apt show nodejs
,
apt-cache policy nodejs
,
apt-cache show nodejs
Работа с прокси репозиториями. Логика работы тоже является 'плавающей'2 т.е. позволяет передавать разный набор параметров для Вашего удобства:
-
C
npm_registry_proxy
:## Export Node.js version for 1.8.2 $ export NODEJS_VERSION='18.19-astra1.8.2-slim' docker build \ --progress=plain \ --build-arg image_registry=example-container.registry.com/ \ --build-arg npm_registry_proxy=https://example-registry.com/repository/npm-proxy \ --build-arg node_identity=18.19.0 \ --build-arg image_version=1.8.2-slim \ -t node:"${NODEJS_VERSION}" \ . .. build ...
-
C
package_registry_proxy
:## Export Node.js version for 1.8.2 $ export NODEJS_VERSION='18.19-astra1.8.2-slim' docker build \ --progress=plain \ --build-arg image_registry=example-container.registry.com/ \ --build-arg package_registry_proxy=https://example-registry.com/repository/npm-proxy \ --build-arg node_identity=18.19.0 \ --build-arg image_version=1.8.2-slim \ -t node:"${NODEJS_VERSION}" \ . .. build ...
Имя | Значение по умолчанию | Тип | Описание |
---|---|---|---|
image_name |
astra | string | Имя образа. |
image_registry |
'' | string | Адрес до реестра образа3. |
image_version |
1.8.2-slim | string | Версия образа. |
npm_registry_proxy |
'' | string | Переменная, для установки своего проксирующего репозитория. |
node_identity |
18.19.0 | string | Ожидаемая версия Node.js1. |
yarn_version |
1.22.22 | string | Ожидаемая версия Yarn v14. |
В результате сборки базового образа идёт наполнение файла /etc/environment
. В нём отражены общие переменные, которые могут использоваться в сборочных образах приложений
-
Пример переменных для образа
20.18
установленного из удаленного и скомпилированного Node.js$ cat /etc/environment NODE_REVISION=Installed-from-URL BEGIN_BUILD_IN_EPOCH=1746545461 NODE_MAJOR_MINOR_PATCH_VERSION=20.18.0 NODE_MAJOR_MINOR_VERSION=20.18
-
Пример переменных для образа
18.19
из репозиториев Astra Linux$ cat /etc/environment NODE_REVISION=18.19.0+dfsg-6~deb12u1+ci2+b1 BEGIN_BUILD_IN_EPOCH=1746544357 NODE_MAJOR_MINOR_PATCH_VERSION=18.19.0 NODE_MAJOR_MINOR_VERSION=18.19
-
Пример переменных для образа
10.24
из репозиториев Astra Linux$ cat /etc/environment NODE_REVISION=10.24.0~dfsg-1~deb10u3 BEGIN_BUILD_IN_EPOCH=1746547096 NODE_MAJOR_MINOR_PATCH_VERSION=10.24.0 NODE_MAJOR_MINOR_VERSION=10.24
Для того чтобы начать использовать данный образ, создайте Dockerfile
с простыми настройками
FROM node:18.19-astra1.8.2-slim
WORKDIR /usr/src/app
COPY package*.json ./
USER node
ENV NPM_CONFIG_LOGLEVEL info
RUN npm install
COPY --chown=node:node . .
EXPOSE 8080
CMD [ "node", "app.js" ]
Затем соберите и запустите полученный образ
$ docker build -t my-node-app .
$ docker run -it --rm --name my-running-app my-node-app
...run logic...
Для того, чтобы запустить одиночный файл Node-ы, Вы можете использовать следующую команду
$ docker run -it --rm --name my-running-script -v "$PWD":/usr/src/app -w /usr/src/app node:18.19-astra1.8.2-slim node your-daemon-or-script.js
...run logic...
Простой тест:
docker run --rm node:18.19-astra1.8.2-slim node -e "console.log('Hello from Node.js')"
Данный раздел будет обеспечивать краткие вводные для того, чтобы Вы в дальнейшем могла проектировать свои Scratch
сборки, на примере небольшой утилиты. Все, что демонстрируется, также подкреплено и всеми задействованными скриптами сборочными или специализированными для сборки через scratch
. Все манипуляции поделены на определенное количество 'шагов' для которых будут даны краткие комментарии:
-
Первым этапом устанавливаем целевую программу, оптимизируем бинарный файл Node.js и формируем базовую структуру, которая будет перенесена в
Scratch
## Install base package RUN npm install --global aasvg@"v0.4.2" ## Install build components RUN \ --mount=type=bind,source=./scripts,target=/usr/local/sbin,readonly \ apt-install.sh \ build-essential ## Change path to work dir WORKDIR /opt ## Prepare structure to scratch image RUN \ ## Directory structure and permissions mkdir -p \ /base/bin \ /base/etc \ /base/tmp \ /base/sbin \ /base/root \ /base/usr/share \ /base/usr/local/{bin,lib/node_modules} \ && chmod 700 /base/root \ && chown root:root /base/root \ && chmod 1777 /base/tmp \ ## UID and GID && echo 'root:x:0:' > /base/etc/group \ && echo 'root:x:0:0:root:/root:/sbin/nologin' > /base/etc/passwd \ ## Nologin binary && echo 'int main() { return 1; }' > nologin.c \ && gcc -Os -no-pie -static -std=gnu99 -s -Wall -Werror -o /base/sbin/nologin nologin.c ## Optimize node RUN \ strip --verbose --strip-debug --strip-unneeded "$(which node)"
-
Вторым этапом переносим основную файловую структуру, для оптимальной и минимальной работы приложения
## Copy depended binary # hadolint ignore=SC1091 RUN \ --mount=type=bind,source=./scratch,target=/usr/local/sbin,readonly \ ## Execute transfer ldd /usr/bin copy-bin.sh \ --prefix "/base" \ --ldd "/usr/bin/node" \ --links "/bin:/sbin:/usr/bin:/usr/sbin" \ && copy-bin.sh \ --prefix "/base" \ --ldd "/usr/bin/env" \ --links "/bin:/sbin:/usr/bin:/usr/sbin" \ ## Copy main libs && cp -R /usr/share/nodejs /base/usr/share/nodejs \ && cp -P /usr/share/node_modules /base//usr/share/node_modules \ ## Copy aasvg && ln -nfs /usr/local/lib/node_modules/aasvg/main.js /base/usr/local/bin/aasvg \ && cp -R /usr/local/lib/node_modules/aasvg /base/usr/local/lib/node_modules/aasvg
-
Третьим этапом происходит интеграция со Scratch образом
COPY --from=base-stage /base/ / ## Set environment ENV \ PATH="/usr/bin:/sbin:/bin:/usr/local/bin" \ LANG=C.UTF-8 ENTRYPOINT [ "aasvg" ] CMD [ "-h" ]
Пример сборки: docker build --progress=plain -f Dockerfile-scratch -t aasvg:v0.4.2 .
Проверить работу можем при помощи команды: docker run --rm -i aasvg:v0.4.2 --source --embed < docs/ascii.txt
Полный Dockerfile
:
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
# Base image #
# First stage, prepare environment #
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
FROM node:18.10-astra1.8.2 AS base-stage
SHELL [ "/bin/bash", "-exo", "pipefail", "-c" ]
## Install base package
RUN npm install --global aasvg@"v0.4.2"
## Install build components
RUN \
--mount=type=bind,source=./scripts,target=/usr/local/sbin,readonly \
apt-install.sh \
build-essential
## Change path to work dir
WORKDIR /opt
## Prepare structure to scratch image
RUN \
## Directory structure and permissions
mkdir -p \
/base/bin \
/base/etc \
/base/tmp \
/base/sbin \
/base/root \
/base/usr/share \
/base/usr/local/{bin,lib/node_modules} \
&& chmod 700 /base/root \
&& chown root:root /base/root \
&& chmod 1777 /base/tmp \
## UID and GID
&& echo 'root:x:0:' > /base/etc/group \
&& echo 'root:x:0:0:root:/root:/sbin/nologin' > /base/etc/passwd \
## Nologin binary
&& echo 'int main() { return 1; }' > nologin.c \
&& gcc -Os -no-pie -static -std=gnu99 -s -Wall -Werror -o /base/sbin/nologin nologin.c
## Optimize node
RUN \
strip --verbose --strip-debug --strip-unneeded "$(which node)"
## Copy depended binary
# hadolint ignore=SC1091
RUN \
--mount=type=bind,source=./scratch,target=/usr/local/sbin,readonly \
## Execute transfer ldd /usr/bin
copy-bin.sh \
--prefix "/base" \
--ldd "/usr/bin/node" \
--links "/bin:/sbin:/usr/bin:/usr/sbin" \
&& copy-bin.sh \
--prefix "/base" \
--ldd "/usr/bin/env" \
--links "/bin:/sbin:/usr/bin:/usr/sbin" \
## Copy main libs
&& cp -R /usr/share/nodejs /base/usr/share/nodejs \
&& cp -P /usr/share/node_modules /base//usr/share/node_modules \
## Copy aasvg
&& ln -nfs /usr/local/lib/node_modules/aasvg/main.js /base/usr/local/bin/aasvg \
&& cp -R /usr/local/lib/node_modules/aasvg /base/usr/local/lib/node_modules/aasvg
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
# Final image #
# Second stage, compact optimize layer #
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
FROM scratch
COPY --from=base-stage /base/ /
## Set environment
ENV \
PATH="/usr/bin:/sbin:/bin:/usr/local/bin" \
LANG=C.UTF-8
ENTRYPOINT [ "aasvg" ]
CMD [ "-h" ]
Лого для проекта создано при помощи aasvg
проекта. Вы можете создать такое же и/или модифицировать имеющееся. Для этого воспользуйтесь сайтом или установите figlet
. Если Вы используете способ с установкой figlet
, то вдобавок необходимо сказать необходимый шрифт, например я использую Doom
. Далее, необходимо воспользоваться aasvg
и конвертировать ascii
арт в svg
. Обратите внимание - по умолчанию будет svg в красном цвете, чтобы изменить цвет, необходимо изменить его определение тут
$ curl 'http://www.figlet.org/fonts/doom.flf' -o /usr/share/figlet/doom.flf
$ curl 'http://www.figlet.org/fonts/larry3d.flf' -o /usr/share/figlet/larry3d.flf
$ figlet -f doom 'NodeJs'
_ _ _ ___
| \ | | | | |_ |
| \| | ___ __| | ___ | |___
| . ` |/ _ \ / _` |/ _ \ | / __|
| |\ | (_) | (_| | __/\__/ \__ \
\_| \_/\___/ \__,_|\___\____/|___/
$ aasvg --source --embed < ./docs/ascii.txt > docs/images/logo.svg
![]() Rocket Turtle под авторством qwen.ai.
|
Footnotes
-
🛠️ За счёт скрипта
node-install-approximately.sh
нас может не волновать полная версия Node.js, мы можем передавать лишь приблизительно желаемую версию, а скрипт позаботится чтобы была выбрана последняя и актуальная из списка ↩ ↩2 -
🛠️ За счёт скрипта
node-set-proxy.sh
мы можем пользоваться и другим набором аргументов, таких как:npm_registry_proxy
илиpackage_registry_proxy
↩ -
🛠️ Например можно использовать свой приватный реестр образов:
--build-arg image_registry=my-container-registry:1111/
↩ -
🛠️ За счёт скрипта
node-install-yarn.sh
мы можем динамически устанавливать любую версию yarn из реестра пакетов npm ↩