31

I found strange behaviour concerning php and /tmp folder. Php uses another folder when it works with /tmp. Php 5.6.7, nginx, php-fpm.

I execute the same script in two ways: via browser and via shell. But when it is launched via browser, file is not in real /tmp folder:

<?php
$name = date("His");

echo "File /tmp/$name.txt\n";

shell_exec('echo "123" > /tmp/'.$name.'.txt');

var_dump(file_exists('/tmp/'.$name.'.txt'));

var_dump(shell_exec('cat /etc/*release | tail -n 1'));

php -f script.php

File /tmp/185617.txt
bool(true)
string(38) "CentOS Linux release 7.0.1406 (Core)

Where is the file? In /tmp

$ find / -name 185617.txt
/tmp/185617.txt

If access it via http://myserver.ru/script.php I get

File /tmp/185212.txt
bool(true)
string(38) "CentOS Linux release 7.0.1406 (Core)

But where is the file?

$ find / -name 185212.txt
/tmp/systemd-private-nABCDE/tmp/185212.txt

Why does php thinks that /tmp should be in /tmp/systemd-private-nABCDE/tmp?

3 Answers 3

44

Because systemd is configured to give nginx a private /tmp. If you must use the system /tmp instead for some reason then you will need to modify the .service file to read "PrivateTmp=no".

Sign up to request clarification or add additional context in comments.

5 Comments

You are right, but that's php-fpm, not nginx. I changed file /usr/lib/systemd/system/php-fpm.service line PrivateTmp=true into PrivateTmp=false. Now php uses correct /tmp folder.
wow this is brilliant. right what we were searching since 2 days :)
Do consider the security implications of this change. /tmp may contain sensitive information and all php-scripts can suddenly access that information.
What if your system does not have the system sub folder? might it be somewhere else?
@Scott find / -type f -name 'php-fpm.service'. You'll need to run that as sudo/root most likely but it will recursively located any file starting from the root (/) directory that is named php-fpm.service.
2

If you are running multiple sites on the server then I think you'll want to leave PrivateTmp=yes so that each site remains segregated even in it's use of temp files. Could be a security issue otherwise, I'd imagine.

Comments

0

Ignacio Vazquez-Abrams have the correct answer, but let me add my functional solution.

I've try "multi-user.target.wants" solution, it have worked but after restart, but at some point, PrivateTmp go back to true. Like my principal use of Apache2 is PHP, I finally edited php.ini and I've uncomment line sys_temp_dir.

By default system use temp dir assigned by function sys_get_temp_dir. Function sys_get_temp_dir will return "/tmp" but the truth is that your tmp files are storing at some path like /tmp/systemd-private-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX-apache2.service-YYYYYY//tmp/*. So, what work for me was:

Edit php.ini (path can change between PHP versions)

sudo nano /etc/php/7.2/cli/php.ini

Then uncomment sys_temp_dir line

; Directory where the temporary files should be placed.
; Defaults to the system default (see sys_get_temp_dir)
sys_temp_dir = "/tmp"

1 Comment

The XXX can be read from /proc/sys/kernel/random/boot_id but from where do you get YYY?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.