Annonce ToutSurTout

Bienvenue sur toutsurtout.biz

Déjà 15 ans !

Radio TST

Si vous souhaitez participer vous aussi aux discussions sur le forum, il faut vous inscrire ou vous identifier.

Le Thème TST Noël est maintenant en place.

Les inscriptions sont actuellement OUVERTES.

Message 1 Discussion postée le 29-01-2014 à 03:34:27

Philippe
Avatar de Philippe


Titre: Banni
Avancement: Niveau 3
Date d'inscription: 26-09-2009
Messages: 3 660

Télécharger une vidéo YouTube sur votre serveur avec cUrl

Ce tutoriel a pour but de vous expliquer comment télécharger une ressource (fichier, stream, ...) distante vers votre serveur.
Notre exemple d'application, sera le téléchargement d'une vidéo Youtube.
Ce tutoriel n'est pas encore complet !

cUrl pour effectuer des requêtes HTTP

Pour nos requêtes HTTP, nous allons utiliser la librairie cUrl avec PHP.
Cette librairie nous permet de large possibilité en terme de transfert de données (elle ne fait pas que HTTP !).
A completer...

Classe pour le téléchargement/sauvegarde de ressources (fichiers, vidéos, ...)

Maintenant utilisons cURl dans notre classe pour télécharger des fichiers.
FileDownloader.class.php :

<?php
set_time_limit(0); // pour les long donwload...
class FileDownloader {
    protected $DL_DIR = "downloadDir/";

    protected function curl_get_contents($url) {
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_HEADER, 0);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        $output = curl_exec($ch);
        curl_close($ch);       
        return $output;
    }

    protected function curl_save_contents($url, $filename) {
        if(!file_exists($this->DL_DIR))
            mkdir($this->DL_DIR); // création du répertoire si inexistant
        $fp = fopen($this->DL_DIR . $filename, "w");
        if(FALSE !== $fp) {
            $ch = curl_init();
            curl_setopt($ch, CURLOPT_URL, $url);
            curl_setopt($ch, CURLOPT_HEADER, 0);
            curl_setopt($ch, CURLOPT_FILE, $fp);
            curl_exec($ch);
            curl_close($ch);
        }
        else
            throw new Exception($this->DL_DIR . $filename . " erreur d'ouverture.");
        fclose($fp);
    }
}
?>

Classe pour le téléchargement de vidéos Youtube

Cette classe permet de parser une page web de Youtube à la recherche de la vidéo uniquement. Puis il est ensuite possible de télécharger cette vidéo sur votre serveur.
Elle permet aussi de récupérer une vidéos en fonction du format vidéo (mp4, flv, webm, ...) définis dans YouTube.
Elle étends (extends) de FileDownloader pour utiliser les méthodes de récupération de fichiers (avec cUrl dans notre cas).

Voici notre classe (YoutubeDownloader.class.php) :

<?php
require_once("FileDownloader.class.php");
class YoutubeDonwloader extends FileDownloader {

    private $_url;

    /* Constantes de format video */
    const _3GP     = "3gp";
    const FLV     = "flv";
    const MP4     = "mp4";
    const VIDEO    = "flv";
    const WEBM     = "webm";

    private $_video_types = array(
        5  => self::FLV,
        13 => self::_3GP,
        17 => self::MP4,
        18 => self::MP4,
        22 => self::MP4,
        34 => self::FLV,
        35 => self::FLV,
        37 => self::MP4,
        38 => self::VIDEO, /* n'importe quel format */
        43 => self::WEBM,
        44 => self::WEBM,
        45 => self::WEBM
    );

    public function __construct($url) {
        $this->DL_DIR = "ytdl/";
        $this->_url = $url;
    }

    private function checkVideoFormat($format) {
        $videos_format = array_values($this->_video_types);
        if( in_array($format, $videos_format) )
            return true;
        return false;
    }

    public function getVideoInfos() {
        $video_infos = array();
        $contents = parent::curl_get_contents($this->_url);
        if(preg_match('#url_encoded_fmt_stream_map=([^&$]*)#', $contents, $match)) {
            foreach( explode(',', urldecode($match[1])) as $url_map) {
                if(preg_match('#url=([^;,\"]+).*&itag=(\d+)#', urldecode($url_map), $result)) {
                    $video_format = isset($this->_video_types[$result[2]]) ? $this->_video_types[$result[2]] : $this->_video_types[38];
                    $video_url = $result[1];
                    if(!isset($video_infos[$video_format])) // un lien par format (à revoir, je crois qu'il y a plusieurs qualités par format)
                        $video_infos[$video_format] = $video_url;
                }
            }
        }
        return $video_infos;
    }

    public function getVideoUrlByFormat($format) {
        $url = null;       
        if( $this->checkVideoFormat($format) ) {
            $infos = $this->getVideoInfos();
            if( !in_array($format, array_keys($infos)) ) {               
                throw new Exception("Format non disponible ($format) pour cette video. Formats disponibles : ". implode(', ', array_keys($infos)));
            }
            $url = $infos[$format];
        }       
        return $url;
    }

    public function saveVideoByFormat($format, $filename = null) {
        $url = $this->getVideoUrlByFormat($format);
        if(!is_null($url)) {
            parent::curl_save_contents($url, (is_null($filename)) ? "YoutubeDonwloader-".time().".".$format : $filename);
        }
    }
}
?>

Et on test notre application :

<?php
try {
    $ytdl = new YoutubeDonwloader($_GET['url']); // https://www.youtube.com/watch?v=xxxxxxxxxx
    //$video_url = $ytdl->getVideoUrlByFormat(YoutubeDonwloader::MP4); // Juste les infos
    $ytdl->saveVideoByFormat(YoutubeDonwloader::MP4);
    echo "DL => OK".PHP_EOL;
} catch(Exception $ex) {
    echo "DL => KO".PHP_EOL;
    echo $ex->getMessage().PHP_EOL;
}
?>

Exemple d'utilisation : http://<host>/<script_path>?url=https://www.youtube.com/watch?v=Lcwk0yoerg8

Voilà ! Vous pouvez télécharger les sources ici : http://uptobox.com/ze7yvuu731ht
Si vous avez des suggestions ou remarques n'hésitez pas !


https://www.world-lolo.com/images/uploads/image.num1445754529.of.world-lolo.com.jpg
Des stades aux entrées payantes sont pleins de gens qui pensent que ceux qu'ils applaudissent sont trop payés, et les bibliothèques à l'entrée gratuite sont vides des gens qui pensent que les livres sont trop chers ...