Cinque Terre

Lien

Telecharger un fichier distant et l'enregistrer en local

Plusieurs fonctions PHP permettent d'enregistrer un fichier distant sur son poste de travail, par exemple file_get_contents(). La class DownloadBinaryFile reprend le même principe en utilisant l'extension cURL.

Telecharger un fichier avec PHP

Pour télécharger une image, une page HTML ou encore une vidéo, le script PHP procède de la manière suivante:
1. la fonction load() charge le contenu du lien $remote dans un tampon mémoire,
2. avec la fonction saveTo(), le contenu du tampon est enregistré dans un fichier $local.
Attention: si un fichier du même nom existe dans le répertoire local, le fichier est automatiquement supprimé par la fonction unlink().
<?php
/**
 * DownloadBinaryFile: Charger un fichier distant et l'enregistrer en local
 *
 * @author Fobec.com 2012
 * @copyright http://www.fobec.com/php5/1113/telecharger-fichier-distant-enregistrer-local.html 
 */
 
class DownloadBinaryFile {
 
    private $UA="Mozilla/5.0 (Windows NT 5.1; rv:10.0.2) Gecko/20100101 Firefox/10.0.2";
    private $REFERER="";
 
    private $rawdata='';
 
/**
 * Télecharger un fichier distant
 * Les données sont stockées dans le tampon $rawdata
 * @param string $url
 * @return boolean
 */
    public function load($url) {
        $curl = curl_init ();
        curl_setopt ($curl, CURLOPT_URL, $url);
        curl_setopt($curl, CURLOPT_HEADER, 0);
        curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
        if (!empty($this->UA)) {
            curl_setopt ($curl, CURLOPT_USERAGENT, $this->UA);
        }
        if (!empty($this->REFERER)) {
            curl_setopt($curl, CURLOPT_REFERER, $this->REFERER);
        }
        curl_setopt($curl, CURLOPT_BINARYTRANSFER,1);
        curl_setopt ($curl, CURLOPT_FOLLOWLOCATION, 1);
        $this->rawdata=curl_exec($curl);
 
        $httpcode=curl_getinfo($curl, CURLINFO_HTTP_CODE);
        if ($httpcode!=200) {
            return FALSE;
        }
 
        curl_close ($curl);
        return TRUE;
    }
 
/**
 * Enregister les données en local
 * @param string $filename
 */
    public function saveTo($filename) {
        if(file_exists($filename)){
            @unlink($filename);
        }
        $fhandle=fopen($filename, "x");
        if ($fhandle) {
            fwrite($fhandle, $this->rawdata);
            fclose($fhandle);
        } else if (isset($error)) {
            throw new Exception("File reading denied to ".$file." !!!");
        }
    }
 
/**
 * Fixer le user agent pour la requet
 * @param string $ua
 */
    public function setUseragent($ua) {
        $this->UA=$ua;
    }
 
 /**
 * Fixer le referer pour la requet
 * @param string $referer
 */
    public function setReferer($referer) {
        $this->REFERER=$referer;
    }
}
?>

Enregistrer une image

Dans le premier exemple, utilisons la class DownloadBinaryFile pour enregistrer une image. Il suffit de définir les liens pour les variables $local et $remote:
$local: chemin de l'image sur notre poste,
$remote: lien du logo sur le site commentcamarche.net.
<?php
require_once $_SERVER['DOCUMENT_ROOT'].'/DownloadBinaryFile.php';
 
$local='/var/www/ccmlogo.png';
$remote='http://static.ccm2.net/www.commentcamarche.net/_skin/_local/img/logo.png?201007091112';
 
$DownloadBinaryFile=new DownloadBinaryFile();
if ($DownloadBinaryFile->load($remote)==TRUE) {
    $DownloadBinaryFile->saveTo($local);
} else {
    echo 'download failed';
}
?>

Enregistrer une page HTML

Voyons comment enregistrer une page HTML sur le même principe. Afin d'éviter un blocage de la part du serveur distant, il est préférable de définir un useragent et un referer avec les fonctions setReferer() et setUseragent().
<?php
require_once $_SERVER['DOCUMENT_ROOT'].'/DownloadBinaryFile.php';
 
$local='/var/www/fobec_index.html';
$remote='http://www.fobec.com/index.php';
 
$DownloadBinaryFile=new DownloadBinaryFile();
$DownloadBinaryFile->setReferer('http://www.fobec.com');
$DownloadBinaryFile->setUseragent('exemple DownloadBinaryFile');
if ($DownloadBinaryFile->load($remote)==TRUE) {
    $DownloadBinaryFile->saveTo($local);
} else {
    echo 'download failed';
}
?>

La class est un exemple d'encapsulation des fonctionnalités de l'extension cUrl. Les mêmes fonctions auraient pu etre obtenues avec file_get_contents() ou directement avec les sockets. Bien que l'architecture de la class est simple, ces fonctions sont utilisées sur le site pour télécharger un fichier à partir d'un serveur vers le disque dur.

'); }); }); 74