Comment créer un widget Tweets récents

Dans ce didacticiel, nous verrons comment créer un widget "Tweets récents". Il existe un bon nombre de plug-ins liés à Twitter dans le référentiel, mais j'espère que ce tutoriel couvrira certaines des méthodes importantes (et généralement applicables) nécessaires à la création d'un tel plug-in (avec ou sans Twitter)..


La classe de widget

La classe Widget, WP_Widget, est une classe d'assistance pour la création de widgets. Pour créer un widget, vous créez simplement une extension de cette classe avec quatre méthodes: __construction, widget, mettre à jour et forme.

 classe WP_Widget_Wptuts_Twitter_Widget étend WP_Widget var $ w_arg; // une variable de classe pour stocker un tableau de nos paramètres de widget et leurs valeurs par défaut function __construct ()  widget de fonction ($ args, $ instance)  function update ($ new_instance, $ ancien_instance)  formulaire de fonction ($ instance) 
  • __construction initialise le widget. Ici, vous définissez l'ID unique du widget, son titre, sa description (pour le côté administrateur) et la ou les classes à attribuer au conteneur du widget au front-end.
  • widget - la méthode responsable de l'impression du contenu du widget sur le front-end.
  • forme - cette méthode devrait imprimer les paramètres du widget dans le formulaire Apparence> Widget
  • mettre à jour - cette fonction est responsable de valider les options envoyées depuis le formulaire du widget (via forme). Le tableau $ new_instance contient les options à valider et le tableau$ old_instance contient les options actuellement enregistrées. Il attend les options validées à renvoyer, ou false pour abandonner la mise à jour des options.

Construction de classe

Nous commençons par construire la classe. Pour enregistrer vos widgets, vous devez vous accrocher à l'action. widgets_init et appeler register_widget, en passant le nom de la classe du widget (WP_Widget_Wptuts_Twitter dans ce cas). Cet extrait se trouve juste après notre classe de widgets:

 add_action ('widgets_init', 'wptuts_register_widget'); fonction wptuts_register_widget () register_widget ('WP_Widget_Wptuts_Twitter_Widget'); 

register_widget crée une instance de notre widget, et appelle donc le __construction méthode. Cela devrait définir certaines constantes de classe, par exemple un identifiant unique (le id_base), et les paramètres de configuration du widget, notamment:

  • la description - une description du widget (elle apparaîtra sur la page d'administration du widget).
  • nom du cours - Classe (s) à ajouter à l'attribut de classe du widget.

Vous pouvez également spécifier un tableau 'options de contrôle' - cela vous permet de spécifier la largeur du formulaire d'administration du widget (généralement 250 pixels), au cas où vous auriez besoin de plus d'espace. Esthétiquement, cependant, il est préférable de ne pas changer cela et de ne pas surcharger vos widgets avec des options excessives.

Pour définir ces configurations, vous pouvez utiliser le WP_Widget :: __ construct méthode (i.e. parent :: __ construct). Cela attend:

  • Base d'identification - un identifiant unique pour la classe Widget
  • prénom - Le nom de votre widget, utilisé dans l'écran d'administration.
  • Options du widget - définit le nom de classe et la description.
  • Options de contrôle - (facultatif) tableau de hauteur et de largeur du formulaire de widget.

Ensuite (éventuellement) nous pouvons définir les paramètres du widget et leurs valeurs par défaut.

 function __construct () $ widget_ops = array ('classname' => 'wptuts_widget_twitter', 'description' => __ ('affiche une liste des tweets récents', 'wptuts_twitter')); parent :: __ construct ('WP_Widget_Wptuts_Twitter', __ ('Twitter', 'wptuts_twitter'), $ widget_ops); // Définit les paramètres et les valeurs par défaut du widget $ this-> w_arg = array ('title' => ", 'screen_name' =>", 'count' => '5', 'published_when' => '1'); 

Vous devez attribuer à vos widgets une classe unique, car cela contribuerait à garantir que le style que vous fournissez aux cibles seulement votre widget.


Récupérer des tweets

Avant d'aller plus loin, nous allons créer une méthode d'assistance qui envoie une demande à l'API Twitter. Cette méthode simple prend la requête (une URL) et utilise la fonction wp_remote_get pour récupérer la réponse. wp_remote_get fait partie de l'API HTTP qui a été couvert dans ce tutoriel.

La méthode recherche ensuite les erreurs éventuelles: soit provoquées par WordPress (avec is_wp_error) ou par Twitter (en vérifiant le code de réponse). L'instruction switch de la méthode vous permet d'agir différemment selon ce code - dans l'exemple ci-dessous, toutes les réponses d'erreur sont converties en un objet d'erreur WordPress ou sinon, la réponse réussie (un tableau de tweets) est renvoyée..

En conservant à la fois le code d'erreur et le message, nous pouvons faciliter le débogage ultérieurement, en cas d'erreur..

 fonction retrieve_remote_tweets ($ request_url) $ raw_response = wp_remote_get ($ request_url, array ('timeout' = 1)); if (is_wp_error ($ raw_response)) renvoie $ raw_response; $ code = (int) wp_remote_retrieve_response_code ($ raw_response); $ response = json_decode (wp_remote_retrieve_body ($ raw_response)); commutateur ($ code): cas 200: retour $ réponse; cas 304: cas 400: cas 401: cas 403: cas 404: cas 406: cas 420: cas 500: cas 502: cas 503: cas 504: renvoyer un nouveau WP_Error ($ code, $ réponse-> erreur); default: return new WP_Error ($ code, __ ('Réponse invalide', 'wptuts_twitter')); interrupteur d'extrémité; 

L'API Twitter

Twitter dispose d'une documentation complète sur son API, qui vous permet entre autres de récupérer vos tweets récents, les tweets de votre page d'accueil ou les tweets correspondant à un terme de recherche. Certaines des fonctionnalités les plus avancées de l'API nécessitent une authentification via OAuth..

Dans ce tutoriel, nous cherchons les tweets d’un utilisateur spécifique (ou le chronologie utilisateur). L'URL pour récupérer ces tweets a une structure très simple:

 https://api.twitter.com/1/statuses/user_timeline.json?screen_name=screen-nameName&arg1=val1&arg2=val2

Nom de l'écran doit être le nom d’écran de l’utilisateur et les autres arguments peuvent être n’importe lequel de ceux énumérés ici. En règle générale, des arguments tels que include_entities serait défini sur true pour obtenir des métadonnées sur les tweets (telles que les URL ou les hashtags qu'ils contiennent).


Caching

Twitter impose une limite au nombre de demandes que vous pouvez effectuer: 150 par heure pour les demandes non authentifiées et 350 pour les autres. Non seulement cela, mais récupérer les tweets prend du temps - augmentant le temps de chargement de votre site. La récupération de vos tweets sur Twitter à chaque chargement de page est inutilement coûteuse - et particulièrement dans le cas où il n'est pas nécessaire que vos tweets apparaissent sur votre site immédiatement après leur publication..

La mise en cache, en particulier les transitoires de WordPress, peut être utilisée pour stocker vos tweets (ou toute autre donnée) dans votre base de données. Les récupérer à partir de la base de données est beaucoup plus rapide que de les récupérer à distance, et cela ne contribue à aucune limite d'API. Bien sûr, les données vont bientôt devenir obsolètes - ce qui explique pourquoi la date d'expiration est conservée avec les tweets..

L'idée est que lors de l'affichage de vos tweets, si les données ont expiré (ou si les tweets ne sont pas présents dans la base de données), vous les récupérez sur Twitter et actualisez le cache. De cette manière, vous pouvez limiter le nombre de demandes adressées à Twitter toutes les 20 minutes, heure ou jour, en fonction de la durée pendant laquelle vous êtes prêt à attendre que vos tweets soient mis à jour. De plus, lorsque les tweets ne sont pas actualisés, vous bénéficierez de temps de chargement plus rapides. La mise en cache, lorsqu'elle est utilisée correctement, constitue un excellent moyen d'améliorer les performances de vos plug-ins ou de vos thèmes. Si vous ne l'avez pas utilisé auparavant, je vous recommande de regarder cette vidéo et de suivre ce tutoriel..

Cependant, supposons que votre mémoire cache de tweet expire et que le service de Twitter soit arrêté pour cause de maintenance. Les tweets sont supprimés de la base de données, mais vous ne pouvez pas récupérer de tweets sur Twitter pour les remplacer et vous n'aurez donc rien à afficher. La solution à cela est 'Soft Caching'.


Mise en cache souple

La mise en cache souple, comme la mise en cache, tente de mettre à jour vos tweets une fois un certain délai écoulé. Cependant, contrairement à la mise en cache 'dure', les données précédentes ne sont pas supprimées tant qu'une réponse valide n'a pas été reçue pour les remplacer. En conséquence, si l'API de Twitter est désactivée, votre site continue d'afficher les tweets de la dernière actualisation..

La mise en cache logicielle n'est pas prise en charge de manière native par WordPress, mais Mark Jaquith et Aaron Campbell en ont produit une excellente implémentation de classe. J'utiliserai une méthode légèrement simplifiée, qui, j'espère, illustrera le fonctionnement de la mise en cache logicielle dans WordPress..

L'idée est de gérer manuellement l'expiration du transitoire. Plutôt que de stocker les tweets en tant que transitoires avec une date d'expiration, vous stockez un tableau contenant les tweets et le délai d'expiration à l'intérieur d'un transitoire qui n'a pas de délai d'expiration. Nous pouvons implémenter cette méthode en utilisant la fonction suivante à la place de set_transient.

 function set_twitter_transient ($ key, $ data, $ expiration) // Heure d'expiration du transitoire $ expire = time () + $ expiration; set_transient ($ key, array ($ expire, $ data)); 

Bien entendu, sans délai d’expiration, les données ne sont jamais (ou en réalité, il n’est pas garanti) d'être supprimées et remplacées par de nouvelles données. Nous devons maintenant nous en occuper nous-mêmes.

Lorsque vous récupérez ce transitoire sans expiration, vous vérifiez si le délai d'expiration stocké est passé. Si c'est le cas, vous tentative récupérer les nouveaux tweets avec la méthode ci-dessus retrieve_remote_tweets. Si cela réussit, vous mettez à jour le transitoire (avec les nouvelles données et un nouveau délai d'expiration) et utilisez ces nouvelles données. Si ce n'est pas le cas, vous utilisez simplement les données actuellement stockées jusqu'à ce que vous obteniez une réponse satisfaisante de Twitter..

Pour récupérer les tweets (à distance ou localement) et gérer le cache, nous définissons la méthode get_tweets. Cela prend un tableau d'arguments avec lequel générer la demande Twitter. Par exemple:

  • Nom de l'écran - le nom du compte Twitter pour suivre
  • compter - le nombre de tweets à récupérer
  • include_rts - 1 | 0 - 1 pour inclure les retweets, 0 pour exclure les retweets.

La méthode utilise alors add_query_arg pour construire l'URL de la demande, et à partir de cela génère une clé pour notre transitoire. Ceci est important car vous souhaitez utiliser la même clé pour une configuration différente du widget, en particulier si vous avez plusieurs instances du widget..

Un code d’expiration de 1 heure est codé en dur dans cette fonction..

 function get_tweets ($ args) // URL de demande de construction $ args ['nom_écran']] '' @ '. $ args [' nom_écran ']]; $ request_url = 'https://api.twitter.com/1/statuses/user_timeline.json'; $ request_url = add_query_arg ($ args, $ request_url); // Génère la clé $ key = 'wptt _'. Md5 ($ request_url); // expire toutes les heures $ expiration = 60 * 60; $ transitoire = get_transient ($ clé); if (false === $ transitoire) // Expiration définitive $ data = $ this-> retrieve_remote_tweets ($ request_url); if (! is_wp_error ($ data)) // Mise à jour du transitoire $ this-> set_twitter_transient ($ key, $ data, $ expiration);  return $ data;  else // Expiration souple. $ transitoire = tableau (date d'expiration, données) if ($ transitoire [0]! == 0 && $ transitoire [0] <= time() )  // Expiration time passed, attempt to get new data $new_data = $this->retrieve_remote_tweets ($ request_url); if (! is_wp_error ($ new_data)) // En cas de succès, renvoie la mise à jour transitoire et les nouvelles données $ this-> set_twitter_transient ($ key, $ new_data, $ expiration); $ transitoire [1] = $ new_data;  return $ transitoire [1]; 

Lorsque vous utilisez l'API transitoire de WordPress, vous devez vérifier si get_transient trouve vos données dans le cache et, si ce n’est pas le cas, récupérez ou générez les données (par exemple de Twitter), puis mettez à jour le transitoire. Cependant, le get_tweets La méthode ci-dessus gèrera tout cela - et retournera vos 'anciennes données' si elle ne parvient pas à les mettre à jour. Cependant, il n’est toujours pas garanti de renvoyer des données: c’est peut-être qu’il n’ya pas de tweets dans la base de données (par exemple, exécutés pour la première fois) et que Twitter ne répond pas avec succès. Dans ces cas, un WP_Error l'objet est renvoyé - et nous devrons nous assurer que votre plug-in résout ce problème et se dégrade gracieusement.


La forme

Le travail de la méthode de formulaire consiste à afficher le formulaire d'options du widget dans la page Apparence> Widget. Il passe les options actuellement sauvegardées sous forme d'argument (un tableau). Bien sûr, vous pouvez ensuite utiliser wp_parse_args remplacer toutes les valeurs "manquantes" par des valeurs par défaut.

En règle générale, le formulaire de widget doit être assez petit (et souvent dans la barre latérale étroite). Vous pouvez l'agrandir à l'aide des options de contrôle mentionnées précédemment, mais il est préférable de respecter l'esthétique de WordPress. Pour cette raison, je suivrai la mise en page du widget par défaut de WordPress..

J'utiliserai aussi les méthodes $ this-> get_field_id et $ this-> get_field_name générer le nom et les valeurs d'identifiant pour les entrées pour chaque instance d'un widget, afin que WordPress puisse gérer leur traitement pour nous.

Dans cet exemple, j'autorise l'utilisateur à fournir un titre pour le widget, le nom d'écran du / des tweets à afficher, un nombre maximal de tweets et l'inclusion ou non du moment où le tweet a été publié..

 forme de la fonction ($ instance = array ()) // Fusionner $ instance avec defaults $ instance = extraire (wp_parse_args ((array) $ instance, $ this-> w_arg)); ?> 

type = "checkbox" value = "1" />


Validation des options

Une fois que vous avez créé le formulaire, vous devez mettre à jour les options du widget lors de leur enregistrement. WordPress s’occupe de tout cela pour nous - mais il faut encore valider les données. Cet article traite en détail de la validation. Si vous ne savez pas exactement ce que vous devez faire ou comment valider vos données, je vous recommande de le vérifier..

Tout ce qui est renvoyé par cette fonction est ajouté à la base de données. Par conséquent, outre la validation des données, nous devons nous assurer qu’elle ne contient que les données attendues. Une bonne technique consiste à commencer par un tableau vide et à n'y ajouter que des données validées. Si vous souhaitez annuler la sauvegarde, vous pouvez retourner faux.

 mise à jour de la fonction ($ new_instance = array (), $ old_instance = array ()) $ validated = array (); $ validated ['title'] = sanitize_text_field ($ new_instance ['title']); $ validated ['screen_name'] = preg_replace ('/ [^ A-Za-z0-9 _] /', ", $ new_instance ['screen_name']); $ validated ['count'] = absint ($ new_instance [' count ']); $ validated [' published_when '] = (isset ($ new_instance [' published_when '])? 1: 0); return $ validated;

Le nom d’écran est validé en supprimant tout sauf les caractères alphanumériques et les traits de soulignement..


Affichage du widget

Enfin, nous arrivons à la méthode d’affichage du widget. Toutes les pièces sont en place, il ne reste plus qu'à produire le contenu du widget. le widget La méthode responsable de cette opération transmet deux arguments: le premier est un tableau d'arguments correspondant aux paramètres du widget de la barre latérale - les arguments d'affichage, y compris before_title, after_title, before_widget, et after_widget. La seconde concerne les paramètres de cette instance particulière du widget. Il s'agit d'un tableau des paramètres enregistrés dans notre formulaire..

J'utiliserai une autre fonction d'assistance pour générer la liste des tweets, mais voici le contour de tous les widgets:

 widget de fonction ($ args, $ instance) extract ($ args); $ title = apply_filters ('widget_title', $ instance ['title']); echo $ before_widget; echo $ before_title.esc_html ($ title). $ after_title; echo $ this-> generate_tweet_list ($ instance); echo $ after_widget; 

le generate_tweet_list méthode récupère simplement les tweets avec get_tweets - et s’il n’ya pas d’erreur, parcourt les tweets et les affiche dans une liste. Pour chaque tweet, il applique la méthode make_clickable - cela scanne le tweet et transforme tout nom d'écran, hashtag ou lien en lien réel (voir ci-dessous).

En fonction des paramètres, il ajoute également lorsque le tweet a été publié à l'aide de la fonction WordPress human_time_diff.

 function generate_tweet_list ($ args = array ()) $ args = shortcode_atts (array ('include_entities' => 'true', 'include_rts' => 1, 'screen_name' => ", 'count' => 5, 'published_when '=> 1), $ args); // Récupérer les tweets $ tweets = $ this-> get_tweets ($ args); $ content ='
    '; if (is_wp_error ($ tweets) ||! is_array ($ tweets) || count ($ tweets) == 0) $ content. = '
  • '. __ ("Pas de tweets disponibles", "wptuts_twitter"). '
  • '; else $ count = 0; foreach ($ tweets en tant que $ tweet) $ content. = '
  • '; $ content. = "". $ this-> make_clickable ($ tweet)."
    "; if ($ args ['published_when'])) $ content. =""; $ href = esc_url (" http://twitter.com/$tweet->user->screen_nameName/statuses/$tweet->id_str "); $ time_diff = human_time_diff (strtotime ($ tweet-> créé à)).' ago '; $ content. = "". $ time_diff. ""; $ content. =''; $ content. = '
  • '; if (++ $ count> = $ args ['count']) break; $ content. = '
'; // wp_enqueue_script ('wptuts_twitter_script'); // wp_enqueue_style ('wptuts_twitter_style'); retourne $ contenu;

Vous remarquerez que j'ai inclus les appels vers wp_enqueue_script et wp_enqueue_style. Celles-ci sont commentées car je n'ai pas eu besoin d'inclure de style ni de script. Mais depuis la version 3.3, vous pouvez utiliser ces fonctions pendant que le corps de la page est généré (c'est-à-dire dans des rappels de widgets ou de codes courts). Si j'ai eu besoin de mettre en file d'attente des scripts pour que ce widget puisse fonctionner, cette opération garantit ici qu'ils ne sont chargés que lorsqu'ils sont réellement nécessaires. Assurez-vous de ne pas charger inutilement des scripts et des styles.


Rendre cliquable

Ici on définit la méthode make_clickable. Cela prend un objet tweet et renvoie le contenu du tweet, après avoir remplacé les URL, hashtags, utilisateurs ou URL de média par un lien approprié. Depuis que nous avons mis include_entities Pour être vrai, l'objet tweet inclut les «entités» du tweet. Une entité est une URL, une mention d'utilisateur, un hashtag ou un média inclus dans le tweet. Pour ce faire, nous utilisons la fonction insensible à la casse str_ireplace.

 fonction make_clickable ($ tweet) $ entités = $ tweet-> entités; $ content = $ tweet-> text; // Rendre tous les liens cliquables si (! Empty ($ entités-> urls)) foreach ($ entités-> urls en tant que $ url) $ content = str_ireplace ($ url-> url, 'Expand_url).' "> . $ url-> display_url. '', $ content); // Rendre les hashtags cliquables si (! empty ($ entités-> hashtags)) foreach ($ entités-> hashtags comme $ hashtag) $ url = 'http://search.twitter.com/search?q='. urlencode ($ hashtag-> text); $ content = str_ireplace ('#'. $ hashtag-> text, '#'. $ hashtag-> text . '', $ content); // Rendre tous les utilisateurs cliquables si (! empty ($ entités-> user_mentions)) foreach ($ entités-> user_mentions en tant que $ utilisateur) $ url = 'http: // twitter .com / '. urlencode ($ user-> nom_écran); $ content = str_ireplace ('@'.$ user-> nom_écran,' @ '. $ utilisateur-> nom_écran.' ', $ contenu); // Rendez toutes les URL de média cliquables si (! Empty ($ entités-> média)) foreach ($ entités-> média en tant que $ média) $ content = str_ireplace ($ media-> url, 'URL_expansion'). '">'. $ media-> display_url. '', $ content);  return $ content; 

Le produit fini (en fonction du style de votre thème) devrait ressembler à ceci:


Petit code

Dans ce tutoriel, j'ai essayé de m'en tenir à un principe de base, mais important: séparation des préoccupations. Notre classe est un ensemble de méthodes. L'idée est que chaque méthode doit être responsable d'un objectif spécifique. J'ai un rappel pour afficher le contour du widget, qui appelle generate_tweet_list pour produire la liste elle-même, qui utilise get_tweets pour récupérer les tweets - lui-même en utilisant retrieve_remote_tweets pour interagir directement avec l'API Twitter.

Il y a plusieurs raisons à cela:

  • Lisibilité - diviser le code en morceaux plus petits, facilite beaucoup la lecture et le débogage
  • Réduire la duplication de code - sans séparer mon code, si j'avais deux méthodes pour tenter de récupérer les tweets de Twitter, les deux devraient inclure toutes les vérifications nécessaires et la gestion du cache. Mais en séparant mes fonctions comme indiqué, ils pourraient utiliser le même get_tweets méthode.
  • Facile à éditer - Si Twitter change jamais d'API, je n'ai plus qu'une fonction à modifier et je peux être sûr que le reste du plug-in continuera à fonctionner correctement..
  • Extensibilité - La mise en page de ce code est plus proche de Lego que de la pâte à modeler. Lego est de loin beaucoup mieux. Nous avons maintenant une collection de fonctions 'Lego brick' avec lesquelles nous pouvons faire plus de choses.

Pour illustrer le dernier point. Nous avons créé un widget qui affiche une liste des tweets récents. En raison de la séparation des préoccupations, avec seulement quelques lignes supplémentaires (ajoutées en dehors de la classe), nous pouvons créer un shortcode qui fait exactement la même chose:

 function wptuts_twitter_shortcode_cb ($ atts) $ args = shortcode_atts (array ('screen_name' => ", 'count' => 5, 'published_when' => 5, 'include_rts' => 1,), $ atts); $ tw = new WP_Widget_Wptuts_Twitter_Widget (); return $ tw-> generate_tweet_list ($ args); add_shortcode ('wptuts_twtter', 'wptuts_twitter_shortcode_cb');

Les tweets peuvent ensuite être affichés avec le shortcode: [wptuts_twtter screen_name = "stephenharris88"]. Il accepte également les attributs compter, publié_quand et include_rts.

Nous avons également la méthode très utile et générique retrieve_remote_tweets qui peut interagir avec Twitter comme bon nous semble. Il renverra soit une réponse valide, soit un objet d'erreur WordPress avec le message d'échec..


Commentaires finaux

La classe WP-TLC-Transients, mentionnée précédemment, est une implémentation plus générique de la mise en cache logicielle, vous permettant de spécifier des fonctions avec lesquelles mettre à jour le cache. Il implémente également la mise à jour en arrière-plan: l'actualisation du cache uniquement une fois la page chargée. La classe est conçue pour être adoptée dans les plug-ins (après avoir renommé pour éviter les conflits), ce qui permet une gestion efficace de la mise en cache logicielle. En fait, c’est ce que fait le plugin Twitter Widget Pro d’Aaron Campbell.

Remarque: Si vous utilisez un hébergement partagé, d'autres sites Web peuvent partager votre adresse IP. Les demandes d'API Twitter de ces sites contribueront à votre limite de taux. Si vous constatez que votre taux est constamment limité, c’est la cause probable..

Le plug-in créé dans ce tutoriel est disponible sur mon GitHub.