Docker stack isn't updating the folder structure with new image - docker-compose

Recently I have changed my dockerfile to use a cleaner folder structure but this isn't being updated in the stack deploy
My folder structure:
├── Dockerfile.dev
├── Dockerfile.prod
├── env/
├── requirements.txt
├── src
│   ├── app
│   │   ├── __init__.py
│   │   ├── modules
│   │   ├── __pycache__
│   │   ├── services
│   │   └── util
│   ├── __init__.py
│   └── main.py
└── version.conf
Docker compose file (recorder api part):
api-recorder:
image: img-api-recorder:latest
build:
context: ../api-recorder-python/
dockerfile: Dockerfile.${DOCKER_ENV}
deploy:
mode: replicated
replicas: 1
restart_policy:
condition: on-failure
placement:
constraints: [node.role == manager]
volumes:
- ${BASE_DIR}api-recorder-python:${WORKDIR}
depends_on:
- zookeeper
environment:
PYTHON_ENV: ${DOCKER_ENV}
Old Dockerfile:
FROM python:3
WORKDIR /usr/src/app
RUN apt-get update
RUN pip install --upgrade pip
RUN pip install kafka-python
RUN pip install python-dotenv
RUN pip install pymongo pymongo[srv]
RUN pip install psycopg2
RUN ln -snf /usr/share/zoneinfo/America/Sao_Paulo \
/etc/localtime && \
echo "America/Sao_Paulo" > /etc/timezone
COPY . .
CMD ["python3", "-u", "src/main.py"]
So what I did was create the requirements.txt and changed the COPY command
New Dockerfile:
FROM python:3
WORKDIR /usr/src
COPY ./requirements.txt ./
RUN apt-get update
RUN pip install --upgrade pip
RUN pip install -r requirements.txt
RUN ln -snf /usr/share/zoneinfo/America/Sao_Paulo \
/etc/localtime && \
echo "America/Sao_Paulo" > /etc/timezone
COPY ./src ./
# CMD ["python3", "-u", "main.py"]
CMD ["python3", "-m", "http.server"]
The weird thing is that the new Dockerfile is being built correctly in a new image because if I run docker run -it [image_name]:latest bash and list the directories I receive this:
which is the new structure made by the new Dockerfile on the other hand if I run the stack deploy and enter inside the container I will be in the /usr/src path and it will have a wrong structure:
The content inside the app folder is wrong, it should have the program code inside it
How can I clean it? I already tried delete all the volumes, images, containers, I even reinstalled docker, I don't know what else to do.

Your docker compose has both an image and build section. Precedence is given to the image so that is being used not the build.
You probably want:
api-recorder:
build:
context: ../api-recorder-python/
dockerfile: Dockerfile.${DOCKER_ENV}
deploy:
mode: replicated
replicas: 1
restart_policy:
condition: on-failure
placement:
constraints: [node.role == manager]
volumes:
- ${BASE_DIR}api-recorder-python:${WORKDIR}
depends_on:
- zookeeper
environment:
PYTHON_ENV: ${DOCKER_ENV}

I discovered what is happening.
In my docker-compose file I was setting a volume that was overwriting my path, this is happening because my WORKDIR environment is set to /usr/src/app which is the same path that I set in my dockerfile but in the docker-compose this path is being mirrored to my api-recorder-python folder structure
So the only thing that I did was change the volume to ${BASE_DIR}api-recorder-python/src:${WORKDIR} and I changed my WORKDIR to /usr/src and all worked fine
Here:
api-recorder:
image: img-api-recorder:latest
build:
context: ../api-recorder-python/
dockerfile: Dockerfile.${DOCKER_ENV}
deploy:
mode: replicated
replicas: 1
restart_policy:
condition: on-failure
placement:
constraints: [node.role == manager]
volumes:
- ${BASE_DIR}api-recorder-python/src:${WORKDIR}
depends_on:
- zookeeper
environment:
PYTHON_ENV: ${DOCKER_ENV}

Related

Multiple dockerised PHP-FPM and Nginx applications

my goal is to get multiple PHP services running. So that I can use the same framework I would copy the code from framework to each service (1 & 2).
tree
├── Framework
│ └── frw.class.php
├── CodeService1
│ └── index.php (rescue frw.class.php)
├── CodeService2
│ └── index.php (rescue frw.class.php)
├── docker-compose.yml
├── nginx
├──conf
└── myapp.conf
version: '2'
services:
phpfpm:
image: 'bitnami/php-fpm:8.0.2'
container_name: project1
networks:
- app-tier
volumes:
- ./Framework:/app
- ./CodeService1:/app/service1
service2:
image: 'bitnami/php-fpm:8.0.2'
container_name: Service1
networks:
- app-tier
volumes:
- ./Framework:/app
- ./CodeService2:/app/service2
nginx:
image: 'bitnami/nginx:latest'
depends_on:
- phpfpm
- service2
networks:
- app-tier
ports:
- '80:8080'
- '443:8443'
volumes:
- ./nginx/conf/myapp.conf:/opt/bitnami/nginx/conf/server_blocks/myapp.conf
networks:
app-tier:
driver: bridge
currently the index-files looks like
CodeService1\index.php
<?php declare (strict_types = 1);
echo ("Service1</br>");
CodeService2\index.php
<?php declare (strict_types = 1);
echo ("Service2</br>");
But this won't work. I also tried to outsource the part of create the service (image and copy files) to separates Dockerfiles. but this also won't run.
i call localshost/service1 or localshost/service1 or .
thanks a lot
Most probable is that in your nginx host you set upstream to phpfpm
set $upstream phpfpm
and that's why CodeService1 only is resolved.
You can set upstream conditionaly, e.g:
# set default to codeservice1
set $upstream phpfpm:9000;
# if service2 url, resolve from service2
if ($request_uri ~ "(^/service2)"){
set $upstream service2:9000
}
fastcgi_pass $upstream;

Docker-compose.yml Volummes: and -mount command not the same results

I have been searching for over a week on this issue with no solution.
I am trying to mount a volume from the docker-compose.yml
Here is my directory structure:
-docker-compose.yml
-api
-dockerfile
-frontend
-dockerfile
-models
I have want the models shared between the api service, and the frontend service. first I attempt to get the models into the container. In the container's /usr/src/models directory along with all of its contents. This command works GREAT
docker run -it --mount src="$(pwd)/models",target=/usr/src/models,type=bind -p 3000:3000 website_api
and an important thing to note is that it produces this, when I inspect the docker container in VS code:
website_api.json:
"Mounts": [
{
"Type": "bind",
"Source": "/home/kevin/source/repos/cropwatch/website/models",
"Target": "/usr/src/models"
}
],
This is inside of the json file with lots of other stuff.
however, when I run my docker-compose, that is setup like so:
version: "3.8"
services:
api:
container_name: api
restart: always
build:
context: ./
dockerfile: ./api/dockerfile
ports:
- "3000:3000"
- "3001:3001"
volumes:
- type: bind
source: "./models"
target: "/usr/src/models"
the mounts path in the json file displays as so:
"Mounts": [],
and the /usr/src/models directory in my container is empty...
So these two things do not do the same thing as I seemed to believe before.
Any ideas as to what I am doing wrong in my docker-compose.yml file?
This should do the job:
tree
.
├── api
│   └── dockerfile
├── docker-compose.yml
└── models
└── someFile
cat docker-compose.yml
version: "3.8"
services:
api:
container_name: api
restart: always
build:
context: ./
dockerfile: ./api/dockerfile
volumes:
- ./models:/usr/src/models
docker-compose up -d
docker exec 5ea0c49003f6 sh -c "ls -la /usr/src/models"
total 8
drwxr-xr-x 2 1000 1000 4096 Aug 3 20:09 .
drwxr-xr-x 1 root root 4096 Aug 3 20:15 ..
-rw-r--r-- 1 1000 1000 0 Aug 3 20:09 someFile
docker container inspect --format '{{.Mounts}}' 5ea0c49003f6
[{bind /home/neo/so-playground/mounts-63236400/models /usr/src/models rw true rprivate}]

How to dockerize my dotnet core + postgresql app?

I have a dotnet core application created with Angular template that communicates with a postgresql database.
On my local machine, I run the following command on my terminal to run the database container:
docker run -p 5432:5432 --name accman-postgresql -e POSTGRES_PASSWORD=mypass -d -v 'accman-postgresql-volume:/var/lib/postgresql/data' postgres:10.4
And then by pressing F5 in VsCode, I see that my application works great.
To dockerise my application, I added this file to the root of my application.
Dockerfile:
FROM mcr.microsoft.com/dotnet/core/sdk:2.2 AS build-env
# install nodejs for angular, webpack middleware
RUN apt-get update
RUN apt-get -f install
RUN apt-get install -y wget
RUN wget -qO- https://deb.nodesource.com/setup_11.x | bash -
RUN apt-get install -y build-essential nodejs
WORKDIR /app
# Copy csproj and restore as distinct layers
COPY *.csproj ./
RUN dotnet restore
# Copy everything else and build
COPY . ./
RUN dotnet publish -c Release -o out
# Build runtime image
FROM mcr.microsoft.com/dotnet/core/aspnet:2.2
WORKDIR /app
COPY --from=build-env /app/out .
ENTRYPOINT ["dotnet", "Web.dll"]
Now I think I have to create a docker-compose file. Would you please help me on creating my docker-compose.yml file?
Thanks,
I figured it out, here is my final version of docker-compose.yml file:
version: '3'
services:
web:
container_name: 'accman-web-app'
image: 'accman-web'
build:
context: .
dockerfile: Dockerfile
ports:
- '8090:80'
depends_on:
- 'postgres'
networks:
- accman-network
postgres:
ports:
- '5432:5432'
container_name: accman-postgresql
environment:
- POSTGRES_PASSWORD=mypass
volumes:
- 'accman-postgresql-volume:/var/lib/postgresql/data'
image: 'postgres:10.4'
networks:
- accman-network
volumes:
accman-postgresql-volume:
networks:
accman-network:
driver: bridge
You can use composerize to find out how you can add services to your docker-compose file.
Now you can run these following commands consecutively:
docker-compose build
docker-compose up
And voila!

Deploying app on Docker with Tomcat and PostgreSQL

I have an testApp.war which I'd like to deploy on Tomcat through docker (docker is on 10.0.2.157). My testApp will work properly only with postgres DB and specified user testUser and password testUserPasswd. I built such a structure:
.
├── db
│   ├── Dockerfile
│   ├── pg_hba.conf
│   └── postgresql.conf
├── docker-compose.yml
└── web
├── context.xml
├── Dockerfile
├── software
│   └── testApp.war
└── tomcat-users.xml
Content of all these files are attached below. I start my containers with command:
docker-compose up -d
However when I go to Tomcat on webbrowser (http://10.0.2.157:8282/manager/html) and try to start my testApp I got:
HTTP Status 404 – Not Found
Type Status Report
Message /testApp/
Description The origin server did not find a current representation
for the target resource or is not willing to disclose that one exists.
Apache Tomcat/8.5.20
What I'm doing wrong? Could you help me with this?
db/Dockerfile
FROM postgres:9.5
MAINTAINER riwaniak
ENV POSTGRES_USER testUser
ENV POSTGRES_PASSWORD testUserPasswd
ENV POSTGRES_DB testUser
ADD pg_hba.conf /etc/postgresql/9.5/main/
ADD postgresql.conf /etc/postgresql/9.5/main/
db/pg_hba.conf
local all all trust
host all all 127.0.0.1/32 md5
host all all 0.0.0.0/0 md5
host all
db/postgresql.conf
listen_addresses='*'
web/context.xml
<?xml version="1.0" encoding="UTF-8"?>
<Context antiResourceLocking="false" privileged="true" >
<!--
<Valve className="org.apache.catalina.valves.RemoteAddrValve"
allow="127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
-->
</Context>
web/Dockerfile
FROM tomcat:8.5.20-jre8
MAINTAINER riwaniak
COPY ./software /usr/local/tomcat/webapps/
CMD ["catalina.sh", "run"]
web/tomcat-users.xml
<?xml version="1.0" encoding="UTF-8"?>
<tomcat-users xmlns="http://tomcat.apache.org/xml"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://tomcat.apache.org/xml tomcat-users.xsd"
version="1.0">
<role rolename="tomcat"/>
<role rolename="admin-gui"/>
<role rolename="manager-gui"/>
<user username="tomcat" password="tomcat" roles="tomcat,admin-gui,manager-gui"/>
</tomcat-users>
and finally docker-compose.yml
version: '2'
services:
testApp:
build: ./web
volumes:
- /path/to/tomcat/folder/web/tomcat-users.xml:/usr/local/tomcat/conf/tomcat-users.xml
- /path/to/tomcat/folder/web/context.xml:/usr/local/tomcat/webapps/HelpdeskApp/META-INF/context.xml
- /path/to/tomcat/folder/web/context.xml:/usr/local/tomcat/webapps/host-manager/META-INF/context.xml
- /path/to/tomcat/folder/web/context.xml:/usr/local/tomcat/webapps/manager/META-INF/context.xml
ports:
- "8282:8080"
links:
- testAppdb
networks:
- testAppnet
testAppdb:
build: ./db
ports:
- "5555:5432"
volumes:
- /srv/docker/postgresql:/var/lib/postgresql
- /path/to/tomcat/folder/db/postgresql.conf:/etc/postgresql/9.5/main/postgresql.conf
- /path/to/tomcat/folder/db/pg_hba.conf:/etc/postgresql/9.5/main/pg_hba.conf
command: postgres -c config_file=/etc/postgresql/9.5/main/postgresql.conf
networks:
- testAppnet
networks:
testAppnet:
driver: bridge
ipam:
driver: default
config:
- subnet: 172.28.0.0/16
OK, I got the solution!
Thanks #Tarun Lalwani for supporting and suggestion.
I had wrong application.yml configuration in Tomcat container. Docker mapped ip addresses of my containers but I shouldn't write just "10.0.2.157" but name of containers. So in my example I've got smth like below:
(...)
environments:
development:
dataSource:
dbCreate: update
url: jdbc:postgresql://10.0.2.157:5432/helpdesk_dev
(...)
However right solution was to map name of postgres container (testAppdb), so correct conf is:
(...)
environments:
development:
dataSource:
dbCreate: update
url: jdbc:postgresql://testAppdb:5432/test_dev
(...)

Including vars into an Ansible playbook

I wanted to give deploying django projects with ansible a shot but I'm stuck on what seems to be a pretty basic issue.
I've created a basic playbook to deploy my Postgres server.
---
- hosts: default
remote_user: myusername
become: yes
become_method: sudo
become_user: postgres
vars:
- include: vars/databases.yml
tasks:
- name: Ensure Postgres server is running
service: name=postgresql state=started enabled=yes
- name: Create postgres database
postgresql_db:
name: '{{ db_name }}'
state: present
encoding: 'UTF-8'
I run the playbook and I get this error
fatal: [default]: FAILED! => {"failed": true, "msg": "'db_name' is undefined"}
In order to keep all of my passwords and such out of version control I've created a directory vars. It's located in my project structure like this with all my ansible yaml files in deploy and all my vars files in the vars subdirectory.
..
├── deploy
│   └── vars
..
├── myproject
├── manage.py
└── utils
# var/databases.yml
db_name: <database name>
What's going on here?
Update: Added contents of var/databases.yml as requested.
The variable db_name must be assigned a value before trying to create a database. the error clearly stating that <"'db_name' is undefined">, the variable db_name is undefined/unassigned.
See below sample code for an example
vars:
dbname: myapp
dbuser: django
dbpassword: mysupersecretpassword
tasks:
- name: ensure database is created
postgresql_db: name={{dbname}}
Can you change the the vars with vars_files like this:
vars_files:
- vars/databases.yml