1

Would anyone know how to make Python return a date format like this from the calendar function?:

date = "20170714"

Basically I am looking for some enhancements if its possible for the API request to gather hourly weather data.. My problem is the code needs to be re-ran for each day.. Its a little clunky and time consuming to rerun the script 365 times to get a years worth of weather data, but its the only way I know how. Can a loop with the calendar function automate things?

from urllib.request import urlopen
from pandas.io.json import json_normalize
import json
import pandas as pd

api_key = ""
date = "20170714"
zip_code = "96345"

response = urlopen("http://api.wunderground.com/api/%s/history_%s/q/%s.json" % (api_key, date, zip_code))

json_data = response.read().decode('utf-8', 'replace')

data = json.loads(json_data)

for observation in data['history']['observations']:
     print("Date/Time:    " + observation['date']['pretty'])
     print("Temperature:  " + observation['tempi'])
     print("Humidity:     " + observation['hum'])

df = json_normalize(data['history']['observations'])

df = df[['date.pretty','tempi','hum']]
df['date.pretty'] = pd.to_datetime(df['date.pretty'])

print(df)

This simple calendar script can return every day in the month of December 2013, but its not in a format that weather underground API would understand... Ultimately I am hoping to create a loop where the API request can gather a months data, (or even an entire year at a time) with the calendar function Vs one day manual fashion.... Is this possible??!

import calendar

tc = calendar.TextCalendar(firstweekday=0)

for i in tc.itermonthdays(2013,12):
    print(i)

Thanks

bbartling
  • 3,288
  • 9
  • 43
  • 88

2 Answers2

1

There are restrictions on how many requests you can make a day with a free API key, but this is the way I would suggest. As a note, anything date and/or time related I almost always use the arrow package. Something along these lines should work for you.

import arrow # learn more: https://python.org/pypi/arrow
from WunderWeather import weather # learn more: https://python.org/pypi/WunderWeather

api_key = ''
extractor = weather.Extract(api_key)
zip = '96345'

# get 20170101 00:00
begin_date = arrow.get("2017","YYYY")
# get 20171231 23:00
end_date = arrow.get("2018","YYYY").shift(hours=-1)
for date in arrow.Arrow.range('hour',begin_date,end_date):
  # get date object for feature
  # http://wunderweather.readthedocs.io/en/latest/WunderWeather.html#WunderWeather.weather.Extract.date
  date_weather = extractor.date(zip,date.format('YYYYMMDD'))

  # use shortcut to get observations and data
  # http://wunderweather.readthedocs.io/en/latest/WunderWeather.html#WunderWeather.date.Observation
  for observation in date_weather.observations:
    print("Date:",observation.date_pretty)
    print("Temp:",observation.temp_f)
  • Wow,thanks.. Yes I will give this a try too... For the free API key, I think I am limited to 10 calls per minute... Ill try this in the for date loop `time.sleep(6)` to hopefully not exceed the 10 calls – bbartling Dec 05 '17 at 14:16
  • Hi do you have a tip for installing the wunderweather module? Im running 3.6 32 bit version IDLE. I went to https://python.org/pypi/WunderWeather and downloaded/extract/installed the WunderWeather-0.2.9.tar.gz (md5) with Windows powershell but I am getting the module not found error.. Any tips? – bbartling Dec 05 '17 at 15:35
  • Typically you'd just run `pip install WunderWeather` and it would install the package in your python path. If this doesn't make sense to you, I'd search around on SO a bit more or post another question. – Methodical Maverick Dec 05 '17 at 23:22
  • Can you help with this other WU post question I have? The script above works awesome. https://stackoverflow.com/questions/47872635/weather-underground-api-python-3 – bbartling Dec 18 '17 at 16:33
  • Methodical Maverick, here's another question for the same script if a feature can be added for limiting the API calls per minute... https://stackoverflow.com/questions/47874185/weather-undground-api-call-limit-per-minute – bbartling Dec 18 '17 at 18:17
  • If you like the answer, an up vote or accept this as the answer would be nice ;P – Methodical Maverick Dec 19 '17 at 22:13
0

Very pythonic, but since you only need to this once I thought this is okay, here is the code I used:

import calendar

datelst = []
year = 2013
for month in range(1,13):
    days = range(1,calendar.monthrange(year,month)[1]+1)
    if month<10:
        for day in days:
            if day<10:
                datelst.append(str(year)+'0'+str(month)+'0'+str(day))
            else:
                datelst.append(str(year)+'0'+str(month)+str(day))
    else:
        for day in days:
            if day<10:
                datelst.append(str(year)+str(month)+'0'+str(day))
            else:
                datelst.append(str(year)+str(month)+str(day))

Now datelst contains all dates from the year 2013 in the way you wanted, so day i of 2013 is now: datelst[i-1]. Use a for loop to loop over all days.

T C Molenaar
  • 3,205
  • 1
  • 10
  • 26
  • Thank you for the response, but is there anyway you can give me more tips on where to implement the code you wrote? Im a little bit of a newb here... print(?) Thank you.... – bbartling Dec 01 '17 at 20:35
  • After my code you can run your code, so you adjust your `date = datelst[i]` (it picks the i-th element of datelst, which contains all dates of 2013. Now you make a for-loop: `for i in datelst:` and you need to indent everything from `api_key` to `print(df)`. So my code comes before this for-loop. Hope you understand it! If not, let me know! – T C Molenaar Dec 02 '17 at 08:45
  • Rodger that, thank you for explaining that to my level, it makes perfect sense.... I am still getting an error, from my part of the code where I convert `date = datelst[i]` as you mentioned above... The shell is giving me this error, date = datelst[i] TypeError: list indices must be integers or slices, not str – bbartling Dec 04 '17 at 22:34