docker : 如何在容器之间共享 ssh-keys?
docker : how to share ssh-keys between containers?
我有 4 个容器配置如下 (docker-compose.yml
):
version: '3'
networks:
my-ntwk:
ipam:
config:
- subnet: 172.20.0.0/24
services:
f-app:
image: f-app
tty: true
container_name: f-app
hostname: f-app.info.my
ports:
- "22:22"
networks:
my-ntwk:
ipv4_address: 172.20.0.5
extra_hosts:
- "f-db.info.my:172.20.0.6"
- "p-app.info.my:172.20.0.7"
- "p-db.info.my:172.20.0.8"
depends_on:
- f-db
- p-app
- p-db
f-db:
image: f-db
tty: true
container_name: f-db
hostname: f-db.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.6
p-app:
image: p-app
tty: true
container_name: p-app
hostname: p-app.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.7
p-db:
image: p-db
tty: true
container_name: prod-db
hostname: p-db.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.8
每张图片都是由同一个 Dockerfile
构建的:
FROM openjdk:8
RUN apt-get update && \
apt-get install -y openssh-server
EXPOSE 22
RUN useradd -s /bin/bash -p $(openssl passwd -1 myuser) -d /home/nf2/ -m myuser
ENTRYPOINT service ssh start && bash
现在我希望能够从 f-app
连接到任何其他机器而无需在 运行 这一行时输入密码:ssh myuser@f-db.info.my
.
我知道我需要在服务器之间交换 ssh 密钥(这不是问题)。我的问题是如何使用 docker 容器以及何时(构建或运行时)!
如果您正在使用 docker compose,一个简单的选择就是像这样转发 SSH 代理:
something:
container_name: something
volumes:
- $SSH_AUTH_SOCK:/ssh-agent # Forward local machine SSH key to docker
environment:
SSH_AUTH_SOCK: /ssh-agent
macOS 主机上的 ssh-forwarding - 而不是挂载 $SSH_AUTH_SOCK
的路径,你必须挂载此路径 - /run/host-services/ssh-auth.sock
或者您可以这样做:
如果您需要在构建时使用 SSH,这是一个更难的问题。例如,如果您使用 git clone
,或者在我的情况下 pip
和 npm
从私有存储库下载。
我找到的解决方案是使用 --build-arg
标志添加密钥。然后您可以使用新的实验性 --squash
命令(1.13 添加)合并层,以便在删除后密钥不再可用。这是我的解决方案:
构建命令
$ docker build -t example --build-arg ssh_prv_key="$(cat ~/.ssh/id_rsa)" --build-arg ssh_pub_key="$(cat ~/.ssh/id_rsa.pub)" --squash .
Docker文件
FROM openjdk:8
ARG ssh_prv_key
ARG ssh_pub_key
RUN apt-get update && \
apt-get install -y \
git \
openssh-server \
libmysqlclient-dev
# Authorize SSH Host
RUN mkdir -p /root/.ssh && \
chmod 0700 /root/.ssh && \
ssh-keyscan github.com > /root/.ssh/known_hosts
# Add the keys and set permissions
RUN echo "$ssh_prv_key" > /root/.ssh/id_rsa && \
echo "$ssh_pub_key" > /root/.ssh/id_rsa.pub && \
chmod 600 /root/.ssh/id_rsa && \
chmod 600 /root/.ssh/id_rsa.pub
RUN apt-get update && \
apt-get install -y openssh-server && \
apt-get install -y openssh-client
EXPOSE 22
RUN useradd -s /bin/bash -p $(openssl passwd -1 myuser) -d /home/nf2/ -m myuser
ENTRYPOINT service ssh start && bash
如果您使用的是 Docker 1.13+ and/or 具有实验性功能,您可以将 --squash
附加到构建命令,这将合并图层,删除 SSH 密钥并隐藏他们来自 docker history
.
要在没有密码的情况下执行 ssh
,您需要在容器中配置 SSH keys
的同时创建无密码用户,此外,您还需要在源容器中添加 ssh keys
加上public 密钥应该添加到目标容器的授权中。
这是工作的 Dockerfile
FROM openjdk:7
RUN apt-get update && \
apt-get install -y openssh-server vim
EXPOSE 22
RUN useradd -rm -d /home/nf2/ -s /bin/bash -g root -G sudo -u 1001 ubuntu
USER ubuntu
WORKDIR /home/ubuntu
RUN mkdir -p /home/nf2/.ssh/ && \
chmod 0700 /home/nf2/.ssh && \
touch /home/nf2/.ssh/authorized_keys && \
chmod 600 /home/nf2/.ssh/authorized_keys
COPY ssh-keys/ /keys/
RUN cat /keys/ssh_test.pub >> /home/nf2/.ssh/authorized_keys
USER root
ENTRYPOINT service ssh start && bash
docker-compose将保持不变,这是您可以尝试的测试脚本。
#!/bin/bash
set -e
echo "start docker-compose"
docker-compose up -d
echo "list of containers"
docker-compose ps
echo "starting ssh test from f-db to f-app"
docker exec -it f-db sh -c "ssh -i /keys/ssh_test ubuntu@f-app"
更多详细信息,您可以尝试上面的工作示例docker-container-ssh
git clone git@github.com:Adiii717/docker-container-ssh.git
cd docker-container-ssh;
./test.sh
您可以更换密钥,因为这些密钥仅用于测试目的。
我有 4 个容器配置如下 (docker-compose.yml
):
version: '3'
networks:
my-ntwk:
ipam:
config:
- subnet: 172.20.0.0/24
services:
f-app:
image: f-app
tty: true
container_name: f-app
hostname: f-app.info.my
ports:
- "22:22"
networks:
my-ntwk:
ipv4_address: 172.20.0.5
extra_hosts:
- "f-db.info.my:172.20.0.6"
- "p-app.info.my:172.20.0.7"
- "p-db.info.my:172.20.0.8"
depends_on:
- f-db
- p-app
- p-db
f-db:
image: f-db
tty: true
container_name: f-db
hostname: f-db.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.6
p-app:
image: p-app
tty: true
container_name: p-app
hostname: p-app.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.7
p-db:
image: p-db
tty: true
container_name: prod-db
hostname: p-db.info.my
networks:
my-ntwk:
ipv4_address: 172.20.0.8
每张图片都是由同一个 Dockerfile
构建的:
FROM openjdk:8
RUN apt-get update && \
apt-get install -y openssh-server
EXPOSE 22
RUN useradd -s /bin/bash -p $(openssl passwd -1 myuser) -d /home/nf2/ -m myuser
ENTRYPOINT service ssh start && bash
现在我希望能够从 f-app
连接到任何其他机器而无需在 运行 这一行时输入密码:ssh myuser@f-db.info.my
.
我知道我需要在服务器之间交换 ssh 密钥(这不是问题)。我的问题是如何使用 docker 容器以及何时(构建或运行时)!
如果您正在使用 docker compose,一个简单的选择就是像这样转发 SSH 代理:
something:
container_name: something
volumes:
- $SSH_AUTH_SOCK:/ssh-agent # Forward local machine SSH key to docker
environment:
SSH_AUTH_SOCK: /ssh-agent
macOS 主机上的 ssh-forwarding - 而不是挂载 $SSH_AUTH_SOCK
的路径,你必须挂载此路径 - /run/host-services/ssh-auth.sock
或者您可以这样做:
如果您需要在构建时使用 SSH,这是一个更难的问题。例如,如果您使用 git clone
,或者在我的情况下 pip
和 npm
从私有存储库下载。
我找到的解决方案是使用 --build-arg
标志添加密钥。然后您可以使用新的实验性 --squash
命令(1.13 添加)合并层,以便在删除后密钥不再可用。这是我的解决方案:
构建命令
$ docker build -t example --build-arg ssh_prv_key="$(cat ~/.ssh/id_rsa)" --build-arg ssh_pub_key="$(cat ~/.ssh/id_rsa.pub)" --squash .
Docker文件
FROM openjdk:8
ARG ssh_prv_key
ARG ssh_pub_key
RUN apt-get update && \
apt-get install -y \
git \
openssh-server \
libmysqlclient-dev
# Authorize SSH Host
RUN mkdir -p /root/.ssh && \
chmod 0700 /root/.ssh && \
ssh-keyscan github.com > /root/.ssh/known_hosts
# Add the keys and set permissions
RUN echo "$ssh_prv_key" > /root/.ssh/id_rsa && \
echo "$ssh_pub_key" > /root/.ssh/id_rsa.pub && \
chmod 600 /root/.ssh/id_rsa && \
chmod 600 /root/.ssh/id_rsa.pub
RUN apt-get update && \
apt-get install -y openssh-server && \
apt-get install -y openssh-client
EXPOSE 22
RUN useradd -s /bin/bash -p $(openssl passwd -1 myuser) -d /home/nf2/ -m myuser
ENTRYPOINT service ssh start && bash
如果您使用的是 Docker 1.13+ and/or 具有实验性功能,您可以将 --squash
附加到构建命令,这将合并图层,删除 SSH 密钥并隐藏他们来自 docker history
.
要在没有密码的情况下执行 ssh
,您需要在容器中配置 SSH keys
的同时创建无密码用户,此外,您还需要在源容器中添加 ssh keys
加上public 密钥应该添加到目标容器的授权中。
这是工作的 Dockerfile
FROM openjdk:7
RUN apt-get update && \
apt-get install -y openssh-server vim
EXPOSE 22
RUN useradd -rm -d /home/nf2/ -s /bin/bash -g root -G sudo -u 1001 ubuntu
USER ubuntu
WORKDIR /home/ubuntu
RUN mkdir -p /home/nf2/.ssh/ && \
chmod 0700 /home/nf2/.ssh && \
touch /home/nf2/.ssh/authorized_keys && \
chmod 600 /home/nf2/.ssh/authorized_keys
COPY ssh-keys/ /keys/
RUN cat /keys/ssh_test.pub >> /home/nf2/.ssh/authorized_keys
USER root
ENTRYPOINT service ssh start && bash
docker-compose将保持不变,这是您可以尝试的测试脚本。
#!/bin/bash
set -e
echo "start docker-compose"
docker-compose up -d
echo "list of containers"
docker-compose ps
echo "starting ssh test from f-db to f-app"
docker exec -it f-db sh -c "ssh -i /keys/ssh_test ubuntu@f-app"
更多详细信息,您可以尝试上面的工作示例docker-container-ssh
git clone git@github.com:Adiii717/docker-container-ssh.git
cd docker-container-ssh;
./test.sh
您可以更换密钥,因为这些密钥仅用于测试目的。