I'm using Mac OS and recently I'm trying to set up a development environment with docker. Docker seems to be nice, but currently I'm facing the following problem:
PROBLEM:
Whenever PHP (in the docker container) is creating a folder with a subfolder, apache results in a 500-error. Apache-log: "... Can't create directory app/../../folder/subfolder/subsubfolder/"
I assume that this is caused by the environment variable umask, because whenever a folder is created, it doesn't have write permission. Because of that subfolders can't be created and so on.
To test this out, I wrote a little test-script (umask-test.php):
$umask = umask(0);
echo ("umask = $umask <br>");
And bingo! Every time I build and run the container and start the script via the browser, the result is:
umask = 18
GOAL:
So I would like to have umask always to be set to 000 (zero)
I figured out, the best place to set this variable would be the Dockerfile, so in the Dockerfile I stated the following:
FROM ubuntu:trusty
...
ENV UMASK 0
...
Problem is, that this results in nothing:
the test-script gives out 18 for umask
folders are still created with the wrong permission
subfolders can't be created.
QUESTIONS:
What am I doing wrong?
How can umask in docker containers always be set to zero?
How can I permit the apache-user (www-data) to create folders that always have write-permissions and in which subfolders can be created?
Problem solved
Since hopefully this is helpful for other, I want to provide the answer to my own question:
The problem is not docker and umask-settings in the container. The problem is the Mac and the umask-setting on the Mac OS!!
Example: If umask on the Mac is set to 022, then folders created on mounted directories by docker have the permissions 755. This causes, that no subfolders can be created.
This link is providing the information about how to set umask for the Mac: https://support.apple.com/en-us/HT201684
So if you type in your terminal
sudo launchctl config user umask 000
and reboot, all your folders will be created with 777-permissions.
Including the folders mounted to docker.
Before I was asking myself why running containers (initialized with run -v ...) are not really working. Now it seems to work all right! :-)
According to the Docker docs environment variables you set with ENV do persist to the running container, but Apache is probably very picky about which ones it pays attention to on start up on security grounds.
Try this answer.
Related
I'm developing PHP app and I'm stuck with Docker volumes. I've tried to create a separate data-only container for my PHP app but couldn't make it work because of permission issues... I've googled and read all I could and the most close to working solution is described here
But it's a bit old and I couldn't make it work too.
I've created a repo with a simple test code:
https://github.com/oleynikd/docker-volumes-permissions/
This simple project uses docker-compose to run 2 containers:
For php fpm
For nginx
The php code is mapped to php container and lives in /src directory.
The main problem is that PHP has no rights to write to code's directory because it runs as www-data user but code's directory belongs to user with id 1000 and group staff.
After running docker-compose up and visiting /index.php you'll see the warning and ls -lah output that shows the permission issue. Here's the screenshot:
I've tried to fix this by adding RUN mkdir -p /src && chown -R www-data:www-data /src to php Dockerfile but that didn't helped.
So questions are:
Why the owner and the group of /src is 1000:staff?
How to fix this?
I'm sure the solution is simple but I can't find it.
Please help!
P.S. Feel free to contribute to repo if you know how to fix this issue.
The owner of the files is 1000:staff because 1000:1000 is the uid:gid of the owner of the files on the host machine.
You could avoid it using volumes without specifying the path of the files on the host machine and adding the files with a COPY instruction in the dockerfile. But maybe you need to easily access to theses files on the host?
For development environments (and development environment only), I use a hacky solution that I described in this answer to manage it.
I'm using Laravel, and whenever the logs or the cache is being written to the storage folder, it's giving 755 permissions, and creating the owner as daemon. I have run sudo chown -R username:username app/storage and sudo chmod -R 775 app/storage numerous times. I have even added username to the group daemon and daemon to the group username.
But, it still writes files as daemon, and with 755 permissions, meaning that username can't write to it.
What am I doing wrong?
This one has also been bugging me for a while but I was too busy to hunt down a solution. Your question got me motivated to fix it. I found the answer on Stack Overflow.
In short, the solution is to change the umask of the Apache process. The link above mentions two possible places to make the change: you add umask 002 to
/etc/init.d/apache2
/etc/apache2/envvars (Debian/Ubuntu) or /etc/sysconfig/httpd (CentOS/Red Hat), or
Edit
I recently upgraded from Ubuntu 12.04 32-bit to 14.04 64-bit and, to my great irritation, I could not get this to work. It worked for some PHP scripts but not others - specifically, a short test script I wrote worked fine, but the Laravel caching code did not. A co-worker put me on to another solution: bindfs.
By mounting my project directory (/var/www/project) in my home directory (~/project) with the appropriate user mapping, all my problems were solved. Here's my fstab entry:
/var/www/project /home/username/project fuse.bindfs map=www-data/username:#www-data/#usergroup
Now I work in ~/project - everything looks like it's owned by username:usergroup and all filesystem changes work as if I own the files. But if I ls -la /var/www/project/, everything is actually owned by www-data:www-data.
Perhaps this is an overly-complicated solution, but if you have trouble getting the umask solution to work, this is another approach.
In this instance Apache isn't doing anything wrong. Apache reads and writes files based on the User and Group settings in its configuration file. The configuration file in question is like /etc/httpd/conf/httpd.conf but the location and even name differs depending on the system you're using.
It's also worth noting, that if you're running PHP as something such as FastCGI, then it'll use the user that FastCGI is set to use, seeing as that is the bit that modifies and creates files, not Apache.
I have a vagrant box setup running my dev code which is a nginx/php setup.
(Quick info on vagrant - its a virtualbox wrapper: http://www.vagrantup.com/).
In the vagrant/virtualbox setup, it is using linux guest additions to mount a shared folder on my host computer (MAC OSX).
linux guest path: /var/www/local
OSX host path: ~/src/
On multiple occasions, I find that php can't seem to write anything through any command (file_put_contents, fwrite.. etc) to any path location on the mounted shared folder, However it is able to write outside of the /var/www/local (for example /var/www/not-mounted/..).
I find this very difficult to work with, as I am using a cache system and it keeps failing to write any of the cache javascript/css files to (/var/www/local/public/root/cache/) which I need to be in the root folder of my website which is (/var/www/local/public/root/index.php).
I have done a lot of research on this topic:
it seems, the folder mount has the right permissions:
When I type mount command in the linux guest, I get this:
/var/www/local on /var/www/local/ type vboxsf (uid=1000,gid=1000,rw)
Clarify:
This happens all the time, it is a known problem I encounter which I try to workaround.
From cat /etc/passwd:
vagrant:x:1000:1000:vagrant,,,:/home/vagrant:/bin/bash
Can anyone help me on this?
I have figured out the problem.
I have forgot to give PHP the correct user-privileges and permissions to write to the folder. Basically, my PHP user/user-group was www-data/www-data however, vagrant has its own user/group (vagrant/vagrant) which mounts the folder /local/.
Since I did not want to mess with my vagrant mounting behaviour, I just simply changed my php config to start PHP with the user/group - vagrant/vagrant.
This fixed the issue for me.
Thanks for the help!
I'm using Apache 2 in Linux mint and I don't know where to store my files and projects. if I store it in var/www it is not accessible for me, I have to use command as super user. Are there any way to solve my problem?
- If I want to store in my home folder, what should I type in the address bar if I want to run my file?
- Are there any other good solution than these? (such as change the accessible to folder /var, or change the Root_Url of apache ...)
The easiest way to solve this provlem is by typing the following line in terminal:
sudo chmod -R 777 /var/www
and then enter your password. And now you are done. You can store all the PHP files in /var/www
You have to do a chmod, you can have more information in your terminal with comand man chmod to set the rights to write in that folder or else point the web-server elsewhere (the setting is in the https.conf file)
There is different solutions:
create a symlink from /var/www/link to your projet and set your project
create a virtualhost with the DocumentRoot to point to your project: http://httpd.apache.org/docs/2.2/vhosts/examples.html
in both cases your project must have gives permissions to the apache user (www-data?) to read/execute you project
You need to active the user_dir mod of apache and then run the content from your home folder.
To run a file in your hole directory you should go to localhost/~youruser/script.php of course after enabling user_dir
Everything depends on the use.
If you are looking for a configuration for a development server that is accessible only from limited host (such as localhost):
You can configure Apache (/etc/apache2/apache2.conf) to run with your user/group.
User myuser
Group mygroup
Store all your project in your user_dir (/home/myuser/projects/...)
Create a virtual host for any of your projects
All files generated by your server will be accessible to you and vice versa
One way to accomplish this is to edit the default virtualhost supplied with Apache 2. In Linux Mint 14 its configuration file is located at:
/etc/apache2/sites-enabled/
This directory should hold symlinks for all active sites, for me the default is named 000-default.
Change the lines with "DocumentRoot" and "Directory" to point wherever you like. The server should have read only privileges by default. If you are working on file manipulation then it will need permission to read and write files.
Once this is set, restart the server ("sudo service apache2 restart") and type localhost in your browser to access the directory you've set above.
For more advanced configs have a look at:
http://community.linuxmint.com/tutorial/view/853
http://community.linuxmint.com/tutorial/view/527
I have 4 drives in my (yes, physically in the box, sata connected) Ubuntu 10.10 system with xampp installed at the /opt/lampp/ dir on the OS drive. The OS drive (ssd, lets call it drive1 for sanity) has the correct file permissions to allow for PHP (user www-data) to read/write to any of my htdocs and vhosts folder(s).
My problem comes with I try to move a file that exists on one of the other 3 drives. Each of my other drives are ntfs (1tb, 1.5tb and 2.0tb) and mounted with fstab. When I view the file permissions with the gui (nautilus) it says that everything is root. So I tried chown, chmod, etc. I found out that you can't change the permissions of ntfs with those commands. So I went to my fstab config, however I can't get those permissions set to allow for PHP to copy/rename/move a file within even one of the drives.
I updated to using the UUID's today, the drives are also shared on my local network and that still works just fine.
I changed to the ntfs-3g driver after installing, restarted the machine but I'm still not able to have php move a file.
Here is my fstab file:
UUID=552A7C6B05CEAAD2 /media/v1tb ntfs-3g defaults,uid=1000 0 0
UUID=DE58539158536775 /media/v1.5tb ntfs-3g defaults,uid=1000 0 0
UUID=3D80C54D5D100280 /media/v2.0tb ntfs-3g defaults,uid=1000 0 0
Also, I tried to use the following and its working just fine:
sudo -u www-data cp '/media/v2.0tb/path/to/file' '/media/v2.0tb/path/to/newfile'
How does imitating a user work, but php's rename/copy functions won't work?
How can I set the php user (www-data) to allow for copying/renaming/deleting files and directories on these ntfs drives? Do I have to reformat them?
Depends on the actual ntfs driver used. For ntfs-3g you can use the uid= and gid= params in the fstab. There is also a usermapping= feature that might be of interest. See also the manpage
If anybody gets a problem like this, sometimes it could be that the permissions on previous directories could affect the access to a directory.
For example, on Ubuntu 12.10, you have the partitions on /media, as many other Ubuntu versions. But on this version, you could have another directory where your partitions, especially the NTFS and external drives, will be located, and is /media/YOUR_USER_NAME. To solve the access to my external hard drive, concretely using PHP, I had to change permissions at /media/MY_USER_NAME, first, and then at /media/MY_USER_NAME/MY_EXTERNAL_DRIVE.
These are the commands used:
sudo chown MY_USER_NAME MY_USER_NAME/
sudo chown MY_USER_NAME MY_USER_NAME/MY_EXTERNAL_DRIVE/
and
sudo mount -t ntfs -o rw,uid=1000,gid=1000,fmask=000,dmask=000 /dev/sdb1 /media/MY_USER_NAME/MY_EXTERNAL_DRIVE
The first and the second one, is to change the Owner of the directory, and the third one, to mount the NTFS drive with the correct permissions.
I've thought this could be usefull to somebody, cause I've spent several hours after I realized that it could be that I couldn't access to previous directories.