Comment un superviseur qui a atteint_max_restart_intensity peut-il supprimer uniquement l'enfant incriminé ?
-
14-11-2019 - |
Question
j'ai un one_for_one
superviseur qui s'occupe d'enfants similaires et totalement indépendants.
Lorsqu'il y a un problème avec un enfant, qui plante et déclenche à plusieurs reprises :
=SUPERVISOR REPORT==== 30-Mar-2011::13:10:42 ===
Supervisor: {local,gateway_sup}
Context: shutdown
Reason: reached_max_restart_intensity
Offender: [{pid,<0.76.0>}, ...
se fermer et également mettre fin à tous les enfants innocents qui, autrement, continueraient à bien fonctionner.
Comment puis-je créer un arbre de supervision à partir de superviseurs Erlang standard qui ne s'arrête que pour redémarrer l'enfant incriminé et laisse les autres tranquilles ?
Je pensais avoir un surveillant supplémentaire avec un seul enfant mais cela me semble lourd.
Y a-t-il d'autres moyens de gérer cela ?
La solution
Je pense que la meilleure solution serait d'avoir deux niveaux de supervision.
Un superviseur qui démarre un couple superviseur + processus pour chacun gen_server
tu veux courir.Ce superviseur est configuré avec one_for_one
stratégie et temporary
enfants.
Chaque superviseur exécuté sous ce superviseur aurait correctement configuré MaxR
et MaxT
valeurs, qui déclencheront un crash de ce superviseur une fois que l'enfant se comportera mal.
Lorsque le superviseur de niveau inférieur plante, le superviseur de niveau supérieur « s'en fiche ».
Un superviseur consomme 233 octets lorsqu'il est démarré avec un enfant (taille totale du tas), la consommation de mémoire ne devrait donc pas être un problème.
L’arbre de supervision devrait ressembler à :
supervisor_top
|
|
+------------------------+----- ...
| |
supervisor_1 supervisor_2
restart temporary restart temporary
| |
gen_server_1 gen_server_2
restart transient restart transient