www.usievents.com #USI2014
Réactif, Parallèle, Asynchrone
Pourquoi!
Henri Tremblay
www.usievents.com #USI2014
Henri Tremblay
OCTO Technology
Architecte Senior
Responsable R&D
Spécialiste Performance
EasyMo...
www.usievents.com #USI2014
Philippe Prados
OCTO Technology
Responsable Pôle Réactif
François-Xavier Bonnet
OCTO Technology...
www.usievents.com #USI2014
www.usievents.com #USI2014
Un peu d’histoire
Lisp (1958) Clojure (2007)
Parallel.forEach
(2010)
Async IO
(2006)
Loi d’Amda...
www.usievents.com #USI2014
www.usievents.com #USI2014
x86
www.usievents.com #USI2014
ProcessusIN OUT
x86
www.usievents.com #USI2014
www.usievents.com #USI2014
Cooperative Multitasking
UNIX Mainframe
Multiprogramming
Je n’ai plus
besoin du CPU.
Je le tend...
www.usievents.com #USI2014
Windows 95
Preemptive Multitasking
Processus 1,
c’est à toi Chef oui chef
Processus 1
Processus...
www.usievents.com #USI2014
cgi-bin
Requête
HTTPD Processus
Fork
www.usievents.com #USI2014
Java
Green threads
www.usievents.com #USI2014
Native threads
www.usievents.com #USI2014
Résumé
Architecture SMP
OS
Processus
Thread
www.usievents.com #USI2014
Loi de Moore
www.usievents.com #USI2014
Synchronisé par défaut
GC généraliste
IO synchrone
Threads créés au besoin
UTF-16
«Un jour les ...
www.usievents.com #USI2014
Herb Sutter (2005)
www.usievents.com #USI2014
Loi de Moore
www.usievents.com #USI2014
Dual core (2007)
www.usievents.com #USI2014
Requêtes
www.usievents.com #USI2014
Le temps de réponse
ne peut plus
s’améliorer
uniquement par le
matériel
www.usievents.com #USI2014
Le temps de réponse
ne peut plus
s’améliorer
uniquement par le
matériel
www.usievents.com #USI2014
www.usievents.com #USI2014
Une requête
Requête
Op 1 Op 2 Op n…
Réponse
IO IO
www.usievents.com #USI2014
Une requête
Op 1
IO
Op 2
Context switching
www.usievents.com #USI2014
2 threads sur 1 CPU
Thread 0 Thread 1
Overhead
1 seconde
www.usievents.com #USI2014
10 threads sur 1 CPU
T0
Overheads
T1 T2 T3 T4 T5 T6 T7 T8 T9
1 seconde
www.usievents.com #USI2014
Attente d’entrée-sortie
Attente de récupération du CPU
Overhead de context switching
Perte de t...
www.usievents.com #USI2014
www.usievents.com #USI2014
Solution #1: Parallel processing
Op 1
Op 2
Op 3
www.usievents.com #USI2014
Solution #2: NIO
Op 1
IO
Op 2Op 3
www.usievents.com #USI2014
Solution #3: 1 thread par CPU
Op 1 Op 2 Op 3
www.usievents.com #USI2014
Complexité
www.usievents.com #USI2014
Oh my God! (1/2)
www.usievents.com #USI2014
Oh my God! (2/2)
www.usievents.com #USI2014
www.usievents.com #USI2014
En JavaScript
Pas de multithreading
Scalabilité en instanciant plusieurs processus
Approche asy...
www.usievents.com #USI2014
Implémentation de LISP du JVM
Prône la programmation fonctionnelle et
l’immutabilité
Facilite l...
www.usievents.com #USI2014
Traitements multi-threadés isolés
l’un de l’autre
Partage explicite des données
Utilisable faci...
www.usievents.com #USI2014
Netty: Gestionnaire d’IO asynchrone sur JVM
Play: Fullstack reactive
Rx: Framework reactive sou...
www.usievents.com #USI2014
Conclusion
www.usievents.com #USI2014
NIO
Avantage
Améliore sensiblement la scalabilité d’un serveur
d’application
Désavantage
Doit ê...
www.usievents.com #USI2014
Parallèle
Avantage
Réduit les temps de réponse d’un système peu sollicité
Maximise l’utilisatio...
www.usievents.com #USI2014
Fonctionnel
Avantage
Implicitement thread-safe
Diminue la quantité de code
Facilement paralléli...
www.usievents.com #USI2014
Immutable
Avantage
Élimine les risques de contention
Facilite les traitements parallèles
Désava...
www.usievents.com #USI2014
Asynchrone
Avantage
Réduit les temps de réponse
Meilleure exploitation des CPUs
Désavantage
Cod...
www.usievents.com #USI2014
www.usievents.com #USI2014
ReactiveScalable Resilient
Event
Driven
Responsive
React to event
React to failure
React to use...
www.usievents.com #USI2014
http://perfug.github.io/
+Henri Tremblay
@henri_tremblay
htremblay@octo.com
Questions?
Prochain SlideShare
Chargement dans…5
×

Réactif, parallèle, asynchrone. Pourquoi!

679 vues

Publié le

My conference at USI 2014 (http://www.usievents.com/en). Explaining how we arrive to reactive programming, why we should care and what to do about it.

In French

Publié dans : Logiciels
0 commentaire
2 j’aime
Statistiques
Remarques
  • Soyez le premier à commenter

Aucun téléchargement
Vues
Nombre de vues
679
Sur SlideShare
0
Issues des intégrations
0
Intégrations
14
Actions
Partages
0
Téléchargements
1
Commentaires
0
J’aime
2
Intégrations 0
Aucune incorporation

Aucune remarque pour cette diapositive
  • http://en.wikipedia.org/wiki/Time-sharing
    http://en.wikipedia.org/wiki/Unix
    http://en.wikipedia.org/wiki/CICS
    http://en.wikipedia.org/wiki/Reactor_pattern
    http://en.wikipedia.org/wiki/Computer_multitasking
    http://en.wikipedia.org/wiki/Preemption_(computing)
  • Aujourd’hui je vais vous faire parcourir l’histoire de l’informatique pour nous permettre de mieux comprendre les nouveaux paradigmes de programmation que nous voyons émerger depuis quelques années.
  • Ce qui est étonnant c’est que certains concepts proviennent du fin fond de l’aube de l’informatique, sont tombés partiellement dans l’oublie.

    Loi d’Amdahl

    Par exemple, …
  • Mais pourquoi maintenant, pourquoi rien pendant 40 ans et soudain on se découvre plein de nouveaux besoins
  • Presque tous les développements d’aujourd’hui sont sur x86

    Au début du x86, tout était simple
  • On lance un processus à la fois, il prend des données en entrées et en fait quelquechose
  • La vie était belle et simple
  • Évidemment, hors du x86, on utilisait depuis déjà 20 ans des paradigmes plus compliqués

    Ken Thompson et Dennis Ritchie

    Multiprogramming:
    Un programme tourne et on passe au suivant lors d’un IO

    Cooperative multitasking (CICS par exemple):
    Un programme tourne et laisse la main des fois pour permettre aux autres de s’exécuter. S’il ne la laisse pas, personne ne peut lui enlever
    Windows 3.1
  • Le premier OS maintenant améliorant la situation fut Windows 95 et Windows NT 3.1.

    Il faisait du preemptive multitasking.

    Évidemment, les systèmes Unix utilisaient eux aussi ce système sur une architecture SMP
  • Par exemple, cgi-bin. Un processus reçoit un appel HTTP et fork un processus correspondant à l’URL en passant des variables.

    Le problème c’est qu’il y a évidemment beaucoup d’overhead à faire des fork. Donc on a eu une autre idée
  • Pourquoi ne pas faire des threads. Le thread, c’est plein de traitements parallèles mais au sein d’un même processus et partagent la même mémoire. Il n’est plus nécessaire de créer un processus complet, uniquement une nouvelle stack d’appel.

    Le problème c’est que des OS comme Solaris n’implémentait pas de threads natifs. Donc, par exemple, lors de la sortie de Java, la JVM sur Solaris utilisait un concept de green threads. C’est la JVM qui gérait le time sharing et non l’OS. Évidemment, ça causait des problèmes. Par exemple, il fallait traiter les IO de façon asynchrone pour ne pas gelé un processus.
  • Donc sommes donc rapidement passé au native threads.

    C’est l’OS qui s’occupe du time sharing des threads. Cela ralentit la synchronisation et la création mais améliore sensiblement la gestion des IO et le context switching.
  • On a donc plusieurs processus sur lesquels l’OS distribue les threads des différents processus en tentant de maximiser l’utilisation CPU.

    Par exemple, si un thread est sur un I/O, pas de soucis, un autre thread prend le relai.

    Il suffit d’ajouter des threads pour avoir une scalabilité infinie. Pour le reste, la loi de Moore devrait nous assurer que dans le futur, l’augmentation des besoins CPUs sera couverts

    SMP = Symmetric multiprocessing
  • Le nombre de transistors double tous les 2 ans et par extension la puissance des ordinateurs
  • D’ailleurs, l’architecture de Java en général comptait beaucoup sur la loi de Moore.

    Plusieurs décisions étaient sciemment lentes pour couvrir un maximum de besoins en se disant que rapidement, cette lenteur se fondrait dans la loi de Moore
  • Et c’est là que le couperet est tombé.

    On a atteint les limites de fréquences possibles pour un ordinateur. Et dans un ordinateur, ce n’est pas vraiment le nombre de transistors qui est important, c’est la fréquence. La fréquence donne la vitesse de passage des portes. Si on ne peut pas augmenter la vitesse de passage des portes, ça ne sert à rien d’ajouter des portes.
  • Donc, les fondeurs n’ont pas trop eu le choix de changer de stratégie.

    Le nombre de transistor continue d’augmenter mais plus la fréquence. À la place, les transistors sont déplacés sur plusieurs cœurs.
  • D’où l’apparition du Dual Core d’Intel en 2007

    Le traitement parallèle n’était plus limité aux serveurs, il était maintenant pour tous
  • À noter, ce n’est pas une problème de scalabilité.

    Par exemple, pour un serveur web, chaque requête est traitée par un thread qui lui-même est assigné à un CPU.

    Donc, il suffit d’ajouter des CPUs, peu importe leurs puissance. Mais ça n’améliore pas mon temps de réponse.

    Si on zoom, un requête c’est ça
  • Évidemment, je simplifie un peu. Les fabricants trouvent des « trucs ». Ils augmentent le cache, les algorithmes de prédiction.

    Mais ce n’est que du patch. Rien de vraiment révolutionnaire
  • Une deuxième fois pour être bien sûr que c’est intégré.

    On a surfé plus de 30 ans sur la vague de la loi de Moore et c’est maintenant terminé.

    Donc, quand les développeurs s’en sont rendus compte, ils se sont mis à la recherche de solution
  • Et ça tombe bien, la passé est plein de solutions

    Mais tombé, jetons un coup d’œil sur ce qu’est vraiment une requête
  • Un requête vu à la loupe ça ressemble à ça.

    On remarque deux choses:
    1- On attend sur des IOs
    2- La fréquence étant désormais constante, il n’y a pas de raison pour que les opérations CPU d’une requête soient plus rapides dans le futur
  • Et si on zoom encore, on voit la chose suivante.

    En pratique, l’opération 1 effectue un IO, l’OS réquisitionne le CPU pour le donner à quelqu’un d’autre, l’IO termine et éventuellement, l’OS redonne la main au CPU.

    Deux autres constatations:
    1- Le context switching a un coût CPU
    2- Le temps de récupération après IO a un coût
  • Et si on zoom encore, on voit la chose suivante.

    En pratique, l’opération 1 effectue un IO, l’OS réquisitionne le CPU pour le donner à quelqu’un d’autre, l’IO termine et éventuellement, l’OS redonne la main au CPU.

    Deux autres constatations:
    1- Le context switching a un coût CPU
    2- Le temps de récupération après IO a un coût
  • Il est assez facile de réaliser que plus on a de threads, plus on a d’overhead dû au context switching.

    Il y a donc une limite
  • On voit maintenant un peu mieux comment ça marche,

    Il nous faut maintenant des solutions, des outils pour améliorer nos performances
  • Les différentes opérations d’une requête serveur sont traités en parallèles pour améliorer les temps de réponse

    Évidemment, ça ne marche que si le serveur n’est pas trop chargé. Si le CPU d’à côté est en train de traiter la requête de quelqu’un d’autre, il n’aura pas le temps de traiter la notre.
  • Non-blocking IO ou asynchronous IO

    Au lieu d’attendre bêtement les fins d’un IO, on fait d’autre chose en attendant d’être notifié de la fin de l’IO

    Évidemment, pour arriver à faire ça, on doit avoir la collaboration de la libraire effectuant l’IO et de l’OS.
  • On utilise 1 thread par CPU. Chaque thread effectue du traitement de tâches à partir des tâches disponibles dans une file de tâche
  • La gestion du multithreading et le partage de données augmente trop la complexité
  • D’autres, moins extrême n’étaient pas contre le multithreading mais contre la mutabilité des données

    Car on peut partager des données immutables sans danger

    Et les ingénieurs, quand ils ont des problèmes, ils ont des solutions
  • Et évidemment, quand il y a un problème, il y a toujours un outil disponible pour le résoudre

    PPR: Stratégie différente, intégration dans les OS, langages, frameworks, etc
  • Aussi dans les navigateurs
  • Un exemple plus raisonnable
  • Un exemple plus raisonnable

    Slide sur le fait que les langages évoluent
  • En conclusion
  • One-liner
  • On parle ici d’immutabilité des données en mémoire. Pas des données persistées
  • Si vous voulez améliorer vos performances ou diminuer vos coûts d’infrastructure, c’est la seule solution.

    Par contre, ça reste relativement compliqué, les technologies et outils ne sont pas encore tous prêts.

    Mais ça vaut quand même la peine de tester sur un petit projet avec des problématiques de performance.
  • C’est ce qui a amené le concept de programmation réactive.

    C’est une énorme buzzword qui constitue en fait un pieu vieux.

    Il consiste à appliquer toutes les nouvelles solutions provenant du passer afin d’atteindre les objectifs suivants
  • Réactive:
    1- Tout en async (orienté évènement)
    2- Pas de points de contention (immutable)
    3- Un seul thread par hard-thread (moins d’overhead)
    4- Scalabilité horizontale infinie

    C’est donc bien évidemment un gros buzzword mais derrière lequel se cachent de vraies valeurs à respecter pour obtenir de meilleures applications.

    De plus en plus de devices connectés et donc de sollicitation serveur. La granularité des requêtes diminues.

    - Petits applications bureautiques: Ne pas faire
    - Propension à augmenter en puissance: Go, avec aide et outillage
  • Réactif, parallèle, asynchrone. Pourquoi!

    1. 1. www.usievents.com #USI2014 Réactif, Parallèle, Asynchrone Pourquoi! Henri Tremblay
    2. 2. www.usievents.com #USI2014 Henri Tremblay OCTO Technology Architecte Senior Responsable R&D Spécialiste Performance EasyMock lead developer Objenesis lead developer
    3. 3. www.usievents.com #USI2014 Philippe Prados OCTO Technology Responsable Pôle Réactif François-Xavier Bonnet OCTO Technology Architecte Senior Pôle Réactif Avec l’aide de
    4. 4. www.usievents.com #USI2014
    5. 5. www.usievents.com #USI2014 Un peu d’histoire Lisp (1958) Clojure (2007) Parallel.forEach (2010) Async IO (2006) Loi d’Amdahl (1967) Real-time (1965) Reactive (2012) 43 ans 49 ans 47 ans
    6. 6. www.usievents.com #USI2014
    7. 7. www.usievents.com #USI2014 x86
    8. 8. www.usievents.com #USI2014 ProcessusIN OUT x86
    9. 9. www.usievents.com #USI2014
    10. 10. www.usievents.com #USI2014 Cooperative Multitasking UNIX Mainframe Multiprogramming Je n’ai plus besoin du CPU. Je le tend à qui veut bien Je le prend. MerciProcessus 1 Processus 2 Je fais un IO, à qui le tour? Moi! Processus 1 Processus 2
    11. 11. www.usievents.com #USI2014 Windows 95 Preemptive Multitasking Processus 1, c’est à toi Chef oui chef Processus 1 Processus 2 Temps écoulé, processus 2 Aye aye sir Un IO, je t’enlève la main
    12. 12. www.usievents.com #USI2014 cgi-bin Requête HTTPD Processus Fork
    13. 13. www.usievents.com #USI2014 Java Green threads
    14. 14. www.usievents.com #USI2014 Native threads
    15. 15. www.usievents.com #USI2014 Résumé Architecture SMP OS Processus Thread
    16. 16. www.usievents.com #USI2014 Loi de Moore
    17. 17. www.usievents.com #USI2014 Synchronisé par défaut GC généraliste IO synchrone Threads créés au besoin UTF-16 «Un jour les ordinateurs seront assez puissants »
    18. 18. www.usievents.com #USI2014 Herb Sutter (2005)
    19. 19. www.usievents.com #USI2014 Loi de Moore
    20. 20. www.usievents.com #USI2014 Dual core (2007)
    21. 21. www.usievents.com #USI2014 Requêtes
    22. 22. www.usievents.com #USI2014 Le temps de réponse ne peut plus s’améliorer uniquement par le matériel
    23. 23. www.usievents.com #USI2014 Le temps de réponse ne peut plus s’améliorer uniquement par le matériel
    24. 24. www.usievents.com #USI2014
    25. 25. www.usievents.com #USI2014 Une requête Requête Op 1 Op 2 Op n… Réponse IO IO
    26. 26. www.usievents.com #USI2014 Une requête Op 1 IO Op 2 Context switching
    27. 27. www.usievents.com #USI2014 2 threads sur 1 CPU Thread 0 Thread 1 Overhead 1 seconde
    28. 28. www.usievents.com #USI2014 10 threads sur 1 CPU T0 Overheads T1 T2 T3 T4 T5 T6 T7 T8 T9 1 seconde
    29. 29. www.usievents.com #USI2014 Attente d’entrée-sortie Attente de récupération du CPU Overhead de context switching Perte de temps
    30. 30. www.usievents.com #USI2014
    31. 31. www.usievents.com #USI2014 Solution #1: Parallel processing Op 1 Op 2 Op 3
    32. 32. www.usievents.com #USI2014 Solution #2: NIO Op 1 IO Op 2Op 3
    33. 33. www.usievents.com #USI2014 Solution #3: 1 thread par CPU Op 1 Op 2 Op 3
    34. 34. www.usievents.com #USI2014 Complexité
    35. 35. www.usievents.com #USI2014 Oh my God! (1/2)
    36. 36. www.usievents.com #USI2014 Oh my God! (2/2)
    37. 37. www.usievents.com #USI2014
    38. 38. www.usievents.com #USI2014 En JavaScript Pas de multithreading Scalabilité en instanciant plusieurs processus Approche asynchrone NodeJS
    39. 39. www.usievents.com #USI2014 Implémentation de LISP du JVM Prône la programmation fonctionnelle et l’immutabilité Facilite le partage des données en mémoire via un STM Clojure
    40. 40. www.usievents.com #USI2014 Traitements multi-threadés isolés l’un de l’autre Partage explicite des données Utilisable facilement en Groovy et Java Vert.X
    41. 41. www.usievents.com #USI2014 Netty: Gestionnaire d’IO asynchrone sur JVM Play: Fullstack reactive Rx: Framework reactive sous .Net Java 8: Évaluation paresseuse Lambda Parallélisme Haskell, Erlang, Go, … Coroutine, Continuation, Promise Pilotes de DB asynchrones Autres
    42. 42. www.usievents.com #USI2014 Conclusion
    43. 43. www.usievents.com #USI2014 NIO Avantage Améliore sensiblement la scalabilité d’un serveur d’application Désavantage Doit être supporté par les frameworks Recommandation: Allez-y Je vais faire un IO, rappelle-moi quand c’est fini. En attendant je fais d’autre chose Processus 1 D’accord
    44. 44. www.usievents.com #USI2014 Parallèle Avantage Réduit les temps de réponse d’un système peu sollicité Maximise l’utilisation CPU Désavantage Algorithmie plus complexe Recommandation: Allez-y… au besoin Yep! Les gars, voici chacun un peu de boulot. Dites-moi quand c’est fini. Je vous attend Processus 1
    45. 45. www.usievents.com #USI2014 Fonctionnel Avantage Implicitement thread-safe Diminue la quantité de code Facilement parallélisable Évaluation paresseuse Désavantage Rapidement illisible si surutilisé Lecture du code plus complexe pour les non initiés Recommandation: Allez-y. Avec retenu Bien sûr Tu pourrais effectuer cette opération sur toutes ces données et me donner le résultat? Méthode 1 Méthode 2
    46. 46. www.usievents.com #USI2014 Immutable Avantage Élimine les risques de contention Facilite les traitements parallèles Désavantage Augmente le travail du GC Les structures de données doivent être compatible Recommandation: Allez-y, sans vous forcer Tout de suite Voici des données. Tu m’en donnes une copie en appliquant cette transformation? Méthode 1 Méthode 2
    47. 47. www.usievents.com #USI2014 Asynchrone Avantage Réduit les temps de réponse Meilleure exploitation des CPUs Désavantage Code plus complexe si utilisé extensivement Mais ça s’améliore par l’évolution des langages Recommandation: Allez-y en opportuniste Yep! Hop, toi fais ça, et hop toi fais ça. Dites-moi quand c’est fini Processus 1
    48. 48. www.usievents.com #USI2014
    49. 49. www.usievents.com #USI2014 ReactiveScalable Resilient Event Driven Responsive React to event React to failure React to users React to load
    50. 50. www.usievents.com #USI2014 http://perfug.github.io/ +Henri Tremblay @henri_tremblay htremblay@octo.com Questions?

    ×