3

这是一个想法。我正在尝试从 PHP 脚本创建文件。文件可以在服务器上的任何公共位置(在公共根目录或其子目录中)创建。归根结底,我想编写这样的函数(它必须在 unix 和 windows 服务器上都可以工作)。

function create_file($path, $filename, $content, $overwrite=false) {
  # body
  ...

  }

参数:

  • $path - 文件路径(空或以 结尾/
  • $filename - 任何有效的文件名(需要点+扩展名)
  • $content - 文件内容(任何东西)
  • $overwrite - 如果设置为true,现有文件将被覆盖(默认为false)。

结果:

函数返回TRUE并创建带有内容的文件,或者FALSE由于任何原因无法创建文件。

问题描述:

我希望这个函数返回并在路径$pathtrue上创建文件$filename,或者如果由于任何原因不可能。此外,如果文件已成功打开以进行写入,则需要将$content放入其中。false

参数$path是公共目录的相对路径,$filename是任何有效的文件名。当然,如果路径指向public directory 之外,我想避免创建文件。可以像这个例子一样从子目录脚本调用函数

# php script: /scripts/test.php
create_file('../data/', 'test.info', 'some contents');
# result file: /data/test.info

到目前为止我尝试了什么?

我已经尝试使用fopen()fwrite()函数来执行此操作,并且在某些服务器上有效,而在某些服务器上无效。我想写入权限和chmod()存在问题,但老实说,我对 chmod 属性不是很熟悉。我也无法检查$path是否指向服务器的公共目录之外。

简而言之,我希望此函数创建文件并TRUE在文件不存在或文件存在且$owerwrite=true. 否则,什么都不会发生并且函数返回FALSE

另外,我想知道为什么无法在某些路径上创建文件的原因(理论上)。不正确的路径/文件名是我唯一想到的,我相信这个问题还有更多。

在此先感谢您提供任何示例/示例/建议。

更新代码

到目前为止,我有这个代码......

  function create_file($path, $filename, $content, $overwrite=false) {
    $reldir = explode('/', trim(str_replace('\\', '/', dirname($_SERVER['PHP_SELF'])), '/'));
    $dirdepth = sizeof($reldir);
    $rpadd = $dirdepth > 0 ? '(\.\./){0,' . $dirdepth . '}' : '';
    $ptpath = '#^/?' . $rpadd . '([a-z0-9]\w*/)*$#i';
    $ptname = '/^[a-z]\w*\.[a-z0-9]+$/i'; 
    if ($res = preg_match($ptpath, $path) && preg_match($ptname, $filename)) {
      $res = false;
      if ($overwrite === true || !file_exists($path.$filename)) {
        if ($f = @fopen($path.$filename, 'w')) {
          fwrite($f, $content);
          fclose($f);
          $res = true;
          }
        }
      }
    return $res;
    }
4

2 回答 2

2

一些建议:

  1. 设置 Web 服务器文档根的所有者: chown -R apache:apache /var/www (我想 /var/www 是您的文档根并且 Web 服务器 apache 与用户 apache 一起运行)。像这样设置文档根目录的权限,以便使用权限 755 来查看文档下的所有目录(只有用户 apache 的所有者可以写入文件夹 /var/www 和子文件夹)
  2. 阻止指向 /var/www 文档根目录的路径:您遇到了称为http://en.wikipedia.org/wiki/Directory_traversal_attack的问题。如果 $path 类似于:/var/www/../../../etc/passwd 呢?Basename php 函数可以帮助您识别这种恶意路径。看这个帖子:php目录遍历问题
  3. 检查文件是否已经存在:http: //php.net/manual/en/function.file-exists.php
于 2012-04-07T09:24:52.600 回答
0

php中的所有文件函数在两种情况下都不能正常工作

  1. 如果您没有足够的应用程序用户权限,那么

  2. 您可能没有正确使用/传递参数/参数。

于 2012-04-07T09:59:15.517 回答