function file_help($route_name, RouteMatchInterface $route_match) {
switch ($route_name) {
case 'help.page.file':
$output = '';
$output .= '<h3>' . t('About') . '</h3>';
$output .= '<p>' . t('The File module allows you to create fields that contain files. See the <a href="!field">Field module help</a> and the <a href="!field_ui">Field UI help</a> pages for general information on fields and how to create and manage them. For more information, see the <a href="!file_documentation">online documentation for the File module</a>.', array('!field' => \Drupal::url('help.page', array('name' => 'field')), '!field_ui' => (\Drupal::moduleHandler()->moduleExists('field_ui')) ? \Drupal::url('help.page', array('name' => 'field_ui')) :'#', '!file_documentation' => 'https://www.drupal.org/documentation/modules/file')) . '</p>';
$output .= '<dd>' . t('The <em>settings</em> and the <em>display</em> of the file field can be configured separately. See the <a href="!field_ui">Field UI help</a> for more information on how to manage fields and their display.', array('!field_ui' => (\Drupal::moduleHandler()->moduleExists('field_ui')) ? \Drupal::url('help.page', array('name' => 'field_ui')) : '#')) . '</dd>';
$output .= '<dd>' . t('In the field settings, you can define the allowed file extensions (for example <em>pdf docx psd</em>) for the files that will be uploaded with the file field.') . '</dd>';
$output .= '<dd>' . t('Uploaded files can either be stored as <em>public</em> or <em>private</em>, depending on the <a href="!file-system">File system settings</a>. For more information, see the <a href="!system-help">System module help page</a>.', array('!file-system' => \Drupal::url('system.file_system_settings'), '!system-help' => \Drupal::url('help.page', array('name' => 'system')))) . '</dd>';
$output .= '<dt>' . t('Restricting the maximum file size') . '</dt>';
$output .= '<dd>' . t('The maximum file size that users can upload is limited by PHP settings of the server, but you can restrict by entering the desired value as the <em>Maximum upload size</em> setting. The maximum file size is automatically displayed to users in the help text of the file field.') . '</dd>';
$output .= '<dt>' . t('Displaying files and descriptions') . '<dt>';
$output .= '<dd>' . t('In the field settings, you can allow users to toggle whether individual files are displayed. In the display settings, you can then choose one of the following formats: <ul><li><em>Generic file</em> displays links to the files and adds icons that symbolize the file extensions. If <em>descriptions</em> are enabled and have been submitted, then the description is displayed instead of the file name.</li><li><em>URL to file</em> displays the full path to the file as plain text.</li><li><em>Table of files</em> lists links to the files and the file sizes in a table.</li><li><em>RSS enclosure</em> only displays the first file, and only in a RSS feed, formatted according to the RSS 2.0 syntax for enclosures.</li></ul> A file can still be linked to directly by its URI even if it is not displayed.') . '</dd>';
$output .= '</dl>';
return $output;
}
}
/**
* Loads file entities from the database.
*
* @param array $fids
* (optional) An array of entity IDs. If omitted, all entities are loaded.
* @param bool $reset
* Whether to reset the internal file_load_multiple() cache.
*
* @return array
* An array of file entities, indexed by fid.
*
* @deprecated in Drupal 8.x, will be removed before Drupal 9.0.
* Copies a file to a new location and adds a file record to the database.
*
* This function should be used when manipulating files that have records
* stored in the database. This is a powerful function that in many ways
* performs like an advanced version of copy().
* - Checks if $source and $destination are valid and readable/writable.
* - If file already exists in $destination either the call will error out,
* replace the file or rename the file based on the $replace parameter.
* - If the $source and $destination are equal, the behavior depends on the
* $replace parameter. FILE_EXISTS_REPLACE will error out. FILE_EXISTS_RENAME
* will rename the file until the $destination is unique.
* - Adds the new file to the files database. If the source file is a
* temporary file, the resulting file will also be a temporary file. See
* file_save_upload() for details on temporary files.
*
* @param \Drupal\file\FileInterface $source
* A file entity.
* @param string $destination
* A string containing the destination that $source should be copied to.
* This must be a stream wrapper URI.
* @param int $replace
* Replace behavior when the destination file already exists:
* - FILE_EXISTS_REPLACE - Replace the existing file. If a managed file with
* the destination name exists then its database entry will be updated. If
* no database entry is found then a new one will be created.
* - FILE_EXISTS_RENAME - Append _{incrementing number} until the filename is
* unique.
* - FILE_EXISTS_ERROR - Do nothing and return FALSE.
*
* @return \Drupal\file\FileInterface|FALSE
* File object if the copy is successful, or FALSE in the event of an error.
*
* @see file_unmanaged_copy()
* @see hook_file_copy()
*/
function file_copy(FileInterface $source, $destination = NULL, $replace = FILE_EXISTS_RENAME) {
if (!file_valid_uri($destination)) {
if (($realpath = drupal_realpath($source->getFileUri())) !== FALSE) {
\Drupal::logger('file')->notice('File %file (%realpath) could not be copied because the destination %destination is invalid. This is often caused by improper use of file_copy() or a missing stream wrapper.', array('%file' => $source->getFileUri(), '%realpath' => $realpath, '%destination' => $destination));
}
else {
\Drupal::logger('file')->notice('File %file could not be copied because the destination %destination is invalid. This is often caused by improper use of file_copy() or a missing stream wrapper.', array('%file' => $source->getFileUri(), '%destination' => $destination));
}
drupal_set_message(t('The specified file %file could not be copied because the destination is invalid. More information is available in the system log.', array('%file' => $source->getFileUri())), 'error');
return FALSE;
}
if ($uri = file_unmanaged_copy($source->getFileUri(), $destination, $replace)) {
$file = $source->createDuplicate();
$file->setFileUri($uri);
$file->setFilename(drupal_basename($uri));
// If we are replacing an existing file re-use its database record.
// @todo Do not create a new entity in order to update it. See
* Moves a file to a new location and update the file's database entry.
*
* Moving a file is performed by copying the file to the new location and then
* deleting the original.
* - Checks if $source and $destination are valid and readable/writable.
* - Performs a file move if $source is not equal to $destination.
* - If file already exists in $destination either the call will error out,
* replace the file or rename the file based on the $replace parameter.
* - Adds the new file to the files database.
*
* @param \Drupal\file\FileInterface $source
* A file entity.
* @param string $destination
* A string containing the destination that $source should be moved to.
* This must be a stream wrapper URI.
* @param int $replace
* Replace behavior when the destination file already exists:
* - FILE_EXISTS_REPLACE - Replace the existing file. If a managed file with
* the destination name exists then its database entry will be updated and
* $source->delete() called after invoking hook_file_move().
* If no database entry is found then the source files record will be
* updated.
* - FILE_EXISTS_RENAME - Append _{incrementing number} until the filename is
* unique.
* - FILE_EXISTS_ERROR - Do nothing and return FALSE.
*
* @return \Drupal\file\FileInterface
* Resulting file entity for success, or FALSE in the event of an error.
*
* @see file_unmanaged_move()
* @see hook_file_move()
*/
function file_move(FileInterface $source, $destination = NULL, $replace = FILE_EXISTS_RENAME) {
if (!file_valid_uri($destination)) {
if (($realpath = drupal_realpath($source->getFileUri())) !== FALSE) {
\Drupal::logger('file')->notice('File %file (%realpath) could not be moved because the destination %destination is invalid. This may be caused by improper use of file_move() or a missing stream wrapper.', array('%file' => $source->getFileUri(), '%realpath' => $realpath, '%destination' => $destination));
}
else {
\Drupal::logger('file')->notice('File %file could not be moved because the destination %destination is invalid. This may be caused by improper use of file_move() or a missing stream wrapper.', array('%file' => $source->getFileUri(), '%destination' => $destination));
}
drupal_set_message(t('The specified file %file could not be moved because the destination is invalid. More information is available in the system log.', array('%file' => $source->getFileUri())), 'error');
return FALSE;
}
if ($uri = file_unmanaged_move($source->getFileUri(), $destination, $replace)) {
$delete_source = FALSE;
$file = clone $source;
$file->setFileUri($uri);
// If we are replacing an existing file re-use its database record.
$errors[] = t('Only files with the following extensions are allowed: %files-allowed.', array('%files-allowed' => $extensions));
}
return $errors;
}
/**
* Checks that the file's size is below certain limits.
*
* @param \Drupal\file\FileInterface $file
* A file entity.
* @param int $file_limit
* An integer specifying the maximum file size in bytes. Zero indicates that
* no limit should be enforced.
* @param int $user_limit
* An integer specifying the maximum number of bytes the user is allowed.
* Zero indicates that no limit should be enforced.
*
* @return array
* An array. If the file size exceeds limits, it will contain an error
* message.
*
* @see hook_file_validate()
*/
function file_validate_size(FileInterface $file, $file_limit = 0, $user_limit = 0) {
$user = \Drupal::currentUser();
$errors = array();
if ($file_limit && $file->getSize() > $file_limit) {
$errors[] = t('The file is %filesize exceeding the maximum file size of %maxsize.', array('%filesize' => format_size($file->getSize()), '%maxsize' => format_size($file_limit)));
}
// Save a query by only calling spaceUsed() when a limit is provided.
if ($user_limit && (\Drupal::entityManager()->getStorage('file')->spaceUsed($user->id()) + $file->getSize()) > $user_limit) {
$errors[] = t('The file is %filesize which would exceed your disk quota of %quota.', array('%filesize' => format_size($file->getSize()), '%quota' => format_size($user_limit)));
}
return $errors;
}
/**
* Checks that the file is recognized as a valid image.
*
* @param \Drupal\file\FileInterface $file
* A file entity.
*
* @return array
* An array. If the file is not an image, it will contain an error message.
*
* @see hook_file_validate()
*/
function file_validate_is_image(FileInterface $file) {
if ($image->getWidth() > $width || $image->getHeight() > $height) {
// Try to resize the image to fit the dimensions.
if ($image->scale($width, $height)) {
$image->save();
$file->filesize = $image->getFileSize();
drupal_set_message(t('The image was resized to fit within the maximum allowed dimensions of %dimensions pixels.', array('%dimensions' => $maximum_dimensions)));
}
else {
$errors[] = t('The image exceeds the maximum allowed dimensions and an attempt to resize it failed.');
}
}
}
if ($minimum_dimensions) {
// Check that it is larger than the given dimensions.
if ($image->getWidth() < $width || $image->getHeight() < $height) {
$errors[] = t('The image is too small; the minimum dimensions are %dimensions pixels.', array('%dimensions' => $minimum_dimensions));
}
}
}
return $errors;
}
/**
* Saves a file to the specified destination and creates a database entry.
*
* @param string $data
* A string containing the contents of the file.
* @param string $destination
* A string containing the destination URI. This must be a stream wrapper URI.
* If no value is provided, a randomized name will be generated and the file
* will be saved using Drupal's default files scheme, usually "public://".
* @param int $replace
* Replace behavior when the destination file already exists:
* - FILE_EXISTS_REPLACE - Replace the existing file. If a managed file with
* the destination name exists then its database entry will be updated. If
* no database entry is found then a new one will be created.
* - FILE_EXISTS_RENAME - Append _{incrementing number} until the filename is
* unique.
* - FILE_EXISTS_ERROR - Do nothing and return FALSE.
*
* @return \Drupal\file\FileInterface
* A file entity, or FALSE on error.
*
* @see file_unmanaged_save_data()
*/
function file_save_data($data, $destination = NULL, $replace = FILE_EXISTS_RENAME) {
$user = \Drupal::currentUser();
if (empty($destination)) {
$destination = file_default_scheme() . '://';
}
if (!file_valid_uri($destination)) {
\Drupal::logger('file')->notice('The data could not be saved because the destination %destination is invalid. This may be caused by improper use of file_save_data() or a missing stream wrapper.', array('%destination' => $destination));
drupal_set_message(t('The data could not be saved because the destination is invalid. More information is available in the system log.'), 'error');
return FALSE;
}
if ($uri = file_unmanaged_save_data($data, $destination, $replace)) {
// Create a file entity.
$file = entity_create('file', array(
'uri' => $uri,
'uid' => $user->id(),
'status' => FILE_STATUS_PERMANENT,
));
// If we are replacing an existing file re-use its database record.
// @todo Do not create a new entity in order to update it. See
\Drupal::logger('file system')->error('Could not delete temporary file "%path" during garbage collection', array('%path' => $file->getFileUri()));
}
}
else {
\Drupal::logger('file system')->info('Did not delete temporary file "%path" during garbage collection because it is in use by the following modules: %modules.', array('%path' => $file->getFileUri(), '%modules' => implode(', ', array_keys($references))));
}
}
}
}
/**
* Saves file uploads to a new location.
*
* The files will be added to the {file_managed} table as temporary files.
* Temporary files are periodically cleaned. Use the 'file.usage' service to
* register the usage of the file which will automatically mark it as permanent.
*
* @param string $form_field_name
* A string that is the associative array key of the upload form element in
* the form array.
* @param array $validators
* An optional, associative array of callback functions used to validate the
* file. See file_validate() for a full discussion of the array format.
* If no extension validator is provided it will default to a limited safe
* list of extensions which is as follows: "jpg jpeg gif png txt
* doc xls pdf ppt pps odt ods odp". To allow all extensions you must
* explicitly set the 'file_validate_extensions' validator to an empty array
* (Beware: this is not safe and should only be allowed for trusted users, if
* at all).
* @param string $destination
* A string containing the URI that the file should be copied to. This must
* be a stream wrapper URI. If this value is omitted, Drupal's temporary
* files scheme will be used ("temporary://").
* @param int $delta
* Delta of the file to save or NULL to save all files. Defaults to NULL.
* @param int $replace
* Replace behavior when the destination file already exists:
* - FILE_EXISTS_REPLACE: Replace the existing file.
* - FILE_EXISTS_RENAME: Append _{incrementing number} until the filename is
* unique.
* - FILE_EXISTS_ERROR: Do nothing and return FALSE.
*
* @return array
* Function returns array of files or a single file object if $delta
* != NULL. Each file object contains the file information if the
* upload succeeded or FALSE in the event of an error. Function
* returns NULL if no file was uploaded.
*
* The documentation for the "File interface" group, which you can find under
* Related topics, or the header at the top of this file, documents the
* components of a file entity. In addition to the standard components,
* this function adds:
* - source: Path to the file before it is moved.
* - destination: Path to the file after it is moved (same as 'uri').
// Return cached objects without processing since the file will have
// already been processed and the paths in $_FILES will be invalid.
if (isset($upload_cache[$form_field_name])) {
if (isset($delta)) {
return $upload_cache[$form_field_name][$delta];
}
return $upload_cache[$form_field_name];
}
// Prepare uploaded files info. Representation is slightly different
// for multiple uploads and we fix that here.
$uploaded_files = $file_upload;
if (!is_array($file_upload)) {
$uploaded_files = array($file_upload);
}
$files = array();
foreach ($uploaded_files as $i => $file_info) {
// Check for file upload errors and return FALSE for this file if a lower
// level system error occurred. For a complete list of errors:
// See http://php.net/manual/features.file-upload.errors.php.
switch ($file_info->getError()) {
case UPLOAD_ERR_INI_SIZE:
case UPLOAD_ERR_FORM_SIZE:
drupal_set_message(t('The file %file could not be saved because it exceeds %maxsize, the maximum allowed size for uploads.', array('%file' => $file_info->getFilename(), '%maxsize' => format_size(file_upload_max_size()))), 'error');
$files[$i] = FALSE;
continue;
case UPLOAD_ERR_PARTIAL:
case UPLOAD_ERR_NO_FILE:
drupal_set_message(t('The file %file could not be saved because the upload did not complete.', array('%file' => $file_info->getFilename())), 'error');
$files[$i] = FALSE;
continue;
case UPLOAD_ERR_OK:
// Final check that this is a valid upload, if it isn't, use the
// default error handler.
if (is_uploaded_file($file_info->getRealPath())) {
break;
}
// Unknown error
default:
drupal_set_message(t('The file %file could not be saved. An unknown error has occurred.', array('%file' => $file_info->getFilename())), 'error');
if (!file_stream_wrapper_valid_scheme($destination_scheme)) {
drupal_set_message(t('The file could not be uploaded because the destination %destination is invalid.', array('%destination' => $destination)), 'error');
$files[$i] = FALSE;
continue;
}
$file->source = $form_field_name;
// A file URI may already have a trailing slash or look like "public://".
// If file_destination() returns FALSE then $replace === FILE_EXISTS_ERROR and
// there's an existing file so we need to bail.
if ($file->destination === FALSE) {
drupal_set_message(t('The file %source could not be uploaded because a file by that name already exists in the destination %directory.', array('%source' => $form_field_name, '%directory' => $destination)), 'error');
if (isset($destination) && !file_prepare_directory($destination, FILE_CREATE_DIRECTORY)) {
\Drupal::logger('file')->notice('The upload directory %directory for the file field !name could not be created or is not accessible. A newly uploaded file could not be saved in this directory as a consequence, and the upload was canceled.', array('%directory' => $destination, '!name' => $element['#field_name']));
$form_state->setError($element, t('The file could not be uploaded.'));