docker
docker copied to clipboard
[Question] Serving fpm-alpine image with nginx
I am trying to get the fpm-alpine
image to work with nginx.
docker-compose.yml
version: "3.7"
networks:
mynet:
volumes:
mariadb_data:
phpmyadmin_data:
services:
mariadb:
image: mariadb:10.4.8-bionic
environment:
MYSQL_DATABASE: mydb
MYSQL_ROOT_PASSWORD: password
MYSQL_USER: admin
MYSQL_PASSWORD: password
volumes:
- mariadb_data:/var/lib/mysql/
networks:
- mynet
phpmyadmin:
image: phpmyadmin/phpmyadmin:fpm-alpine
volumes:
- phpmyadmin_data:/var/www/html/
networks:
- mynet
depends_on:
- mariadb
nginx:
image: nginx:1.17.4-alpine
volumes:
- ./default.conf:/etc/nginx/conf.d/default.conf:ro
- phpmyadmin_data:/var/www/html/:ro
ports:
- "80:80"
networks:
- mynet
depends_on:
- mariadb
- phpmyadmin
default.conf
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name www.example.com;
root /var/www/html/;
index index.php index.html index.htm;
set $upstream phpmyadmin:9000;
location ~ \/pma {
fastcgi_pass $upstream;
fastcgi_index index.php;
fastcgi_split_path_info ^(.+\.php)(/.*)$;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
Then: docker-compose up
.
When I access http://www.example.com/pma
I get
502 Bad Gateway
I also tried to get it working using a port instead of path, i.e. http://www.example.com:8080
instead of http://www.example.com/pma
.
The docs show examples using traefik and haproxy, but not for nginx.
Can someone spot the error in my setup, or does someone have a working example to share?
@lonix1 try port 9000
on host phpmyadmin
for fastcgi_pass
since you are sending the script to the cgi and not to the web server
If it does not work comment back here :)
@williamdes Thanks - yes you are right it should be 9000
! I edited it above.
However, it still does not work :-(
curl http://www.example.com/pma
gives:
File not found.
The docker log shows:
"GET /pma/index.php" 404
maybe you should change /var/www/html
to /usr/src/phpmyadmin
See: https://github.com/phpmyadmin/docker/blob/master/fpm-alpine/Dockerfile#L77
I assume you have data into the volume phpmyadmin_data
https://superuser.com/a/435969/609233 I would write the nginx config block like that
location ~ \/pma {
rewrite ^/pma(/.*)$ $1 last;
fastcgi_pass $upstream;
fastcgi_index index.php;
include snippets/fastcgi-php.conf;
# remove line below ?
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
You are maybe missing the rewrite part since the files are in the root folder and not in /pma
When I do docker-compose up
for the first time, it says
phpMyAdmin not found in /var/www/html - copying now... Complete! phpMyAdmin has been successfully copied to /var/www/html
That's why I used that path. But even if I use /usr/src/phpmyadmin
it fails with same error. I checked that there are files in there, looks okay.
I tried the new location
block also. Same error (file not found).
Does that actually work for you?
I will carry on fiddling to get it working. Maybe we can then add it to the docs.
~After hours (since my last post) I could not make a rewrite folder that worked.~
Light version
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name williamdes.local default_server;
root /var/www/html/;
index index.php index.html index.htm;
set $upstream phpmyadmin:9000;
location ~ \.php$ {
try_files $uri = 404;
#fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass $upstream;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
version: "3.7"
networks:
mynet:
volumes:
mariadb_data:
phpmyadmin_data:
services:
mariadb:
image: mariadb:10.4.8-bionic
environment:
MYSQL_DATABASE: mydb
MYSQL_ROOT_PASSWORD: password
MYSQL_USER: admin
MYSQL_PASSWORD: password
volumes:
- mariadb_data:/var/lib/mysql/
networks:
- mynet
phpmyadmin:
image: phpmyadmin/phpmyadmin:fpm-alpine
environment:
PMA_HOST: mariadb
volumes:
- phpmyadmin_data:/var/www/html/
networks:
- mynet
depends_on:
- mariadb
nginx:
image: nginx:1.17.4-alpine
volumes:
- ./default.conf:/etc/nginx/conf.d/default.conf:ro
- phpmyadmin_data:/var/www/html/:ro
ports:
- "90:80"
networks:
- mynet
depends_on:
- mariadb
- phpmyadmin
Using a proxy
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name williamdes.local default_server;
root /var/www/html/;
index index.php index.html index.htm;
set $upstream phpmyadmin:9000;
location ^~ /pma {
rewrite /pma/(.*) /$1 last;
proxy_pass http://localhost:80;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-Proto $http_x_forwarded_proto;
proxy_cache_bypass $http_upgrade;
proxy_redirect off;
}
location ~ \.php$ {
try_files $uri = 404;
#fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass $upstream;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
Using CGI
Thanks to: https://stackoverflow.com/a/29213330/5155484
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name williamdes.local default_server;
root /var/www/html/;
index index.php index.html index.htm;
set $upstream phpmyadmin:9000;
location ^~ /pma {
rewrite /pma/(.*) /$1 last;
try_files $uri = 404;
#fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass $upstream;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
location ~ \.php$ {
try_files $uri = 404;
#fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass $upstream;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
@lonix1 the CGI version is what you want
@williamdes wow thanks! I used the "Using CGI" section, and got it working finally, but on the wrong path:
curl http://www.example.com/pma
gives 404
but
curl http://www.example.com/
gives the phpmyadmin login page
BTW, I assume your "Using a proxy" section is for the latest
image, and "Using CGI" is for the fpm-alpine
and fpm
images?
I think you are correct on what you assume
@lonix1 can you paste your final configuration?
I made it work with the ^~
and position can be important from what Internet says
Okay I got it to work, thanks to this!
Notes:
- No rewriting necessary
- I did not need to set
PMA_ABSOLUTE_URI
- not sure why?
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name www.example.com example.com;
set $upstream phpmyadmin:9000;
location ^~ /phpmyadmin {
alias /var/www/html/;
index index.php;
location ~ \.php$ {
try_files $uri = 404;
fastcgi_pass $upstream;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $request_filename;
}
}
}
This should be in the docs. If someone knows how to do that, please add @williamdes' code for latest
image and my code for fpm-alpine
and fpm
images.
@williamdes BTW thanks for taking the time to help me... Appreciated!
@lonix1 I think it is because all files need to know their base path?
@williamdes Yes... so we need to correctly set SCRIPT_FILENAME
.
@lonix1 please post the config when you have a working example ;)
@williamdes This works for me:
docker-compose.yml
version: "3.7"
networks:
mynet:
volumes:
mariadb_data:
phpmyadmin_data:
services:
mariadb:
image: mariadb:10.4.8-bionic
environment:
MYSQL_DATABASE: mydb
MYSQL_ROOT_PASSWORD: password
MYSQL_USER: admin
MYSQL_PASSWORD: password
volumes:
- mariadb_data:/var/lib/mysql/
networks:
- mynet
phpmyadmin:
image: phpmyadmin/phpmyadmin:fpm-alpine
environment:
PMA_HOST: mariadb
#PMA_ABSOLUTE_URI: http://www.example.com/phpmyadmin/
volumes:
- phpmyadmin_data:/var/www/html/
#- ./config.user.inc.php:/etc/phpmyadmin/config.user.inc.php:ro
networks:
- mynet
depends_on:
- mariadb
nginx:
image: nginx:1.17.4-alpine
volumes:
- ./default.conf:/etc/nginx/conf.d/default.conf:ro
- phpmyadmin_data:/var/www/html/:ro
ports:
- "80:80"
networks:
- mynet
depends_on:
- mariadb
- phpmyadmin
default.conf
resolver 127.0.0.11 valid=15s;
server {
listen 80;
server_name www.example.com example.com;
set $upstream phpmyadmin:9000;
location ^~ /phpmyadmin {
alias /var/www/html/;
index index.php;
location ~ \.php$ {
try_files $uri = 404;
include fastcgi_params;
fastcgi_split_path_info ^\/phpmyadmin\/(.+\.php)(.*)$;
fastcgi_param SCRIPT_FILENAME $fastcgi_script_name;
fastcgi_pass $upstream;
}
}
}
Of course, in production, nginx would not be in the same stack (but should be in the same docker network).
@lonix1 Thank you !
From what I understand removing $document_root
solved the URI issue.
If you want to open a pull-request let me know, if not I will do it
I'm not sure how to do that... what I mean is that maybe the documents site can have this info...
@lonix1 Does nginx server need to have phpmyadmin volume attached to it? In my case I'd like to use host machine's nginx but don't want to share phpmyadmin docker's volume into host machine to actually use it as 'stateless' as possible.
@Jason-2020 From what I remember the alpine image doesn't come with a webserver, that's why you need to use nginx.
If you want phpmyadmin to be completely isolated, then don't use the alpine image. The normal image comes with apache, I think.
@lonix1 yes, there is an apache version I think you need to have the volume attached or you will get 404 errors if you do not bypass the file check on the nginx side before sending requests to the fpm server
I'm trying to serve PHPMyAdmin on the root of a subdomain using Nginx, to avoid having two web-server running (I use Nginx for the rest of my application, so having Apache just for PMA is not really optimal...), but I cannot get it working.
I followed the conversation here, but all I get is a "404 not found", and this in the Nginx logs:
2020/02/14 21:34:49 [error] 15#15: *1 FastCGI sent in stderr: "Primary script unknown" while reading response header from upstream, client: 172.18.0.1, server: phpmyadmin.example.com, request: "GET / HTTP/1.1", upstream: "fastcgi://172.18.0.5:9000", host: "phpmyadmin.example.com"
Here's what I have for now for my Nginx config:
server {
server_name phpmyadmin.example.com;
root /var/www/html;
index index.php index.html index.htm;
location ~ \.php$ {
try_files $uri = 404;
fastcgi_pass phpmyadmin:9000;
#fastcgi_split_path_info ^(.+\.php)(/.*)$;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $fastcgi_script_name;
fastcgi_param HTTPS off;
}
error_log /var/log/nginx/phpmyadmin_error.log;
access_log /var/log/nginx/phpmyadmin_access.log;
}
Any idea?
Hi @ThibaultVlacich
Maybe you should follow https://github.com/phpmyadmin/docker/issues/253#issuecomment-543938409 and use fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
Did this work ?
It... worked...
Swear I tried it already but I guess not. Thanks @williamdes.
Okay I got it to work, thanks to this!
Notes:
- No rewriting necessary
- I did not need to set
PMA_ABSOLUTE_URI
- not sure why?resolver 127.0.0.11 valid=15s; server { listen 80; server_name www.example.com example.com; set $upstream phpmyadmin:9000; location ^~ /phpmyadmin { alias /var/www/html/; index index.php; location ~ \.php$ { try_files $uri = 404; fastcgi_pass $upstream; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $request_filename; } } }
This should be in the docs. If someone knows how to do that, please add @williamdes' code for
latest
image and my code forfpm-alpine
andfpm
images.
I user this config ,www.example.com/phpmyadmin is work,but i add
location / {
uwsgi_pass unix:/api/api.sock;
include uwsgi_params;
}
location /phpmyadmin {
alias /var/www/html/;
index index.php;
location ~ \.php$ {
try_files $uri = 404;
fastcgi_pass $upstream;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $request_filename;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
browser www.example.com will be download file , have any idea?
when fastcgi_param SCRIPT_FILENAME $request_filename;
change to fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
it www.example.com/phpmyadmin does not work, i am not clear konw about fastcgi_param and variables does mean what
browser www.example.com will be download file , have any idea?
You did not configure correctly the .php file handler IMO
@williamdes I guess probably is browser cause it , I use edge to browse www.example.com ,it can show me page correctly ,but chrome do not,always download the php file
@zengzhengrong Are you sure the URLs are exactly the same ? What about using curl or wget to have a test without a browser ?
@williamdes I test curl or wget ,it both correctly route to my api.sock and postman as good as well,only chrome do not
Very strange, could you send all the nginx config file?
https://github.com/zengzhengrong/django-forum-backend/blob/master/nginx/conf.d/django.conf
resolver 127.0.0.11 valid=15s;
server {
listen 80;
charset utf-8;
client_max_body_size 75M;
server_name 192.168.1.235;
set $upstream phpmyadmin:9000;
location /static {
alias /api/static;
}
location /media {
alias /api/media;
expires 24h;
}
location /flower-internal/ {
internal;
rewrite ^/flower-internal/(.*)$ /$1 break;
proxy_pass http://django-forum-backend:5555;
proxy_set_header Host $host;
}
location / {
uwsgi_pass unix:/api/api.sock;
include uwsgi_params;
}
location /phpmyadmin {
alias /var/www/html/;
index index.php;
location ~ \.php$ {
try_files $uri = 404;
fastcgi_pass $upstream;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $request_filename;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
}
}
@zengzhengrong Could you copy the request from F12 > Network > The request (index.php) > Copy > as curl and post it here after trying it into a terminal ?