arm64 环境利用 docker 编译 redis filebeat airflow hue 以及 alertmanager 镜像

本文涉及的产品
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
云数据库 Tair(兼容Redis),内存型 2GB
简介: arm64 环境利用 docker 编译 redis filebeat airflow hue 以及 alertmanager 镜像

先准备一个编译环境压压惊

  • 首先要有一个 docker

部署 docker

wget https://download.docker.com/linux/static/stable/aarch64/docker-19.03.11.tgz
tar xvf docker-19.03.11.tgz
mv docker/* /usr/bin/
docker.service
cat <<EOF> /usr/lib/systemd/system/docker.service
[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
BindsTo=containerd.service
After=network-online.target firewalld.service containerd.service
Wants=network-online.target
Requires=docker.socket
 
[Service]
Type=notify
# the default is not to use systemd for cgroups because the delegate issues still
# exists and systemd currently does not support the cgroup feature set required
# for containers run by docker
ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
ExecReload=/bin/kill -s HUP \$MAINPID
TimeoutSec=0
RestartSec=2
Restart=always
 
# Note that StartLimit* options were moved from "Service" to "Unit" in systemd 229.
# Both the old, and new location are accepted by systemd 229 and up, so using the old location
# to make them work for either version of systemd.
StartLimitBurst=3
 
# Note that StartLimitInterval was renamed to StartLimitIntervalSec in systemd 230.
# Both the old, and new name are accepted by systemd 230 and up, so using the old name to make
# this option work for either version of systemd.
StartLimitInterval=60s
 
# Having non-zero Limit*s causes performance problems due to accounting overhead
# in the kernel. We recommend using cgroups to do container-local accounting.
LimitNOFILE=infinity
LimitNPROC=infinity
LimitCORE=infinity
 
# Comment TasksMax if your systemd version does not support it.
# Only systemd 226 and above support this option.
TasksMax=infinity
# set delegate yes so that systemd does not reset the cgroups of docker containers
Delegate=yes
 
# kill only the docker process, not all processes in the cgroup
KillMode=process
 
[Install]
WantedBy=multi-user.target
EOF
docker.socket
cat <<EOF> /usr/lib/systemd/system/docker.socket
[Unit]
Description=Docker Socket for the API
PartOf=docker.service
 
[Socket]
ListenStream=/var/run/docker.sock
SocketMode=0660
SocketUser=root
SocketGroup=docker
 
[Install]
WantedBy=sockets.targe
EOF
containerd.service
cat <<EOF> /usr/lib/systemd/system/containerd.service
#   Copyright 2018-2020 Docker Inc.
 
#   Licensed under the Apache License, Version 2.0 (the "License");
#   you may not use this file except in compliance with the License.
#   You may obtain a copy of the License at
 
#       http://www.apache.org/licenses/LICENSE-2.0
 
#   Unless required by applicable law or agreed to in writing, software
#   distributed under the License is distributed on an "AS IS" BASIS,
#   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
#   See the License for the specific language governing permissions and
#   limitations under the License.
 
[Unit]
Description=containerd container runtime
Documentation=https://containerd.io
After=network.target
 
[Service]
ExecStartPre=-/sbin/modprobe overlay
ExecStart=/usr/bin/containerd
KillMode=process
Delegate=yes
LimitNOFILE=1048576
# Having non-zero Limit*s causes performance problems due to accounting overhead
# in the kernel. We recommend using cgroups to do container-local accounting.
LimitNPROC=infinity
LimitCORE=infinity
TasksMax=infinity
 
[Install]
WantedBy=multi-user.target
EOF
daemon.json
groupadd docker
mkdir /etc/docker/
cat > /etc/docker/daemon.json <<EOF
   {
    "live-restore": true,
    "exec-opts": ["native.cgroupdriver=systemd"],
    "log-driver": "json-file",
    "registry-mirrors": ["https://v16stybc.mirror.aliyuncs.com"],
    "log-opts": {
       "max-size": "100m"
    },
    "storage-driver": "overlay2",
    "storage-opts": [
    "overlay2.override_kernel_check=true"
    ]
    }
EOF

准备镜像

FROM centos:7
ARG work_dir=/usr/local

ENV PS1='\[\e[7;34m\]\u@\h\[\e[0m\]\[\e[0;35m\]:$(pwd) \[\e[0m\]\[\e[0;35m\]\t\[\e[0m\]\n\[\e[0;32m\]> \[\e[0m\]'
ENV LANG=en_US.UTF-8
ENV TZ="Asia/Shanghai"
ENV GOPATH=/usr/local/src
ENV GOPROXY=https://goproxy.cn
ENV GO_HOME=${work_dir}/go
ENV PATH=${PATH}:${GO_HOME}/bin

WORKDIR ${work_dir}
ADD ./go1.17.9.linux-arm64.tar.gz ./
RUN curl -o /etc/yum.repos.d/ http://mirrors.aliyun.com/repo/Centos-altarch-7.repo  && \
    yum install -y wget vim unzip bash-completion git gcc gcc-c++ make cmake protobuf-* automake libtool zlib-devel openssl-devel && \
    yum clean all && \
    echo '/usr/bin/sleep 315360000' > start.sh && \
    chmod +x start.sh
CMD ["/usr/bin/bash","start.sh"]
以 host 网络模式来 build docker 镜像

nat 模式局限性比较大,很多网络会超时

docker build --network host -t go_make:arm64_1.17.9 .
把容器放后台启动,方便进进出出
docker run -d --network host --name make_some_thing go_make:arm64_1.17.9
进入容器
docker exec -it make_some_thing bash

修改 go 模块的下载地址为国内

go env -w GOPROXY=https://goproxy.cn

编译 redis

wget https://download.redis.io/releases/redis-4.0.14.tar.gz
tar xvf redis-4.0.14.tar.gz
cd redis-4.0.14/
make
make install
查看 redis 版本,验证编译是否成功
./src/redis-cli --version

其他细节

`GLIBC_2.28' not found
  • 编译好的 redis-server 拿到其他环境,可能会出现的问题
redis-server: /lib64/libc.so.6: version `GLIBC_2.28' not found
GLIBC 2.8 对于 make 的版本有要求,不能低于 4.x ,我们这边用 4.2 版本的

不升级 make ,编译的时候会报错 These critical programs are missing or too old: make bison compiler

编译 make
wget https://ftp.gnu.org/gnu/make/make-4.2.tar.gz --no-check-certificate
tar xvf make-4.2.tar.gz
cd make-4.2/
./configure && make -j $(nproc) && make install
mv /usr/bin/make{,-$(make --version | head -1 | awk '{print $NF}')}
mv make /usr/bin/
查看 make 版本,验证编译是否成功
make --version
编译 glibc 2.8
  • 升级 gcc

    • These critical programs are missing or too old: bison compiler
    • 编译的时候会有上面的报错表示 gcc 版本太低了,最少要 gcc-7
yum install -y centos-release-scl bison
yum install -y devtoolset-7-gcc devtoolset-7-gcc-c++ devtoolset-7-binutils
# 使环境生效,通过 gcc -v 可以查看版本已经变成 7.x了
scl enable devtoolset-7 bash
# 永久生效
echo "source /opt/rh/devtoolset-7/enable" >>/etc/profile
source /etc/profile
  • 编译 glibc 2.8
切记, glibc 2.8 不要在 /usr/local 目录下编译,编译的时候会有下面这样的提示,要使用 --prefix 指定路径
*** On GNU/Linux systems the GNU C Library should not be installed into
*** /usr/local since this might make your system totally unusable.
*** We strongly advise to use a different prefix.  For details read the FAQ.
*** If you really mean to do this, run configure again using the extra
*** parameter `--disable-sanity-checks'.
wget https://ftp.gnu.org/gnu/glibc/glibc-2.28.tar.xz --no-check-certificate
tar xvf glibc-2.28.tar.xz
cd glibc-2.28
# 为什么要建一个新目录?
## 因为直接执行'./configure',会报错'configure: error: you must configure in a separate build directory'
mkdir build
cd build/
mkdir /lib64/glibc-2.28/etc
# 可能会遇到这个报错:Warning: ignoring configuration file that cannot be opened: /lib64/glibc-2.28/etc/ld.so.conf: No such file or directory
## find 查找一下文件,然后做个软连接就可以了
ln -s $(find / -name "ld.so.conf") /lib64/glibc-2.28/etc/ld.so.conf
../configure --prefix=/lib64/glibc-2.28 && make -j $(nproc) && make install

编译 filebeat

wget https://github.com/elastic/beats/archive/refs/tags/v7.7.0.tar.gz
tar xvf v7.7.0.tar.gz
cd beats-7.7.0/filebeat
make
执行的时候会有一段时间终端没有任务输出,耐心等待就可以了,输出类似如下内容,表示编译完成
fatal: Not a git repository (or any of the parent directories): .git
go build -ldflags "-X github.com/elastic/beats/libbeat/version.buildTime=2022-04-29T08:21:45Z -X github.com/elastic/beats/libbeat/version.commit="
go: downloading github.com/imdario/mergo v0.3.6
go: downloading github.com/urso/go-bin v0.0.0-20180220135811-781c575c9f0e
go: downloading github.com/google/gofuzz v1.0.0
go: downloading github.com/davecgh/go-spew v1.1.1
go: downloading github.com/google/go-cmp v0.4.0
go: downloading github.com/json-iterator/go v1.1.7
go: downloading github.com/modern-go/reflect2 v1.0.1
go: downloading google.golang.org/grpc v1.27.1
go: downloading github.com/containerd/containerd v1.3.3
go: downloading github.com/sirupsen/logrus v1.4.2
go: downloading github.com/docker/distribution v2.7.1+incompatible
go: downloading github.com/eapache/queue v1.1.0
go: downloading github.com/pierrec/lz4 v2.2.6+incompatible
go: downloading github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21
go: downloading github.com/eapache/go-resiliency v1.1.0
go: downloading github.com/hashicorp/go-uuid v1.0.1
go: downloading gopkg.in/jcmturner/dnsutils.v1 v1.0.1
go: downloading gopkg.in/jcmturner/aescts.v1 v1.0.1
go: downloading gopkg.in/jcmturner/rpc.v1 v1.1.0
go: downloading github.com/golang/snappy v0.0.1
go: downloading github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd
go: downloading google.golang.org/genproto v0.0.0-20191230161307-f3c370f40bfb
查看 filebeat 版本,验证编译是否成功
./filebeat version
从容器内打包的时候,需要注意一个细节,在宿主机上执行 file filebeat 命令会看到有 lib 文件依赖,在其他环境使用的时候,也要注意把 lib 文件复制过去

通过 file 命令可以看到,依赖的 lib 文件的路径和名称为 /lib/ld-linux-aarch64.so.1

filebeat-7.7.0-linux-arm64/filebeat: ELF 64-bit LSB executable, ARM aarch64, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-aarch64.so.1, for GNU/Linux 3.7.0, Go BuildID=2ZFlNlPqOIS1j0hZOMLt/zmkml0JZODmFUTnWldZe/wMGZe6JzkJmCcs5EeF-6/ID26ze0hYOJZMk5gMX19, BuildID[sha1]=438f66d9c4384ccde3a4a395034160565df6280e, not stripped

安装 airflow

yum install -y python3 python3-devel python3-pip
pip3 install --upgrade pip
pip3 install apache-airflow==2.2.3

升级 sqlite3

官方要求 airflow 2.0+ 版本的环境, python 的 sqlite3 版本不能低于 3.15.0

arm 环境下载的 python 3.6 使用的 sqlite3 版本是 3.7.17 的,运行 airflow --version 会报错 error: sqlite C library version too old (< 3.15.0)

Python 3.6.8 (default, Nov 16 2020, 16:33:14)
[GCC 4.8.5 20150623 (Red Hat 4.8.5-44)] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import sqlite3
>>> sqlite3.sqlite_version
'3.7.17'
wget --no-check-certificate https://sqlite.org/2022/sqlite-autoconf-3380400.tar.gz
tar xvf sqlite-autoconf-3380400.tar.gz
cd sqlite-autoconf-3380400/
export CFLAGS="-DSQLITE_ENABLE_FTS3 \
    -DSQLITE_ENABLE_FTS3_PARENTHESIS \
    -DSQLITE_ENABLE_FTS4 \
    -DSQLITE_ENABLE_FTS5 \
    -DSQLITE_ENABLE_JSON1 \
    -DSQLITE_ENABLE_LOAD_EXTENSION \
    -DSQLITE_ENABLE_RTREE \
    -DSQLITE_ENABLE_STAT4 \
    -DSQLITE_ENABLE_UPDATE_DELETE_LIMIT \
    -DSQLITE_SOUNDEX \
    -DSQLITE_TEMP_STORE=3 \
    -DSQLITE_USE_URI \
    -O2 \
    -fPIC"
export PREFIX="/usr/local/sqlite3"
LIBS="-lm" ./configure --disable-tcl --enable-shared --enable-tempstore=always --prefix="$PREFIX"
make -j $(nproc)
make install
这里的 /usr/local 要和上面编译的时候 --prefix 路径一致
export LD_LIBRARY_PATH=/usr/local/sqlite3/lib:$LD_LIBRARY_PATH
查看 airflow 版本,验证编译是否成功
airflow version

编译 hue

安装相关依赖

  • 编译 hue 需要安装 python-devel 否则 make 的时候会报错:/usr/local/hue-release-4.7.1/Makefile.vars:65: *** "Error: must have python development packages for python2.7. Could not find Python.h. Please install python2.7-devel". Stop
  • 不安装 libffi-devel ,pip 安装 cffi 的时候会报错:fatal error: ffi.h: No such file or directory
  • 不安装 MySQL-python,pip 安装 mysql-python 会报错:EnvironmentError: mysql_config not found
  • 不安装 mysql-devel,pip 安装 mysql-python 会报错:EnvironmentError: mysql_config not found
  • 不安装 sqlite-devel ,编译的时候会报错:fatal error: sqlite3.h: No such file or directory
  • 不安装 cyrus-sasl-devel,编译的时候会报错:fatal error: sasl/sasl.h: No such file or directory
  • 不安装 openldap-devel,编译的时候会报错:fatal error: lber.h: No such file or directory
  • 不安装 libxslt-devel,编译的时候会报错:fatal error: libxml/xmlversion.h: No such file or directory
yum install -y python-devel \
libffi-devel \
MySQL-python \
mysql-devel \
sqlite-devel \
cyrus-sasl-devel \
openldap-devel \
libxslt-devel
安装 nodejs
如何确定 nodejs 的版本

下载好 hue 的安装包,解压后进入 hue 的路径下,执行下面的命令

grep setup tools/container/base/hue/Dockerfile
curl -sL https://rpm.nodesource.com/setup_10.x 这里就可以看到,用到的是 10.x 的版本
wget https://nodejs.org/dist/v10.19.0/node-v10.19.0-linux-arm64.tar.gz
tar xvf node-v10.19.0-linux-arm64.tar.gz
echo 'export NODE_HOME=/usr/local/node-v10.19.0-linux-arm64' >> /etc/profile
echo 'export PATH=$PATH:$NODE_HOME/bin' >> /etc/profile
source /etc/profile
# 验证环境变量是否生效
node -v
npm -v

开始编译

wget https://github.com/cloudera/hue/archive/refs/tags/release-4.7.1.tar.gz
tar xvf release-4.7.1.tar.gz
cd hue-release-4.7.1/
build/env/bin/python2.7 -m pip install cffi \
mysql-python \
traitlets \
backports.shutil-get-terminal-size \
pathlib2 \
pexpect \
pickleshare \
simplegeneric==0.8.1 \
prompt-toolkit==1.0.4 
make apps
通过 cat tools/container/base/hue/Dockerfile 可以看到 hue 的编译需要解决的依赖,但是我为了让镜像更小,能不装的就不装,所以在一步一步的试错
报错1
distutils.errors.DistutilsError: Command '['/usr/local/hue-release-4.7.1/build/env/bin/python2.7', '-m', 'pip', '--disable-pip-version-check', 'wheel', '--no-deps', '-w', '/usr/local/hue-release-4.7.1/desktop/core/ext-py/cryptography-2.9/temp/tmpojt9TZ', '--quiet', 'cffi!=1.11.3,>=1.8']' returned non-zero exit status 1
build/env/bin/python2.7 -m pip install cffi
报错2
sh: mysql_config: command not found
build/env/bin/python2.7 -m pip install mysql-python
报错3

` File "/tmp/easy_install-_GDIGO/traitlets-5.1.1/setup.py", line 41

print(error, file=sys.stderr)`
build/env/bin/python -m pip install traitlets
报错4
` ERROR: pip's legacy dependency resolver does not consider dependency conflicts when selecting packages. This behaviour is the source of the following dependency conflicts.
ipython 5.2.0 requires backports.shutil-get-terminal-size, which is not installed.
ipython 5.2.0 requires pathlib2, which is not installed.
ipython 5.2.0 requires pexpect, which is not installed.
ipython 5.2.0 requires pickleshare, which is not installed.
ipython 5.2.0 requires prompt-toolkit<2.0.0,>=1.0.4, which is not installed.
ipython 5.2.0 requires simplegeneric>0.8, which is not installed.`
build/env/bin/python -m pip install backports.shutil-get-terminal-size \
pathlib2 \
pexpect \
pickleshare \
prompt-toolkit==1.0.4 \
simplegeneric==0.8.1 

制作 alertmanager 镜像

获取二进制文件

alertmanager github

wget https://github.com/prometheus/alertmanager/releases/download/v0.14.0/alertmanager-0.14.0.linux-arm64.tar.gz
tar xvf alertmanager-0.14.0.linux-arm64.tar.gz
mv alertmanager-0.14.0.linux-arm64/a* .
vim config.yaml
route:
  group_by: ['alertname']
  group_wait: 30s
  group_interval: 5m
  repeat_interval: 1h
  receiver: 'web.hook'
receivers:
  - name: 'web.hook'
    webhook_configs:
      - url: 'http://127.0.0.1:5001/'
inhibit_rules:
  - source_match:
      severity: 'critical'
    target_match:
      severity: 'warning'
    equal: ['alertname', 'dev', 'instance']
利用 busybox 来制作 alertmanager 镜像 (因为 busybox 很小)
FROM busybox:latest

COPY amtool /bin/amtool
COPY alertmanager /bin/alertmanager
COPY config.yml /etc/alertmanager/config.yml

RUN mkdir -p /alertmanager && \
    chown -R nobody:nobody etc/alertmanager /alertmanager

USER       nobody
EXPOSE     9093
VOLUME     [ "/alertmanager" ]
WORKDIR    /alertmanager
ENTRYPOINT [ "/bin/alertmanager" ]
CMD        [ "--config.file=/etc/alertmanager/config.yml", \
             "--storage.path=/alertmanager" ]
docker build -t prom/alertmanager:v0.14.0 .
相关实践学习
基于Redis实现在线游戏积分排行榜
本场景将介绍如何基于Redis数据库实现在线游戏中的游戏玩家积分排行榜功能。
云数据库 Redis 版使用教程
云数据库Redis版是兼容Redis协议标准的、提供持久化的内存数据库服务,基于高可靠双机热备架构及可无缝扩展的集群架构,满足高读写性能场景及容量需弹性变配的业务需求。 产品详情:https://www.aliyun.com/product/kvstore &nbsp; &nbsp; ------------------------------------------------------------------------- 阿里云数据库体验:数据库上云实战 开发者云会免费提供一台带自建MySQL的源数据库&nbsp;ECS 实例和一台目标数据库&nbsp;RDS实例。跟着指引,您可以一步步实现将ECS自建数据库迁移到目标数据库RDS。 点击下方链接,领取免费ECS&amp;RDS资源,30分钟完成数据库上云实战!https://developer.aliyun.com/adc/scenario/51eefbd1894e42f6bb9acacadd3f9121?spm=a2c6h.13788135.J_3257954370.9.4ba85f24utseFl
目录
相关文章
|
25天前
|
NoSQL Linux Redis
Docker学习二(Centos):Docker安装并运行redis(成功运行)
这篇文章介绍了在CentOS系统上使用Docker安装并运行Redis数据库的详细步骤,包括拉取Redis镜像、创建挂载目录、下载配置文件、修改配置以及使用Docker命令运行Redis容器,并检查运行状态和使用Navicat连接Redis。
183 3
|
1月前
|
存储 NoSQL 大数据
大数据-51 Redis 高可用方案CAP-AP 主从复制 一主一从 全量和增量同步 哨兵模式 docker-compose测试
大数据-51 Redis 高可用方案CAP-AP 主从复制 一主一从 全量和增量同步 哨兵模式 docker-compose测试
31 3
|
1月前
|
消息中间件 NoSQL Kafka
Flink-10 Flink Java 3分钟上手 Docker容器化部署 JobManager TaskManager Kafka Redis Dockerfile docker-compose
Flink-10 Flink Java 3分钟上手 Docker容器化部署 JobManager TaskManager Kafka Redis Dockerfile docker-compose
33 4
|
2月前
|
应用服务中间件 nginx Docker
Docker镜像-基于DockerFile制作编译版nginx镜像
这篇文章介绍了如何基于Dockerfile制作一个编译版的nginx镜像,并提供了详细的步骤和命令。
375 17
Docker镜像-基于DockerFile制作编译版nginx镜像
|
2月前
|
NoSQL 关系型数据库 Redis
mall在linux环境下的部署(基于Docker容器),Docker安装mysql、redis、nginx、rabbitmq、elasticsearch、logstash、kibana、mongo
mall在linux环境下的部署(基于Docker容器),docker安装mysql、redis、nginx、rabbitmq、elasticsearch、logstash、kibana、mongodb、minio详细教程,拉取镜像、运行容器
mall在linux环境下的部署(基于Docker容器),Docker安装mysql、redis、nginx、rabbitmq、elasticsearch、logstash、kibana、mongo
|
1月前
|
NoSQL MongoDB Docker
求助,有没有大神可以找到arm64架构下mongodb的3.6.8版本的docker镜像?
在Docker Hub受限的情况下,寻求适用于ARM架构的docker镜像资源或拉取链接,以便在x86架构上获取;内网中的机器为ARM架构,因此优先请求适合ARM的Docker镜像或Dockerfile,非常感激您的帮助。
|
1月前
|
缓存 NoSQL Redis
docker运行redis镜像
这篇文章介绍了如何使用Docker运行Redis镜像,并提供了启动和配置Redis容器的具体命令和步骤。
91 0
|
3月前
|
Android开发 Docker 容器
docker中编译android aosp源码,出现Build sandboxing disabled due to nsjail error
在使用Docker编译Android AOSP源码时,如果遇到"Build sandboxing disabled due to nsjail error"的错误,可以通过在docker run命令中添加`--privileged`参数来解决权限不足的问题。
500 1
|
3月前
|
NoSQL Redis 数据安全/隐私保护
深入探索利用Docker安装Redis
【8月更文挑战第27天】
216 2
|
3月前
|
NoSQL 数据可视化 Linux
一文教会你如何在Linux系统中使用Docker安装Redis 、以及如何使用可视化工具连接【详细过程+图解】
这篇文章详细介绍了如何在Linux系统中使用Docker安装Redis,并提供了使用可视化工具连接Redis的步骤。内容包括安装Redis镜像、创建外部配置文件、映射文件和端口、启动和测试Redis实例、配置数据持久化存储,以及使用可视化工具连接和操作Redis数据库的过程。