jonathang commited on
Commit
655f886
1 Parent(s): fb62fc7

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +54 -22
app.py CHANGED
@@ -20,6 +20,7 @@ import gradio as gr
20
  import cachetools.func
21
  from huggingface_hub import hf_hub_download
22
  import concurrent.futures
 
23
 
24
 
25
  logger = structlog.getLogger()
@@ -31,6 +32,11 @@ art_styles = [x.strip() for x in open('art_styles.txt').readlines()]
31
  font_path = hf_hub_download("ybelkada/fonts", "Arial.TTF")
32
 
33
 
 
 
 
 
 
34
 
35
  class Chat:
36
  class Model(enum.Enum):
@@ -91,23 +97,42 @@ class Weather:
91
  self.zip_code = zip_code
92
  self.api_key = api_key
93
 
 
94
  def get_weather(self):
95
- url = f"https://api.weatherapi.com/v1/forecast.json?q={self.zip_code}&days=1&lang=en&aqi=yes&key={self.api_key}"
 
96
  headers = {'accept': 'application/json'}
97
  return requests.get(url, headers=headers).json()
98
 
99
- @cachetools.func.ttl_cache(maxsize=128, ttl=15*60)
100
  def get_info(self):
101
- weather = self.get_weather()
102
- next_hour = None
103
- for hour_data in weather['forecast']['forecastday'][0]["hour"]:
104
- if abs(hour_data["time_epoch"] - time.time()) < 60 * 60:
105
- next_hour = hour_data
106
- return {
107
- "now": weather["current"],
108
- "day": weather["forecast"]["forecastday"][0]["day"],
109
- "hour": next_hour,
 
 
 
 
 
110
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
111
 
112
 
113
  class Image:
@@ -228,13 +253,13 @@ Do not include specific numbers.'''.replace('\n', ' '))
228
  # Draw text on the image
229
  y_text = 5
230
  items_to_display = {
231
- 'Now': {'Temperature': weather_data['now']['temp_f'],
232
- 'Condition': weather_data['now']['condition']['text'],
233
- 'AQI': max(v for c, v in weather_data['now']['air_quality'].items() if c != 'co')},
234
- 'Hour': {'Condition': weather_data['hour']['condition']['text']},
235
- 'Day': {'High': weather_data['day']['maxtemp_f'],
236
- 'Low': weather_data['day']['mintemp_f'],
237
- 'Condition': weather_data['day']['condition']['text']},
238
  }
239
 
240
  for category, values in items_to_display.items():
@@ -247,14 +272,20 @@ Do not include specific numbers.'''.replace('\n', ' '))
247
 
248
  # Download the weather condition icon for now, day and next hour
249
  for index, time in enumerate(items_to_display.keys()):
250
- icon_url = "https:" + weather_data[time.lower()]['condition']['icon']
 
 
 
 
 
 
251
  response = requests.get(icon_url)
252
  icon = PIL.Image.open(io.BytesIO(response.content))
253
  # Resize the icon
254
  icon = icon.resize((60, 60))
255
  # Paste the icon on the image
256
- image.paste(icon, (180, index*80))
257
-
258
  return image
259
 
260
  def step(self, zip_code='10001', **kwargs):
@@ -263,6 +294,7 @@ Do not include specific numbers.'''.replace('\n', ' '))
263
  with concurrent.futures.ThreadPoolExecutor(max_workers=4) as e:
264
  runs = {}
265
  for time, data in forecast.items():
 
266
  runs[e.submit(self.step_one_forecast, data, **kwargs)] = time, data
267
  for r in concurrent.futures.as_completed(runs.keys()):
268
  img, txt = r.result()
@@ -270,7 +302,7 @@ Do not include specific numbers.'''.replace('\n', ' '))
270
  images.append(overlay_text_on_image(img, time, 'top-right', decode=True))
271
  # images.append(overlay_text_on_image(img, '', 'top-right', decode=True))
272
  texts.append(txt)
273
- return create_collage(*images, self.weather_img(forecast)), *texts, str(forecast)
274
 
275
 
276
  # Define Gradio interface
 
20
  import cachetools.func
21
  from huggingface_hub import hf_hub_download
22
  import concurrent.futures
23
+ import geopy
24
 
25
 
26
  logger = structlog.getLogger()
 
32
  font_path = hf_hub_download("ybelkada/fonts", "Arial.TTF")
33
 
34
 
35
+ @cachetools.cached(cache={})
36
+ def get_lat_long(zip):
37
+ loc = geopy.Nominatim(user_agent='weatherboy-gpt').geocode(str(zip))
38
+ return loc.latitude, loc.longitude
39
+
40
 
41
  class Chat:
42
  class Model(enum.Enum):
 
97
  self.zip_code = zip_code
98
  self.api_key = api_key
99
 
100
+ @cachetools.func.ttl_cache(maxsize=128, ttl=15*60)
101
  def get_weather(self):
102
+ lat, long = get_lat_long(self.zip_code)
103
+ url = f"https://forecast.weather.gov/MapClick.php?lat={lat:.2f}&lon={long:.2f}&unit=0&lg=english&FcstType=json"
104
  headers = {'accept': 'application/json'}
105
  return requests.get(url, headers=headers).json()
106
 
 
107
  def get_info(self):
108
+ data = self.get_weather()
109
+ new_data = {}
110
+ new_data['now'] = data['currentobservation']
111
+
112
+ # The 'time' and 'data' keys seem to have hourly/daily data
113
+ # Assuming the first entry in these lists is for the current hour
114
+ new_data['hour'] = {
115
+ 'time': data['time']['startValidTime'][0],
116
+ 'tempLabel': data['time']['tempLabel'][0],
117
+ 'temperature': data['data']['temperature'][0],
118
+ 'pop': data['data']['pop'][0],
119
+ 'weather': data['data']['weather'][0],
120
+ 'iconLink': data['data']['iconLink'][0],
121
+ 'text': data['data']['text'][0],
122
  }
123
+
124
+ # And the rest of the 'time' and 'data' lists are for the rest of the day
125
+ new_data['day'] = {
126
+ 'time': data['time']['startValidTime'][1:],
127
+ 'tempLabel': data['time']['tempLabel'][1:],
128
+ 'temperature': data['data']['temperature'][1:],
129
+ 'pop': data['data']['pop'][1:],
130
+ 'weather': data['data']['weather'][1:],
131
+ 'iconLink': data['data']['iconLink'][1:],
132
+ 'text': data['data']['text'][1:],
133
+ }
134
+
135
+ return new_data
136
 
137
 
138
  class Image:
 
253
  # Draw text on the image
254
  y_text = 5
255
  items_to_display = {
256
+ 'now': {'Temperature': weather_data['now']['Temp'],
257
+ 'Condition': weather_data['now']['Weather'],},
258
+ 'hour': {'Temperature': weather_data['hour']['temperature'],
259
+ 'Condition': weather_data['hour']['weather']},
260
+ 'day': {'High': max(weather_data['day']['temperature']),
261
+ 'Low': min(weather_data['day']['temperature']),
262
+ 'Condition': weather_data['day']['weather'][0]},
263
  }
264
 
265
  for category, values in items_to_display.items():
 
272
 
273
  # Download the weather condition icon for now, day and next hour
274
  for index, time in enumerate(items_to_display.keys()):
275
+ if time == 'day':
276
+ icon_url = weather_data['day']['iconLink'][0]
277
+ elif time == 'now':
278
+ icon_url = 'https://forecast.weather.gov/newimages/medium/'+weather_data['now']['Weatherimage']
279
+ else:
280
+ icon_url = weather_data[time]['iconLink']
281
+ print(time, icon_url)
282
  response = requests.get(icon_url)
283
  icon = PIL.Image.open(io.BytesIO(response.content))
284
  # Resize the icon
285
  icon = icon.resize((60, 60))
286
  # Paste the icon on the image
287
+ image.paste(icon, (index*70 + 10, 190))
288
+
289
  return image
290
 
291
  def step(self, zip_code='10001', **kwargs):
 
294
  with concurrent.futures.ThreadPoolExecutor(max_workers=4) as e:
295
  runs = {}
296
  for time, data in forecast.items():
297
+ if time == 'etc': continue
298
  runs[e.submit(self.step_one_forecast, data, **kwargs)] = time, data
299
  for r in concurrent.futures.as_completed(runs.keys()):
300
  img, txt = r.result()
 
302
  images.append(overlay_text_on_image(img, time, 'top-right', decode=True))
303
  # images.append(overlay_text_on_image(img, '', 'top-right', decode=True))
304
  texts.append(txt)
305
+ return create_collage(*images, self.weather_img(forecast)), *texts
306
 
307
 
308
  # Define Gradio interface