Difference between revisions of "Docker"

From Leaky
Jump to: navigation, search
(Copied explanation of accessing host services from containers)
 
Line 1: Line 1:
 +
== Installation of Docker on CentOS7 ==
 +
 +
Use the docker-ce (community edition) packages rather than whatever might come with the OS or EPEL.
 +
 +
yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
 +
yum install docker-ce docker-compose
 +
 +
systemctl start docker
 +
systemctl enable docker
 +
docker run hello-world
 +
 +
"Installing" docker-compose (downloading the script)
 +
 +
curl -L https://github.com/docker/compose/releases/download/1.20.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
 +
chmod +x /usr/local/bin/docker-compose
 +
 +
== Assorted links ==
 +
 
A 5+bonus part guide to developing using docker - https://lockmedown.com/docker-4-devs-containerizing-app/
 
A 5+bonus part guide to developing using docker - https://lockmedown.com/docker-4-devs-containerizing-app/
  
 
See also [[Flynn]] which can provision apps using docker images.
 
See also [[Flynn]] which can provision apps using docker images.
  
 +
http://blog.dubizzle.com/boilerroom/2016/08/18/setting-development-environment-docker-compose/
 +
https://docs.docker.com/compose/wordpress/
 +
https://hub.docker.com/_/php/
 +
 +
== Sample Dockerfile which builds an Apache container ==
 +
 +
cat > Dockerfile <<'EOF'
 +
FROM php:7.2-apache
 +
# RUN docker-php-ext-install
 +
COPY php-shop.ini /tmp/etc/php.d/shop.ini
 +
ENV APACHE_DOCUMENT_ROOT /home/docker1/public_html
 +
RUN sed -ri -e 's!/var/www/html!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/sites-available/*.conf
 +
RUN sed -ri -e 's!/var/www/!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
 +
RUN sed -ri -e 's!User www-data!User shop!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
 +
RUN sed -ri -e 's!Group www-data!Group shop!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
 +
EOF
 +
 +
Build the image
 +
 +
docker build -t testshop .
 +
 +
Create the container from the new image. This uses port 8010 for the web server and mounts /home/docker1/public_html from the host into the container
 +
 +
docker create --name myshopcontainer -it -p 8010:80/tcp --mount type=bind,source=/home/docker1/public_html,target=/home/docker1/public_html testshop:latest
 +
 +
Start the container
 +
 +
docker start myshopcontainer
 +
 +
== Other commands ==
 +
 +
Show all the containers that currently exist on the host
 +
 +
docker container list --all
 +
 +
Remove '''all''' stopped containers
 +
 +
docker container prune
 +
 +
List all images that are available in the cache
 +
 +
docker image list
 +
 +
Remove an image from the host cache
  
 +
docker image rm NAME
  
  

Latest revision as of 11:22, 11 October 2021

Installation of Docker on CentOS7

Use the docker-ce (community edition) packages rather than whatever might come with the OS or EPEL.

yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
yum install docker-ce docker-compose
systemctl start docker
systemctl enable docker
docker run hello-world

"Installing" docker-compose (downloading the script)

curl -L https://github.com/docker/compose/releases/download/1.20.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose

Assorted links

A 5+bonus part guide to developing using docker - https://lockmedown.com/docker-4-devs-containerizing-app/

See also Flynn which can provision apps using docker images.

http://blog.dubizzle.com/boilerroom/2016/08/18/setting-development-environment-docker-compose/ https://docs.docker.com/compose/wordpress/ https://hub.docker.com/_/php/

Sample Dockerfile which builds an Apache container

cat > Dockerfile <<'EOF'
FROM php:7.2-apache
# RUN docker-php-ext-install
COPY php-shop.ini /tmp/etc/php.d/shop.ini
ENV APACHE_DOCUMENT_ROOT /home/docker1/public_html
RUN sed -ri -e 's!/var/www/html!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/sites-available/*.conf
RUN sed -ri -e 's!/var/www/!${APACHE_DOCUMENT_ROOT}!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
RUN sed -ri -e 's!User www-data!User shop!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
RUN sed -ri -e 's!Group www-data!Group shop!g' /etc/apache2/apache2.conf /etc/apache2/conf-available/*.conf
EOF

Build the image

docker build -t testshop .

Create the container from the new image. This uses port 8010 for the web server and mounts /home/docker1/public_html from the host into the container

docker create --name myshopcontainer -it -p 8010:80/tcp --mount type=bind,source=/home/docker1/public_html,target=/home/docker1/public_html testshop:latest

Start the container

docker start myshopcontainer

Other commands

Show all the containers that currently exist on the host

docker container list --all

Remove all stopped containers

docker container prune

List all images that are available in the cache

docker image list

Remove an image from the host cache

docker image rm NAME


Docker containers unable to access services on host

Copied from https://github.com/moby/moby/issues/16137#issuecomment-271615192 as it took me a while to find.

The ultra short version of the fix

Run all these commands

nmcli connection modify docker0 connection.zone trusted
systemctl stop NetworkManager.service
firewall-cmd --permanent --zone=trusted --change-interface=docker0
systemctl start NetworkManager.service
nmcli connection modify docker0 connection.zone trusted
systemctl restart docker.service

The explained version and how to check everything worked

The current workaround that seems to work ends up creating a trusted.xml file AND a ifcfg-docker0 file. The trusted.xml file would set the zone after a reboot (read and used by firewalld) and the ifcfg-docker0 would set the zone after reload or restart of services and interface or connections restarted (read and used mainly by NetworkManager).

To achieve that:

  • After having the new interface (e.g. after installing Docker) and having FirewallD enabled and started, set the zone of the interface with NetworkManager's nmcli:
nmcli connection modify docker0 connection.zone trusted

...that would set the zone in NetworkManager and FirewallD for the current session and will create the ifcfg-docker0 file for services, network or interfaces' restarts and reloads.

  • Check that the file was created with:
cat /etc/sysconfig/network-scripts/ifcfg-docker0

...it should output something like:

DEVICE=docker0
STP=no
BRIDGING_OPTS=ageing_time=299
TYPE=Bridge
BOOTPROTO=none
IPADDR=172.17.0.1
PREFIX=16
DEFROUTE=yes
IPV4_FAILURE_FATAL=no
IPV6INIT=no
NAME=docker0
UUID=5ccc8292-95a2-40d5-9ed6-ab6202fa629e
ONBOOT=no
ZONE=trusted

...specifically, it should have a:

ZONE=trusted
  • Now we need FirewallD to generate that trusted.xml file so that it uses it while booting, but for FirewallD to write that file it must think that NetworkManager is not active, so stop NetworkManager:
systemctl stop NetworkManager.service
  • Now set the zone with FirewallD's firewall-cmd:
firewall-cmd --permanent --zone=trusted --change-interface=docker0
  • As NetworkManager is stopped, it won't modify (or even try to create) an ifcfg-docker0 file, if NetworkManager was running it would try to create that same file and wouldn't work after reboot. But this time, as Networkmanager is stopped, it will create a file in the other place for configurations, we can see it with:
cat /etc/firewalld/zones/trusted.xml

...outputs:

<?xml version="1.0" encoding="utf-8"?>
<zone target="ACCEPT">
  <short>Trusted</short>
  <description>All network connections are accepted.</description>
  <interface name="docker0"/>
</zone>

...we can see that the docker0 interface was added to this trusted zone by the:

<interface name="docker0"/>
  • And now we can start NetworkManager again:
systemctl start NetworkManager.service
  • It is possible that you need to set the zone with NetworkManager again as firewalld might have "forgotten" the zone settings, it won't do any harm:
nmcli connection modify docker0 connection.zone trusted
  • We can check that FirewallD thinks that the docker0 is in the trusted zone. Check the zone of the docker0 interface as seen by FirewallD:
firewall-cmd --get-zone-of-interface=docker0

...outputs:

trusted
  • And NetworkManager also thinks that it is in the trusted zone. Check the zone of the docker0 interface as seen by NetworkManager:
nmcli connection show docker0 | grep zone

...outputs something like:

connection.zone:                        trusted
  • We can restart the system and check that the zone will persist, for both FirewallD and NetworkManager.
  • If you already checked that it worked and don't want to restart the system, you still will have to restart the Docker service for it to re-create it's ipatables rules:
systemctl restart docker.service
  • If you need to change more things with FirewallD and NetworkManager, or if something doesn't seem to be working, please read that issue in FirewallD, as here I'm not showing a lot of the details: https://github.com/t-woerner/firewalld/issues/195