Skip to content

Commit 3ee0783

Browse files
committed
added examples for concurrency
1 parent 79732aa commit 3ee0783

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

58 files changed

+2880
-0
lines changed

examples/async/async_executor.py

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
An example of runing a blocking task in an Executor:
5+
"""
6+
7+
import asyncio
8+
import time
9+
import datetime
10+
import random
11+
12+
13+
async def small_task(num):
14+
"""
15+
Just something to give us little tasks that run at random intervals
16+
These will go on forever
17+
"""
18+
while True: # keep doing this until break
19+
print("task: {} run".format(num))
20+
# pause for a random amount of time between 0 and 2 seconds
21+
await asyncio.sleep(random.random() * 2)
22+
23+
async def slow_task():
24+
while True: # keep going forever
25+
print("running the slow task- blocking!")
26+
# This will block for 2-10 seconds!
27+
# result = slow_function(random.random() * 8 + 2)
28+
# uncomment to put it on a different thread:
29+
result = await loop.run_in_executor(None,
30+
slow_function,
31+
random.random() * 8 + 2)
32+
print("slow function done: result", result)
33+
#await asyncio.sleep(0.0) # to release the loop
34+
35+
36+
def slow_function(duration):
37+
"""
38+
this is a fake function that takes a long time, and blocks
39+
"""
40+
time.sleep(duration)
41+
print("slow task complete")
42+
return duration
43+
44+
45+
# get a loop going:
46+
loop = asyncio.get_event_loop()
47+
48+
# or add tasks to the loop like this:
49+
loop.create_task(small_task(1))
50+
loop.create_task(small_task(2))
51+
loop.create_task(small_task(3))
52+
loop.create_task(small_task(4))
53+
54+
# Add the slow one
55+
loop.create_task(slow_task())
56+
57+
print("about to run loop")
58+
# this is a blocking call
59+
# we will need to hit ^C to stop it...
60+
loop.run_forever()
61+
print("loop exited")

examples/async/async_timer.py

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
Simple async example derived from python docs.
5+
6+
Will only work on Python 3.5 and above
7+
"""
8+
9+
import asyncio
10+
import time
11+
import datetime
12+
import random
13+
14+
15+
# using "async" makes this a coroutine:
16+
# its code can be run by the event loop
17+
async def display_date(num):
18+
end_time = time.time() + 10.0 # we want it to run for 10 seconds.
19+
while True: # keep doing this until break
20+
print("instance: {} Time: {}".format(num, datetime.datetime.now()))
21+
if (time.time()) >= end_time:
22+
print("instance: {} is all done".format(num))
23+
break
24+
# pause for a random amount of time
25+
await asyncio.sleep(random.randint(0, 3))
26+
27+
28+
def shutdown():
29+
print("shutdown called")
30+
# you can access the event loop this way:
31+
loop = asyncio.get_event_loop()
32+
loop.stop()
33+
34+
35+
# You register "futures" on the loop this way:
36+
asyncio.ensure_future(display_date(1))
37+
asyncio.ensure_future(display_date(2))
38+
39+
loop = asyncio.get_event_loop()
40+
41+
# or add tasks to the loop like this:
42+
loop.create_task(display_date(3))
43+
loop.create_task(display_date(4))
44+
45+
# this will shut the event loop down in 15 seconds
46+
loop.call_later(15, shutdown)
47+
48+
print("about to run loop")
49+
# this is a blocking call
50+
loop.run_forever()
51+
print("loop exited")
52+

examples/async/client_test.py

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
simplest possible example of using aiohttp client
5+
6+
from docs
7+
"""
8+
9+
import asyncio
10+
import aiohttp
11+
12+
async def get_events():
13+
async with aiohttp.ClientSession() as session:
14+
print("created a session")
15+
async with session.get('https://api.github.com/events',
16+
) as resp:
17+
print("status: resp.status")
18+
print(await resp.json())
19+
20+
loop = asyncio.get_event_loop()
21+
loop.run_until_complete(get_events())
22+
loop.close()
23+
24+
25+
26+

examples/async/gather.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
test of gather()
5+
6+
adapted from:
7+
8+
https://docs.python.org/3/library/asyncio-task.html
9+
10+
"""
11+
12+
import asyncio
13+
14+
async def factorial(name, number):
15+
f = 1
16+
for i in range(2, number+1):
17+
print("Task %s: Compute factorial(%s)..." % (name, i))
18+
await asyncio.sleep(1)
19+
f *= i
20+
print("Task %s: factorial(%s) = %s" % (name, number, f))
21+
22+
loop = asyncio.get_event_loop()
23+
loop.run_until_complete(asyncio.gather(
24+
factorial("A", 2),
25+
factorial("B", 3),
26+
factorial("C", 4),
27+
))
28+
loop.close()

examples/async/get_news.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
2+
3+
NEWS_API_KEY = 1fabc23bb9bc485ca59b3966cbd6ea26
4+
5+
url = https://newsapi.org/

examples/async/get_news_async.py

Lines changed: 104 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
An Asynchronous version of the script to see how much a given word is
5+
mentioned in the news today
6+
7+
Takes advantage of:
8+
9+
Uses data from the NewsAPI:
10+
11+
https://newsapi.org
12+
"""
13+
14+
import time
15+
import asyncio
16+
import aiohttp
17+
import requests
18+
19+
WORD = "trump"
20+
21+
NEWS_API_KEY = "84d0483394c44f288965d7b366e54a74"
22+
23+
base_url = 'https://newsapi.org/v1/'
24+
25+
# use one session for the whole script
26+
# recommended by the docs
27+
# session = aiohttp.ClientSession()
28+
29+
30+
# this has to run first, so doesn't really need async
31+
# but why use two reuests libraries ?
32+
async def get_sources(sources):
33+
"""
34+
get all the english language sources of news
35+
36+
'https://newsapi.org/v1/sources?language=en'
37+
"""
38+
url = base_url + "sources"
39+
params = {"language": "en"}
40+
session = aiohttp.ClientSession()
41+
async with aiohttp.ClientSession() as session:
42+
async with session.get(url, ssl=False, params=params) as resp:
43+
data = await resp.json()
44+
print("Got the sources")
45+
sources.extend([src['id'].strip() for src in data['sources']])
46+
47+
48+
async def get_articles(source):
49+
"""
50+
https://newsapi.org/v1/articles?source=associated-press&sortBy=top&apiKey=1fabc23bb9bc485ca59b3966cbd6ea26
51+
"""
52+
url = base_url + "articles"
53+
params = {"source": source,
54+
"apiKey": NEWS_API_KEY,
55+
# "sortBy": "latest", # some sources don't support latest
56+
"sortBy": "top",
57+
# "sortBy": "popular",
58+
}
59+
print("requesting:", source)
60+
async with aiohttp.ClientSession() as session:
61+
async with session.get(url, ssl=False, params=params) as resp:
62+
if resp.status != 200: # aiohttpp has "status"
63+
print("something went wrong with: {}".format(source))
64+
await asyncio.sleep(0)
65+
return
66+
data = await resp.json()
67+
print("got the articles from {}".format(source))
68+
# the url to the article itself is in data['articles'][i]['url']
69+
titles.extend([str(art['title']) + str(art['description'])
70+
for art in data['articles']])
71+
72+
73+
def count_word(word, titles):
74+
word = word.lower()
75+
count = 0
76+
for title in titles:
77+
if word in title.lower():
78+
count += 1
79+
return count
80+
81+
82+
start = time.time()
83+
84+
# start up a loop:
85+
loop = asyncio.get_event_loop()
86+
87+
# create the objects to hold the data
88+
sources = []
89+
titles = []
90+
91+
# get the sources -- this is essentially synchronous
92+
loop.run_until_complete(get_sources(sources))
93+
94+
# running the loop for the articles
95+
jobs = asyncio.gather(*(get_articles(source) for source in sources))
96+
loop.run_until_complete(jobs)
97+
loop.close()
98+
# session.close()
99+
100+
art_count = len(titles)
101+
word_count = count_word(WORD, titles)
102+
103+
print(WORD, "found {} times in {} articles".format(word_count, art_count))
104+
print("Process took {:.0f} seconds".format(time.time() - start))

examples/async/get_news_sync.py

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
#!/usr/bin/env python
2+
3+
"""
4+
Regular synchronous script to see how much a given word is mentioned in the
5+
news today
6+
7+
Took about 21 seconds for me.
8+
9+
Uses data from the NewsAPI:
10+
11+
https://newsapi.org
12+
13+
NOTE: you need to register with the web site to get a KEY.
14+
"""
15+
import time
16+
import requests
17+
18+
WORD = "trump"
19+
20+
NEWS_API_KEY = "84d0483394c44f288965d7b366e54a74"
21+
22+
base_url = 'https://newsapi.org/v1/'
23+
24+
25+
def get_sources():
26+
"""
27+
get all the english language sources of news
28+
29+
'https://newsapi.org/v1/sources?language=en'
30+
"""
31+
url = base_url + "sources"
32+
params = {"language": "en"}
33+
resp = requests.get(url, params=params)
34+
data = resp.json()
35+
sources = [src['id'].strip() for src in data['sources']]
36+
return sources
37+
38+
39+
def get_articles(source):
40+
"""
41+
https://newsapi.org/v1/articles?source=associated-press&sortBy=top&apiKey=1fabc23bb9bc485ca59b3966cbd6ea26
42+
"""
43+
url = base_url + "articles"
44+
params = {"source": source,
45+
"apiKey": NEWS_API_KEY,
46+
# "sortBy": "latest", # some sources don't support latest
47+
"sortBy": "top",
48+
# "sortBy": "popular",
49+
}
50+
print("requesting:", source)
51+
resp = requests.get(url, params=params)
52+
if resp.status_code != 200: # aiohttpp has "status"
53+
print("something went wrong with {}".format(source))
54+
print(resp)
55+
print(resp.text)
56+
return []
57+
data = resp.json()
58+
# the url to the article itself is in data['articles'][i]['url']
59+
titles = [str(art['title']) + str(art['description'])
60+
for art in data['articles']]
61+
return titles
62+
63+
64+
def count_word(word, titles):
65+
word = word.lower()
66+
count = 0
67+
for title in titles:
68+
if word in title.lower():
69+
count += 1
70+
return count
71+
72+
73+
start = time.time()
74+
sources = get_sources()
75+
76+
art_count = 0
77+
word_count = 0
78+
for source in sources:
79+
titles = get_articles(source)
80+
art_count += len(titles)
81+
word_count += count_word('trump', titles)
82+
83+
print(WORD, "found {} times in {} articles".format(word_count, art_count))
84+
print("Process took {:.0f} seconds".format(time.time() - start))

0 commit comments

Comments
 (0)