Utilisez Memcached pour les performances d'entreprise Java, Partie 1: Architecture et configuration

Développée par Danga Interactive pour améliorer les performances du site sur LiveJournal.com, l'architecture distribuée de Memcached prend aujourd'hui en charge l'évolutivité exponentielle des applications Web sociales comme Twitter, Facebook et Wikipédia. Dans ce didacticiel en deux parties, Sunil Patil présente l'architecture de table de hachage distribuée de Memcached et vous permet de commencer à l'utiliser pour mettre en cache les données de vos propres applications d'entreprise Java basées sur une base de données.

Ce didacticiel vous présente l'utilisation de Memcached pour améliorer les performances des applications d'entreprise Java. La première moitié commence par un aperçu des architectures de mise en cache Java traditionnelles par rapport à l'architecture de Memcached. Nous allons également installer Memcached sur votre machine et je vous présenterai la configuration et les commandes pour travailler avec Memcached via Telnet. Dans la seconde moitié, nous développerons un programme client "Hello Memcached" en Java, que nous utiliserons pour regarder sous le capot d'un client spymemcached. Vous apprendrez également à utiliser Memcached pour réduire la charge sur votre serveur de base de données et à l'utiliser pour mettre en cache le balisage de page généré dynamiquement. Enfin, nous examinerons quelques options avancées pour configurer les clients spymemcached.

En savoir plus sur la mise en cache Java sur JavaWorld

  • Voir «Architectures d'équilibrage de charge serveur, Partie 1: Équilibrage de charge au niveau du transport» pour une discussion plus approfondie de la mise en cache distribuée avec Memcached.
  • Voir également «Projets Java open source: Java Caching System» pour en savoir plus sur la mise en cache Java traditionnelle.

Présentation des architectures de mise en cache Memcached et Java

Les frameworks de mise en cache Java comme EHCache et OSCache sont essentiellement des HashMapobjets dans le code de votre application. Chaque fois que vous ajoutez un nouvel objet au cache, il sera stocké dans la mémoire de votre application. Cette stratégie fonctionne bien pour stocker de petites quantités de données, mais elle ne fonctionne pas pour la mise en cache de plus de quelques gigaoctets (Go). Les concepteurs du serveur Memcached ont adopté une approche architecturale distribuée, qui permet l'évolutivité du système. En conséquence, vous pouvez utiliser Memcached pour mettre en cache une énorme quantité de données.

L'architecture de Memcached se compose de deux pièces. Le premier est un serveur Memcached qui s'exécute dans son propre processus. Si vous souhaitez faire évoluer votre application, vous pouvez installer et exécuter le serveur Memcached sur des machines supplémentaires. Les instances du serveur Memcached ne se reconnaissent pas. Le client Memcached, la deuxième pièce du système Memcached, ne sait sur chacun des serveurs. Le client est chargé de récupérer le serveur pour chaque entrée de cache et de stocker ou d'obtenir l'entrée de cache - un processus que je discuterai en détail plus loin dans l'article.

Si vous avez une certaine expérience de travail sur les applications Web Java EE, il est probable que vous ayez déjà utilisé un cadre de mise en cache Java open source tel que EHCache ou OSCache. Vous avez peut-être également utilisé une infrastructure de mise en cache commerciale fournie avec votre serveur d'applications, telle que DynaCache (qui est livré avec IBM WebSphere Application Server) ou JBoss Cache (qui est livré avec JBoss AS). Avant d'entrer dans la partie d'apprentissage pratique de ce didacticiel, il est important de comprendre en quoi Memcached diffère de ces frameworks de mise en cache Java traditionnels.

Utilisation d'un cache Java traditionnel

L'utilisation d'un cadre de mise en cache Java traditionnel est assez simple, que vous choisissiez une option open source ou commerciale. Pour un framework open source tel que EHCache ou OSCache, vous devez télécharger les binaires et ajouter les fichiers JAR nécessaires au chemin de classe de votre application. Vous devrez peut-être également créer un fichier de configuration que vous utiliseriez pour configurer la taille du cache, le déchargement du disque, etc. Pour un cadre de mise en cache fourni avec un serveur d'applications, vous n'avez généralement pas à télécharger de fichiers JAR supplémentaires car ils seraient fournis avec le logiciel.

Après avoir ajouté la prise en charge du cadre de mise en cache dans votre application, vous pouvez commencer à l'utiliser en créant un CacheManagerobjet et en obtenant et en définissant des entrées de cache. Sous le capot, le cadre de mise en cache créerait les CacheManagerobjets dans la même JVM où votre application s'exécutait. Chaque fois que vous ajoutiez une entrée de cache, cet objet était également ajouté à un type de table de hachage géré par l'infrastructure de mise en cache.

Si votre serveur d'applications s'exécutait sur plusieurs nœuds, vous souhaiterez peut-être également prendre en charge la mise en cache distribuée. Dans un système de cache distribué, lorsque vous ajoutez un objet dans le cache sur AppServer1, cet objet est également disponible sur AppServer2 et AppServer3. Les caches Java traditionnels utilisent la réplication pour la mise en cache distribuée, ce qui signifie que lorsque vous ajoutez une entrée de cache sur AppServer1, elle est automatiquement répliquée sur les autres serveurs d'applications de votre système. En conséquence, l'entrée sera disponible sur tous vos nœuds.

Utilisation de Memcached

Afin d'utiliser Memcached pour la mise en cache, vous devez d'abord télécharger et installer le serveur Memcached pour la plate-forme de votre choix. Une fois que vous avez installé le serveur Memcached, il écoutera sur un port TCP ou UDP pour la mise en cache des appels.

Ensuite, vous allez télécharger un client Java pour Memcached et ajouter les JAR client à votre application. Après cela, vous pouvez créer un objet client Memcached et commencer à appeler sa méthode pour obtenir et définir des entrées de cache. Lorsque vous ajoutez un objet au cache, le client Memcached prendra cet objet, le sérialisera et enverra un tableau d'octets au serveur Memcached pour le stockage. À ce stade, l'objet mis en cache peut être récupéré à partir de la JVM sur laquelle votre application s'exécute.

Lorsque vous avez besoin de cet objet mis en cache, vous pouvez appeler la get()méthode du client Memcached . Le client prendra la getdemande, la sérialisera et l'enverra au serveur Memcached. Le serveur Memcached utilisera la demande pour rechercher l'objet dans le cache. Une fois qu'il a l'objet, il renverra le tableau d'octets au client Memcached. L'objet client Memcached prendra ensuite le tableau d'octets et le désérialisera pour créer l'objet et le renvoyer à votre application.

Même si votre application s'exécute sur plusieurs serveurs d'applications, tous peuvent pointer vers le même serveur Memcached et l'utiliser pour obtenir et définir des entrées de cache. Si vous avez plus d'un serveur Memcached, les serveurs ne se connaîtront pas. Au lieu de cela, vous allez configurer votre client Memcached afin qu'il connaisse tous les serveurs Memcached disponibles. Par exemple, si votre application crée un objet Java sur AppServer1 et appelle la set()méthode de Memcached, le client Memcached déterminera à quel serveur Memcached cette entrée va. Il commencera alors à communiquer uniquement avec ce serveur Memcached. De même, lorsque votre code dans AppServer2 ou AppServer3 tente d'accéder à getune entrée, le client Memcached déterminera d'abord sur quel serveur cette entrée est stockée, puis communiquera uniquement avec ce serveur.

Logique client Memcached

Dans sa configuration par défaut, le client Memcached utilise une logique très simple pour sélectionner le serveur pour une opération get ou set. Lorsque vous effectuez un appel get()ou set(), le client prend la clé de cache et appelle sa hashCode()méthode pour obtenir un entier tel que 11. Il prend ensuite ce nombre et le divise par le nombre de serveurs Memcached disponibles, disons deux. Il prend alors la valeur du reste, qui vaut 1 dans ce cas. L'entrée de cache ira au serveur Memcached 1. Cet algorithme simple garantit que le client Memcached sur chacun de vos serveurs d'applications choisit toujours le même serveur pour une clé de cache donnée.

Installation de Memcached

Memcached fonctionne sous Unix, Linux, Windows et MacOSX. Vous pouvez soit télécharger le source Memcached et le compiler, soit télécharger les binaires compilés par quelqu'un d'autre et les utiliser pour installer Memcached. Ici, je vais parcourir le processus de téléchargement des binaires pour la plate-forme de votre choix; voir Ressources si vous préférez compiler à partir des sources.

Les instructions d'installation suivantes concernent un ordinateur Windows XP 32 bits. Voir Ressources pour les instructions d'installation pour d'autres plates-formes telles que Linux. Notez également que l'exemple de code de cet article a été développé sur un ordinateur Windows XP 32 bits, bien qu'il doive fonctionner sur n'importe quelle autre plate-forme.

  1. Le code Jellycan a une version modifiée de Memcached qui est facile et efficace à utiliser. Commencez ici en téléchargeant le fichier ZIP binaire win32
  2. Développez Memcached--win32-bin.zipsur votre disque dur. Notez que tout ce qu'il contient est memcached.exe. Exécutez ce fichier pour démarrer le serveur Memcached.
  3. Exécutez maintenant memcached.exe -d installpour enregistrer memcached.exe en tant que service. Vous pourrez utiliser la console Services pour démarrer et arrêter le serveur Memcached.

CL démarrage / arrêt

Essayez de démarrer et d'arrêter le serveur Memcached à partir de la ligne de commande plutôt qu'à partir d'un panneau de services. Cela vous donnera plus de flexibilité pour essayer différentes options de ligne de commande et déterminer la meilleure configuration possible pour vos besoins.

Lorsque vous exécutez le memcached.exesans aucune option de ligne de commande, le serveur Memcached démarrera par défaut sur le port 11211 avec 64 Mo de mémoire. Dans certains cas, vous souhaiterez peut-être avoir un contrôle plus granulaire de la configuration. Par exemple, disons que le port 11211 est utilisé par un autre processus sur votre machine et que vous voulez que le serveur Memcached utilise le port 12000; ou si vous démarriez le serveur Memcached dans un environnement de contrôle qualité ou de production, vous voudriez lui donner plus de mémoire que les 64 Mo par défaut. Dans ces cas, vous pouvez utiliser des options de ligne de commande pour personnaliser le comportement du serveur. L'exécution de la memcache.exe -helpcommande donnera une liste complète des options de ligne de commande comme celles illustrées à la figure 3.

Connectez-vous avec Memcached via Telnet

Une fois le serveur Memcached démarré, il écoute sur le port auquel vous l'avez attribué. Le client Memcached se connecte au serveur sur le port TCP ou UDP, envoie des commandes et reçoit des réponses, puis ferme la connexion. (Voir Ressources pour plus de détails sur le protocole utilisé par le client pour communiquer avec le serveur.)

Vous pouvez vous connecter à votre serveur Memcached de différentes manières. Si vous utilisez un client Java, comme nous le ferons dans la seconde moitié de ce didacticiel, vous pourrez accéder à une API simple pour stocker et récupérer des objets du cache. Vous pouvez également utiliser un client Telnet pour vous connecter directement au serveur. Savoir comment utiliser le client Telnet pour communiquer avec le serveur Memcached est important pour déboguer le client Java, nous allons donc commencer par là.

Commandes Telnet

Vous devrez d'abord utiliser le client Telnet de votre choix pour vous connecter au serveur Memcached. Sur une machine Windows XP, vous pouvez simplement exécuter en telnet localhost 11211supposant que le serveur Memcached fonctionne sur la même machine et écoute sur le port 11211 par défaut. Les commandes suivantes sont essentielles pour travailler avec Memcached via Telnet:

  • setajoute un nouvel élément au cache. L'appel est: Set . Vous pouvez taper la valeur réelle qui doit être stockée sur la ligne suivante. Si vous ne voulez pas que l'entrée de cache expire, entrez 0 comme valeur.
  • getrenvoie la valeur de la clé de cache. Utilisez get pour obtenir la valeur du keyName.
  • addajoute une nouvelle clé uniquement si elle n'existe pas déjà. Par exemple:add
  • replaceremplacera une valeur uniquement si la clé existe. Par exemple:replace
  • deletesupprime l'entrée de cache pour la clé. Vous pouvez utiliser l'appel delete pour supprimer la valeur du keyName.

La capture d'écran de la figure 4 représente un exemple d'interaction avec le serveur Memcached via Telnet. Comme vous pouvez le voir, le serveur Memcached fournit une rétroaction à chaque commande, par exemple STORED, NOT_STOREDet ainsi de suite.

Conclusion de la partie 1

Jusqu'à présent, nous avons brièvement discuté des différences entre l'architecture distribuée de Memcached et les systèmes de cache Java plus traditionnels. Nous avons également mis en place une implémentation Memcached dans votre environnement de développement et vous vous êtes entraîné à vous connecter à Memcached via Telnet. Dans la partie suivante de ce didacticiel, nous utiliserons le client Java spymemcached pour configurer une solution de mise en cache distribuée pour un exemple d'application Java. Dans le processus, vous en apprendrez beaucoup plus sur Memcached et comment il peut améliorer les performances de vos applications Java EE.

Sunil Patil est un architecte Java EE travaillant pour Avnet Technology à San Francisco, Californie. Il est l'auteur de Java Portlets 101 (SourceBeat, avril 2007) et a écrit de nombreux articles publiés par JavaWorld, IBM developerWorks et O'Reilly Media. En plus d'être un développeur et un administrateur d'applications WebSphere Portal Server certifié IBM, il est programmeur Java certifié Sun Microsystems, développeur de composants Web et développeur de composants métier. Vous pouvez consulter le blog de Sunil sur //www.webspherenotes.com.