Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Introduction to Python Asyncio

615 views

Published on

Dive into Python asyncio programming! This talk will cover basics of using Python asyncio, tips, gotchas and explanations on why asyncio is amazing.

Published in: Technology

Introduction to Python Asyncio

  1. 1. AN INTRODUCTIONTO PYTHON ASYNCIO NathanVan Gheem
 @vangheezy nathanvangheem.com Lead Platform Engineer @ Onna
  2. 2. ABOUT ME Plone core contributor, framework, ui, sec teams,
 Developer of Guillotina,
 Lead Platform Engineer @ Onna
  3. 3. ASYNCIO,A DEFINITION “This module provides infrastructure for writing single-threaded concurrent code using coroutines, multiplexing I/O access over sockets and other resources, running network clients and servers, and other related primitives” - https://docs.python.org/3/library/asyncio.html
  4. 4. ASYNC - IO Asynchronous programming using async/await syntax I/O with aTCP socket
  5. 5. WHAT DOES IT LOOK LIKE?
  6. 6. SO WHAT? Web applications useTCP sockets A way to improve performance and scale web applications Also think micro services
  7. 7. BENEFITS The event loop allows you to handle a larger number of network connections at once.
  8. 8. BENEFITS Code does not block on network activity, so you can have long running connections with very little performance impact(HTML5 sockets for example)
  9. 9. REQUIREMENTS Python >= 3.4 best features and performance in 3.6
  10. 10. HOWTYPICAL WEB SERVERS ARE DESIGNED • Pyramid • Flask • Django • Plone • Etc..
  11. 11. User Request(Web Browser) Web Application Use Available PythonThread Render Request Send Response to User(Web Browser) Start over
  12. 12. SERVING REQUESTS(LEGACY) Threads X Processes = Number of simultaneous requests
  13. 13. THREADED MODEL
 AND WEB SOCKETS Not practical
 Can not keep threads open
  14. 14. THREADS AND PYTHON Threads are expensive(GIL, context switching, CPU),
 Processes are expensive on RAM
  15. 15. WEB SERVERTHREADING MODEL… If no threads available because they are busy, 
 further requests are blocked,
 waiting for an open thread
  16. 16. NETWORKTRAFFIC IS USED EVERYWHERE
  17. 17. NETWORKTRAFFIC (BROWSER/SERVER)
  18. 18. NETWORKTRAFFIC (WEB APPLICATION/DATABASE)
  19. 19. NETWORKTRAFFIC (WEB APPLICATION/CACHING)
  20. 20. NETWORKTRAFFIC (WEB APPLICATION/AUTH)
  21. 21. NETWORKTRAFFIC
 (WEB APPLICATION/CLOUD)
  22. 22. ASYNCIO SERVERS Block on CPU(obviously)
  23. 23. ASYNCIO SERVERS Can accept many simultaneous connections
  24. 24. ASYNCIO SERVERS No blocking on network traffic “reactive”
  25. 25. ASYNCIO SERVERS Server Requests
 from user AsyncIOTask
 Request objects
  26. 26. ASYNCIO DEMONSTRATION
  27. 27. CPU ISTHE LIMIT Limit CPU intensive operations
 Scale with more processes,
 or with connected micro-services(network traffic)
  28. 28. DETAILS… In order to benefit,
 the whole stack needs to be AsyncIO aware
  29. 29. NO - ASYNC - IO Anywhere in your application server that is not AsyncIO and does network traffic WILL BLOCK all other connections while it is doing it’s network traffic(example: using requests library instead of aiohttp)
  30. 30. GETTING STARTED 1. Get active event loop or create new one 2. Run coroutine inside event loop with asyncio.run_until_complete
  31. 31. GETTING STARTED(CODE) (basic.py)
  32. 32. AND WE HAVE FUTURES… asyncio.run_until_complete automatically wraps your coroutine into a Future object and waits for it to finish asyncio.ensure_future will wrap a coroutine in a future and return it to you So you can schedule multiple coroutines that can run at the same time
  33. 33. BASIC CONTINUED(CODE) (basic2.py)
  34. 34. TASKS You can also schedule long running tasks on the event loop Tasks are like futures Tasks are futures, but pluggable on the event loop with different implementations
  35. 35. LONG RUNNING TASKS(CODE) (basic3.py)
  36. 36. TASKS/FUTURES/COROUTINES Well, it’s a bit odd we have distinctions Consider all of these synonyms until you dive deeper
  37. 37. GOTCHA: EVERYTHING MUST BE ASYNC If you want part of your code to be async, the complete stack of the caller must be async and running on the event loop
  38. 38. ONCEYOU’RE ASYNC,
 YOU’RE GOOD You can also consider asyncio.run_until_complete as a sort of bootstrap function
  39. 39. ASYNC EVERYTHING(CODE) (async-everything.py)
  40. 40. SINGLETHREADED Only 1 event loop can run in a thread at a time Running multi-threaded code with AsyncIO code running in a thread loop is unsafe You can multi-(process|thread) and run multiple threads at the same time
  41. 41. (multi-loop.py)
  42. 42. “MULTI” PROCESSING IN ASYNCIO asyncio.gather allows you to run multiple coroutines at the same time, waiting for all of them to finish There are also async context managers
  43. 43. MULTI PROCESS WITH GATHER (gather.py)
  44. 44. LOOPS We can also utilize asyncio in for loops + yield
  45. 45. ASYNC LOOP(CODE) (yield.py)
  46. 46. SCHEDULING loop.call_later: arrange to call function on a delay loop.call_at: arrange function to be called at specified time
  47. 47. SCHEDULING(CODE) (schedule.py)
  48. 48. EXECUTORS An executor is available to use when you have non-async code that needs to be made async, or CPU intensive code A typical executor is a thread executor.This means, anything you run in an executor is being thrown in a thread to run. Try to avoid but it’s a tool available It’s worse to have non-async code than to use thread executors
  49. 49. EXECUTORS(CODE) (exec.py)
  50. 50. ASYNC SUBPROCESS The Python AsyncIO library comes with an amazing subprocess module
  51. 51. SUBPROCESS (subp).py)
  52. 52. EVENT LOOP IS PLUGGABLE
  53. 53. ALTERNATIVE
 LOOP IMPLEMENTATIONS • uvloop • tokio(rust) • Curio
  54. 54. AWESOME AIO • aiohttp: client and server library • aioes: elastic search • asyncpg: postgresql • aioredis • aiobotocore • aiosmtpd: smtp • and many more. Check out https://github.com/aio-libs
  55. 55. DEBUGGING • Debugging is more difficult than regular sequential programs • pdb(debugger) statements do not properly skip over await calls(because thread loop causes debugging to pay attention to another call stack) • pdb also causes thread loop to halt right there, there is no way to manually execute task in loop in a pdb prompt either • Making matters more annoying, python prompt doesn’t work with asyncio
  56. 56. DEBUGGINGTOOLS • aioconsole: allows you to have a python prompt with asyncio loop already setup for you. So you can run await statements! Guillotina runs it’s shell command in an aioconsole. • aiomonitor: attach to already running event loop and get info on running tasks.Also integrated with guillotina(run `g -m`)
  57. 57. GUILLOTINA! guillotina: full web application built with asyncio technologies. Lots of great examples
  58. 58. PYTHON 3.7 Execution context: like thread locals but for coroutines(right now with aiotask-context)
  59. 59. QUESTIONTIME

×