New Linux Container Virtualization Technology from Docker
+
Docker is an open-source engine that automates the deployment of any application as a lightweight, portable, self-sufficient container that will run virtually anywhere.
The Docker, new container-based virtualization tech startup has started it’s venture to the server virtualization industry by offering their newest version of the software, the Docker 0.8. The company has been known for their production of a faster alternative when it comes to running virtual machines over that of hypervisors.
CONCEPTO DE DOCKER.
Docker es un proyecto de software libre que permite la automatización de despliegue de aplicaciones dentro de contenedores, esto provee una capa adicional en la virtualización a nivel de sistema operativo en Linux. Docker usa recursos del sistemas totalmente aislados, función que la provee cgroups en Linux desde la versión 2.6.29, también se utilizan nombre de espacios en el kernel para la ejecución de instancias simples de Linux o también llamadas "contenedores" LXC (Linux Containers). En las últimas versiones de Docker se ha introducido drivers de Docker y una librería llamada libcontainer, que ayuda a que Docker sea totalmente multiplataforma, teniendo compatibilidad con Windows y Mac OS X, además de Linux.
El proyecto Docker ha recibido gran acogida por parte de la comunidad, y actualmente servicios como AWS (Amazon Web Service) dan soporte a esta tecnología.
El futuro de los SysAdmin y DevOps
Actualmente la mayoría de los sistemas en internet se ejecutan en servidores dedicados exclusivamente o en sistemas de computación en la nube, y hosting compartido. Pero gracias al desarollo del kernel Linux tenemos la posibilidad de tener entornos aislados de Linux, inclusive de una distribución distinta a la que esté instalada en el host, esto nos permitirá tener entornos virtualizados sin necesidad de virtualizar a través de hardware o software, aprovechando los recursos de la máquina en las aplicaciones que se ejecuten.
Con Docker todo esto se convierte en algo sencillo de hacer, así como VirtualBox lleva la virtualización a más personas, Docker lleva el uso de contenedores a más personas. El proyecto es joven, su primer release se publicó en el 2013, y actualmente se encuentra en la versión 1.2.
Antes de seguir hablando de Docker, es bueno definir el término "imágenes", dentro de Docker una imagen es una instancia de Linux básica o preconfigurada con las aplicaciones que queremos ejecutar.
Esto básicamente es una infraestructura sobre Docker, donde se tiene el motor de Docker (Docker Engine), que nos permite realizar todas las acciones sobre las imágenes que descarguemos o construyamos y dentro de las imágenes se encuentran las librerías, binarios que necesitamos y las aplicaciones.
Ya sabemos técnicamente que es Docker, pero, ¿Para qué me sirve?
El principal objetivo de Docker es simplificar la infraestructura de aplicaciones, para su despliegue y distribución, es decir, que si yo logro implementar Docker en una aplicación puedo distribuir ese contenedor entre otros desarrolladores (sin importar que sistema operativo usen), reduciendo el tiempo de implementación en desarrollo y producción dentro del equipo de trabajo, de esta manera la brecha entre desarrolladores y administradores de sistemas se vuelve más pequeña.
Docker da la posibilidad de tener todo el entorno para la aplicación y publicar los cambios que se realicen fácilmente, además de hacer todo el despliegue en producción de una manera bastante fácil y profesional.
Otra cosa que el proyecto nos ofrece es un repositorio de imágenes al estilo Github, Docker se convierte en el Github de los SysAdmin y DevOps, este componente del proyecto se llama Registry o Docker Hub y desde cualquier lugar podemos, crear, compartir y consumir imágenes creadas por nosotros o por terceros
The Concept of Docker
For the benefit of those who are not that familiar with this technology’s concept, 'Docker’ is an application container that offers a way to package as well as compact an application in a virtual container, thereby allowing the running across all different Linux distributions.
Pioneered by Hykes, Docker was first introduced in March 2013 as an internal application for PaaS company dotCloud.
Because of its innovative nature, the application has attracted and generated a lot of interest from its target market, thereby pushing the company to even re-brand it from dotCloud in to Docker Inc. Later in the process, the software hasgained US$15 million in venture capital investment from its Greylock Partners.
Although the basic idea of this application is to be PaaS-centric, the company has seen the need to transform it into a platform and has now been downloaded for over 400,000 times by a lot of different companies and organizations from the IT industry and offered by giants like Google Compute Engine (GCE) as well as the Red Hat for the beta version of their distribution.
Docker vs. Traditional Virtual Machines?
Just like the virtual machines concept, a container is designed in order to hold an application thereby relieving the developer from worrying about setting up the underlying system software. I’m aware that’s not much of an argument as VM’s can be cloned, in like, 2 seconds time.
However, unlike full virtual machines, Docker containers do not include a fully-blown OS but instead, it shares the OS with the host.
In this set up, containers can be way faster as well as less resource-hungry as compared to hypervisor-based virtualization technoloigies we have today.
Moreover, when compared to a virtual machine, containers can be simply launched and initiated in matter of seconds.
Moreover, when compared to a virtual machine, containers can be simply launched and initiated in matter of seconds.
For the Docker technology, it is estimated that contained application can run about two times faster than those running in traditional virtual machine; more containers can also be packaged into a single server since the OS is not doubled for each application that is present in the system.
Additional edge of this new virtualization technology is that it is based on simplicity and it offers an API which administrators can make use of in order to weave images into a bigger scripted workflow.
The New Technology and It’s Improvements
This new technology is primarily manufactured in order to cater and accommodate enterprise-based utilization by different companies. According to Docker mastermind, Solomon Hykes, such recent invention is made in order to release features that evolve the backseat to quality.
Docker team realizes and acknowledges the fact that some companies that are using it are looking forward to putting the software into mission critical roles, which is why they are ensuring to make it in a much higher quality and more comprehensive as much as possible.
It is of the company’s knowledge that the concept of containers among their customers has encouraged them to embrace a lot of abilities and potentials to run lightweight portable applications that often have low overhead and are easily scaled and movable across cloud and even physical infrastructures. TT
More of the improvements in the recent version, the 0.8, have been focused on making the software faster in such a way that containers as well as images can be deleted from a system in a quicker manner. Furthermore, it is also observed that the daemon begins and stops faster so as with building sources images. Added is the caching layer, being the most requested feature that can eliminate the necessity to upload the image from a disk again when it has not been modified.
Having a smaller memory footprint and the ability to make a bigger number of containers as well as the elimination of many race conditions also made the new version of this cutting-edge software more stable.
Overwhelming Additional Features
Aside from the mentioned perks above, the 0.8 version also boasts its capability to create container on an OSXworkstation as it provides a smaller virtual machine known as the Boot2Docker. This is definitely a huge leap for developers who are conducting local testing and development.
Although the system is primarily crafted to run on Linux, it is now being reconfigured as a plug-in infrastructure thereby allowing it to operate on other platforms including Windows expanding it’s coverage when it comes to making others experience its full features. For the first time, this software was also crafted to support experimental BTRFS.
Future Plans
With the incredible and highly significant interest posed by their clients, Docker is planning on updating the software once a month, with their next release of 0.9 version.
Additionally, the company is also looking forward to a full production-ready v1, which is planned to be released on April. And to further ensure that their product is being state-of-the-art, Docker is also reviewing and investigating various mechanisms in order to commercialize the open source technology under the Apache license thus fund future development.
They are also planning on developing the services for signing images, indexing as well as making private registries for the images. The company will also provide commercial support.
Installing Docker - CentOS-7
you must first disable selinux
Change SELINUX=enforcing
to SELINUX=disabled
This will disable SELinux on your next reboot.
To enable btrfs support for Docker on Oracle Linux:
# chkconfig docker on
# service docker start
To enable the Docker daemon on system boot and start Docker on OL7:
# systemctl enable docker.service
# systemctl start docker.service
# service docker status
To check that Docker is up and running on OL7:
# systemctl status docker.service
You can also get more information from Docker itself:
# docker info
# docker version
Once you have Docker up and running, follow the upstream Docker documentation to get started.
Installation
To install Docker on Oracle Linux 6:
- Enable the ol6_addons channel in /etc/yum.repos.d/public-yum-ol6.repo
- Run:
# yum install docker
To install Docker on Oracle Linux 7:
- Enable the ol7_addons channel in /etc/yum.repos.d/public-yum-ol7.repo
- Run:
# yum install docker
Enable btrfs support
Docker uses device-mapper devices as the default storage engine. To switch to using btrfs as the storage engine, ensure that /var/lib/docker is mounted on a btrfs filesystem. Check Chapter 5 of the Oracle Linux Administrator's Solutions Guide for more details on how to create and mount btrfs filesystems.To enable btrfs support for Docker on Oracle Linux:
- Ensure that /var/lib/docker is on a btrfs filesystem
- Edit /etc/sysconfig/docker and add "-s btrfs" to the other_args fields.
- Restart the Docker daemon:
# service docker restart
Enabling and starting Docker
To enable the Docker daemon on system boot and start Docker on OL6:# chkconfig docker on
# service docker start
To enable the Docker daemon on system boot and start Docker on OL7:
# systemctl enable docker.service
# systemctl start docker.service
Checking Docker status
To check that Docker is up and running on OL6:# service docker status
To check that Docker is up and running on OL7:
# systemctl status docker.service
You can also get more information from Docker itself:
# docker info
# docker version
Once you have Docker up and running, follow the upstream Docker documentation to get started.
Known Issues
Docker unmounts btrfs filesystems on shutdown
If you're running Docker using the btrfs storage engine and you stop the Docker service, it will unmount the btrfs filesystem during the shutdown process. You should ensure the filesystem is mounted properly prior to restarting the Docker service. On Oracle Linux 7, you can use a systemd.mount definition and modify the Docker systemd.service to depend on the btrfs mount defined in systemd.SElinux support with btrfs on Oracle Linux 7
SElinux must be set to Permissive or Disabled in order to use the btrfs storage engine on Oracle Linux 7.
************************************************
Docker is included in the CentOS-Extras repository. You can simply run
yum install docker
Once docker is installed, you will need to start the service in order to use it.
service docker start chkconfig docker on # start the docker service on boot
Installing Docker - CentOS-6
Installing Docker on CentOS-6 requires the use of the EPEL repository. Once you have enabledEPEL you may continue with the rest of the installation
|
To install docker on CentOS-6 install the docker-io package with the following command:
yum install docker-io
service docker start chkconfig docker on # start the docker service on boot
Using Docker
By default, docker must be run as root, or via sudo privileges. You may also allow a user to run docker directly by adding the user to the 'docker' group.
Be aware that this may allow for privilege escalation for that user, should they escape the container.
|
usermod -a -G docker <your-user>
To get the official CentOS images in the Docker Index :
docker pull centos
To verify the images have been fetched locally:
[root@lappy ~]# docker images centos REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE centos centos7 1a7dc42f78ba 6 hours ago 236.4 MB centos latest 1a7dc42f78ba 6 hours ago 236.4 MB centos centos6 cd934e0010d5 18 hours ago 206.9 MB
Running a basic cat command using docker:
[root@lappy ~]# docker run centos:latest cat /etc/centos-release CentOS Linux release 7.0.1406 (Core)
Running other basic cat command using docker:
[root@lappy ~]# docker run -p 80:80 -i -t ubuntu1410:apache /bin/bash
Docker Images
The Docker images are built using ami_creator with the kickstart files in the sig-cloud-instance-build project
The finished builds can be found in the sig-cloud-images project, branched per version.
How to Run Apache Under Docker on centos 7
Grab Centos image from Docker repo
Start new container based on
Install LAMP packages inside container Environment
How to Run Apache Under Docker on centos 7
Grab Centos image from Docker repo
sudo docker pull centos
centos
Imagesudo docker run -i -t centos /bin/bash
$ yum install httpd php php-common php-cli php-pdo php-mysql php-xml php-mbstring mysql mysql-server
$ Exit
Snapshot to a new image called LAMP
sudo docker commit 6751f9bcb5c5 LAMP
Run Container
sudo docker run -i -t -p 80:80 LAMP /bin/bash
#bash-4.2# /usr/sbin/httpd *Para arrancar el servicio.
List the containers on the machine:
#sudo docker ps -a
Save the containers as a new image:
#sudo docker commit conntainerid yourimagename
Network Configuration
TL;DR
When Docker starts, it creates a virtual interface nameddocker0
on the host machine. It randomly chooses an address and subnet from the private range defined by RFC 1918 that are not in use on the host machine, and assigns it to docker0
. Docker made the choice 172.17.42.1/16
when I started it a few minutes ago, for example — a 16-bit netmask providing 65,534 addresses for the host machine and its containers.Note: This document discusses advanced networking configuration and options for Docker. In most cases you won't need this information. If you're looking to get started with a simpler explanation of Docker networking and an introduction to the concept of container linking see the Docker User Guide.But
docker0
is no ordinary interface. It is a virtual Ethernet bridge that automatically forwards packets between any other network interfaces that are attached to it. This lets containers communicate both with the host machine and with each other. Every time Docker creates a container, it creates a pair of “peer” interfaces that are like opposite ends of a pipe — a packet sent on one will be received on the other. It gives one of the peers to the container to become its eth0
interface and keeps the other peer, with a unique name like vethAQI2QT
, out in the namespace of the host machine. By binding every veth*
interface to the docker0
bridge, Docker creates a virtual subnet shared between the host machine and every Docker container.The remaining sections of this document explain all of the ways that you can use Docker options and — in advanced cases — raw Linux networking commands to tweak, supplement, or entirely replace Docker's default networking configuration.
Quick Guide to the Options
Here is a quick list of the networking-related Docker command-line options, in case it helps you find the section below that you are looking for.Some networking command-line options can only be supplied to the Docker server when it starts up, and cannot be changed once it is running:
-b BRIDGE
or--bridge=BRIDGE
— see Building your own bridge--bip=CIDR
— see Customizing docker0-H SOCKET...
or--host=SOCKET...
— This might sound like it would affect container networking, but it actually faces in the other direction: it tells the Docker server over what channels it should be willing to receive commands like “run container” and “stop container.”--icc=true|false
— see Communication between containers--ip=IP_ADDRESS
— see Binding container ports--ip-forward=true|false
— see Communication between containers--iptables=true|false
— see Communication between containers--mtu=BYTES
— see Customizing docker0
docker run
is invoked. When provided at startup, set the default value that docker run
will later use if the options are not specified:--dns=IP_ADDRESS...
— see Configuring DNS--dns-search=DOMAIN...
— see Configuring DNS
docker run
because they specify something specific to one container:-h HOSTNAME
or--hostname=HOSTNAME
— see Configuring DNS and How Docker networks a container--link=CONTAINER_NAME:ALIAS
— see Configuring DNS and Communication between containers--net=bridge|none|container:NAME_or_ID|host
— see How Docker networks a container-p SPEC
or--publish=SPEC
— see Binding container ports-P
or--publish-all=true|false
— see Binding container ports
Configuring DNS
How can Docker supply each container with a hostname and DNS configuration, without having to build a custom image with the hostname written inside? Its trick is to overlay three crucial
/etc
files inside the container with virtual files where it can write fresh information. You can see this by running mount
inside a container:$$ mount
...
/dev/disk/by-uuid/1fec...ebdf on /etc/hostname type ext4 ...
/dev/disk/by-uuid/1fec...ebdf on /etc/hosts type ext4 ...
tmpfs on /etc/resolv.conf type tmpfs ...
...
This arrangement allows Docker to do clever things like keep resolv.conf
up to date across all containers when the host machine receives new configuration over DHCP later. The exact details of how Docker maintains these files inside the container can change from one Docker version to the next, so you should leave the files themselves alone and use the following Docker options instead.Four different options affect container domain name services.
-h HOSTNAME
or--hostname=HOSTNAME
— sets the hostname by which the container knows itself. This is written into/etc/hostname
, into/etc/hosts
as the name of the container's host-facing IP address, and is the name that/bin/bash
inside the container will display inside its prompt. But the hostname is not easy to see from outside the container. It will not appear indocker ps
nor in the/etc/hosts
file of any other container.--link=CONTAINER_NAME:ALIAS
— using this option as yourun
a container gives the new container's/etc/hosts
an extra entry namedALIAS
that points to the IP address of the container namedCONTAINER_NAME
. This lets processes inside the new container connect to the hostnameALIAS
without having to know its IP. The--link=
option is discussed in more detail below, in the section Communication between containers. Because Docker may assign a different IP address to the linked containers on restart, Docker updates theALIAS
entry in the/etc/hosts
file of the recipient containers.--dns=IP_ADDRESS...
— sets the IP addresses added asserver
lines to the container's/etc/resolv.conf
file. Processes in the container, when confronted with a hostname not in/etc/hosts
, will connect to these IP addresses on port 53 looking for name resolution services.--dns-search=DOMAIN...
— sets the domain names that are searched when a bare unqualified hostname is used inside of the container, by writingsearch
lines into the container's/etc/resolv.conf
. When a container process attempts to accesshost
and the search domainexample.com
is set, for instance, the DNS logic will not only look uphost
but alsohost.example.com
.
/etc/resolv.conf
inside of each container look like the /etc/resolv.conf
of the host machine where the docker
daemon is running. The options then modify this default configuration.Communication between containers and the wider world
Whether a container can talk to the world is governed by one main factor.
Is the host machine willing to forward IP packets? This is governed by the
ip_forward
system parameter. Packets can only pass between containers if this parameter is 1
. Usually you will simply leave the Docker server at its default setting --ip-forward=true
and Docker will go set ip_forward
to 1
for you when the server starts up. To check the setting or turn it on manually:# Usually not necessary: turning on forwarding,
# on the host where your Docker server is running
$ cat /proc/sys/net/ipv4/ip_forward
0
$ sudo echo 1 > /proc/sys/net/ipv4/ip_forward
$ cat /proc/sys/net/ipv4/ip_forward
1
Many using Docker will want ip_forward
to be on, to at least make communication possible between containers and the wider world.May also be needed for inter-container communication if you are in a multiple bridge setup.
Communication between containers
Whether two containers can communicate is governed, at the operating system level, by two factors.
- Does the network topology even connect the containers' network interfaces? By default Docker will attach all containers to a single
docker0
bridge, providing a path for packets to travel between them. See the later sections of this document for other possible topologies. - Do your
iptables
allow this particular connection to be made? Docker will never make changes to your systemiptables
rules if you set--iptables=false
when the daemon starts. Otherwise the Docker server will add a default rule to theFORWARD
chain with a blanketACCEPT
policy if you retain the default--icc=true
, or else will set the policy toDROP
if--icc=false
.
--icc=true
or change it to --icc=false
(on Ubuntu, by editing the DOCKER_OPTS
variable in /etc/default/docker
and restarting the Docker server) so that iptables
will protect other containers — and the main host — from having arbitrary ports probed or accessed by a container that gets compromised.If you choose the most secure setting of
--icc=false
, then how can containers communicate in those cases where you want them to provide each other services?The answer is the
--link=CONTAINER_NAME:ALIAS
option, which was mentioned in the previous section because of its effect upon name services. If the Docker daemon is running with both --icc=false
and --iptables=true
then, when it sees docker run
invoked with the --link=
option, the Docker server will insert a pair of iptables
ACCEPT
rules so that the new container can connect to the ports exposed by the other container — the ports that it mentioned in the EXPOSE
lines of its Dockerfile
. Docker has more documentation on this subject — see the linking Docker containers page for further details.Note: The valueYou can run theCONTAINER_NAME
in--link=
must either be an auto-assigned Docker name likestupefied_pare
or else the name you assigned with--name=
when you randocker run
. It cannot be a hostname, which Docker will not recognize in the context of the--link=
option.
iptables
command on your Docker host to see whether the FORWARD
chain has a default policy of ACCEPT
or DROP
:# When --icc=false, you should see a DROP rule:
$ sudo iptables -L -n
...
Chain FORWARD (policy ACCEPT)
target prot opt source destination
DROP all -- 0.0.0.0/0 0.0.0.0/0
...
# When a --link= has been created under --icc=false,
# you should see port-specific ACCEPT rules overriding
# the subsequent DROP policy for all other packets:
$ sudo iptables -L -n
...
Chain FORWARD (policy ACCEPT)
target prot opt source destination
ACCEPT tcp -- 172.17.0.2 172.17.0.3 tcp spt:80
ACCEPT tcp -- 172.17.0.3 172.17.0.2 tcp dpt:80
DROP all -- 0.0.0.0/0 0.0.0.0/0
Note: Docker is careful that its host-wide iptables
rules fully expose containers to each other's raw IP addresses, so connections from one container to another should always appear to be originating from the first container's own IP address.
Binding container ports to the host
By default Docker containers can make connections to the outside world, but the outside world cannot connect to containers. Each outgoing connection will appear to originate from one of the host machine's own IP addresses thanks to an
iptables
masquerading rule on the host machine that the Docker server creates when it starts:# You can see that the Docker server creates a
# masquerade rule that let containers connect
# to IP addresses in the outside world:
$ sudo iptables -t nat -L -n
...
Chain POSTROUTING (policy ACCEPT)
target prot opt source destination
MASQUERADE all -- 172.17.0.0/16 !172.17.0.0/16
...
But if you want containers to accept incoming connections, you will need to provide special options when invoking docker run
. These options are covered in more detail in the Docker User Guide page. There are two approaches.First, you can supply
-P
or --publish-all=true|false
to docker run
which is a blanket operation that identifies every port with an EXPOSE
line in the image's Dockerfile
and maps it to a host port somewhere in the range 49153–65535. This tends to be a bit inconvenient, since you then have to run other docker
sub-commands to learn which external port a given service was mapped to.More convenient is the
-p SPEC
or --publish=SPEC
option which lets you be explicit about exactly which external port on the Docker server — which can be any port at all, not just those in the 49153-65535 block — you want mapped to which port in the container.Either way, you should be able to peek at what Docker has accomplished in your network stack by examining your NAT tables.
# What your NAT rules might look like when Docker
# is finished setting up a -P forward:
$ iptables -t nat -L -n
...
Chain DOCKER (2 references)
target prot opt source destination
DNAT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:49153 to:172.17.0.2:80
# What your NAT rules might look like when Docker
# is finished setting up a -p 80:80 forward:
Chain DOCKER (2 references)
target prot opt source destination
DNAT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:80 to:172.17.0.2:80
You can see that Docker has exposed these container ports on 0.0.0.0
, the wildcard IP address that will match any possible incoming port on the host machine. If you want to be more restrictive and only allow container services to be contacted through a specific external interface on the host machine, you have two choices. When you invoke docker run
you can use either -p IP:host_port:container_port
or -p IP::port
to specify the external interface for one particular binding.Or if you always want Docker port forwards to bind to one specific IP address, you can edit your system-wide Docker server settings (on Ubuntu, by editing
DOCKER_OPTS
in /etc/default/docker
) and add the option --ip=IP_ADDRESS
. Remember to restart your Docker server after editing this setting.Again, this topic is covered without all of these low-level networking details in the Docker User Guide document if you would like to use that as your port redirection reference instead.
Customizing docker0
By default, the Docker server creates and configures the host system's
docker0
interface as an Ethernet bridge inside the Linux kernel that can pass packets back and forth between other physical or virtual network interfaces so that they behave as a single Ethernet network.Docker configures
docker0
with an IP address and netmask so the host machine can both receive and send packets to containers connected to the bridge, and gives it an MTU — the maximum transmission unit or largest packet length that the interface will allow — of either 1,500 bytes or else a more specific value copied from the Docker host's interface that supports its default route. Both are configurable at server startup:--bip=CIDR
— supply a specific IP address and netmask for thedocker0
bridge, using standard CIDR notation like192.168.1.5/24
.--mtu=BYTES
— override the maximum packet length ondocker0
.
DOCKER_OPTS
setting in /etc/default/docker
on your Docker host and restarting the Docker service.Once you have one or more containers up and running, you can confirm that Docker has properly connected them to the
docker0
bridge by running the brctl
command on the host machine and looking at the interfaces
column of the output. Here is a host with two different containers connected:# Display bridge info
$ sudo brctl show
bridge name bridge id STP enabled interfaces
docker0 8000.3a1d7362b4ee no veth65f9
vethdda6
If the brctl
command is not installed on your Docker host, then on Ubuntu you should be able to run sudo apt-get install bridge-utils
to install it.Finally, the
docker0
Ethernet bridge settings are used every time you create a new container. Docker selects a free IP address from the range available on the bridge each time you docker run
a new container, and configures the container's eth0
interface with that IP address and the bridge's netmask. The Docker host's own IP address on the bridge is used as the default gateway by which each container reaches the rest of the Internet.# The network, as seen from a container
$ sudo docker run -i -t --rm base /bin/bash
$$ ip addr show eth0
24: eth0: <BROADCAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 32:6f:e0:35:57:91 brd ff:ff:ff:ff:ff:ff
inet 172.17.0.3/16 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::306f:e0ff:fe35:5791/64 scope link
valid_lft forever preferred_lft forever
$$ ip route
default via 172.17.42.1 dev eth0
172.17.0.0/16 dev eth0 proto kernel scope link src 172.17.0.3
$$ exit
Remember that the Docker host will not be willing to forward container packets out on to the Internet unless its ip_forward
system setting is 1
— see the section above on Communication between containers for details.Building your own bridge
If you want to take Docker out of the business of creating its own Ethernet bridge entirely, you can set up your own bridge before starting Docker and use
-b BRIDGE
or --bridge=BRIDGE
to tell Docker to use your bridge instead. If you already have Docker up and running with its old docker0
still configured, you will probably want to begin by stopping the service and removing the interface:# Stopping Docker and removing docker0
$ sudo service docker stop
$ sudo ip link set dev docker0 down
$ sudo brctl delbr docker0
Then, before starting the Docker service, create your own bridge and give it whatever configuration you want. Here we will create a simple enough bridge that we really could just have used the options in the previous section to customize docker0
, but it will be enough to illustrate the technique.# Create our own bridge
$ sudo brctl addbr bridge0
$ sudo ip addr add 192.168.5.1/24 dev bridge0
$ sudo ip link set dev bridge0 up
# Confirming that our bridge is up and running
$ ip addr show bridge0
4: bridge0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state UP group default
link/ether 66:38:d0:0d:76:18 brd ff:ff:ff:ff:ff:ff
inet 192.168.5.1/24 scope global bridge0
valid_lft forever preferred_lft forever
# Tell Docker about it and restart (on Ubuntu)
$ echo 'DOCKER_OPTS="-b=bridge0"' >> /etc/default/docker
$ sudo service docker start
The result should be that the Docker server starts successfully and is now prepared to bind containers to the new bridge. After pausing to verify the bridge's configuration, try creating a container — you will see that its IP address is in your new IP address range, which Docker will have auto-detected.Just as we learned in the previous section, you can use the
brctl show
command to see Docker add and remove interfaces from the bridge as you start and stop containers, and can run ip addr
and ip route
inside a container to see that it has been given an address in the bridge's IP address range and has been told to use the Docker host's IP address on the bridge as its default gateway to the rest of the Internet.How Docker networks a container
While Docker is under active development and continues to tweak and improve its network configuration logic, the shell commands in this section are rough equivalents to the steps that Docker takes when configuring networking for each new container.
Let's review a few basics.
To communicate using the Internet Protocol (IP), a machine needs access to at least one network interface at which packets can be sent and received, and a routing table that defines the range of IP addresses reachable through that interface. Network interfaces do not have to be physical devices. In fact, the
lo
loopback interface available on every Linux machine (and inside each Docker container) is entirely virtual — the Linux kernel simply copies loopback packets directly from the sender's memory into the receiver's memory.Docker uses special virtual interfaces to let containers communicate with the host machine — pairs of virtual interfaces called “peers” that are linked inside of the host machine's kernel so that packets can travel between them. They are simple to create, as we will see in a moment.
The steps with which Docker configures a container are:
- Create a pair of peer virtual interfaces.
- Give one of them a unique name like
veth65f9
, keep it inside of the main Docker host, and bind it todocker0
or whatever bridge Docker is supposed to be using. - Toss the other interface over the wall into the new container (which will already have been provided with an
lo
interface) and rename it to the much prettier nameeth0
since, inside of the container's separate and unique network interface namespace, there are no physical interfaces with which this name could collide. - Give the container's
eth0
a new IP address from within the bridge's range of network addresses, and set its default route to the IP address that the Docker host owns on the bridge.
eth0
(virtual) network card and will find itself able to communicate with other containers and the rest of the Internet.You can opt out of the above process for a particular container by giving the
--net=
option to docker run
, which takes four possible values.--net=bridge
— The default action, that connects the container to the Docker bridge as described above.--net=host
— Tells Docker to skip placing the container inside of a separate network stack. In essence, this choice tells Docker to not containerize the container's networking! While container processes will still be confined to their own filesystem and process list and resource limits, a quickip addr
command will show you that, network-wise, they live “outside” in the main Docker host and have full access to its network interfaces. Note that this does not let the container reconfigure the host network stack — that would require--privileged=true
— but it does let container processes open low-numbered ports like any other root process. It also allows the container to access local network services like D-bus. This can lead to processes in the container being able to do unexpected things like restart your computer. You should use this option with caution.--net=container:NAME_or_ID
— Tells Docker to put this container's processes inside of the network stack that has already been created inside of another container. The new container's processes will be confined to their own filesystem and process list and resource limits, but will share the same IP address and port numbers as the first container, and processes on the two containers will be able to connect to each other over the loopback interface.--net=none
— Tells Docker to put the container inside of its own network stack but not to take any steps to configure its network, leaving you free to build any of the custom configurations explored in the last few sections of this document.
--net=none
as described in that last bullet point, here are the commands that you would run to reach roughly the same configuration as if you had let Docker do all of the configuration:# At one shell, start a container and
# leave its shell idle and running
$ sudo docker run -i -t --rm --net=none base /bin/bash
root@63f36fc01b5f:/#
# At another shell, learn the container process ID
# and create its namespace entry in /var/run/netns/
# for the "ip netns" command we will be using below
$ sudo docker inspect -f '{{.State.Pid}}' 63f36fc01b5f
2778
$ pid=2778
$ sudo mkdir -p /var/run/netns
$ sudo ln -s /proc/$pid/ns/net /var/run/netns/$pid
# Check the bridge's IP address and netmask
$ ip addr show docker0
21: docker0: ...
inet 172.17.42.1/16 scope global docker0
...
# Create a pair of "peer" interfaces A and B,
# bind the A end to the bridge, and bring it up
$ sudo ip link add A type veth peer name B
$ sudo brctl addif docker0 A
$ sudo ip link set A up
# Place B inside the container's network namespace,
# rename to eth0, and activate it with a free IP
$ sudo ip link set B netns $pid
$ sudo ip netns exec $pid ip link set dev B name eth0
$ sudo ip netns exec $pid ip link set eth0 up
$ sudo ip netns exec $pid ip addr add 172.17.42.99/16 dev eth0
$ sudo ip netns exec $pid ip route add default via 172.17.42.1
At this point your container should be able to perform networking operations as usual.When you finally exit the shell and Docker cleans up the container, the network namespace is destroyed along with our virtual
eth0
— whose destruction in turn destroys interface A
out in the Docker host and automatically un-registers it from the docker0
bridge. So everything gets cleaned up without our having to run any extra commands! Well, almost everything:# Clean up dangling symlinks in /var/run/netns
find -L /var/run/netns -type l -delete
Also note that while the script above used modern ip
command instead of old deprecated wrappers like ipconfig
and route
, these older commands would also have worked inside of our container. The ip addr
command can be typed as ip a
if you are in a hurry.Finally, note the importance of the
ip netns exec
command, which let us reach inside and configure a network namespace as root. The same commands would not have worked if run inside of the container, because part of safe containerization is that Docker strips container processes of the right to configure their own networks. Using ip netns exec
is what let us finish up the configuration without having to take the dangerous step of running the container itself with --privileged=true
.Tools and Examples
Before diving into the following sections on custom network topologies, you might be interested in glancing at a few external tools or examples of the same kinds of configuration. Here are two:- Jérôme Petazzoni has created a
pipework
shell script to help you connect together containers in arbitrarily complex scenarios: https://github.com/jpetazzo/pipework - Brandon Rhodes has created a whole network topology of Docker containers for the next edition of Foundations of Python Network Programming that includes routing, NAT'd firewalls, and servers that offer HTTP, SMTP, POP, IMAP, Telnet, SSH, and FTP: https://github.com/brandon-rhodes/fopnp/tree/m/playground
Building a point-to-point connection
By default, Docker attaches all containers to the virtual subnet implemented by
docker0
. You can create containers that are each connected to some different virtual subnet by creating your own bridge as shown in Building your own bridge, starting each container with docker run --net=none
, and then attaching the containers to your bridge with the shell commands shown in How Docker networks a container.But sometimes you want two particular containers to be able to communicate directly without the added complexity of both being bound to a host-wide Ethernet bridge.
The solution is simple: when you create your pair of peer interfaces, simply throw both of them into containers, and configure them as classic point-to-point links. The two containers will then be able to communicate directly (provided you manage to tell each container the other's IP address, of course). You might adjust the instructions of the previous section to go something like this:
# Start up two containers in two terminal windows
$ sudo docker run -i -t --rm --net=none base /bin/bash
root@1f1f4c1f931a:/#
$ sudo docker run -i -t --rm --net=none base /bin/bash
root@12e343489d2f:/#
# Learn the container process IDs
# and create their namespace entries
$ sudo docker inspect -f '{{.State.Pid}}' 1f1f4c1f931a
2989
$ sudo docker inspect -f '{{.State.Pid}}' 12e343489d2f
3004
$ sudo mkdir -p /var/run/netns
$ sudo ln -s /proc/2989/ns/net /var/run/netns/2989
$ sudo ln -s /proc/3004/ns/net /var/run/netns/3004
# Create the "peer" interfaces and hand them out
$ sudo ip link add A type veth peer name B
$ sudo ip link set A netns 2989
$ sudo ip netns exec 2989 ip addr add 10.1.1.1/32 dev A
$ sudo ip netns exec 2989 ip link set A up
$ sudo ip netns exec 2989 ip route add 10.1.1.2/32 dev A
$ sudo ip link set B netns 3004
$ sudo ip netns exec 3004 ip addr add 10.1.1.2/32 dev B
$ sudo ip netns exec 3004 ip link set B up
$ sudo ip netns exec 3004 ip route add 10.1.1.1/32 dev B
The two containers should now be able to ping each other and make connections successfully. Point-to-point links like this do not depend on a subnet nor a netmask, but on the bare assertion made by ip route
that some other single IP address is connected to a particular network interface.Note that point-to-point links can be safely combined with other kinds of network connectivity — there is no need to start the containers with
--net=none
if you want point-to-point links to be an addition to the container's normal networking instead of a replacement.A final permutation of this pattern is to create the point-to-point link between the Docker host and one container, which would allow the host to communicate with that one container on some single IP address and thus communicate “out-of-band” of the bridge that connects the other, more usual containers. But unless you have very specific networking needs that drive you to such a solution, it is probably far preferable to use
--icc=false
to lock down inter-container communication, as we explored earlier.Editing networking config files
Starting with Docker v.1.2.0, you can now edit/etc/hosts
, /etc/hostname
and /etc/resolve.conf
in a running container. This is useful if you need to install bind or other services that might override one of those files.Note, however, that changes to these files will not be saved by
docker commit
, nor will they be saved during docker run
. That means they won't be saved in the image, nor will they persist when a container is restarted; they will only "stick" in a running container.
Thanks for your clear explanation on your topic please share more valuable content on Devops Online Training Hyderabad
ResponderEliminarkayseriescortu.com - alacam.org - xescortun.com
ResponderEliminarpiadopuncre Jamie Jackson https://marketplace.visualstudio.com/items?itemName=nutnafes-hi.Hunahpu-Quest--Mechanoid-gratuita-2021
ResponderEliminargiftfittiti
perde modelleri
ResponderEliminarMobil onay
mobil ödeme bozdurma
nft nasıl alınır
ankara evden eve nakliyat
trafik sigortası
dedektor
web sitesi kurma
Aşk kitapları
maltepe daikin klima servisi
ResponderEliminarüsküdar alarko carrier klima servisi
tuzla alarko carrier klima servisi
kadıköy daikin klima servisi
kartal toshiba klima servisi
ümraniye toshiba klima servisi
kartal beko klima servisi
ümraniye beko klima servisi
üsküdar lg klima servisi
başakşehir
ResponderEliminarbayrampaşa
beşiktaş
beykoz
beylikdüzü
SAW
mecidiyeköy
ResponderEliminarsakarya
istanbul
kayseri
ordu
FZQ