jeudi 18 mai 2017

Vert.X : "Don’t block the event loop", même en debug ?

Il y a une règle essentielle dans Vert.X. Elle est affichée, répétée dans la documentation, mais elle me gène pour debugger :

Don’t block the event loop

Voilà pourquoi, et comment j'ai contourné le problème...

Mes débuts en Vert.X

J'ai débuté récemment avec Vert.X 3, après avoir assisté à des conférences de Julien Viet, Clément Escoffier, Julien Ponge et Thomas Segismont. Ils sont tous les quatre français et font partie de l'équipe de développement de Vert.X.

J'ai été convaincu par leurs présentations. Si vous voulez jeter un coup d’œil, certaines sont disponibles en vidéo :

Non-bloquant

Je ne vais pas revenir sur les principes de Vert.X, c'est très bien expliqué dans les vidéos. Et je vous renverrai volontiers vers mon wiki sur lequel j'ai consigné mes notes d'apprentissage de Vert.X.

Ce qui m'a gêné c'est sa règle d'or  :

Don’t block the event loop


Je sais, je l'ai déjà citée, mais ils semblent vraiment y tenir chez Vert.X.


Ça signifie qu'il ne faut pas exécuter d'opération bloquante dans un verticle classique. Tout ce qui peut bloquer un thread sur une durée significative doit être fait dans un worker verticle ou appelé via vertx.executeBlocking().

Significatif ?

Pour Vert.X, une durée significative, c'est deux secondes.


C'est la valeur de la constante DEFAULT_MAX_EVENT_LOOP_EXECUTE_TIME dans VertxOptions. Et ça peut être modifié au démarrage.

Si on dépasse ?

Si le thread est bloqué plus de deux secondes, on peut avoir une alerte :
Jan 01, 1970 0:00:00 AM io.vertx.core.impl.BlockedThreadChecker
WARNING: Thread[vert.x-eventloop-thread-2,5,main] has been blocked for 3615 ms,
         time limit is 2000
io.vertx.core.VertxException: Thread blocked
    at ...

How cool is that ?

Je n'ai rien à redire à ce comportement, sauf en debug. Chaque point d'arrêt va bloquer le thread, et on va avoir une sortie standard polluée par le BlockedThreadChecker.

Pour éviter ça, on peut augmenter la valeur de maxEventLoopExecuteTime ou, mieux encore, augmenter le délai de vérification

  vertxOptions.setBlockedThreadCheckInterval(1_000_000L);

Uniquement en debug

Évidemment, je ne voudrais avoir cette ligne qu'en debug. Pour ça, je peux parcourir les arguments de démarrage et vérifier si -agentlib:jdwp est présent.


  if (ManagementFactory.getRuntimeMXBean()
                     .getInputArguments()
                     .stream()
                     .anyMatch(arg -> arg.startsWith("-agentlib:jdwp"))) {
      vertxOptions.setBlockedThreadCheckInterval(1_000_000L);
  }

Comme ça, je peux debugger sans être pollué par les alertes du BlockedThreadChecker, mais je les conserve en exécution normale.

Evidemment, si vous avez d'autres solutions à proposer, n'hésitez pas à partager.

Edit (18 mai 2017)
Lorsqu'on lance Vert.X en debug avec son plugin, il met MaxEventLoopExecuteTime à une valeur très élévée (environs 300 000 ans).

Aucun commentaire:

Enregistrer un commentaire