Why docker not syncing files inside container on Windows 10? - php

I have issue after last docker update (seems so) on Windows 10 (local development). When I changed files in PhpStorm (and in another editors - Sublime, Notepad+), after a while, files inside container didn't receive changes.
Steps that can help for a while:
If I completely shut down all containers and after that arise them again. docker-compose down && docker-compoes up
If I get into php-fpm container and for file that not changed ran touch file.php (this file will be immidiatly changed).
What I tried and it didn't help:
I restarted php-fpm and nginx containers docker-compose restart php-fpm nginx (Yes it's strange, because down|up for all container helped)
I changed inside PhpStorm setting Use Safe write(save changes for temporary file first)
Also I checked inode for file inside container. With ls -lai file.php. Before changes worked and after they broked I had the same inode number. There is no determined number of changes I must to do to break syncing, it's random, sometime 2 changes enough.
I have:
Docker version 19.03.5, build 633a0ea
docker-compose version 1.25.2, build 698e2846
docker-compose.yml
version: '3'
services:
nginx:
container_name: pr_kpi-nginx
build:
context: ./
dockerfile: docker/nginx.docker
volumes:
- ./:/var/www/kpi
- ./docker/nginx/default.conf:/etc/nginx/conf.d/default.conf
- ./docker/nginx/fastcgi.conf:/etc/nginx/fastcgi.conf
ports:
- "8081:80"
links:
- php-fpm
networks:
- internal
php-fpm:
container_name: pr_kpi-php-fpm
build:
context: ./
dockerfile: docker/php-fpm.docker
volumes:
- ./:/var/www/kpi
links:
- kpi-mysql
environment:
# 192.168.221.1 -> host.docker.internal for Mac and Windows
XDEBUG_CONFIG: "remote_host=host.docker.internal remote_enable=1"
PHP_IDE_CONFIG: "serverName=Docker"
networks:
- internal
mailhog:
container_name: pr_kpi-mailhog
image: mailhog/mailhog
restart: always
ports:
# smtp
- "1025:1025"
# http
- "8025:8025"
networks:
- internal
kpi-mysql:
container_name: pr_kpi-kpi-mysql
image: mysql:5.7
command: mysqld --sql_mode="STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
volumes:
- ./docker/storage/kpi-mysql:/var/lib/mysql
environment:
# We must change prod secrets, this is not good approach
- "MYSQL_ROOT_PASSWORD=pass"
- "MYSQL_USER=user"
- "MYSQL_PASSWORD=user_pass"
- "MYSQL_DATABASE=kpi_db"
ports:
- "33061:3306"
networks:
- internal
kpi-npm:
container_name: pr_kpi-npm
build:
context: ./
dockerfile: docker/npm.docker
volumes:
- ./:/var/www/kpi
- /var/www/kpi/admin/node_modules
ports:
- "4200:4200"
networks:
- internal
tty: true
# For xdebug
networks:
internal:
driver: bridge
ipam:
driver: default
config:
- subnet: 192.168.221.0/28
P.S. There is opened issue:
https://github.com/docker/for-win/issues/5530
P.P.S. We need to update Docker from 2.2.0.0 to 2.2.0.3, Seems it's fixed

I have a separate container for syncing my folder:
app:
image: httpd:2.4.38
volumes:
- ./:/var/www/html
command: "echo true"
I just use the basic apache image, you could use anything really though. Then in my actual containers, I use the following volumes_from key:
awesome.scot:
build: ./build/httpd
links:
- php
ports:
- 80:80
- 443:443
volumes_from:
- app
php:
build: ./build/php
ports:
- 9000
- 9001
volumes_from:
- app
links:
- mariadb
- mail
environment:
APPLICATION_ENV: 'development'
I've never had an issue using this set up, files always sync fast, and I have tested both on Mac OSX and MS Windows.
If you're interested, here is my full LAMP stack on Github https://github.com/delboy1978uk/lamp

I have the same issue on Windows10 since 31st Jan.
I have commented a line in PhpStorm and checked it in the container using vim.
The changes were not there.
If I run docker-compose down and up, the changes go in the container.
Docker version 19.03.5, build 633a0ea
docker-compose version 1.25.4, build 8d51620a
Nothing changed in my docker-compose.yml since 2018.

Related

Symfony 5 DATABASE_URL with Docker containers

I Created a docker configuration for LEMP local server. I Tried to connect the Symfony app with MySQL database version 8 but the Connection is refused.
Error: SQLSTATE[HY000] [2002] Connection refused.
The problem is with DATABASE_URL in .env file required by Symfony 5.
What is the correct value for DATABASE_URL for a given docker-compose.yml configuration ? I run this on Docker for Windows. I was Able to connect to mysql bash with username root and root password.
docker-compose.yml:
###############################################################################
# Generated on phpdocker.io #
###############################################################################
version: "3.1"
services:
memcached:
image: memcached:alpine
container_name: sampleapp-memcached
mailhog:
image: mailhog/mailhog:latest
container_name: sampleapp-mailhog
ports:
- "8001:8025"
redis:
image: redis:alpine
container_name: sampleapp-redis
mysql:
image: mysql:8.0
container_name: sampleapp-mysql
working_dir: /app
volumes:
- .:/app
environment:
- MYSQL_ROOT_PASSWORD=Ur7HJWzZ2QK9
- MYSQL_DATABASE=maindatabase
- MYSQL_USER=sampleuser
- MYSQL_PASSWORD=FxGBWfJ86ykq
ports:
- "8002:3306"
elasticsearch:
image: elasticsearch:6.5.4
container_name: sampleapp-elasticsearch
webserver:
image: nginx:alpine
container_name: sampleapp-webserver
working_dir: /app
volumes:
- .:/app
- ./phpdocker/nginx/nginx.conf:/etc/nginx/conf.d/default.conf
ports:
- "8000:80"
php-fpm:
build: phpdocker/php-fpm
container_name: sampleapp-php-fpm
working_dir: /app
volumes:
- .:/app
- ./phpdocker/php-fpm/php-ini-overrides.ini:/etc/php/7.4/fpm/conf.d/99-overrides.ini
Usually the DATABASE_URL string is a standard one:
mysql://user:pwd#host:port/db
In this case:
DATABASE_URL=mysql://sampleuser:FxGBWfJ86ykq#127.0.0.1:8002/maindatabase
Put it in your .env.local file and it should work. Note however that I work on unix and I do not have a Windows machine nearby.
Update
Following Alexander's suggestion, if you are running your Symfony app in a container (I didn't notice your webserver container, sorry!), then you should change the string to
DATABASE_URL=mysql://sampleuser:FxGBWfJ86ykq#mysql:3306/maindatabase
Note, however, that for container to container communications you should use the default port (or expose a new one).
As regards setting the serverVersion, you can use the query parameter or (IMHO a better approach) set it in your doctrine.yaml config file. In addition, note that your server version should match the one you've specified in your docker-compose file.

LAMP-Stack with Docker: How to modify httpd.conf to get access to PHP-FPM?

I have some trouble to get access from my apache container to Php-fpm. My docker-compose file is ready and works fine. But I don't know how to modify the httpd.conf in order to establish communication between both containers (Apache and Php-fpm). I have looked for some useful tutorials on the internet, but everyone uses Nginx instead of Apache2. There is also a preconfigured Docker image consisting of a Apache webserver and Php-fpm on Docker Hub, but I prefer two seperated images, because of replaceability.
Here is my docker-compose file:
version: "3.5"
services:
webserver:
build: apache/
ports:
- "8080:80"
- "443:443"
volumes:
- ~/Docker-Images/example/apache/html:/usr/local/apache2/htdocs
links:
- php-fpm
php-fpm:
build: php-fpm/
ports:
- "9000:9000"
links:
- database
database:
build: mysql/
ports:
- "3306:3306"
volumes:
- ~/Docker-Images/example/mysql/init-scripts:/init-scripts
volumes:
webserver:
database:
If you need my httpd.conf, let me know! I haven't added it, because it is a very long file with only default values.

How to use composer with docker-compose?

I am configuring the docker-compose.yml file and I want to run a PHP stack that contains Elastic, Redis, Symfony, and composer.
Now the problem that I have is, that I don't know how can I use composer with docker because some features of composer need to have PHP and some extension. I don't want to build a new image and install Nginx and PHP and composer and extension of PHP on it, I won't to have all of them in a disparate image.
What I have tried so far its this:
version : '2'
services:
nginx:
image: tutum/nginx
ports:
- "80:80"
volumes:
- ./nginx/default:/etc/nginx/sites-available/default
- ./nginx/default:/etc/nginx/sites-enabled/default
- ./logs/nginx-error.log:/var/log/nginx/error.log
- ./logs/nginx-access.log:/var/log/nginx/access.log
- ./app:/usr/share/nginx/html
phpfpm:
image: php:fpm
ports:
- 9000:9000
volumes:
- ./app:/usr/share/nginx/html
composer:
image: composer/composer:php7
command: install
volumes:
- ./app:/app
elastic2.4.4:
image: elasticsearch:2.4.4
ports:
- 9200:9200
volumes:
- ./esdata1:/usr/share/elasticsearch/data
redis:
image: redis:3.2
ports:
- 6379:6379
but this won't install dependencies.
I set up my docker-compose.yml file so one docker instance would use the composer/composer image and execute composer install within a shared container. All of the other images would then be able to access the vendor directory that composer created. The tricky part was realizing that the composer/composer image assumes that the composer.json file will be in an /app directory. I had to override this behavior by specifying my shared container as the working_dir instead:
version: '3'
services:
#=====================#
# nginx proxy service #
#=====================#
nginx_proxy:
image: nginx:alpine
networks:
- test_network
ports:
- "80:80"
- "443:443"
volumes:
# self-signed testing wildcard ssl certificate
- "./certs:/certs"
# proxy needs access to static files
- "./site1/public:/site1/public"
- "./site2/public:/site2/public"
# proxy needs nginx configuration files
- "./site1/site1.test.conf:/etc/nginx/conf.d/site1.test.conf"
- "./site2/site2.test.conf:/etc/nginx/conf.d/site2.test.conf"
container_name: nginx_proxy
#===============#
# composer.test #
#===============#
composer.test:
image: composer/composer
networks:
- test_network
ports:
- "9001:9000"
volumes:
- "./composer:/composer"
container_name: composer.test
working_dir: /composer
command: install
#============#
# site1.test #
#============#
site1.test:
build: ./site1
networks:
- test_network
ports:
- "9002:9000"
environment:
- "VIRTUAL_HOST=site1.test"
volumes:
- "./composer:/composer"
- "./site1:/site1"
container_name: site1.test
#============#
# site2.test #
#============#
site2.test:
build: ./site2
networks:
- test_network
ports:
- "9003:9000"
environment:
- "VIRTUAL_HOST=site2.test"
volumes:
- "./composer:/composer"
- "./site2:/site2"
container_name: site2.test
# networks
networks:
test_network:
Here is how the directory structure looks:
certs
test.crt
test.key
composer
composer.json
site1
app
public
Dockerfile
site1.test.conf
site2
app
public
Dockerfile
site2.test.conf
docker-compose.yml
If you look at composer/composer:php7 Dockerfile, then you will see, that it is based on php:7.0-alpine and it doesn't seem like fpm is included. So, you could use composer/composer:php7 as base image to install php-fpm on top of it.
So, since you do the mapping of your project in all three containers, running composer install in one container should result in the changes be visible in all three containers.
Me personally, I do not see a point in segregating PHP and nginx into 2 different containers, because one is highly dependable on another. And mapping your app into both containers is also a perfect example of nonsense. That's why I maintain my own public build of nginx+php Docker image. You can check it out here. There are more builds with more flavors. And they all come with composer inside.

How to run linux daemon in container linked to another container with docker-compose?

I have the following docker-compose.yml file which runs nginx with PHP support:
version: '3'
services:
nginx:
container_name: my-app-nginx
image: nginx:1.13.6
ports:
- 8080:80
volumes:
- ./nginx-default.conf:/etc/nginx/conf.d/default.conf
- ./my-app:/var/www/my-app
restart: always
depends_on:
- php
php:
container_name: my-app-php
image: php:7.1-fpm
volumes:
- ./my-app:/var/www/my-app
restart: always
The PHP application inside /var/www/my-app needs to communicate with a linux daemon (let's call it myappd).
The way I see it, I need to either:
Copy the myappd into the nginx container to /usr/local/bin, make it executable with chmod +x and run it in the background.
Create a different container, copy myappd to /usr/local/bin, make it executable with chmod +x and run it in the foreground.
Now, I'm new to Docker and I'm researching and learning about it but my best guess, given that I'm using Docker Composer, is that option 2 is probably the recommended one? Given my limited knowledge about Docker, I'd have to guess that this container would require some sort of linux-based image (like Ubuntu or something) to run this binary. So maybe option 1 is preferred? Or maybe option 2 is possible with a minimal Ubuntu image or maybe it's possible without such image?
Either way, I have no idea how would I implement that on the composer file. Especially option 2, how would the PHP application communicate with the daemon in a different container? Just "sharing" a volume (where the binary is located) like I did for nginx/php services would suffice? Or something else is required?
Simple answer is adding command entry to php service in docker-compose.yml.
Given that myappd is at ./my-app/ on host machine and at /var/www/my-app/, updated docker-compose.yml is something like following.
version: '3'
services:
nginx:
container_name: my-app-nginx
image: nginx:1.13.6
ports:
- 8080:80
volumes:
- ./nginx-default.conf:/etc/nginx/conf.d/default.conf
- ./my-app:/var/www/my-app
restart: always
depends_on:
- php
php:
container_name: my-app-php
image: php:7.1-fpm
volumes:
- ./my-app:/var/www/my-app
restart: always
command: ["/bin/sh", "/var/www/my-app/mappd", "&&", "php-fpm"]
Better answer is to create the third container which runs linux daemon.
New Dockerfile is something like following.
FROM debian:jessie
COPY ./myappd /usr/src/app/
EXPOSE 44444
ENTRYPOINT ['/bin/sh']
CMD ['/usr/src/app/myappd']
Build image and name it myapp/myappd.
Updated docker-compose.yml is something like following.
version: '3'
services:
nginx:
container_name: my-app-nginx
image: nginx:1.13.6
ports:
- 8080:80
volumes:
- ./nginx-default.conf:/etc/nginx/conf.d/default.conf
- ./my-app:/var/www/my-app
restart: always
depends_on:
- php
php:
container_name: my-app-php
image: php:7.1-fpm
volumes:
- ./my-app:/var/www/my-app
restart: always
networks:
- network1
depends_on:
- daemon
daemon:
container_name: my-app-daemon
image: myapp/myappd
restart: always
networks:
- network1
networks:
network1:
You can send request with hostname daemon from inside php. Docker container has capability to resolve hostname of another container in the same network.

Docker - how to set up Apache + PHP in docker-compose.yml

I use this to set up nginx for PHP:
nginx:
image: nginx:latest
ports:
- 8080:80
volumes:
- ./code:/code
- ./site.conf:/etc/nginx/conf.d/site.conf
links:
- php
php:
image: php:7-fpm
volumes:
- ./code:/code
But how about Apache? How can I set up Apache + PHP in docker-compose.yml?
Following this guide:
version: '2'
services:
php:
build: php
ports:
- "80:80"
- "443:443"
volumes:
- ./php/www:/var/www/html
Error:
ERROR: In file './docker-compose.yml' service 'version' doesn't have any configuration options. All top level keys in your docker-compose.yml must map to a dictionary of configuration options.
Any ideas? I'm on Xubuntu 16.04.
EDIT:
After managing to upgrade docker-compose to 1.9, I try with this file below:
version: '2'
services:
php:
build: php
expose:
- 9000
volumes:
- ./php/www:/var/www/html
apache2:
image: webdevops/apache:latest
args:
- PHP_SOCKET=php:9000
volumes:
- ./php/www:/var/www/html
ports:
- 80:80
- 443:443
links:
- php
Error:
$ sudo docker-compose up -d
Building php
ERROR: Cannot locate specified Dockerfile: Dockerfile
Docker is such as pain!
Any ideas how to fix this?
I would choose webdevops dockerized apache, because it has simple configuration:
version: '2'
services:
php:
build: php
expose:
- 9000
volumes:
- ./php/www:/var/www/html
apache2:
image: webdevops/apache:latest
args:
- PHP_SOCKET=php:9000
volumes:
- ./php/www:/var/www/html
ports:
- 80:80
- 443:443
links:
- php
Since the example above does not work, here is a different approach:
docker-compose.yml
version: '3.1'
services:
php:
image: php:apache
ports:
- 80:80
volumes:
- ./php/www:/var/www/html/
Launch the server with
docker-compose up
We need to create a new folders /php/www in current path
Create a file under php folder save as "Dockerfile" which contains as below without quote
"FROM php:5.6-apache
RUN docker-php-ext-install mysqli"
Copy your docker-compose.yml file in your current folder where your "php" folder has.
Create a sample file "index.php" under www folder (/php/www/index.php)
Run in command prompt docker-compose up -d
Open your browser type "localhost" you can see your sample file results.
Note: Above steps as per above mentioned docker-compose.yml file.
You can check this question.
If you use build instead of image, then you need "Dockerfile". Dockerfile would be use as configuration file for building image.
You maybe miss part in guide, where you should create file with name "Dockerfile" inside directory "php". Directory "php" must be in the same directory, where your "docker-compose.yml". In "docker-compose.yml" you have this line.
build: php
The line mean, that configuration file (by default: "Dockerfile") is inside of directory "php". So you should create directory "php" and file "Dockerfile" inside of it.
This is "Dockerfile" from your guide.
FROM php:5.6-apache
RUN docker-php-ext-install mysqli
docker-compose.yml reference version 2
Dockerfile reference
I found an elegant way to dynamically configure the ports and other parameters: In apache2's configuration files you can reference environment variables.
#/etc/apache2/ports.conf
# If you just change the port or add more ports here, you will likely also
# have to change the VirtualHost statement in
# /etc/apache2/sites-enabled/000-default.conf
#APACHE_HTTP_PORT_NUMBER:80
#APACHE_HTTPS_PORT_NUMBER:443
Listen ${APACHE_HTTP_PORT_NUMBER}
<IfModule ssl_module>
Listen ${APACHE_HTTPS_PORT_NUMBER}
</IfModule>
<IfModule mod_gnutls.c>
Listen ${APACHE_HTTPS_PORT_NUMBER}
</IfModule>
you can set the variables in Dockerfile or docker-compose.yml
You can set a directory with diferente Dockerfiles an declare in each service:
...
image: php:custom
build:
context: .
dockerfile: ./dockerfiles/Dockerfile-php
...
I have created a working example of PHP, APACHE, MYSQL, and PHPMYADMIN for PHP developers. You may find it useful if you need the original old-school working style. Please note that I am using port 8080 for my website and port 8081 for PHPMyAdmin. You can change these as you like.
version: '3.8'
services:
php-apache-environment:
container_name: php-apache
image: php:7.4-apache
volumes:
- ./php/src:/var/www/html/
ports:
- 8080:80
db:
image: mysql
command: --default-authentication-plugin=mysql_native_password
container_name: mysql
environment:
MYSQL_ROOT_PASSWORD: admin
MYSQL_DATABASE: ezapi
MYSQL_USER: root
MYSQL_PASSWORD: password
ports:
- "6033:3306"
volumes:
- dbdata:/var/lib/mysql
phpmyadmin:
image: phpmyadmin/phpmyadmin
container_name: phpmyadmin
links:
- mysql
environment:
PMA_HOST: mysql
PMA_PORT: 3306
PMA_ARBITRARY: 1
restart: always
ports:
- 8081:80
volumes:
dbdata:

Categories