1
0
mirror of https://github.com/php/doc-fr.git synced 2026-03-24 07:02:06 +01:00
Files
2024-12-05 19:34:46 +00:00

210 lines
6.9 KiB
XML

<?xml version="1.0" encoding="utf-8"?>
<!-- EN-Revision: 3e871fe7eab38f9b0398569c57a1dd0c21e69652 Maintainer: Fan2Shrek Status: ready -->
<!-- Reviewed: yes -->
<section xml:id="mongodb.tutorial.apm" xmlns="http://docbook.org/ns/docbook" xmlns:xlink="http://www.w3.org/1999/xlink">
<title>Surveillance de la performance de l'application (Application Performance Monitoring - APM)</title>
<para>
L'extension contient une API d'observations événements, qui permet aux applications de
surveiller les commandes et les activités internes liées à la
<link xlink:href="&url.mongodb.sdam;">Spécification de découverte et de surveillance du serveur</link>.
Ce tutoriel démontrera la surveillance des commandes en utilisant l'interface
<classname>MongoDB\Driver\Monitoring\CommandSubscriber</classname>.
</para>
<para>
L'interface
<classname>MongoDB\Driver\Monitoring\CommandSubscriber</classname>
définit trois méthodes: <literal>commandStarted</literal>,
<literal>commandSucceeded</literal>, et <literal>commandFailed</literal>.
Chacune de ces trois méthodes accepte un seul argument <parameter>event</parameter>
d'une classe spécifique pour l'événement respectif. Par exemple, l'argument
<parameter>$event</parameter> de <literal>commandSucceeded</literal>
est un objet <classname>MongoDB\Driver\Monitoring\CommandSucceededEvent</classname>.
</para>
<para>
Dans ce tutoriel, nous allons implémenter un observateur qui crée une liste de tous
les profils de requête et le temps moyen qu'ils ont pris.
</para>
<section>
<title>Structure des classes d'observations</title>
<para>
Nous commençons par le cadre de notre observateur:
</para>
<programlisting role="php">
<![CDATA[
<?php
class QueryTimeCollector implements \MongoDB\Driver\Monitoring\CommandSubscriber
{
public function commandStarted( \MongoDB\Driver\Monitoring\CommandStartedEvent $event ): void
{
}
public function commandSucceeded( \MongoDB\Driver\Monitoring\CommandSucceededEvent $event ): void
{
}
public function commandFailed( \MongoDB\Driver\Monitoring\CommandFailedEvent $event ): void
{
}
}
?>
]]>
</programlisting>
</section>
<section>
<title>Enregistrement de l'observateur</title>
<para>
Une fois qu'un objet observateur est instancié, il doit être enregistré avec le
système de surveillance de l'extension. Cela se fait en appelant
<methodname>MongoDB\Driver\Monitoring\addSubscriber</methodname> ou
<methodname>MongoDB\Driver\Manager::addSubscriber</methodname> pour enregistrer
l'observateur globalement ou avec un Manager spécifique, respectivement.
</para>
<programlisting role="php">
<![CDATA[
<?php
\MongoDB\Driver\Monitoring\addSubscriber( new QueryTimeCollector() );
?>
]]>
</programlisting>
</section>
<section>
<title>Implémenter la logique</title>
<para>
Avec l'objet enregistré, la seule chose qui reste est d'implémenter la logique
dans la classe observatrice. Pour corréler les deux événements qui composent une
commande exécutée avec succès (commandStarted et commandSucceeded), chaque
objet d'événement expose un champ <literal>requestId</literal>.
</para>
<para>
Pour enregistrer le temps moyen par forme de requête, nous allons commencer par vérifier
une commande <literal>find</literal> dans l'événement commandStarted. Nous allons ensuite
ajouter un élément à la propriété <literal>pendingCommands</literal> indexé par son
<literal>requestId</literal> et avec sa valeur représentant la forme de requête.
</para>
<para>
Si nous recevons un événement commandSucceeded correspondant avec le même
<literal>requestId</literal>, nous ajoutons la durée de l'événement (depuis
<literal>durationMicros</literal>) au temps total et incrémentons le
compteur d'opérations.
</para>
<para>
Si un événement commandFailed correspondant est rencontré, nous supprimons
simplement l'entrée de la propriété <literal>pendingCommands</literal>.
</para>
<programlisting role="php">
<![CDATA[
<?php
class QueryTimeCollector implements \MongoDB\Driver\Monitoring\CommandSubscriber
{
private $pendingCommands = [];
private $queryShapeStats = [];
/* Créer une forme de requête à partir de l'argument de filtre. Pour l'instant, il ne prend en compte que
* les champs de premier niveau */
private function createQueryShape( array $filter )
{
return json_encode( array_keys( $filter ) );
}
public function commandStarted( \MongoDB\Driver\Monitoring\CommandStartedEvent $event ): void
{
if ( 'find' === $event->getCommandName() )
{
$queryShape = $this->createQueryShape( (array) $event->getCommand()->filter );
$this->pendingCommands[$event->getRequestId()] = $queryShape;
}
}
public function commandSucceeded( \MongoDB\Driver\Monitoring\CommandSucceededEvent $event ): void
{
$requestId = $event->getRequestId();
if ( array_key_exists( $requestId, $this->pendingCommands ) )
{
$this->queryShapeStats[$this->pendingCommands[$requestId]]['count']++;
$this->queryShapeStats[$this->pendingCommands[$requestId]]['duration'] += $event->getDurationMicros();
unset( $this->pendingCommands[$requestId] );
}
}
public function commandFailed( \MongoDB\Driver\Monitoring\CommandFailedEvent $event ): void
{
if ( array_key_exists( $event->getRequestId(), $this->pendingCommands ) )
{
unset( $this->pendingCommands[$event->getRequestId()] );
}
}
public function __destruct()
{
foreach( $this->queryShapeStats as $shape => $stats )
{
echo "Shape: ", $shape, " (", $stats['count'], ")\n ",
$stats['duration'] / $stats['count'], "µs\n\n";
}
}
}
$m = new \MongoDB\Driver\Manager( 'mongodb://localhost:27016' );
/* Ajouter l'observateur */
\MongoDB\Driver\Monitoring\addSubscriber( new QueryTimeCollector() );
/* Faire une série de requêtes */
$query = new \MongoDB\Driver\Query( [
'region_slug' => 'scotland-highlands', 'age' => [ '$gte' => 20 ]
] );
$cursor = $m->executeQuery( 'dramio.whisky', $query );
$query = new \MongoDB\Driver\Query( [
'region_slug' => 'scotland-lowlands', 'age' => [ '$gte' => 15 ]
] );
$cursor = $m->executeQuery( 'dramio.whisky', $query );
$query = new \MongoDB\Driver\Query( [ 'region_slug' => 'scotland-lowlands' ] );
$cursor = $m->executeQuery( 'dramio.whisky', $query );
?>
]]>
</programlisting>
</section>
</section>
<!-- Keep this comment at the end of the file
Local variables:
mode: sgml
sgml-omittag:t
sgml-shorttag:t
sgml-minimize-attributes:nil
sgml-always-quote-attributes:t
sgml-indent-step:1
sgml-indent-data:t
indent-tabs-mode:nil
sgml-parent-document:nil
sgml-default-dtd-file:"~/.phpdoc/manual.ced"
sgml-exposed-tags:nil
sgml-local-catalogs:nil
sgml-local-ecat-files:nil
End:
vim600: syn=xml fen fdm=syntax fdl=2 si
vim: et tw=78 syn=sgml
vi: ts=1 sw=1
-->