无法访问使用Plupload上传的文件

时间:2011-03-24 18:04:36

标签: php file-upload plupload

我们正在使用多文件上传器插件,我们希望使用move_uploaded_file()将其保存到服务器,并在成功上传后发送包含所有文件的直接链接的邮件。我们正在关注数组...

Array
(
    [html5_uploader_0_tmpname] => p15rkfr6oogdt1ln91t0r4obrrh3.jpg
    [html5_uploader_0_name] => show_041.jpg
    [html5_uploader_0_status] => done
    [html5_uploader_1_tmpname] => p15rkfr8mb1plfu4q1giu3v01jl74.jpg
    [html5_uploader_1_name] => 23.jpg
    [html5_uploader_1_status] => done
    [html5_uploader_count] => 2
)

我们正在使用以下代码......

    $("#html5_uploader").pluploadQueue({
    // General settings
    runtimes : 'html5',
    url : 'upload.php',
    max_file_size : '10mb',
    chunk_size : '1mb',
    unique_names : true,
    filters : [
        {title : "Image files", extensions : "jpg,gif,png"},
        {title : "Zip files", extensions : "zip"}
    ],

    // Resize images on clientside if we can
    //resize : {width : 320, height : 240, quality : 90}
});

}

所以问题是我们应该在$ _FILES [“file”] [“tmp_name”]和$ _FILES [“file”] [“name”]的位置传递这个数组。

2 个答案:

答案 0 :(得分:3)

感谢您更新的帖子。

如果在单个表单中有多个文件上传,它们共享一个数组格式的元素名称$_FILES会变得一团糟。而不是在表单元素名称和文件信息之间添加另一个层it adds another layer after the file information

可视化它可能更好:

array(
    'name' => array(
        0 => 'foo.gif',
        1 => 'bar.jpeg'
    ),
    'tmp_name' => array(
        0 => '/tmp/something',
        1 => '/tmp/else',
    )
);

不是你的预期,对吗?

现在,您的代码正在做完全无意义的事情。您正在循环$_POST,但之后您正在处理$_FILES。事情不会这样。

不知道你在哪里获得你发布的原始数组,所以我将忽略它。

让我们假装'file'是多文件上传表单元素的名称,完全重建$_FILES数组

$fixed_files = array();
foreach($_FILES['file'] as $expected => $unexpected) {
    foreach($unexpected as $index => $data)
        $fixed_files[$index][$expected] = $data;
}

(如果内部值不是数组,此代码可能失败 - 请参阅multiple upload page in the PHP manual了解其他修复$_FILES的选项。)

有。现在我们可以像我们应该从一开始就循环遍历$fixed_files

foreach($fixed_files as $uploaded) {
    $safe_name = preg_replace('/[^A-Za-z0-9_-\.]/', '', $uploaded["name"]);
    move_uploaded_file($uploaded["tmp_name"], "upload/" . $safe_name);
    $links[] = "upload/" . $safe_name;
}

请注意以前代码的新增内容 - $safe_name。数组的name元素来自用户,不应该被信任。正则表达式除去字母,数字,短划线,下划线和句点之外的其他内容。

如果可以,您还应该对上传的数据进行更多验证!例如,如果您需要图像,则应尝试验证文件确实是图像。如果您使用的是PHP 5.3,请查看finfo_file。您可以使用它来检索文件的MIME类型,并确保它是您可以使用的文件类型。

答案 1 :(得分:0)

发布后收到的输出存储在$ _POST中,这是您显示的数组来自的地方。

为了更好地使用$ _POST数组输出,首先需要将Form Posts输出更改为多维数组/输出。

我这样做的方法是改变plupload .js文件将html表单构造成多部分表单的位置。使用以下PHP方法multiple upload page in the PHP manual作为@Charles提到。

我在下面编辑的行的示例,使用计数周围的'[]'括号和“name”标记中值的名称,将$ _POST数据拆分为多维数组。

    if (file.target_name) {
    inputHTML += '<input type="hidden" name="' + id + '[' + inputCount + '][tmpname]" value="' + plupload.xmlEncode(file.target_name) + '" />';
    }

    inputHTML += '<input type="hidden" name="' + id + '[' + inputCount + '][name]" value="' + plupload.xmlEncode(file.name) + '" />';
    inputHTML += '<input type="hidden" name="' + id + '[' + inputCount + '][status]" value="' + (file.status == plupload.DONE ? 'done' : 'failed') + '" />';

这转变了:

Array
(
    [html5_uploader_0_tmpname] => p15rkfr6oogdt1ln91t0r4obrrh3.jpg
    [html5_uploader_0_name] => show_041.jpg
    [html5_uploader_0_status] => done
    [html5_uploader_1_tmpname] => p15rkfr8mb1plfu4q1giu3v01jl74.jpg
    [html5_uploader_1_name] => 23.jpg
    [html5_uploader_1_status] => done
    [html5_uploader_count] => 2
)

进入这个:

array
  'uploader' => 
    array
      0 => 
        array
          'tmpname' => string 'p15rkfr6oogdt1ln91t0r4obrrh3.jpg'
          'name' => string 'show_041.jpg'
          'status' => string 'done'
      'count' => string '1'

然后你可以使用Plupload保存在“Upload.php”中找到的临时(tmp)文件的位置以及tmpname $_POST['tmpname']来移动文件。

    $targetDir = ini_get("upload_tmp_dir") . DIRECTORY_SEPARATOR . "plupload";
    move_uploaded_file($targetDir . $_POST['tmpname'], $destination);