You are here

public function FetchManager::fetch in Stage File Proxy 8

Downloads a remote file and saves it to the local files directory.

Parameters

string $server: The origin server URL.

string $remote_file_dir: The relative path to the files directory on the origin server.

string $relative_path: The path to the requested resource relative to the files directory.

array $options: Options for the request.

Return value

bool Returns true if the content was downloaded, otherwise false.

Overrides FetchManagerInterface::fetch

File

src/FetchManager.php, line 60

Class

FetchManager
Fetch manager.

Namespace

Drupal\stage_file_proxy

Code

public function fetch($server, $remote_file_dir, $relative_path, array $options) {
  try {

    // Fetch remote file.
    $url = $server . '/' . UrlHelper::encodePath($remote_file_dir . '/' . $relative_path);
    $options['Connection'] = 'close';
    $response = $this->client
      ->get($url, $options);
    $result = $response
      ->getStatusCode();
    if ($result != 200) {
      $this->logger
        ->warning('HTTP error @errorcode occurred when trying to fetch @remote.', [
        '@errorcode' => $result,
        '@remote' => $url,
      ]);
      return FALSE;
    }

    // Prepare local target directory and save downloaded file.
    $file_dir = $this
      ->filePublicPath();
    $destination = $file_dir . '/' . dirname($relative_path);
    if (!$this->fileSystem
      ->prepareDirectory($destination, FileSystemInterface::CREATE_DIRECTORY | FileSystemInterface::MODIFY_PERMISSIONS)) {
      $this->logger
        ->error('Unable to prepare local directory @path.', [
        '@path' => $destination,
      ]);
      return FALSE;
    }
    $destination = str_replace('///', '//', "{$destination}/") . $this->fileSystem
      ->basename($relative_path);
    $response_headers = $response
      ->getHeaders();
    $content_length = array_shift($response_headers['Content-Length']);
    $response_data = $response
      ->getBody()
      ->getContents();
    if (isset($content_length) && strlen($response_data) != $content_length) {
      $this->logger
        ->error('Incomplete download. Was expecting @content-length bytes, actually got @data-length.', [
        '@content-length' => $content_length,
        '@data-length' => $content_length,
      ]);
      return FALSE;
    }
    if ($this
      ->writeFile($destination, $response_data)) {
      return TRUE;
    }
    $this->logger
      ->error('@remote could not be saved to @path.', [
      '@remote' => $url,
      '@path' => $destination,
    ]);
    return FALSE;
  } catch (GuzzleException $e) {

    // Do nothing.
  }
  $this->logger
    ->error('Stage File Proxy encountered an unknown error by retrieving file @file', [
    '@file' => $server . '/' . UrlHelper::encodePath($remote_file_dir . '/' . $relative_path),
  ]);
  return FALSE;
}