【问题标题】:package uninstalls when adding a new dependency?添加新依赖项时软件包卸载?
【发布时间】:2020-04-27 12:20:12
【问题描述】:

在基于 alpine linux 的 docker 的入口点脚本中,我有以下几行:

#!/bin/sh
echo "============== START ============"
echo $@
NOLOAD=0
FILE=""

RET=1

if [ !  -f /initialized ]; then
  echo "not initialized"
  apk add --virtual .init-deps bash
  echo "bash installed"
  echo "Building from server"
  apk add --virtual .init-deps git
  echo "git installed"
  bash load_git.sh "${GIT_SERVER}" "${GIT_USERNAME}" "${GIT_PASSWORD}" "${GIT_BRANCH}"
  RET=$?
  echo cloning done
fi
echo "just before purging all dependencies"
apk --purge del .init-deps

我希望安装 bash 以及 git 并使用 bash 运行 load_git.sh 脚本。我每隔一行进行一次文学记录,但在运行 load_git.sh 脚本之前得到了一些奇怪的结果:

============== START ============

not initialized
(1/6) Installing ncurses-terminfo-base (6.1_p20191130-r0)
(2/6) Installing ncurses-terminfo (6.1_p20191130-r0)
(3/6) Installing ncurses-libs (6.1_p20191130-r0)
(4/6) Installing readline (8.0.1-r0)
(5/6) Installing bash (5.0.11-r1)
Executing bash-5.0.11-r1.post-install
(6/6) Installing .init-deps (20200109.202215)
Executing busybox-1.31.1-r8.trigger
OK: 18 MiB in 24 packages
bash installed
Building from server
(1/12) Installing ca-certificates (20191127-r0)
(2/12) Installing nghttp2-libs (1.40.0-r0)
(3/12) Installing libcurl (7.67.0-r0)
(4/12) Installing expat (2.2.9-r1)
(5/12) Installing pcre2 (10.34-r1)
(6/12) Installing git (2.24.1-r0)
(7/12) Upgrading .init-deps (20200109.202215 -> 20200109.202216)
(8/12) Purging bash (5.0.11-r1)
Executing bash-5.0.11-r1.pre-deinstall
(9/12) Purging readline (8.0.1-r0)
(10/12) Purging ncurses-libs (6.1_p20191130-r0)
(11/12) Purging ncurses-terminfo (6.1_p20191130-r0)
(12/12) Purging ncurses-terminfo-base (6.1_p20191130-r0)
Executing busybox-1.31.1-r8.trigger
Executing ca-certificates-20191127-r0.trigger
OK: 25 MiB in 25 packages
git installed
/init.sh: line 17: bash: not found
cloning done
outside if statement to get source
just before purging all dependencies
Build failed, starting shell

我无法理解这样一个事实,即在安装 git 时它还会清除 bash,这完全没有意义。

编辑:只有在 Synology nas 中通过 ssh 连接启动 docker 时才会发生这种情况,当使用本地 docker 映像并在本地启动它时,它工作得非常好。

【问题讨论】:

  • load_git.sh 中有什么?
  • 另一个脚本(应该下载已经从 git 审查过的最新版本)。 - 脚本顶部有一个回声,我知道它没有运行。只输入echo "outdir" 表明两者之一(也没有设置返回变量)。

标签: bash shell docker alpine


【解决方案1】:

我尝试在远程机器上复制并使用以下脚本进行管理:

#!/bin/sh
if [ !  -f /initialized ]; then
  apk add --virtual .init-deps bash
  apk add --virtual .init-deps git
  bash -c "bash works"
fi

但连续运行有不同的结果:

ubuntu@dev:~$ docker run c81a2d3a5f6b
fetch http://dl-cdn.alpinelinux.org/alpine/v3.11/main/x86_64/APKINDEX.tar.gz
fetch http://dl-cdn.alpinelinux.org/alpine/v3.11/community/x86_64/APKINDEX.tar.gz
(1/6) Installing ncurses-terminfo-base (6.1_p20191130-r0)
(2/6) Installing ncurses-terminfo (6.1_p20191130-r0)
(3/6) Installing ncurses-libs (6.1_p20191130-r0)
(4/6) Installing readline (8.0.1-r0)
(5/6) Installing bash (5.0.11-r1)
Executing bash-5.0.11-r1.post-install
(6/6) Installing .init-deps (20200109.224208)
Executing busybox-1.31.1-r8.trigger
OK: 15 MiB in 20 packages
(1/12) Installing ca-certificates (20191127-r0)
(2/12) Installing nghttp2-libs (1.40.0-r0)
(3/12) Installing libcurl (7.67.0-r0)
(4/12) Installing expat (2.2.9-r1)
(5/12) Installing pcre2 (10.34-r1)
(6/12) Installing git (2.24.1-r0)
(7/12) Upgrading .init-deps (20200109.224208 -> 20200109.224209)
(8/12) Purging bash (5.0.11-r1)
Executing bash-5.0.11-r1.pre-deinstall
(9/12) Purging readline (8.0.1-r0)
(10/12) Purging ncurses-libs (6.1_p20191130-r0)
(11/12) Purging ncurses-terminfo (6.1_p20191130-r0)
(12/12) Purging ncurses-terminfo-base (6.1_p20191130-r0)
Executing busybox-1.31.1-r8.trigger
Executing ca-certificates-20191127-r0.trigger
OK: 22 MiB in 21 packages
/test.sh: line 5: bash: not found

ubuntu@dev:~$ docker run c81a2d3a5f6b
fetch http://dl-cdn.alpinelinux.org/alpine/v3.11/main/x86_64/APKINDEX.tar.gz
fetch http://dl-cdn.alpinelinux.org/alpine/v3.11/community/x86_64/APKINDEX.tar.gz
(1/6) Installing ncurses-terminfo-base (6.1_p20191130-r0)
(2/6) Installing ncurses-terminfo (6.1_p20191130-r0)
(3/6) Installing ncurses-libs (6.1_p20191130-r0)
(4/6) Installing readline (8.0.1-r0)
(5/6) Installing bash (5.0.11-r1)
Executing bash-5.0.11-r1.post-install
(6/6) Installing .init-deps (20200109.224207)
Executing busybox-1.31.1-r8.trigger
OK: 15 MiB in 20 packages
OK: 15 MiB in 20 packages
bash works

所以我认为这是apk中的时间问题

【讨论】:

    【解决方案2】:

    看起来这里发生的事情是apk add --virtual .init-deps 选项创建了一个虚拟包并使其依赖于刚刚安装的其他包。当您第二次执行此操作时,它会创建一个新的虚拟包,该包(仅)依赖于第二组包,并将虚拟包升级到新版本;当您这样做时,第一组软件包会自动卸载。

    这里有两个简单的解决方法:要么从两行中删除此 --virtual .init-deps 选项,要么将所有安装合并到一个 apk add 行中。

    (在容器启动时下载包通常不是很好的做法,特别是因为删除和重新创建容器是相当常规的操作。更好的做法是在映像的 Dockerfile 中执行一次

    RUN apk add bash git
    

    还要考虑您是否真的需要这些工具中的任何一个来运行打包在映像中的应用程序。)

    【讨论】:

    • 那么容器将在第一次加载时从 git 下载代码,它使用 bash 实际处理来自 git 的潜在错误并显示良好的日志。由于在初始加载后不再需要 bash 和 git,或者如果我使用另一个源代码控制方案(如 hg/svn)需要安装另一个包,我认为最好动态安装这些包,并在你的混乱和使用时删除。
    • 我推荐的路径是在运行 Docker 之前克隆主机上的存储库,并在 Dockerfile COPY 中将应用程序源克隆到映像中。那么镜像是应用程序的一个固定的独立副本,它不依赖于在启动时拥有源代码控制工具(或其凭据),并且如果外部源代码控制系统不可用,容器也不会失败。
    猜你喜欢
    • 2021-11-16
    • 1970-01-01
    • 2016-08-04
    • 1970-01-01
    • 1970-01-01
    • 2021-11-06
    • 1970-01-01
    • 2011-11-11
    • 2015-06-08
    相关资源
    最近更新 更多