Chloé v/s Twitter API : Round 2

La dernière fois nous avions découvert l’API de Twitter, et avions récupéré nos premiers Tweets.

Aujourd’hui, nous allons expliquer le script permettant de tout faire automatiquement et la documentation pour ce faire se trouve ici. Il s’agit de la partie authentification pour accéder à l’API via un script.
Comme nous l’avions vu la dernière fois, l’API Twitter est protégé par le protocole oAuth, ce qui nécessitait d’avoir des customer key et secret délivrés par Twitter pour y accéder.

Ainsi, la doc Twitter nous donne trois étapes pour nous authentifier sur l’API :
1. Encoder les consumer key et secret en URL encoding (de l’ASCII étendu en sorte), puis concaténer la ckey, un ‘:’ et le csecret en une seule chaine de caractères et enfin encoder cette string en Base64.
2. Faire une requête HTTP POST dont le header (l’en tête) doit contenir les champs « Authorization » et « Content-type » ayant pour valeurs respectives « Basic Ckey:Csecret_encodés_en_base_64 » et « application/x-www-form-urlencoded;charset=UTF-8 », et le body (corps) de la requête doit être « grant_type=client_credentials ». La réponse à cette requête sera un Bearer Token, qui nous servira à nous authentifier lors de nos futures requêtes.
3. Faire la requête avec le champ « Authorization » dans l’en-tête ayant pour valeur « Bearer token_obtenu_dans_l’étape_précédente » (commençant souvent par AAAAAA).

Notre script ressemble donc à ceci :

#!/bin/bash

ckey='******************';
echo $ckey;
csecret='**********************************';
echo $csecret;

# urlencode
#on passe pour l'instant, on y reviendra si Twitter fait des modifications dans le format des ckey/secret

# concatenation et encodage en Base64
code=$(echo -ne "$ckey:$csecret" | base64 --wrap=0);
echo $code;

# envoi de la requete POST pour obtenir le token
curl -v --data "grant_type=client_credentials" https://api.twitter.com/oauth2/token HTTP/1.1 --header "Authorization: Basic <$code>Content-Type: application/x-www-form-urlencoded" > reponse.json;

#requete complete :
# POST /oauth2/token HTTP/1.1
# Host: api.twitter.com
# User-Agent: My Twitter App v1.0.23
# Authorization: Basic (ckey:csecret encodes en base64)Content-Type: application/x-www-form-urlencoded;charset=UTF-8
# Content-Length: 29
# Accept-Encoding: gzip

# grant_type=client_credentials

#requete pour les resultats de recherche

if grep bearer reponse.json; then
echo token trouve;

bearer=$(grep -o "AA*.*\b" reponse.json);
echo $bearer;
curl --get 'https://api.twitter.com/1.1/search/tweets.json' --data 'count=100&lang=en&q=Putin&result_type=recent' --header "Authorization: Bearer $bearer" -v >> resultats_en.txt;
curl --get 'https://api.twitter.com/1.1/search/tweets.json' --data 'count=100&lang=fr&q=Poutine&result_type=recent' --header "Authorization: Bearer $bearer" -v >> resultats_fr.txt;
curl --get 'https://api.twitter.com/1.1/search/tweets.json' --data 'count=100&lang=ru&q=%D0%9F%D1%83%D1%82%D0%B8%D0%BD&result_type=recent' --header "Authorization: Bearer $bearer" -v >> resultats_ru.txt;

else
echo Token non trouve;
fi;

La prochaine étape sera de planifier l’exécution du script sur une certaine période afin d’avoir le plus de données possibles.

 

Publicités

Chloé v/s Twitter API : Round 1

Pour le corpus de notre projet, en plus des articles de presse, nous avons pensé exploiter des tweets.
Pour accéder à ces données (qui sont en nombre immense), nous avons deux solutions : une simple et très très chronophage, une compliquée et très très rapide.
La simple consiste à utiliser le code source de la page. Seulement, cette solution ne permet d’avoir accès qu’aux 20 premiers résultats d’une recherche, enfin aux 20 premiers tweets qui s’affichent. 20 fois 140 caractères c’est pas immense pour un corpus, on en conviendra. Pour que cette solution soit viable, il faudrait recharger la page tous les 20 tweets (et par conséquent calculer la fréquence de publication des dits tweets).
Cette solution est très longue et fastidieuse, et ne permet pas d’extraire un nombre important de données en une seule fois.
Heureusement pour nous, il existe ce qu’on appelle une API (pour Application Programming Interface), soit interface de programmation, qui dans le cas de Twitter est (presque) librement accessible et très bien documentée.
Utiliser l’API permet de lire et d’écrire des tweets de façon automatique. Autrement dit, cela permet de scripter à peu près tout ce qu’on veut faire sur Twitter (bouton ‘tweeter’ dans un site web, faire un Twitterbot, accéder aux tweets ET à leur métadonnées, etc…)
C’est donc cette solution que nous avons choisi, d’une part pour sa rapidité, mais surtout parce que c’est beaucoup plus intéressant d’un point de vue technique.

Pré requis

Utiliser l’API de Twitter requiert d’avoir un compte d’utilisateur Twitter validé par téléphone, ainsi que d’avoir déclaré la création d’une application. En effet, depuis la mise à jour de l’API en version 1.1 en octobre 2012, la plupart des requêtes nécessitent d’avoir deux codes : un Customer Key et un Customer Secret.
Par ailleurs, un peu de documentation n’est pas négligeable, ainsi je conseille la lecture préalable du fonctionnement du protocole HTTP, du format Json ainsi que celle de la documentation de l’API Twitter.

Procédure en images

Ainsi, nous avons un compte Twitter validé par téléphone,. Il nous faut maintenant déclarer notre application et ça se passe sur cette page.

Tuto_Twitter1
On renseigne ici le nom, la description et le site de son appli. Le champ callback Url n’est pas obligatoire mais il est recommandé de le remplir pour valider la création de l’appli.

Une fois l’application validée, Twitter nous attribue nos Customer Key et Secret. Ces codes sont indispensables car ils donnent l’autorisation d’accéder à l’API.
Ensuite, nous devons faire une requête pour extraire les tweets en fonction de la recherche. Nous devons donc aller sur cette page et sélectionner notre appli dans le menu déroulant (sous la liste des paramètres) afin d’accéder au générateur de signature pour faire notre requête. Ce qui donne ceci :

Tuto_Twitter2

 

Détaillons la requête.
C’en est une de type GET puisque (ayant lu la page wikipédia du protocole HTTP) nous voulons lire le contenu.
q=Putin
    ‘q’ est l’opérateur de requête (comme dans ‘query’).
lang=en
    ici nous choisissons la langue, donc l’anglais (‘fr’ pour français, ‘ru’ pour russe).
result_type=recent
    ce paramètre nécessite de connaître un petit peu Twitter pour être compris. Au moment où l’on fait une recherche, Twitter n’affiche pas par défaut les résultats par ordre chronologique, mais par popularité. Ce paramètre peut prendre une des trois options suivantes : ‘recent’ (ordre de publication, le plus récent en haut), ‘popular’ (les plus populaires) et ‘mixed’ (un mélange des deux). Si elle n’est pas précisée, la valeur par défaut est ‘mixed’.
count=100
    ici on indique le nombre de résultats par page (le maximum est 100).

Une fois notre requête terminée, on valide en cliquant sur ‘Get oAuth signature’ et ceci apparaît :

Le dernier bloc est la commande à entrer dans le shell Unix pour extraire les tweets.

Format des données extraites

L’output de la requête est au format Json (un format d’organisation des données par balises, un peu comme le XML), et ça ressemble à peu près à ça dans un document txt :

Tuto_Twitter4
(presque) illisible, quoi.

ABSOLUMENT TOUTES les métadonnées relatives aux tweets sont renseignées (en vrac : le pseudo de l’auteur, le texte, le nombre de retweet et de favoris, la date et l’heure du tweet, mais aussi presque toutes les informations relatives au compte de l’auteur, nombre d’abonnés et d’abonnements, géolocalisation si activée, photo de profil, etc…).
Bref, nous avons extrait une mine d’informations, qui dans notre cas, ne nous serons pas d’un grand intérêt mais qui sont extrêmement utiles à ceux qui analysent les phénomènes d’influence par exemple.

Bonus : Librairies

Certains développeurs ont créé des librairies permettant l’accès à l’API dans un script. Twitter en a validé et recensées quelques unes avec des exemples (ici), qui sont donc a priori stables.
En bonus, le lien vers la librairie Python (que je n’ai pas encore testée, mais ça ne devrait tarder).

A suivre…

La prochaine étape pour l’obtention d’un set de données le plus complet possible sera l’écriture d’un script qui extraira automatiquement les tweets à une fréquence déterminée. Je travaille encore dessus, et je posterai évidemment le détail dans un prochain article.

Du tableau en HTML

Cet article est la suite de l’article précédent, c’est à dire la suite des exercices d’application du cours de Programmation et Projet Encadré.

Les consignes de la deuxième partie étaient de créer un fichier texte qui contiendrait le nom du blog et le mot étudié, puis un fichier HTML qui contiendrait un tableau de deux cellules sur deux lignes avec ces mêmes informations. Ensuite, il fallait programmer un scripts shell permettant de créer de manière automatique ce même tableau. Pris au jeu, j’ai décidé de ne faire qu’un seul script qui s’occuperait des deux premières tâches.

html
Script entier

Le script est séparé en deux blocs, la partie création du fichier texte et la partie création du fichier HTML.

shebang
Shebang

La première ligne qui commence par #!, le « shebang », est un en-tête du fichier qui indique au système d’exploitation que le fichier est un script et quel interpréteur utiliser pour l’exécuter.

Création du fichier .txt
Création du fichier .txt

Le premier bloc va donc créer un fichier contenu.txt dans le dossier DUMP-TEST. Ainsi, il demande à l’utilisateur via la console d’entrer le nom de son blog et le mot qu’il étudie. La commande read va assigner aux variables $NOM et $MOT les réponses de l’utilisateur pour pouvoir les écrire dans contenu.txt immédiatement avec echo, et pour remplir le tableau plus tard.

Création du fichier .html
Création du fichier .html

Le second bloc quant à lui va créer le fichier tableau.html dans le dossier TABLEAUX. Pour écrire chaque ligne du fichier HTML, il faut encore une fois utiliser echo. On remarque que là aussi, on se sert des variables associées avec read.

Parlons maintenant un peu plus précisément de la structure du fichier du tableau. HTML est un langage de balisage, c’est-à-dire qu’il est composé de balises au format <balise>contenu</balise>. Le premier mot entre chevrons indique que le contenu entre les balises va avoir des propriétés particulières à l’affichage, comme par exemple qu’il s’agit d’un titre, d’un texte en gras, d’un lien hypertexte…  Il doit absolument être suivi après son contenu de sa balise fermante, écrite avec un slash après le premier chevron. Une balise peut comprendre dans son contenu d’autres balises.

Le fichier HTML assez simple qui est présenté ici peut-être décomposé en trois parties.

doctype
Doctype

Comme le script shell, le fichier HTML commence par un en-tête qui indique au navigateur qu’il est bien écrit en HTML, <!DOCTYPE html>. Il est suivi de l’élément <html>, qui comprend comme son nom l’indique tout le code HTML.

head

L’élément qui suit est <head>, qui contient les méta-données du fichier. Il peut par exemple indiquer l’encodage du fichier, définir les styles pour les différents types de paragraphes du fichier, ou même les importer d’un fichier CSS. Ici, on s’en sert pour pouvoir afficher le titre de la page web dans la barre d’onglets du navigateur avec la balise <title> qui contient la variable $NOM, le nom du blog que l’on a demandé à l’utilisateur plus tôt avec read.

body et table
body et table

La dernière partie de ce fichier est <body>, le contenu affiché de la page web. Elle contient le corps du document, son contenu. Dans notre cas, il ne contient que le tableau.

Le tableau commence par la balise <table>. Cependant, utiliser la balise nue de cette façon donne une organisation en lignes et en colonnes, mais sans bordures. Si on en veut une, on y rajoute donc l’argument border= »1″ pour obtenir une bordure de largeur 1. Chaque ligne du tableau est délimitée par les balises <tr>, et chaque cellule par <td>.

Maintenant, vérifions que le script fonctionne bien. D’abord, on entre les réponses demandées par la machine.

read enregistre les valeurs entrées dans les variables $NOM et $MOT
read enregistre les valeurs entrées dans les variables $NOM et $MOT

Le script tourne, regardons si les fichiers ont bien été écrits comme on le souhaitait.

Cet output a été obtenu grâce à la commande less
Cet output a été obtenu grâce à la commande less
tableau.html
tableau.html

Le script a donc bien fonctionné, on a obtenu les deux fichiers qu’on voulait créer. Maintenant, il faut encore voir si tableau.html s’affiche correctement dans un navigateur.

firefox
tableau.html sous Firefox

Le tableau n’est pas très beau, mais il contient bien les bonnes informations, le bon nombre de lignes et de cellules et porte le bon titre.

Ainsi s’achèvent les premiers exercices d’application du cours de PPE. N’hésitez pas à nous indiquer si vous repérez des erreurs dans les exercices, elles seront corrigées aussi vite que possible.

De la ligne de commande et l’environnement Unix

Aujourd’hui, il s’agira de mettre en pratique ce qui nous a été présenté en cours sur Unix et l’utilisation du terminal ces deux dernières semaines. On verra comment se déplacer dans l’arborescence de fichiers, comment créer un dossier et observer son contenu, comment créer et lire des fichiers.

On commence par créer un environnement de travail en lançant un script fourni au préalable. On obtient un dossier plein d’autres dossiers vides, pour nous aider à organiser notre travail au fur et à mesure de l’avancement du projet.

Un environnement de travail plein de promesses

Ensuite, nous allons créer des dossiers tests pour pouvoir appliquer quelques commandes Unix. D’abord, on demande à travailler dans /zak/Travaux/PPE avec la commande cd, puis on crée trois dossiers tests, TEST1, TEST2 et TEST3 avec mkdir.

cd et mkdir à l'oeuvre
cd et mkdir à l’oeuvre

Après ça, essayons de créer des fichiers nommés vide1.txt dans TEST1 et vide2.txt dans TEST2 avec touch.

On ajoute un fichier dans TEST2 tout en continuant à travailler dans TEST1 grâce à la référence ../
On ajoute un fichier dans TEST2 tout en continuant à travailler dans TEST1 grâce à la référence ../

On ajoute ensuite une ligne de texte dans vide1.txt avec echo et l’opérateur de redirection >, puis on en rajoute une autre sans écraser le texte précédent avec un autre opérateur, >>.

L'opérateur >> permet d'ajouter une ligne sans écraser le texte déjà existant
L’opérateur >> permet d’ajouter une ligne sans écraser le texte déjà existant

Puisque vide1.txt contient quelque chose, on le renomme jenesuisplusvide.txt grâce à mv.

mv
mv permet soit de déplacer un fichier, soit de le renommer

Pour finir, on déplace ce fichier vers TEST2, et dans TEST1 on crée une copie du fichier nommée moinonplus.txt en utilisant cp.

cp permet soit de déplacer un fichier soit de le renommer
Il est possible de copier des fichiers vers d’autres dossiers

Avant de continuer avec d’autres créations de fichier, on vérifie que tout s’est bien passé. On utilise donc ls pour observer la liste des fichiers présents dans un dossier, et cat pour pouvoir lire le contenu d’un fichier.

 Tout va bien, on respire.
Tout va bien, on respire

Et si on voulait garder le résultat d’une commande dans un fichier ? Encore une fois, on va utiliser l’opérateur > pour rediriger l’output d’une commande vers un fichier. Ici, on redirige l’output de ls vers le fichier liste.txt, puis on va rajouter une autre fois cet output à la fin de notre fichier.

Rediriger vers un fichier inexistant va créer ce fichier
Rediriger vers un fichier inexistant va créer ce fichier

En cours, on a vu un autre opérateur de redirection, 2>. Celui-ci permet d’écrire les messages d’erreur dans un fichier plutôt que de les afficher dans le terminal. Par exemple, on va utiliser la commande lsd, qui n’existe pas, et on va rediriger le message d’erreur vers erreur.txt.

On voit ici que le message d'erreur n'apparait pas avec 2>
Le message d’erreur n’apparaît pas avec 2>

On en a fini de manipuler ces fichiers. Cependant, on remarque qu’on n’a pas touché à vide2.txt dans TEST2, ni à TEST3. On va donc les supprimer avec respectivement rm et rmdir.

rm pour supprimer un fichier, rmdir pour un dossier
rm pour supprimer un fichier, rmdir pour un dossier

On veut maintenant savoir combien de fichiers il y a dans TEST2, et combien de dossiers il y a dans notre environnement de travail. On va donc créer un fichier contenant l’output d’un ls pour chaque dossier, puis on on utilisera wc -l pour compter le nombre de lignes de chaque fichier, donc le nombre d’éléments qu’ils contiennent.

ls prend en compte le fichier qu'on crée avec la redirection
ls prend en compte le fichier qu’on crée avec la redirection, donc wc aussi

Dernières subtilités d’Unix à être présentées dans cet article, on va parler de quelques symboles utiles. On va commencer avec le séparateur ; qui permet d’exécuter plusieurs commandes à la suite, indépendamment les unes des autres. Dans notre exemple, on utilise who qui indique les utilisateurs connectés en ce moment, et pwd qui affiche le répertoire de travail actuel.

On obtient les outputs de chaque commande dans leur ordre respectif
On obtient les outputs de chaque commande dans leur ordre respectif

Dans la même idée, le regroupement permet de rediriger plusieurs commandes vers le même fichier. Il suffit de mettre les commandes souhaitées entre parenthèses et séparées d’un point-virgule.

L'output va être identique à celui du screenshot précédent
L’output va être identique à celui du screenshot précédent

On finit d’effleurer les possibilités d’Unix avec l’imbrication, qui permet d’utiliser le résultat d’une commande comme argument d’une autre commande. On utilise la syntaxe qui suit :

Le résultat est une version plus loquace de pwd
Le résultat est une version plus loquace de pwd

C’est tout pour Unix aujourd’hui. Mais il est certain qu’au fil du temps, nous découvrirons encore de nombreuses commandes utiles pour la réalisation de notre projet, et elles seront documentées au moment venu, au fur et à mesure.

Cet article commençant à être suffisamment long et peu digeste, la partie HTML des exercices d’application suit dans un second article.

Un début de corpus

Aujourd’hui, on va commencer à parler travail.

L’objectif du projet étant d’étudier un mot dans plusieurs langues et pays, nous allons construire trois corpus que nous allons tirer du web : un en français, un autre en anglais, et un dernier en russe que l’on va tirer du web.

Pour commencer, on a donc cherché des liens d’articles de presse en ces trois langues. Ce sont des sources pratiques pour concevoir un corpus, vu que l’orthographe et la syntaxe devraient y être plus soignées que sur des forums ou sur des réseaux sociaux. Bien entendu, nous n’exclurons pas ces derniers dans notre analyse pour autant, ils offriront un tout autre type de contenu.

Pour les trouver, on aurait pu utiliser des commandes Unix sophistiquées, mais mes connaissances balbutiantes en ligne de commande m’ont poussé à plutôt utiliser une extension Firefox, Link Gopher. Elle permet de facilement extraire tous les liens d’une page internet. Dans notre cas, nous l’avons utilisée sur les résultats de recherche obtenus avec Google Actualités.

C’est là qu’on a rencontré un léger problème : les hommes politiques ont souvent une actualité très riche, et c’est encore plus vrai pour Vladimir Poutine avec les attaques qu’il mène contre l’État islamique en ce moment. On se retrouve donc avec beaucoup d’articles très récents sur ces événements, ce qui peut fausser notre analyse avec des articles très partiaux sur la situation. On a donc essayé d’y remédier en prenant aussi des articles vieux de plus d’un an. On pourra aussi envisager de prendre le problème à l’envers et décider de se concentrer justement sur les impressions que les gens ont sur Poutine et sa politique dans ce contexte houleux.

Voilà donc trois fichiers contenant chacun 50 URL d’articles de presse : frurl pour les URL françaises, enurl pour les URL anglaises et ruurl pour les URL russes. Ce n’est certainement pas une liste définitive : elle sera complétée, étendue, affinée et retravaillée.

À très bientôt pour une série d’exercices sur Unix, et un post expliquant la démarche pour faire une recherche efficace et exploitable sur Twitter.

helloworld.blog

Bonjour, et bienvenue sur PoutineInput !

Nous sommes Chloé Tuillier et Zakarya Després, deux étudiants en première année du master pluriTAL.

Ce blog a pour but de présenter les avancées, semaine après semaine, d’un projet que nous devons achever dans le cadre du cours Programmation et Projet Encadré, sous la supervision de Jean-Michel Daube et Serge Fleury.

Le sujet du projet en question est d’étudier la vie multilingue d’un mot sur le web. Pour être plus précis, nous allons observer et un mot et son contexte au sein d’un corpus que nous allons tirer du web, puis les analyser grâce aux outils du traitement automatique des langues. La finalité de ce projet est la création d’un site web pour présenter nos travaux.

Dans notre cas, nous allons étudier le nom « Poutine », celui de l’actuel président de la Russie, en travaillant avec le français, l’anglais et le russe. L’idée d’observer ce que pensaient différents pays d’un même homme politique a été proposée par Chloé, et il nous paraissait intéressant de se pencher plus particulièrement sur une personnalité controversée comme Vladimir Poutine.

Ce blog est donc notre journal de bord pour ce projet. Progressivement, nous y ajouterons nos avancées sur la constitution de notre corpus de travail, son analyse, la création du site web final, ainsi que nos éventuels coups de génies et désillusions.

Pour l’instant, le projet est encore à l’état d’embryon, ce blog est donc encore vide de contenu. Mais pas d’inquiétude, il sera rempli bien assez vite.

À très bientôt !