I am a newbie to docker and trying to understand how to create dockerfiles.
While attempting the same I created this sample file
FROM debian
RUN apt-get update && apt-get upgrade -y
RUN apt-get install apache2 -y
COPY ./index.html /etc/www/html/
CMD service apache2 start && /bin/bash
The CMD part has always confused me and I am using the /bin/bash mostly because I read somewhere that we need to make sure that there is some running command in the Docker Image when we are bringing it up. I use this to run the image :-
docker run -t -p 5000:8080 --name myfinal 912ccd578eae
where I'm using the id of the image built. As you can see, I'm a novice and even the minutest of details would help.
The usual CMD for apache2 should be
CMD ["/usr/sbin/apache2", "-D", "FOREGROUND"]
That way, you don't have to use the "bash" trick to keep a foreground process running.
And any exit signal will impact correctly the apache2 process, not the bash one.
No need for ENTRYPOINT here: Docker maintains a default entrypoint, /bin/sh.
So this (with CMD) is the same as:
/bin/sh -c “apachectl -D FOREGROUND”
Related
This question already has answers here:
systemctl command doesn't work inside docker-container
(2 answers)
Closed 1 year ago.
I am new in docker, I want to build an image with Ubuntu 20.04 and bind9 service installation.
below is my code of docker file
FROM ubuntu:20.04
ENV TZ=Asia
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
RUN apt-get update && apt-get install -y \
apt-utils \
systemctl \
bind9
CMD ["/usr/sbin/named", "-g", "-c", "/etc/bind/named.conf", "-u", "bind"]
CMD systemctl restart bind9
When I execute following command to build an image,
sudo docker image build --tag bind9server .
It works fine.
Step 6/6 : CMD systemctl restart bind9
---> Running in f982f314c216
But when I run this docker image, I am getting an error like below
ERROR:systemctl:Unit bind9.service could not be found.
Can anyone help me, after installation of Bind9, why I am getting an error with above command?
Error comes with Docker only, if I run same command in Host environment which is Ubuntu 20.04 then it works fine.
First thing: you should use a long running command for your last CMD, otherwise the container will exit once done. The purpose of CMD is to provide a default entry-point to your container, so even if there was a bind9 service, you container would exit immediately. Also, only the last CMD takes effect (see docs).
Second: see this question for an explanation of why it's not such a good idea to run with systemd inside a Docker container. You are much better off with your first try, that is calling named directly.
Third: on a "normal" host, when you are unsure about an unit name such as bind9, you can try to inspect all the known units with systemctl list-units --all. It looks like your service is called named.
I am new in docker, I want to build an image with Ubuntu 20.04 and bind9 service installation.
below is my code of docker file
FROM ubuntu:20.04
ENV TZ=Asia
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
RUN apt-get update && apt-get install -y \
apt-utils \
systemctl \
bind9
RUN /usr/sbin/named -g -c /etc/bind/named.conf -u bind
RUN systemctl restart bind9
I am getting an error like below
ERROR:systemctl:Unit bind9.service could not be found.
Can anyone help me, after installation of Bind9, why I am getting an error with above command?
Error comes with Docker only, if I run same command in Host environment which is Ubuntu 20.04 then it works fine.
You generally cannot use service management commands (like service or systemctl, etc) in a container, because there is no service manager running.
Additionally, even if there were a service manager running, it wouldn't make any sense to interact with it in a RUN command: these commands are part of the image build process, and there are no persistent services running at this point. A RUN command runs in an isolated environment that is completely torn down when the RUN command completes.
If you want bind to start when you run a container using your image, you would need to place the appropriate bind command line into the CMD option. For example, the official bind9 image includes:
CMD ["/usr/sbin/named", "-g", "-c", "/etc/bind/named.conf", "-u", "bind"]
(See the Dockerfile for details)
I am new in docker and I am learning how to build a new container. I faced an issue to build a container, inherited from Ubuntu. I want to install Python3 and some other packages on the Ubuntu container with proper messages, but it does not work.
When I build a container with Dockerfile with:
FROM ubuntu
CMD echo "hello new Ubuntu"
RUN apt-get upgrade && apt-get update && apt-get install -y python3
CMD echo "installed python"
the call of the built Ubuntu with docker run -it my_new_ubuntu does not enter to the interactive mode and it only prints installed python, not even the "hello new Ubuntu".
Although, when I build a container with Dockerfile without any message:
FROM ubuntu RUN apt-get upgrade && apt-get update && apt-get install
-y python3
and call the built container with docker run -it my_new_ubuntu, it enters the Ubuntu root and I can call python. I am not sure why the first Dockerfile does not work. It seems that I cannot mix RUN and CMD commands together.
I appreciate any help or comment.
RUN specifies a command to run while building an image from your Dockerfile. You can have multiple RUN instructions, and each will apply to the image in the order specified.
CMD specifies the default command the image has been instantiated into a container and started. If there are multiple CMD instructions, only the last one applies.
Trying to run sendmailconfig after my PHP FPM (7.1-fpm) docker has started, but i'm having a hard time doing so without getting in the way of the FPM part of the container.
FROM php:7.1-fpm
RUN apt-get update && apt-get install
CMD "/usr/local/bin/config.sh" && /bin/bash
I've tried making a script that purely executes yes | sendmailconfig but seems to stop the image's default script from running which causes PHP-FPM to never actually run.
The reason I want this done in the image is because I have to run the sendmailconfig command every time I restart the container, which is impractical when managing multiple docker stacks.
Set your entrypoint to run a file you've copied in, that file should have something like the following in it
/usr/local/bin/config.sh
# If this isn't the correct command for you to start php-fpm look up the correct one for your image
sudo service php7.1-fpm start
# Execute the CMD passed in from the dockerfile
sudo -H bash -c "$#;"
# You'll probably be ok with just `bash -c "$#;"` if you don't have sudo installed
Dockerfile
FROM drupal
RUN apt-get update
RUN apt-get install openssh-server -y
RUN apt-get install -y supervisor
#SS Related Fix : https://github.com/Microsoft/WSL/issues/3621
RUN mkdir -p /run/sshd
# SS Access Configuration
RUN echo "root:Docker!" | chpasswd
#Project Uplaod
RUN rm -rf /var/www/html/*
COPY ./html/ /var/www/html/
# Startup Configuration
COPY servername.conf /etc/apache2/conf-enabled/servername.conf
ADD supervisord.conf /etc/supervisor/conf.d/supervisord.conf
CMD ["/usr/bin/supervisord"]
Start Command : docker -D run -p 80:80 -p 2222:22 -it /bin/bash
[supervisord]
nodaemon=true
[program:SSH]
command=/usr/sbin/sshd start
[program:Apache]
command=/etc/init.d/apache2 start
when i jump into Shell and run that command it works but when i start container its not starting up the web server.
As standing in documentation
To start supervisord, run $BINDIR/supervisord. The resulting process
will daemonize itself and detach from the terminal. It keeps an
operations log at $CWD/supervisor.log by default.
You may start the supervisord executable in the foreground by passing
the -n flag on its command line. This is useful to debug startup
problems.
So systemd detach from main process what means for docker that process ended - exit container. To solve your problem you need to change CMD section to
CMD ["/usr/bin/supervisord", "-n"]
When you run
docker -D run -p 80:80 -p 2222:22 -it /bin/bash
The last part of the command, /bin/bash, replaces the CMD in the Dockerfile, so you only get the GNU bash shell. You should remove that part of the line and the standard command from your image will run.
You might consider how much you actually need an interactive shell in your Docker environment. Most application images are set up to run totally on their own without manual setup steps; compare the stock mysql or nginx images, for instance, which don't include any kind of remote login system. Also consider that anyone who can run docker history can now trivially find out your root password, and you have no way to manage the sshd host keys. I'd suggest removing this entire supervisord/sshd system and just packaging your application.