Google Takeout, Buzz et l'export des favoris

Comme annoncé dans un article précédent, Google Reader a mis fin aux partages d’articles comme on le connaissait. Dommage pour moi, je m’en servais aussi comme outil de bookmarking (un peu comme ce que d’autres font avec Delicious)

J’ai pu trouver la liste de ces partages en bidouillant des URL (genre ils sont cachés ici: http://www.google.com/reader/shared/06987377928849278758, la solution sautait aux yeux dès le départ !) mais il ne fait aucun doute que ça va bientôt disparaître, cette page comme mes liens. Donc il me fallait un moyen de les récupérer.

Heureusement, avec la sortie de Google+, Google a rendu disponible un outil nommé Google Takeout (développé par un groupuscule interne: le Data Liberation Front, les joyeux drilles sur la photo ci-dessus) qui promet de nous permettre de télécharger toutes les données que Google a sur nous. Je m’attendais donc à voir une belle option: « Google Reader » dans la liste. Mais non.

Les options de Google Takeout

C’est là que je me suis souvenu que les partages Google Reader se retrouvaient automatiquement sur Buzz. Logiquement en téléchargeant mes données Buzz je devrais récupérer ce que j’ai partagé (je ne m’en suis jamais servi autrement que via Reader…)

Et effectivement, Google me propose un fichier zip contenant 287 fichiers html. Oui, un fichier par partage:

screenshot.10

Et ce n’est même pas une capture de la page partagée : il n’y a que la photo de profil, et le lien:

screenshot.11

Ce n’est donc pas décemment exploitable. J’ai donc passé mon après-midi sur une solution permettant de regrouper tous ces liens et d’en faire un fichier bookmarks.html au format Netscape qui puisse être importé dans tous les navigateurs et services de bookmarking. Ça tombe bien, j’apprends le PHP, c’est un bon exercice.

Étant débutant, il se peut que vous trouviez des choses un peu aberrantes, des endroits où le code peut être optimisé. J’ai fait au mieux de mes compétences actuelles, n’hésitez pas à me corriger si vous voyez quelque chose qui vous choque.

Il me fallait d’abord un outil simple pour parcourir le code HTML et récupérer les éléments nécessaires, j’ai trouvé mon bonheur avec « PHP Simple HTML DOM Parser. » Ensuite il me fallait des infos sur la norme des bookmarks.html, j’ai trouvé ma réponse chez Microsoft.

Le minimum est là, on peut donc commencer:

    $file = file_get_contents('./buzz/example.html');
    $html = str_get_html($file);
    $title = $html->find('div[class=entry-title]', 0)->plaintext;
    $date = $html->find('abbr[class=published]', 0)->title;
    $link = $html->find('div[class=entry-content]', 0)->first_child()->href;

    echo '
'.$title.'
'."n"; $html->clear(); unset($html);

Les problèmes qui se présentent à ce stade, c’est que la date doit être au format UNIX alors que Buzz l’a mise dans un format un peu chelou: 0000-00-00T00:00:00.000. Dans certains partages, il n’y a tout simplement pas de lien, ce qui affole un peu PHP au niveau des E_NOTICE. Et pour finir, le parser n’aime pas trop les accents.

Pour résoudre le problème de la date, un peu de comptage de caractères est nécessaire:

function date_convert($date){
    $year = substr($date, 0, 4);
    $month = substr($date, 5, 2);
    $day = substr($date, 8, 2);
    $hour = substr($date, 11, 2);
    $min = substr($date, 14, 2);
    $sec = substr($date, 17, 2);

    $date = mktime($hour, $min, $sec, $month, $day, $year);
    return $date;
}

Pour les accents c’est un peu plus astucieux, il va falloir encoder tous les caractères en HTML puis décoder les balises pour que le parser puisse faire son boulot:

function char_convert($text){
    $text = htmlentities($text, ENT_NOQUOTES, "UTF-8");
    $text = htmlspecialchars_decode($text);
    return $text;
}

Et pour les fichiers sans lien, un « if » suffit.

Maintenant qu’on récupère tout à peu près correctement, on va pouvoir peaufiner. Comme ce sont des liens de flux RSS on voit souvent du http://feedproxy.google.com/~r/9gag/~3/3dFZLa-CYI8/466983 au lieu d’avoir une belle URL claire et limpide. Il va falloir sortir cURL pour faire le ménage (et on va aussi en profiter pour virer les liens morts ainsi que les paramètres que rajoute feedburner pour les statistiques) :

function real_url($link){
    if ( ! empty($link) ) { return; }
    $options = array(
     CURLOPT_NOBODY         => true,     // Asks header only
     CURLOPT_RETURNTRANSFER => true,     // return web page
     CURLOPT_HEADER         => true,    // return headers
     CURLOPT_FOLLOWLOCATION => true,     // follow redirects
     CURLOPT_ENCODING       => "",       // handle all encodings
     CURLOPT_USERAGENT      => "spider", // who am i
     CURLOPT_AUTOREFERER    => true,     // set referer on redirect
     CURLOPT_CONNECTTIMEOUT => 10,      // timeout on connect
     CURLOPT_TIMEOUT        => 15,      // timeout on response
     CURLOPT_MAXREDIRS      => 10,       // stop after 10 redirects
    );

    $ch      = curl_init( $link );
    curl_setopt_array( $ch, $options );
    $content = curl_exec( $ch );
    $err     = curl_errno( $ch );
    $errmsg  = curl_error( $ch );
    $header  = curl_getinfo( $ch );
    curl_close( $ch );

    $http_code = $header["http_code"];
    $url = $header["url"];

    if ( $http_code != 404 ) {
     // Ces trois lignes suppriment les paramètres feedburner.
     // Merci Sebastien SAUVAGE ;D
     $i=strpos($url,'&utm_source='); if ($i) $url=substr($url,0,$i);
     $i=strpos($url,'?utm_source='); if ($i) $url=substr($url,0,$i);
     $i=strpos($url,'#xtor=RSS-'); if ($i) $url=substr($url,0,$i);

     return $url;
    }
    else {
     return;
    }
}

Le résultat final est disponible ici : Télécharger le script pour passer de Buzz à bookmarks.html.

J’y ai ajouté une variable pour choisir le dossier qui contient les fichiers html de Buzz, ainsi que la boucle qui les parcourt. Il ne prend pas de paramètres et vous aurez besoin du fichier simple_html_dom.php. Au niveau du temps d’exécution… La vérification de la validité des liens prend un peu de temps: Pour 287 fichiers il a fallu 5 minutes et le nombre de lien valides est de 209 (mais là ça dépendra de vos partages.)

Maintenant que vous avez vos liens dans un format standard, libre à vous d’en faire ce que vous voulez. Pour ma part je pense installer Shaarli prochainement.