How to get a remote file's size in PHP without downloading it

Submitted by dannix on Mon, 04/08/2019 - 14:35

I needed to get the size of an mp3 file in the PHP code that I wrote to make XML data for Podcasts.

Bellow is three different functions that achieve that objective, using the curl, get_headers and fopen functions. Hope this helps!

<?php
function curl_get_file_size( $url ) {
  // Assume failure.
  $result = 0; // use ZERO for unknown length - this is what the feed validator told me to do
  try {
    $curl = curl_init( $url );
 
    // Issue a HEAD request and follow any redirects.
    curl_setopt( $curl, CURLOPT_NOBODY, true );
    curl_setopt( $curl, CURLOPT_HEADER, true );
    curl_setopt( $curl, CURLOPT_RETURNTRANSFER, true );
    curl_setopt( $curl, CURLOPT_FOLLOWLOCATION, true );
    curl_setopt( $curl, CURLOPT_USERAGENT, $_SERVER[HTTP_USER_AGENT] );
 
    // set the port # as needed
    curl_setopt( $curl, CURLOPT_PORT, 80 );
 
    $data = curl_exec( $curl );
 
    if (FALSE === $data)
        throw new Exception(curl_error($curl), curl_errno($curl));
 
  } catch(Exception $e) {
 
    //print 'Curl failed with error '.$e->getCode().': '. $e->getMessage();
    trigger_error(sprintf(
        'Curl failed with error #%d: %s',
        $e->getCode(), $e->getMessage()),
        E_USER_ERROR);
 
  }
 
  curl_close( $curl );
 
  if( $data ) {
    $status = "unknown";
 
    if( preg_match( "/^HTTP\/1\.[01] (\d\d\d)/", $data, $matches ) ) {
      $status = (int)$matches[1];
    }
 
    if( preg_match( "/Content-Length: (\d+)/", $data, $matches ) ) {
      $content_length = (int)$matches[1];
    }
 
    // http://en.wikipedia.org/wiki/List_of_HTTP_status_codes
    if( $status == 200 || ($status > 300 && $status <= 308) ) {
      $result = $content_length;
    }
  }
 
  return $result;
}
 
 
function remote_filesize($url) {
    static $regex = '/^Content-Length: *+\K\d++$/im';
    if (!$fp = @fopen($url, 'rb')) {
        return '-1';
    }
    if (
        isset($http_response_header) &&
        preg_match($regex, implode("\n", $http_response_header), $matches)
    ) {
        return (int)$matches[0];
    }
    return strlen(stream_get_contents($fp));
}
 
 
function get_file_size($url) {
  echo $url;
  $head = get_headers($url, TRUE);
  $filesize = $head['Content-Length'];
  return $filesize;
}
 
?>