如何设置 Alpine Linux 镜像
简介
本文档描述了如何设置 Alpine Linux 镜像,并通过 http 和 rsync 使其可用。
我们将
- 创建存放镜像的目录
- 设置一个 cron 任务,每小时与主镜像同步
- 设置 lighttpd 用于 http 访问
- 设置 rsync,以便其他镜像可以从您这里 rsync
确保您有足够的磁盘空间。
当前 (2024-12-31) 磁盘使用量 (GB)
edge | v3.0 | v3.1 | v3.2 | v3.3 | v3.4 | v3.5 | v3.6 | v3.7 | v3.8 | v3.9 | v3.10 | v3.11 | v3.12 | v3.13 | v3.14 | v3.15 | v3.16 | v3.17 | v3.18 | v3.19 | v3.20 | v3.21 | 总计 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
499 | 17 | 18 | 15 | 21 | 25 | 27 | 45 | 43 | 59 | 73 | 92 | 126 | 148 | 156 | 181 | 194 | 209 | 244 | 298 | 288 | 361 | 400 | 3538 |
用于计算大小的脚本
#!/bin/sh total=0 dest="$(mktemp -d)" for dir in edge v3.0 v3.1 v3.2 v3.3 v3.4 v3.5 v3.6 v3.7 v3.8 v3.9 v3.10 v3.11 v3.12 v3.13 v3.14 v3.15 v3.16 v3.17 v3.18 v3.19 v3.20 v3.21; do old_total="$total" src="rsync://rsync.alpinelinux.org/alpine/$dir/" size=$(rsync -a -n --stats "$src" "$dest" | grep '^Total file size' | tr -d ',' | awk '{ print $4 }') total=$(( old_total + size )) echo "$dir: $size" | awk '{ print $1 sprintf("%.1f", $2/1073741824) }' done echo "total: $total" | awk '{ print $1 sprintf("%.1f", $2/1073741824) }' rm -r "$dest"
设置 cron 任务
安装 rsync,它将用于从主镜像同步。
apk add rsync
将以下文件另存为 /etc/periodic/hourly/alpine-mirror
#!/bin/sh # make sure we never run 2 rsync at the same time lockfile="/tmp/alpine-mirror.lock" if [ -z "$flock" ] ; then exec env flock=1 flock -n $lockfile "$0" "$@" fi src=rsync://rsync.alpinelinux.org/alpine/ dest=/var/www/localhost/htdocs/alpine/ # uncomment this to exclude old v2.x branches #exclude="--exclude v2.*" mkdir -p "$dest" /usr/bin/rsync \ --archive \ --update \ --hard-links \ --delete \ --delete-after \ --delay-updates \ --timeout=600 \ $exclude \ "$src" "$dest"
(或使用 此脚本)
使其可执行
chmod +x /etc/periodic/hourly/alpine-mirror
现在它将每小时同步一次。(假设 cron 正在运行)
通过 lighttpd 设置 HTTP 访问
安装 lighttpd 服务器
apk add lighttpd
通过取消注释 /etc/lighttpd/lighttpd.conf 中的以下行来启用目录列表
dir-listing.activate = "enable"
还要设置 cache-control 以强制缓存每 30 分钟重新验证。取消注释 /etc/lighttpd/lighttpd.conf 中的 mod_setenv
"mod_setenv",
还要将以下行添加到 /etc/lighttpd/lighttpd.conf
setenv.add-response-header += ( "Cache-Control" => "must-revalidate" )
启动 lighttpd 并使其在启动时启动
rc-service lighttpd start rc-update add lighttpd
如果是这样,只需安装、启动和自动启动 Web 服务器:
apk add darkhttpd && rc-service darkhttpd start && rc-update add darkhttpd
Darkhttpd 默认情况下将提供目录列表并从 /var/www/localhost/htdocs/ 提供数据。
请参阅关于 Darkhttpd 的主要文章,以获取更多配置选项设置 rsyncd
将以下行添加到 /etc/rsyncd.conf
[alpine] path = /var/www/localhost/htdocs/alpine comment = My Alpine Linux Mirror
可选地在 /etc/conf.d/rsyncd 中设置带宽限制。在此示例中,我们将限制为 500Kbytes/s(约 5Mbit/s)
RSYNC_OPTS="--bwlimit=500"
镜像统计信息
简单的带宽统计信息可以使用 vnstat 生成。
apk add vnstat
编辑 /etc/vnstat.conf 并将接口名称替换为适当的名称。
启动 vnstatd
rc-service vnstatd start
将以下脚本复制到 /etc/periodic/15min/stats 并确保您的 crond 正在运行。请注意 heredoc 应该使用制表符缩进,否则脚本将失败。一个可用的副本可以在这里找到: https://tpaste.us/RrMv
#!/bin/sh output="/var/www/localhost/htdocs/.stats" nic="eth0" generate_index() { cat <<-EOF <!doctype html> <html lang="en"> <head> <meta charset="utf-8"> <meta http-equiv="cache-control" content=no-cache"> <meta http-equiv="refresh" content="3000"> <title>Alpine Linux mirror statistics</title> </head> <body> <table border="0"> <tr><td><img src="summary.png" alt="summary"></td><td><img src="hours.png" alt="hours"></td></tr> <tr><td rowspan="2"><img src="days.png" alt="days"></td><td><img src="top10.png" alt="top10"></td></tr> <tr><td><img src="months.png" alt="months"></td></tr> </table> </body> </html> EOF } if [ ! -f "$output"/index.html ]; then mkdir -p $output generate_index > "$output"/index.html fi for type in hours days months top10 summary hsummary vsummary; do vnstati --${type} -i $nic -o $output/${type}.png done
从 mqtt 更新镜像
如果您希望您的镜像与我们的主镜像相比真正是最新的,您可以订阅 Alpine Linux 消息服务器 "msg.alpinelinux.org" 并检查上传消息。添加 mqtt-exec 以便能够在发送特定主题时执行进程。
apk add mqtt-exec
mqtt-exec 支持多次运行,因此我们需要设置一个特定的配置。
ln -s mqtt-exec /etc/init.d/mqtt-exec.sync-mirror
ln -s mqtt-exec /etc/conf.d/mqtt-exec.sync-mirror
编辑 /etc/conf.d/mqtt-exec.sync-mirror
mqtt_topics="rsync/rsync.alpinelinux.org/#" exec_user="buildozer" exec_command="/usr/local/bin/sync-mirror"
将以下文件复制到 /usr/local/bin/sync-mirror 并使其可执行(不要忘记更新变量)。
#!/bin/sh src="rsync://rsync.alpinelinux.org/alpine/" dest="/var/www/localhost/htdocs/alpine/" lock="/tmp/sync-mirror.lock" topic="$1" dir="$2" [ -z "$flock" ] && exec env flock=1 flock $lock $0 "$@" if [ -n "$dir" ] && [ -d "$dest/${dir%/*}" ]; then logger "Syncing directory: $dir" src="${src}${dir%/}/" dest="${dest}${dir%/}/" else logger "Syncing all directories" fi /usr/bin/rsync \ --archive \ --update \ --verbose \ --progress \ --timeout=600 \ --delay-updates \ --delete-after \ "$src" \ "$dest"
最后启动 mqtt-exec 并使其监听 msg.alpinelinux.org
rc-service mqtt-exec.sync-mirror start
为了确保您不会遗漏任何软件包(以防 MQTT 订阅出现问题),您可以定期同步所有目录,方法是将脚本添加到 cron。
ln -s /usr/local/bin/sync-mirror /etc/periodic/hourly/sync-mirror
现在查看您的 syslog,它应该会告诉您何时更新本地镜像中的目录。
使用 nginx 的部分镜像
对于私有镜像,仅同步最新版本或 Alpine 的某些架构以节省空间可能是有意义的,但是如果您确实将旧的 Alpine 版本指向您的镜像,他们仍然应该能够安装软件包。我们可以通过使用 nginx 来服务镜像内容并将所有 404 错误请求重定向到公共镜像来实现这一点。
假设您选择仅镜像 v3.13 及更高版本的 Alpine 版本。如果客户端向您的镜像请求 v3.10,则应重定向到另一个镜像。
您的 nginx 配置服务器块应该如下所示
server { listen 80; server_name alpine.mydomain.local; root /data/alpine; # point to where your alpine mirror is located. make sure nginx is allowed to read it autoindex on; # Enable indexing error_page 404 = @alpinemirror; location @alpinemirror { return 302 http://dl-cdn.alpinelinux.org/alpine$request_uri; } }
相应的同步脚本可能如下所示
#!/bin/sh # make sure we never run 2 rsync at the same time lockfile="/tmp/alpine-mirror.lock" if [ -z "$flock" ] ; then exec env flock=1 flock -n $lockfile "$0" "$@" fi src=rsync://rsync.alpinelinux.org/alpine/ dest=/data/alpine/ exclude="--exclude v2.* --exclude v3.0 --exclude v3.1 --exclude v3.2 --exclude v3.3 --exclude v3.4 --exclude v3.5 --exclude v3.6 --exclude v3.7 --exclude v3.8 --exclude v3.9 --exclude v3.10 --exclude v3.11 --exclude v3.12" mkdir -p "$dest" /usr/bin/rsync -vvv \ --archive \ --update \ --hard-links \ --delete \ --delete-after \ --delete-excluded \ --delay-updates \ --timeout=600 \ $exclude \ "$src" "$dest"