如何在 amazonlinux2 上获取 node18?

如何在 amazonlinux2 上获取 node18?

我目前正在尝试在 amazoncorretto:11 基础映像上安装 node18。我收到错误

#6 11.04 Error: Package: 2:nodejs-18.16.0-1nodesource.x86_64 (nodesource)
#6 11.04            Requires: libc.so.6(GLIBC_2.28)(64bit)
#6 11.04 Error: Package: 2:nodejs-18.16.0-1nodesource.x86_64 (nodesource)
#6 11.04            Requires: libm.so.6(GLIBC_2.27)(64bit)

描述如下:https://github.com/nodesource/distributions/issues/1381

我想我需要将 glibc 更新到支持 node18 的版本,但这在 amazonlinux2 上可行吗?

答案1

答案位于:
Node.js 18编译为glibc 2.28
虽然非常不能令人满意,但肯定是正确的。

您无法在系统上运行二进制文件,因为它依赖glibc无法使用在您的系统上。

$ docker run -it amazoncorretto:11 bash
bash-4.2# cat /etc/os-release
NAME="Amazon Linux"
VERSION="2"
ID="amzn"
ID_LIKE="centos rhel fedora"
VERSION_ID="2"
PRETTY_NAME="Amazon Linux 2"
ANSI_COLOR="0;33"
CPE_NAME="cpe:2.3:o:amazon:amazon_linux:2"
HOME_URL="https://amazonlinux.com/"
bash-4.2# rpm -q --provides glibc|grep -i libc.so
libc.so.6()(64bit)
libc.so.6(GLIBC_2.10)(64bit)
libc.so.6(GLIBC_2.11)(64bit)
libc.so.6(GLIBC_2.12)(64bit)
libc.so.6(GLIBC_2.13)(64bit)
libc.so.6(GLIBC_2.14)(64bit)
libc.so.6(GLIBC_2.15)(64bit)
libc.so.6(GLIBC_2.16)(64bit)
libc.so.6(GLIBC_2.17)(64bit)
libc.so.6(GLIBC_2.18)(64bit)
libc.so.6(GLIBC_2.2.5)(64bit)
libc.so.6(GLIBC_2.2.6)(64bit)
libc.so.6(GLIBC_2.22)(64bit)
libc.so.6(GLIBC_2.23)(64bit)
libc.so.6(GLIBC_2.24)(64bit)
libc.so.6(GLIBC_2.25)(64bit)
libc.so.6(GLIBC_2.26)(64bit)
libc.so.6(GLIBC_2.3)(64bit)
libc.so.6(GLIBC_2.3.2)(64bit)
libc.so.6(GLIBC_2.3.3)(64bit)
libc.so.6(GLIBC_2.3.4)(64bit)
libc.so.6(GLIBC_2.4)(64bit)
libc.so.6(GLIBC_2.5)(64bit)
libc.so.6(GLIBC_2.6)(64bit)
libc.so.6(GLIBC_2.7)(64bit)
libc.so.6(GLIBC_2.8)(64bit)
libc.so.6(GLIBC_2.9)(64bit)

它最多仅支持GLIBC_2.26

并且amazoncorretto:latest仅支持最多glibc 2.26

$ docker run -it amazoncorretto bash
bash-4.2# cat /etc/os-release
NAME="Amazon Linux"
VERSION="2"
ID="amzn"
ID_LIKE="centos rhel fedora"
VERSION_ID="2"
PRETTY_NAME="Amazon Linux 2"
ANSI_COLOR="0;33"
CPE_NAME="cpe:2.3:o:amazon:amazon_linux:2"
HOME_URL="https://amazonlinux.com/"
bash-4.2# rpm -q --provides glibc|grep -i libc.so
libc.so.6()(64bit)
libc.so.6(GLIBC_2.10)(64bit)
libc.so.6(GLIBC_2.11)(64bit)
libc.so.6(GLIBC_2.12)(64bit)
libc.so.6(GLIBC_2.13)(64bit)
libc.so.6(GLIBC_2.14)(64bit)
libc.so.6(GLIBC_2.15)(64bit)
libc.so.6(GLIBC_2.16)(64bit)
libc.so.6(GLIBC_2.17)(64bit)
libc.so.6(GLIBC_2.18)(64bit)
libc.so.6(GLIBC_2.2.5)(64bit)
libc.so.6(GLIBC_2.2.6)(64bit)
libc.so.6(GLIBC_2.22)(64bit)
libc.so.6(GLIBC_2.23)(64bit)
libc.so.6(GLIBC_2.24)(64bit)
libc.so.6(GLIBC_2.25)(64bit)
libc.so.6(GLIBC_2.26)(64bit)
libc.so.6(GLIBC_2.3)(64bit)
libc.so.6(GLIBC_2.3.2)(64bit)
libc.so.6(GLIBC_2.3.3)(64bit)
libc.so.6(GLIBC_2.3.4)(64bit)
libc.so.6(GLIBC_2.4)(64bit)
libc.so.6(GLIBC_2.5)(64bit)
libc.so.6(GLIBC_2.6)(64bit)
libc.so.6(GLIBC_2.7)(64bit)
libc.so.6(GLIBC_2.8)(64bit)
libc.so.6(GLIBC_2.9)(64bit)

无法更新你的glibc图书馆,因为它是Linux 内核。当您迁移到较新的操作系统版本

让它在你的系统上运行的方法是重建它来自源代码适合您的系统并将其打包以便于轻松重现安装。

您可以从以下位置设置 docker 镜像amazoncorretto基础映像封装环境设置。

构建于打包 Docker 主机可安装在所有amazoncorretto:11系统。

有用的是预先构建的.spec文件,可以在以下位置找到:
NodeJS .spec文件
然后你只需要构建你的rpmbuild环境来创建可安装的NodeJS .rpm包裹。

AWSNodeJSLambda 运行器:

@Rich 提到了public.ecr.aws/lambda/nodejs:18AWS Lambda Runner 镜像。
这是一个旨在运行NodeJS在启动时使用 dockerfile 指令来执行任务CMD
实际上,对于某些单次射击任务(它的设计目的)或直接启动ExpressJSWeb 应用程序.
缺点是无法独立更新NodeJS引擎无需升级整个基础镜像,因为NodeJS引擎未作为系统包安装。


$ docker run -it public.ecr.aws/lambda/nodejs:18 
19 Jun 2023 09:53:51,148 [INFO] (rapid) exec '/var/runtime/bootstrap' (cwd=/var/task, handler=)


^C19 Jun 2023 09:54:26,776 [INFO] (rapid) Received signal signal=interrupt
19 Jun 2023 09:54:26,776 [INFO] (rapid) Shutting down...
19 Jun 2023 09:54:26,776 [WARNING] (rapid) Reset initiated: SandboxTerminated
19 Jun 2023 09:54:26,776 [INFO] (rapid) Stopping runtime domain
19 Jun 2023 09:54:26,776 [INFO] (rapid) Waiting for runtime domain processes termination
19 Jun 2023 09:54:26,776 [INFO] (rapid) Stopping operator domain
19 Jun 2023 09:54:26,776 [INFO] (rapid) Starting runtime domain
$ docker run --entrypoint bash -it public.ecr.aws/lambda/nodejs:18
bash-4.2# rpm -qa|grep -i node|wc -l
0
bash-4.2# node --version
v18.16.0
bash-4.2# npm --version
9.5.1
bash-4.2# cat /lambda-entrypoint.sh
#!/bin/sh
# Copyright 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.

if [ $# -ne 1 ]; then
  echo "entrypoint requires the handler name to be the first argument" 1>&2
  exit 142
fi
export _HANDLER="$1"

RUNTIME_ENTRYPOINT=/var/runtime/bootstrap
if [ -z "${AWS_LAMBDA_RUNTIME_API}" ]; then
  exec /usr/local/bin/aws-lambda-rie $RUNTIME_ENTRYPOINT
else
  exec $RUNTIME_ENTRYPOINT
fi
bash-4.2# ls -lah /usr/local/bin/aws-lambda-rie
-rwxr-xr-x 1 root root 5.6M Jun 12 13:21 /usr/local/bin/aws-lambda-rie
bash-4.2# ls -lah /etc/yum.repos.d
total 12K
drwxr-xr-x 2 root root 4.0K Jun 23  2022 .
drwxr-xr-x 1 root root 4.0K Jun 19 09:57 ..
-rw-r--r-- 1 root root 1003 Oct 26  2021 amzn2-core.repo

答案2

基于 Bodo Hugo Barwich 的回答和 Rich 的评论:

如果您不想直接使用 Docker 镜像 public.ecr.aws/lambda/nodejs:18,您可以通过多阶段构建将节点从该镜像复制到您自己的镜像中:

FROM public.ecr.aws/lambda/nodejs:18 as nodesource

FROM amazonlinux:2
ENV PATH="$PATH:/var/lang/bin"
COPY --from=nodesource /var/lang /var/lang

RUN npm i whatever

答案3

可以使用以下脚本在 RHEL7 和 Amazon Linux 2 上从源代码编译 NodeJS v18 和 v20:

#!/bin/bash

# install YUM package preques
sudo yum -y update
sudo yum groupinstall -y "Development Tools"
sudo yum install -y git libffi-devel openssl-devel openssl-devel \
  dbus-devel p11-kit-devel \
  python3-devel pip3 rust cargo clang llvm-devel readline-devel \
  libcurl-devel expat-devel libarchive-devel libpng-devel \
  libspectre-devel bzip2-devel brotli-devel gperf libjpeg-turbo-devel \
  openjpeg2-devel libtiff-devel lcms2-devel \
  gcc10-c++ gcc10-gdb-plugin gcc10-plugin-devel gcc10 gcc10-binutils \
  gcc10-binutils-devel gcc10-binutils-gold clang-devel clang-tools-extra

# Python script helps fetch the most current version of NodeJS v18 or v20
cat << "EOL" > "nodejs_version.py"
import sys
import re
import urllib.request

def usage():
    sys.stderr.write(f'usage: {sys.argv[0]} <node-ver: 18 or 20>')
    sys.exit(1)

def node_version_fetch(url, src_re):
    with urllib.request.urlopen(url) as response:
        html = response.read().decode('utf-8')
        return src_re.search(html)

try:
    node_ver = sys.argv[1]
except (IndexError):
    usage()

nver_src_mo = node_version_fetch(
    f'https://nodejs.org/download/release/latest-v{node_ver}.x/',
    re.compile(f'node-v{node_ver}\.(\d+)\.(\d+)\.tar\.gz', re.M)
)
node_full_ver = f'{node_ver}.{nver_src_mo.group(1)}.{nver_src_mo.group(2)}'
print(node_full_ver)
EOL

# fetch most current version of NodeJS
NODE_MAJOR_VERSION=20
NODE_VERSION=$(python3 nodejs_version.py ${NODE_MAJOR_VERSION})
echo "BUILDING NODEJS VERSION=${NODE_VERSION}"

# prepare envionment
BUILDDIR=build-v${NODE_VERSION}
NODE_DIR=node-v${NODE_VERSION}
SOURCE_URL="https://nodejs.org/dist/v${NODE_VERSION}/${NODE_DIR}.tar.gz"
PREFIX=/opt/node/${NODE_DIR}
NPROC=$(nproc)
CC=gcc10-gcc
CXX=gcc10-g++
export CC CXX

# build, test, install
rm -rf ${BUILDDIR}
mkdir -p ${BUILDDIR}
pushd ${BUILDDIR}
wget "${SOURCE_URL}"
tar xf ${NODE_DIR}.tar.gz
pushd ${NODE_DIR}
./configure --prefix=${PREFIX}
make clean
make -j${NPROC}
make -j${NPROC} test-only
sudo make -j${NPROC} install
popd
popd

答案4

多个 AWS 团队已为 Amazon Linux 2 编译了 NodeJS v18.x 的二进制文件。您可以在与 ElasticBeanstalk 和 Cloud9 资源相关的 CloudWatch 日志中找到它们。

借用 Cloud9 团队的二进制文件,您可以在基于 Amazon Linux 2 的主机上安装 NodeJS 版本。

wget -nv https://d3rnber7ry90et.cloudfront.net/linux-x86_64/node-v18.17.1.tar.gz
mkdir /usr/local/lib/node
tar -xf node-v18.17.1.tar.gz
mv node-v18.17.1 /usr/local/lib/node/nodejs
### Unload NVM, use the new node in the path, then install some items globally.
echo "export NVM_DIR=''" >> /home/ec2-user/.bashrc
echo "export NODEJS_HOME=/usr/local/lib/node/nodejs" >> /home/ec2-user/.bashrc
echo "export PATH=\$NODEJS_HOME/bin:\$PATH" >> /home/ec2-user/.bashrc
### Reload environment
. /home/ec2-user/.bashrc
### Verify NodeJS v18.x is operating
node -e "console.log('Running Node.js ' + process.version)"

相关内容