Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
adapter pattern is created
  • Loading branch information
bjy19 committed Aug 11, 2021
commit a86140f454ceb3cbd63b17f92f67bb41baf52fa2
9 changes: 2 additions & 7 deletions app/data/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
"""app.data"""
from app.services.location import LocationService
from ..services.location.csbs import CSBSLocationService
from ..services.location.jhu import JhuLocationService
from ..services.location.nyt import NYTLocationService
Expand All @@ -12,10 +13,4 @@


def data_source(source):
"""
Retrieves the provided data-source service.

:returns: The service.
:rtype: LocationService
"""
return DATA_SOURCES.get(source.lower())
return LocationService(DATA_SOURCES.get(source.lower()))
30 changes: 8 additions & 22 deletions app/services/location/__init__.py
Original file line number Diff line number Diff line change
@@ -1,28 +1,14 @@
"""app.services.location"""
from abc import ABC, abstractmethod


class LocationService(ABC):
"""
Service for retrieving locations.
"""
class LocationService:

@abstractmethod
async def get_all(self):
"""
Gets and returns all of the locations.

:returns: The locations.
:rtype: List[Location]
"""
raise NotImplementedError
def __init__(self, resource):
self.resource = resource

@abstractmethod
async def get(self, id): # pylint: disable=redefined-builtin,invalid-name
"""
Gets and returns location with the provided id.
async def get_all(self):
return await self.resource.get_locations()

:returns: The location.
:rtype: Location
"""
raise NotImplementedError
async def get(self, id):
locations = await self.get_all()
return locations[id]
15 changes: 3 additions & 12 deletions app/services/location/csbs.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,21 +15,11 @@
LOGGER = logging.getLogger("services.location.csbs")


class CSBSLocationService(LocationService):
class CSBSLocationService:
"""
Service for retrieving locations from csbs
"""

async def get_all(self):
# Get the locations.
locations = await get_locations()
return locations

async def get(self, loc_id): # pylint: disable=arguments-differ
# Get location at the index equal to the provided id.
locations = await self.get_all()
return locations[loc_id]


# Base URL for fetching data
BASE_URL = "https://facts.csbs.org/covid-19/covid19_county.csv"
Expand Down Expand Up @@ -84,7 +74,8 @@ async def get_locations():
# Coordinates.
Coordinates(item["Latitude"], item["Longitude"]),
# Last update (parse as ISO).
datetime.strptime(last_update, "%Y-%m-%d %H:%M").isoformat() + "Z",
datetime.strptime(
last_update, "%Y-%m-%d %H:%M").isoformat() + "Z",
# Statistics.
int(item["Confirmed"] or 0),
int(item["Death"] or 0),
Expand Down
32 changes: 10 additions & 22 deletions app/services/location/jhu.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,27 +21,12 @@
PID = os.getpid()


class JhuLocationService(LocationService):
class JhuLocationService:
"""
Service for retrieving locations from Johns Hopkins CSSE (https://github.com/CSSEGISandData/COVID-19).
"""

async def get_all(self):
# Get the locations.
locations = await get_locations()
return locations

async def get(self, loc_id): # pylint: disable=arguments-differ
# Get location at the index equal to provided id.
locations = await self.get_all()
return locations[loc_id]


# ---------------------------------------------------------------


# Base URL for fetching category.
BASE_URL = "https://raw.githubusercontent.com/CSSEGISandData/2019-nCoV/master/csse_covid_19_data/csse_covid_19_time_series/"
# Base URL for fetching category.
BASE_URL = "https://raw.githubusercontent.com/CSSEGISandData/2019-nCoV/master/csse_covid_19_data/csse_covid_19_time_series/"


@cached(cache=TTLCache(maxsize=4, ttl=1800))
Expand Down Expand Up @@ -82,10 +67,12 @@ async def get_category(category):

for item in data:
# Filter out all the dates.
dates = dict(filter(lambda element: date_util.is_date(element[0]), item.items()))
dates = dict(
filter(lambda element: date_util.is_date(element[0]), item.items()))

# Make location history from dates.
history = {date: int(float(amount or 0)) for date, amount in dates.items()}
history = {date: int(float(amount or 0))
for date, amount in dates.items()}

# Country for this location.
country = item["Country/Region"]
Expand All @@ -101,7 +88,7 @@ async def get_category(category):
"country_code": countries.country_code(country),
"province": item["Province/State"],
# Coordinates.
"coordinates": {"lat": item["Lat"], "long": item["Long"],},
"coordinates": {"lat": item["Lat"], "long": item["Long"], },
# History.
"history": history,
# Latest statistic.
Expand Down Expand Up @@ -178,7 +165,8 @@ async def get_locations():
location["country"],
location["province"],
# Coordinates.
Coordinates(latitude=coordinates["lat"], longitude=coordinates["long"]),
Coordinates(
latitude=coordinates["lat"], longitude=coordinates["long"]),
# Last update.
datetime.utcnow().isoformat() + "Z",
# Timelines (parse dates as ISO).
Expand Down
32 changes: 10 additions & 22 deletions app/services/location/nyt.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,27 +16,12 @@
LOGGER = logging.getLogger("services.location.nyt")


class NYTLocationService(LocationService):
class NYTLocationService:
"""
Service for retrieving locations from New York Times (https://github.com/nytimes/covid-19-data).
Service for retrieving locations from Johns Hopkins CSSE (https://github.com/CSSEGISandData/COVID-19).
"""

async def get_all(self):
# Get the locations.
locations = await get_locations()
return locations

async def get(self, loc_id): # pylint: disable=arguments-differ
# Get location at the index equal to provided id.
locations = await self.get_all()
return locations[loc_id]


# ---------------------------------------------------------------


# Base URL for fetching category.
BASE_URL = "https://raw.githubusercontent.com/nytimes/covid-19-data/master/us-counties.csv"
# Base URL for fetching category.
BASE_URL = "https://raw.githubusercontent.com/nytimes/covid-19-data/master/us-counties.csv"


def get_grouped_locations_dict(data):
Expand Down Expand Up @@ -104,18 +89,21 @@ async def get_locations():
# Make location history for confirmed and deaths from dates.
# List is tuples of (date, amount) in order of increasing dates.
confirmed_list = histories["confirmed"]
confirmed_history = {date: int(amount or 0) for date, amount in confirmed_list}
confirmed_history = {date: int(amount or 0)
for date, amount in confirmed_list}

deaths_list = histories["deaths"]
deaths_history = {date: int(amount or 0) for date, amount in deaths_list}
deaths_history = {date: int(amount or 0)
for date, amount in deaths_list}

# Normalize the item and append to locations.
locations.append(
NYTLocation(
id=idx,
state=county_state[1],
county=county_state[0],
coordinates=Coordinates(None, None), # NYT does not provide coordinates
# NYT does not provide coordinates
coordinates=Coordinates(None, None),
last_updated=datetime.utcnow().isoformat() + "Z", # since last request
timelines={
"confirmed": Timeline(
Expand Down