Differences Between: [Versions 311 and 403] [Versions 400 and 403] [Versions 401 and 403] [Versions 402 and 403]
1 <?php 2 // This file is part of Moodle - http://moodle.org/ 3 // 4 // Moodle is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // Moodle is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU General Public License for more details. 13 // 14 // You should have received a copy of the GNU General Public License 15 // along with Moodle. If not, see <http://www.gnu.org/licenses/>. 16 17 namespace core_contentbank\form; 18 19 use core\output\notification; 20 21 /** 22 * Upload files to content bank form 23 * 24 * @package core_contentbank 25 * @copyright 2020 Amaia Anabitarte <amaia@moodle.com> 26 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 27 */ 28 class upload_files extends \core_form\dynamic_form { 29 30 /** 31 * Add elements to this form. 32 */ 33 public function definition() { 34 $mform = $this->_form; 35 36 $mform->addElement('hidden', 'contextid'); 37 $mform->setType('contextid', PARAM_INT); 38 39 $mform->addElement('hidden', 'id'); 40 $mform->setType('id', PARAM_INT); 41 42 $mform->addElement('filepicker', 'file', get_string('file', 'core_contentbank'), null, $this->get_options()); 43 $mform->addHelpButton('file', 'file', 'core_contentbank'); 44 $mform->addRule('file', null, 'required'); 45 } 46 47 /** 48 * Validate incoming data. 49 * 50 * @param array $data 51 * @param array $files 52 * @return array 53 */ 54 public function validation($data, $files) { 55 $errors = array(); 56 $draftitemid = $data['file']; 57 $options = $this->get_options(); 58 if (file_is_draft_area_limit_reached($draftitemid, $options['areamaxbytes'])) { 59 $errors['file'] = get_string('userquotalimit', 'error'); 60 } 61 return $errors; 62 } 63 64 /** 65 * Check if current user has access to this form, otherwise throw exception 66 * 67 * Sometimes permission check may depend on the action and/or id of the entity. 68 * If necessary, form data is available in $this->_ajaxformdata or 69 * by calling $this->optional_param() 70 */ 71 protected function check_access_for_dynamic_submission(): void { 72 require_capability('moodle/contentbank:upload', $this->get_context_for_dynamic_submission()); 73 74 // Check the context used by the content bank is allowed. 75 $cb = new \core_contentbank\contentbank(); 76 if (!$cb->is_context_allowed($this->get_context_for_dynamic_submission())) { 77 throw new \moodle_exception('contextnotallowed', 'core_contentbank'); 78 } 79 80 // If $id is defined, the file content will be replaced (instead of uploading a new one). 81 // Check that the user has the right permissions to replace this content file. 82 $id = $this->optional_param('id', null, PARAM_INT); 83 if ($id) { 84 $content = $cb->get_content_from_id($id); 85 $contenttype = $content->get_content_type_instance(); 86 if (!$contenttype->can_manage($content) || !$contenttype->can_upload()) { 87 throw new \moodle_exception('nopermissions', 'error', '', null, get_string('replacecontent', 'contentbank')); 88 } 89 } 90 } 91 92 /** 93 * Returns form context 94 * 95 * If context depends on the form data, it is available in $this->_ajaxformdata or 96 * by calling $this->optional_param() 97 * 98 * @return \context 99 */ 100 protected function get_context_for_dynamic_submission(): \context { 101 $contextid = $this->optional_param('contextid', null, PARAM_INT); 102 return \context::instance_by_id($contextid, MUST_EXIST); 103 } 104 105 /** 106 * File upload options 107 * 108 * @return array 109 * @throws \coding_exception 110 */ 111 protected function get_options(): array { 112 global $CFG; 113 114 $maxbytes = $CFG->userquota; 115 $maxareabytes = $CFG->userquota; 116 if (has_capability('moodle/user:ignoreuserquota', $this->get_context_for_dynamic_submission())) { 117 $maxbytes = USER_CAN_IGNORE_FILE_SIZE_LIMITS; 118 $maxareabytes = FILE_AREA_MAX_BYTES_UNLIMITED; 119 } 120 121 $cb = new \core_contentbank\contentbank(); 122 $id = $this->optional_param('id', null, PARAM_INT); 123 if ($id) { 124 $content = $cb->get_content_from_id($id); 125 $contenttype = $content->get_content_type_instance(); 126 $extensions = $contenttype->get_manageable_extensions(); 127 $acceptedtypes = implode(',', $extensions); 128 } else { 129 $acceptedtypes = $cb->get_supported_extensions_as_string($this->get_context_for_dynamic_submission()); 130 } 131 132 return ['subdirs' => 1, 'maxbytes' => $maxbytes, 'maxfiles' => -1, 'accepted_types' => $acceptedtypes, 133 'areamaxbytes' => $maxareabytes]; 134 } 135 136 /** 137 * Process the form submission, used if form was submitted via AJAX 138 * 139 * This method can return scalar values or arrays that can be json-encoded, they will be passed to the caller JS. 140 * 141 * Submission data can be accessed as: $this->get_data() 142 * 143 * @return mixed 144 */ 145 public function process_dynamic_submission() { 146 global $USER; 147 148 // Get the file and create the content based on it. 149 $usercontext = \context_user::instance($USER->id); 150 $fs = get_file_storage(); 151 $files = $fs->get_area_files($usercontext->id, 'user', 'draft', $this->get_data()->file, 'itemid, filepath, 152 filename', false); 153 if (!empty($files)) { 154 $file = reset($files); 155 $cb = new \core_contentbank\contentbank(); 156 try { 157 if ($this->get_data()->id) { 158 $content = $cb->get_content_from_id($this->get_data()->id); 159 $contenttype = $content->get_content_type_instance(); 160 $content = $contenttype->replace_content($file, $content); 161 } else { 162 $content = $cb->create_content_from_file($this->get_context_for_dynamic_submission(), $USER->id, $file); 163 } 164 $params = ['id' => $content->get_id(), 'contextid' => $this->get_context_for_dynamic_submission()->id]; 165 $url = new \moodle_url('/contentbank/view.php', $params); 166 } catch (\moodle_exception $e) { 167 // Redirect to the right page (depending on if content is new or existing) and display an error. 168 if ($this->get_data()->id) { 169 $content = $cb->get_content_from_id($this->get_data()->id); 170 $params = [ 171 'id' => $content->get_id(), 172 'contextid' => $this->get_context_for_dynamic_submission()->id, 173 'errormsg' => $e->errorcode, 174 ]; 175 $url = new \moodle_url('/contentbank/view.php', $params); 176 } else { 177 $url = new \moodle_url('/contentbank/index.php', [ 178 'contextid' => $this->get_context_for_dynamic_submission()->id, 179 'errormsg' => $e->errorcode], 180 ); 181 } 182 } 183 184 return ['returnurl' => $url->out(false)]; 185 } 186 187 return null; 188 } 189 190 /** 191 * Load in existing data as form defaults 192 * 193 * Can be overridden to retrieve existing values from db by entity id and also 194 * to preprocess editor and filemanager elements 195 * 196 * Example: 197 * $this->set_data(get_entity($this->_ajaxformdata['id'])); 198 */ 199 public function set_data_for_dynamic_submission(): void { 200 $data = (object)[ 201 'contextid' => $this->optional_param('contextid', null, PARAM_INT), 202 'id' => $this->optional_param('id', null, PARAM_INT), 203 ]; 204 $this->set_data($data); 205 } 206 207 /** 208 * Returns url to set in $PAGE->set_url() when form is being rendered or submitted via AJAX 209 * 210 * This is used in the form elements sensitive to the page url, such as Atto autosave in 'editor' 211 * 212 * If the form has arguments (such as 'id' of the element being edited), the URL should 213 * also have respective argument. 214 * 215 * @return \moodle_url 216 */ 217 protected function get_page_url_for_dynamic_submission(): \moodle_url { 218 $params = ['contextid' => $this->get_context_for_dynamic_submission()->id]; 219 220 $id = $this->optional_param('id', null, PARAM_INT); 221 if ($id) { 222 $url = '/contentbank/view.php'; 223 $params['id'] = $id; 224 } else { 225 $url = '/contentbank/index.php'; 226 } 227 228 return new \moodle_url($url, $params); 229 } 230 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body