diff --git a/file_entity/file_entity.module b/file_entity/file_entity.module index fdaf6bb..eade2e9 100644 --- a/file_entity/file_entity.module +++ b/file_entity/file_entity.module @@ -336,9 +336,7 @@ function file_entity_file_formatter_file_image_view($file, $display, $langcode) return; } - $scheme = file_uri_scheme($file->uri); - $local_wrappers = file_get_stream_wrappers(STREAM_WRAPPERS_LOCAL); - if (isset($local_wrappers[$scheme]) && $image = image_load($file->uri)) { + if (file_entity_file_is_local($file) && $image = image_load($file->uri)) { if (!empty($display['settings']['image_style'])) { $element = array( '#theme' => 'image_style', @@ -452,3 +450,18 @@ function file_entity_file_mimetype_mapping_alter(&$mapping) { $mapping['extensions'][$extension] = $index; } } + +/** + * Check if a file entity is considered local or not. + * + * @param object $file + * A file entity object from file_load(). + * + * @return + * TRUE if the file is using a local stream wrapper, or FALSE otherwise. + */ +function file_entity_file_is_local($file) { + $scheme = file_uri_scheme($file->uri); + $wrappers = file_get_stream_wrappers(STREAM_WRAPPERS_LOCAL); + return !empty($wrappers[$scheme]) && empty($wrappers[$scheme]['remote']); +} diff --git a/includes/media.browser.inc b/includes/media.browser.inc index f4b96dd..34cfc3d 100644 --- a/includes/media.browser.inc +++ b/includes/media.browser.inc @@ -142,9 +142,10 @@ function media_browser_list() { // I think PDO should protect them, but I'm not 100% certain. array_walk_recursive($params, '_media_recursive_check_plain'); - $types = isset($params['types']) ? $params['types'] : NULL; + $remote_types = isset($params['types']) ? $params['types'] : NULL; $url_include_patterns = isset($params['url_include_patterns']) ? $params['url_include_patterns'] : NULL; $url_exclude_patterns = isset($params['url_exclude_patterns']) ? $params['url_exclude_patterns'] : NULL; + $allowed_schemes = isset($params['schemes']) ? array_filter($params['schemes']) : array(); $start = isset($params['start']) ? $params['start'] : 0; $limit = isset($params['limit']) ? $params['limit'] : media_variable_get('browser_pager_limit'); @@ -154,22 +155,41 @@ function media_browser_list() { $query->range($start, $limit); $query->orderBy('f.timestamp', 'DESC'); - // Add conditions based on file type *or* allowed extensions. - $condition = $query; - if (!empty($types) && !empty($params['file_extensions'])) { - $condition = db_or(); - } - if (!empty($types)) { - $condition->condition('f.type', $types, 'IN'); - } + // Add conditions based on remote file type *or* local allowed extensions. + $or_condition = db_or(); + + // Include local files with the allowed extensions. if (!empty($params['file_extensions'])) { $extensions = array_filter(explode(' ', $params['file_extensions'])); - foreach ($extensions as $extension) { - $condition->condition('f.uri', '%' . db_like('.' . $extension), 'LIKE'); + $local_wrappers = array_intersect_key(media_get_local_stream_wrappers(), $allowed_schemes); + if (!empty($local_wrappers) && !empty($extensions)) { + $local_condition = db_or(); + foreach (array_keys($local_wrappers) as $scheme) { + foreach ($extensions as $extension) { + $local_condition->condition('f.uri', db_like($scheme . '://') . '%' . db_like('.' . $extension), 'LIKE'); + } + } + $or_condition->condition($local_condition); } } - if ($condition instanceof DatabaseCondition) { - $query->condition($condition); + + // Include remote files with the allowed file types. + if (!empty($remote_types)) { + $remote_wrappers = array_intersect_key(media_get_remote_stream_wrappers(), $allowed_schemes); + if (!empty($remote_wrappers)) { + $remote_condition = db_and(); + $wrapper_condition = db_or(); + foreach (array_keys($remote_wrappers) as $scheme) { + $wrapper_condition->condition('f.uri', db_like($scheme . '://') . '%', 'LIKE'); + } + $remote_condition->condition($wrapper_condition); + $remote_condition->condition('f.type', $remote_types, 'IN'); + $or_condition->condition($remote_condition); + } + } + + if ($or_condition->conditions()) { + $query->condition($or_condition); } if ($url_include_patterns) { diff --git a/includes/media.fields.inc b/includes/media.fields.inc index 7a9b61c..bcd4546 100644 --- a/includes/media.fields.inc +++ b/includes/media.fields.inc @@ -314,34 +314,41 @@ function media_field_widget_form(&$form, &$form_state, $field, $instance, $langc * Implements hook_field_validate(). * * Possible error codes: - * - 'media_fid_illegal_value': The value is not part of the list of allowed values. + * - 'media_remote_file_type_not_allowed': The remote file is not an allowed + * file type. */ function media_field_validate($obj_type, $object, $field, $instance, $langcode, $items, &$errors) { - $allowed_types = array_keys(array_filter($instance['widget']['settings']['allowed_types'])); // @TODO: merge in stuff from media_uri_value foreach ($items as $delta => $item) { - if ($item['fid'] == 0) { + if (empty($item['fid'])) { return TRUE; //@TODO: make support for submiting with just a URI here? } - $result = db_select('file_managed', 'f') - ->fields('f') - ->condition('fid', $item['fid']) - ->condition('type', $allowed_types, 'IN') - ->execute() - ->fetchField(); - if (!$result) { - $errors[$field['field_name']][$langcode][$delta][] = array( - 'error' => 'media_fid_illegal_value', - 'message' => t('%name: illegal value.', array('%name' => t($instance['label']))), - ); + + $file = file_load($item['fid']); + + // Only validate allowed types if the file is remote and not local. + if (!file_entity_file_is_local($file)) { + if (!in_array($file->type, $allowed_types)) { + $errors[$field['field_name']][$langcode][$delta][] = array( + 'error' => 'media_remote_file_type_not_allowed', + 'message' => t('%name: Only remote files with the following types are allowed: %types-allowed.', array('%name' => t($instance['label']), '%types-allowed' => !empty($allowed_types) ? implode(', ', $allowed_types) : t('no file types selected'))), + ); + } } } } /** + * Implements_hook_field_widget_error(). + */ +function media_field_widget_error($element, $error, $form, &$form_state) { + form_error($element['fid'], $error['message']); +} + +/** * @todo Is this function ever called? If not, remove it. The Field API now * supports automatic serialization / unserialization, so this should no * longer be needed. After verifying with a module that uses the 'data' diff --git a/media.module b/media.module index 6b4eb4a..e6bd321 100644 --- a/media.module +++ b/media.module @@ -1152,6 +1152,23 @@ function media_get_hidden_stream_wrappers() { } /** + * Helper function to get a list of local stream wrappers. + */ +function media_get_local_stream_wrappers() { + return file_get_stream_wrappers(STREAM_WRAPPERS_LOCAL_NORMAL); +} + +/** + * Helper function to get a list of remote stream wrappers. + */ +function media_get_remote_stream_wrappers() { + $wrappers = file_get_stream_wrappers(); + $wrappers = array_diff_key($wrappers, file_get_stream_wrappers(STREAM_WRAPPERS_LOCAL_NORMAL)); + $wrappers = array_diff_key($wrappers, file_get_stream_wrappers(STREAM_WRAPPERS_LOCAL_HIDDEN)); + return $wrappers; +} + +/** * Implements hook_views_api(). */ function media_views_api() {