使用以下代码:
foreach ($form_state['values']['uploads'] as $key => $value) {
if (strlen($value)) {
$file = file_save_upload($key, array(
'file_validate_is_image' => array(), // Validates file is really an image.
'file_validate_extensions' => array('png gif jpg jpeg'), // Validate extensions.
));
// If the file passed validation:
if ($file) {
// Move the file, into the Drupal file system
if ($file = file_move($file, 'public://')) {
// Save the file for use in the submit handler.
$form_state['values']['uploaded_photos'][] = $file;
$x++;
} else {
form_set_error($key, t('Failed to write the uploaded file the site\'s file folder.'));
}
}
}
}
我正在尝试使用CTools将附加到表单的图像保存到缓存对象中。所有这一切都运行良好,直到我再次尝试上传相同的文件,我得到一个白色的屏幕,上面写着“错误 - 网站遇到错误。” (从看门狗身上撕掉):
SQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry 'public://ad-10.jpg'; for key 2: UPDATE {file_managed} SET uid=:db_update_placeholder_0, filename=:db_update_placeholder_1, uri=:db_update_placeholder_2, filemime=:db_update_placeholder_3, filesize=:db_update_placeholder_4, status=:db_update_placeholder_5, timestamp=:db_update_placeholder_6
WHERE (fid = :db_condition_placeholder_0) ; Array
(
[:db_update_placeholder_0] => 0
[:db_update_placeholder_1] => ad-10.jpg
[:db_update_placeholder_2] => public://ad-10.jpg
[:db_update_placeholder_3] => image/jpeg
[:db_update_placeholder_4] => 4912
[:db_update_placeholder_5] => 0
[:db_update_placeholder_6] => 1326221376
[:db_condition_placeholder_0] => 834
)
";s:9:"%function";s:21:"drupal_write_record()";
由于我没有设置$ replace参数,它不应该默认为FILE_EXISTS_RENAME,因此不会抛出此错误吗?我该如何解决这个问题?
答案 0 :(得分:6)
试试这个模块。它修复了写入db的并发文件对象的问题。 https://drupal.org/project/upload_qc
答案 1 :(得分:2)
我不能评论为什么它不起作用(它看起来肯定应该)但我可以提供一个更简单的解决方案。
Drupal实际上有一个内置的表单小部件来处理文件上传,managed_file
类型。它为您处理所有文件上传/验证,您只需要在表单的提交处理程序中将文件标记为永久文件。
所以在你的表单函数中:
$form['files'] = array('#tree' => TRUE);
for ($i = 0; $i < $num_file_fields; $i++) {
$form['files']["file_$i"] = array(
'#type' => 'managed_file',
'#title' => 'Select a file',
'#upload_location' => 'public://',
'#upload_validators' => array(
'file_validate_is_image' => array(),
'file_validate_extensions' => array('png gif jpg jpeg')
)
);
}
然后在你的提交处理程序中:
$count = count($form_state['values']['files']);
for ($i = 0; $i < $count; $i++) {
$file = file_load($form_state['values']['files']["file_$i"]);
$file->status = FILE_STATUS_PERMANENT;
file_save($file);
}
希望有所帮助
答案 2 :(得分:1)
由于奇怪的未使用的临时文件,我遇到了同样的问题。 您可以使用以下方法检查是否有未使用的文件:
$result = db_select('file_managed', 'f')
->fields('f', array('fid'))
->condition('f.uri', db_like('temporary://') . '%', 'LIKE')
->execute()->fetchCol();
foreach ($result as $fid) {
if ($file = file_load($fid)) {
if (!file_usage_list($file)) {
dpm($file->filename);
}
}
}
如果您无法上传与您看到的名称相同的文件,则可以将其删除(但先仔细检查并备份):
/**
* Clean unused temporary files.
*/
function MYMODULE_update_7007() {
$files = db_select('file_managed', 'f')
->fields('f', array('fid'))
->condition('f.uri', db_like('temporary://') . '%', 'LIKE')
->execute()->fetchCol();
foreach ($files as $fid) {
if ($file = file_load($fid)) {
$references = file_usage_list($file);
if (empty($references)) {
if (!file_delete($file)) {
watchdog('file system', 'Could not delete temporary file "%path" during garbage collection', array('%path' => $file->uri), WATCHDOG_ERROR);
}
}
else {
watchdog('file system', 'Did not delete temporary file "%path" during garbage collection, because it is in use by the following modules: %modules.', array('%path' => $file->uri, '%modules' => implode(', ', array_keys($references))), WATCHDOG_INFO);
}
}
}
}