docker 和 宿主机上 veth 设备的关系没有命令可以直接查到。不过可以进入容器可以看到。如果有个脚本能看到就好太多,docker 后续应该在docker ps加入一个类似的功能。
传统方式:
1、docker exec 进入容器内部
2、宿主机上执行: ip a
自动化方式:
#!/bin/sh NL=$'\n' #################### # DEFINE FUNCTIONS # #################### usage () { printf %s \ "dockerveth.sh - Show which docker containers are attached to which \`veth\` interfaces. Usage: dockerveth.sh [DOCKER PS OPTIONS] | [-h, --help] Options: DOCKER PS OPTIONS Pass any valid \`docker ps\` flags. Do not pass a '--format' flag. -h, --help Show this help and exit. Output: If stdout is not a tty, column headers are omitted. " } get_container_data () { # Get data about the running containers. Accepts arbitrary arguments, so you can pass # a filter to `docker ps` if desired. # Input: `docker ps` arguments (optional) # Output: A multi-line string where each line contains the container id, followed by # a space, and then any friendly names. docker ps --format '{{.ID}} {{.Names}}' "$@" } get_veth () { # Get the host veth interface attached to a container. # Input: docker container ID; also needs $dockerveth__addrs # Output: the veth name, like "veth6638cfa" c_if_index=$(get_container_if_index "$1") a="${dockerveth__addrs%%@if${c_if_index}:*}" b="${a##*${NL}}" printf "${b#* }" } get_container_if_index () { # Get the index number of a docker container's first veth interface (typically eth0) # Input: the container ID # Output: The index number, like "42" c_pid=$(get_pid "$1") ip_netns_export "$c_pid" ils=$(ip netns exec "ns-${c_pid}" ip link show type veth) printf "${ils%%:*}" } ip_netns_export () { # Make a docker container's networking info available to `ip netns` # Input: the container's PID # Output: None (besides return code), but performs the set-up so that `ip netns` commands # can access this container's namespace. if [ ! -d /var/run/netns ]; then mkdir -p /var/run/netns fi ln -sf "/proc/${1}/ns/net" "/var/run/netns/ns-${1}" } get_pid () { # Get the PID of a docker container # Input: the container ID # Output: The PID, like "2499" docker inspect --format '{{.State.Pid}}' "$1" } make_row () { # Produce a table row for output # Input: # 1 - The container ID # 2 - The container's friendly name # Output: A row of data, like "1e8656e195ba veth1ce04be thirsty_meitner" id="${1}" name="${2}" veth=$(get_veth "$id") printf "${id}\t${veth}\t${name}" } make_table () { # Produce a table for output # Input: raw data rows, like `c26682fe4545 friendly-name` # Output: A multi-line string consisting of rows from `make_row`. Does not # contain table column headers. for i in $@; do id="${i%% *}" name="${i#* }" r=$(make_row "$id" "$name") printf "${r}\n" done } ###################### # PARSE COMMAND LINE # ###################### case "$1" in -h|--help) usage exit 0 ;; *) ;; esac ################## # EXECUTE SCRIPT # ################## set -e container_data=$(get_container_data "$@") dockerveth__addrs="$(ip address show)" table=$(IFS="$NL"; make_table $container_data) if [ -t 1 ]; then printf "CONTAINER ID\tVETH \tNAMES\n" fi printf "${table}\n"