Retour

Comment utiliser JMeter pour analyser les performances d'un service de BDD vs DBaaS

1. Préambule

Pour de nombreuses applications hébergées chez Digital Garden, la base de données continue une partie cruciale, vitale de l’écosystème des sites web. Celle-ci doit répondre aux problématiques suivantes :

  • Gestion des accès : La base de données doit être accessible uniquement par les applications qui l’utilisent, sécurisée au maximum pour prévenir toute fuites de données.
  • La performance : Le serveur de base de données doit être convenablement dimensionné pour pouvoir répondre à la charge demandée par le site.
  • La scalabilité : Découlant directement de la problématique de performance, au fur et à mesure que le site peut grossir, il peut être judicieux de prévoir une augmentation des ressources attribuées à la base de données.
  • La résilience : En cas de problème, que ce soit au niveau du serveur et des données, il faut pouvoir restaurer la base de données dans un certain état.

 

C’est dans ces objectifs que Digital Garden migre peu à peu ses bases de données dans des solutions cloud (DbaaS), ces dernières permettant plus simplement de sauvegarder, restaurer, isoler et contrôler l’accès aux SGBD par rapport à une solution sur serveur « classique ». Cependant, afin d’être certain de ne pas dégrader les performances des applications ainsi migrées, il a été décidé d’effectuer des tests de performance sur les applications configurées avec leur base de données actuelle et la base de données DbaaS, et d’utiliser l’application Apache JMeter.

2. JMeter

Apache JMeter est une application qui permet, entre autres, de créer des scénarios de tests pour des applications web. Le principe est simple: l’application va «mimer» l’utilisation du site par un ou plusieurs utilisateurs, pour générer un rapport d’utilisation. Il est ainsi possible de simplement d’industrialiser des tests sur plusieurs plateformes, d’effectuer des tests de charges en parallélisant ces utilisateurs virtuels, etc.

Or dans notre cas d’usage, où l’on souhaite mesurer précisément la différence de performance entre la base de données« classique » et la base de données DbaaS, exécuter les tests sur une machine pourrait manquer de précision de par la dimension réseau. Si pendant un des tests le réseau se voyait encombré, on pourrait voir une différence de performance totalement étrangère à la base de données.

Cependant, toujours avec JMeter, il est possible d’exécuter les tests sur une machine différente de celle possédant le client,grâce à 2 solutions :

·        L’utilisation de jmeter en mode« console » par l’option -n sur les machines distantes. Il suffit alors de sauvegarder le test sous format .jmx et d’exécuter la commande :
jmeter -n -t montest.jmx.

·        L’utilisation de jmeter-server permet d’ajouter des serveurs à l’interface graphique qui viendront s’ajouter au menu Run > Remote Start… de l’application :

3. Utilisation de JMeter en mode console

Pour l’exemple, nous allons tester une API, en effectuant les requêtes suivantes :

  • Récupération du token « access_token » OAuth.
  • Récupération des éléments « audits »

On va donc configurer le test JMeter suivant :  

(L’utilisation de la fonction __P() permet de fournir des propriétés par l’option -J de la ligne de commande).  

La requête de l’access_token :

 

La requête "Get audits" :

Et enfin, on envoie le rapport dans un fichier :

On va en suite envoyer le fichier Test OAuth2 Api.jmx sur chacun des serveurs à tester, et exécuter la commande jmeter :

ssh srv1 jmeter -n -t Test\ OAuth2\ Api.jmx \ 
  -Jreport_file=report1.csv \ 
  -Jhost=srv1.digital-garden.fr 

ssh srv2 jmeter -n -t Test\ OAuth2\ Api.jmx \ 
  -Jreport_file=report2.csv \ 
  -Jhost=srv2.digital-garden.fr 

Nous récupérons alors les rapports de chacun des serveurs :  

report1.csv :

timeStamp elapsed label responseCode responseMessage threadName dataType success failureMessage bytes sentBytes grpThreads allThreads URL Latency IdleTime Connect
1742830549359 771 Get access token 200 OK Thread Group 1-1 text true 1950 521 1 1 https://staging-api-audit-eva.gulfstream-group.fr/oauth2/token 763 0 397
1742830550182 21267 Get Audits 200 OK Thread Group 1-1 text true 923032 980 1 1 https://staging-api-audit-eva.gulfstream-group.fr/audits 21188 0 0

report2.csv :

timeStamp elapsed label responseCode responseMessage threadName dataType success failureMessage bytes sentBytes grpThreads allThreads URL Latency IdleTime Connect
1742830604624 1237 Get access token 200 OK Thread Group 1-1 text true 1948 521 1 1 https://staging-api-audit-eva.gulfstream-group.fr/oauth2/token 1209 0 587
1742830606046 26999 Get Audits 200 OK Thread Group 1-1 text true 923032 978 1 1 https://staging-api-audit-eva.gulfstream-group.fr/audits 26853 0 0

On peut voir, dans notre exemple, qu’il y a en effet une différence entre la connexion DbaaS. Sur la récupération de notre liste d’Audit, nous avons une différence d’environs 5s (27s contre 21s pour la version serveur « classique »). Il s’agit là d’un test sur une requête spécifique, à voir selon le projet si cela est acceptable vis à vis des gains apportés d’un passage en DbaaS.

 

4. Utilisation de JMeter Serveur

Afin de configurer JMeter en mode controller pour qu’il execute les tests sur les serveurs distant plutôt que sur la machine cliente, plusieurs choses sont à modifier dans le fichier user.properties de JMeter.

Il faut tout d’abord générer une clé « rmi » (typiquement une clé SSL) pour permettre l’échange du client avec les serveurs de manière sécurisée.  Pour cela jmeter fourni un script :

create-rmi-keystroke.sh : 

./create-rmi-keystore.sh -dname 'CN={{CN}},OU={{OU}},O={{O}},C={{C}}' -storepass '{{storepass}}' -keypass '{{keypass}}' 

Où {{storepass}} et {{keypass}} sont respectivement des mots de passes pour le fichier de clé et la clé elle-même, que j’ai mis identique pour plus de simplicité dans cette démonstration.

Cette clé est ensuite copiée sur chacune des machines (client comme serveurs), puis on indique au moment de lancer les commandes jmeter, soit en modifiant le fichier user.properties directement dans le dossier de l’exécutable jmeter, soit en paramètres de la commande où trouver notre clé rmi (par défaut dans le dossier de l’executable), ainsi que les mots de passes choisis. Voici par exemple les commandes serveurs :

Commande JMeter server

jmeter-server \ 

  -J server.rmi.ssl.keystore.file=/etc/jmeter/rmi_keystroke.jks 

  -J server.rmi.ssl.keystore.password={{keypass}} 

Enfin, on fait de même pour le client, en rajoutant en plus la liste de nos serveurs, toujours dans le fichier user.properties ou dans la commande :

Commande JMeter client

jmeter \ 
  -J server.rmi.ssl.keystore.file=/etc/jmeter/rmi_keystroke.jks 

  -J server.rmi.ssl.keystore.password={{keypass}} 

  -J remote_hosts=172.31.0.2,172.31.0.3 

Attention : J’ai remarqué que le chemin de la keystroke doit être identique entre client et serveur, sinon nous avons une erreur :

Nos serveurs se retrouveront alors dans l’interface de JMeter dans menu Run > Remote Start :

Il nous suffit alors de lancer Remote Start All pour lancer notre test en parallèle sur nos deux serveurs, et retrouver nos résultats dans les rapports comme si nous l’avions exécuté en local :

5. Conclusion

Grace à JMeter, il nous est possible de mettre en place des tests directement exécutés sur une ou plusieurs machines distantes, afin de faire des mesures précises sur les temps de nos différentes architectures en évitant les écarts pouvant être causé par le hardware réseau. Cette constatation nous permet d’aller encore plus loin, pour par exemple exécuter les tests régulièrement sur les serveurs distants, simuler des attaques sous différentes localités, tester nos sécurités firewall, et bien d’autres cas encore.

D’autres projets à découvrir