From 208f6dfce06bb8a052de46a7c78f8d834f2540f5 Mon Sep 17 00:00:00 2001 From: Johannes Burk Date: Thu, 25 Jun 2015 16:45:51 +0200 Subject: [PATCH] MDL-49750 mod_data: fix updating file/picture fields breaks references Use file_save_draft_area_files on file/picture update and set content to null if file was removed. --- mod/data/field/file/field.class.php | 34 +++++------------ mod/data/field/picture/field.class.php | 51 ++++++++++++-------------- 2 files changed, 33 insertions(+), 52 deletions(-) diff --git a/mod/data/field/file/field.class.php b/mod/data/field/file/field.class.php index 22c275d366d..e29a7d69967 100644 --- a/mod/data/field/file/field.class.php +++ b/mod/data/field/file/field.class.php @@ -176,36 +176,22 @@ class data_field_file extends data_field_base { $content = $DB->get_record('data_content', array('id'=>$id)); } - // delete existing files - $fs->delete_area_files($this->context->id, 'mod_data', 'content', $content->id); + file_save_draft_area_files($value, $this->context->id, 'mod_data', 'content', $content->id); $usercontext = context_user::instance($USER->id); - $files = $fs->get_area_files($usercontext->id, 'user', 'draft', $value, 'timecreated DESC'); + $files = $fs->get_area_files($this->context->id, 'mod_data', 'content', $content->id, 'itemid, filepath, filename', false); - if (count($files)<2) { - // no file + // We expect no or just one file (maxfiles = 1 option is set for the form_filemanager). + if (count($files) == 0) { + $content->content = null; } else { - foreach ($files as $draftfile) { - if (!$draftfile->is_directory()) { - $file_record = array( - 'contextid' => $this->context->id, - 'component' => 'mod_data', - 'filearea' => 'content', - 'itemid' => $content->id, - 'filepath' => '/', - 'filename' => $draftfile->get_filename(), - ); - - $content->content = $file_record['filename']; - - $fs->create_file_from_storedfile($file_record, $draftfile); - $DB->update_record('data_content', $content); - - // Break from the loop now to avoid overwriting the uploaded file record - break; - } + $content->content = array_values($files)[0]->get_filename(); + if (count($files) > 1) { + // This should not happen with a consistent database. Inform admins/developers about the inconsistency. + debugging('more then one file found in mod_data instance {$this->data->id} file field (field id: {$this->field->id}) area during update data record {$recordid} (content id: {$content->id})', DEBUG_NORMAL); } } + $DB->update_record('data_content', $content); } function text_export_supported() { diff --git a/mod/data/field/picture/field.class.php b/mod/data/field/picture/field.class.php index 8db472092f5..36bcd55bc05 100644 --- a/mod/data/field/picture/field.class.php +++ b/mod/data/field/picture/field.class.php @@ -235,39 +235,34 @@ class data_field_picture extends data_field_base { switch ($names[2]) { case 'file': $fs = get_file_storage(); - $fs->delete_area_files($this->context->id, 'mod_data', 'content', $content->id); + file_save_draft_area_files($value, $this->context->id, 'mod_data', 'content', $content->id); $usercontext = context_user::instance($USER->id); - $files = $fs->get_area_files($usercontext->id, 'user', 'draft', $value); - if (count($files)<2) { - // no file + $files = $fs->get_area_files( + $this->context->id, + 'mod_data', 'content', + $content->id, + 'itemid, filepath, filename', + false); + + // We expect no or just one file (maxfiles = 1 option is set for the form_filemanager). + if (count($files) == 0) { + $content->content = null; } else { - $count = 0; - foreach ($files as $draftfile) { - $file_record = array('contextid'=>$this->context->id, 'component'=>'mod_data', 'filearea'=>'content', 'itemid'=>$content->id, 'filepath'=>'/'); - if (!$draftfile->is_directory()) { - $file_record['filename'] = $draftfile->get_filename(); + $file = array_values($files)[0]; - $content->content = $draftfile->get_filename(); - - $file = $fs->create_file_from_storedfile($file_record, $draftfile); - - // If the file is not a valid image, redirect back to the upload form. - if ($file->get_imageinfo() === false) { - $url = new moodle_url('/mod/data/edit.php', array('d' => $this->field->dataid)); - redirect($url, get_string('invalidfiletype', 'error', $file->get_filename())); - } - - $DB->update_record('data_content', $content); - $this->update_thumbnail($content, $file); - - if ($count > 0) { - break; - } else { - $count++; - } - } + if (count($files) > 1) { + // This should not happen with a consistent database. Inform admins/developers about the inconsistency. + debugging('more then one file found in mod_data instance {$this->data->id} picture field (field id: {$this->field->id}) area during update data record {$recordid} (content id: {$content->id})', DEBUG_NORMAL); } + + if ($file->get_imageinfo() === false) { + $url = new moodle_url('/mod/data/edit.php', array('d' => $this->field->dataid)); + redirect($url, get_string('invalidfiletype', 'error', $file->get_filename())); + } + $content->content = $file->get_filename(); + $this->update_thumbnail($content, $file); } + $DB->update_record('data_content', $content); break;