Docker,TravisCI,PHP文件上传和/ tmp上的间歇性权限错误

时间:2017-08-18 11:35:14

标签: php symfony docker travis-ci

我有一个间歇性的文件上传错误,只发生在Travis:

Warning: file_put_contents(/tmp/customerDownload_1502892540/image.png): failed to open stream: Permission denied (500 Internal Server Error)

这是一个在PHP 7.1 Docker容器上运行的Symfony 2.8项目。有一个Behat场景可以测试管理员上传文件和用户下载。我创建文件的方法如下:

/**
 * @param string $fileContents
 * @param Media $file
 * @return File
 */
private function createLocalTemporaryFile(string $fileContents, Media $file): File
{
    $tmpDir = '/tmp/customerDownload_' . time();
    if (!file_exists($tmpDir)) {
        mkdir($tmpDir);
    }
    $tmpFilePath = $tmpDir . '/' . $file->getName();
    file_put_contents($tmpFilePath, base64_decode($fileContents));
    $tmpFile = new File(realpath($tmpFilePath));

    return $tmpFile;
}

大约20%的时间失败,这是一个重要的数额。但从不在本地或在生产中。我已尝试在/tmp上设置权限以包含www-data用户:组,但它无效。我很困惑为什么它不能将内容放到它首先创建的目录中的文件中。

任何人都可以建议为什么会发生这种情况,或者如何确保它不会发生?

1 个答案:

答案 0 :(得分:0)

我认为这是某种竞争条件和文件命名问题。我正在使用相同的文件进行测试,也许测试运行得足够快,以至于它试图写一个文件而不能。将方法更新为以下内容并且到目前为止在12次测试中都没有失败。

/**
 * @param string $fileContents
 * @param Media $file
 * @return File
 */
private function createLocalTemporaryFile(string $fileContents, Media $file): File
{
    $tmpDir = '/tmp/' . uniqid('customerDownload_', true);
    mkdir($tmpDir);
    $tmpFilePath = $tmpDir . '/' . $file->getName();
    file_put_contents($tmpFilePath, base64_decode($fileContents));
    $tmpFile = new File(realpath($tmpFilePath));

    return $tmpFile;
}
相关问题