Skip to content

Instantly share code, notes, and snippets.

@jasonsnell
Last active March 29, 2022 22:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jasonsnell/caeff4fef6978f8271780f40da58db9c to your computer and use it in GitHub Desktop.
Save jasonsnell/caeff4fef6978f8271780f40da58db9c to your computer and use it in GitHub Desktop.
WeatherCat storm log generator
#! /usr/local/bin/python3
# Storm Log script
# For WeatherCat - https://trixology.com
# By Jason Snell <jsnell@sixcolors.com>
import re
from collections import defaultdict
import datetime
# Path to folder containing WeatherCat data files in year-folder format
# It's usually '/Users/[your-username]/Library/WeatherCatData/[your-location]/'
weatherCatPath = '/Users/admin/Library/WeatherCatData/Location1/'
# Path to folder where you want image to be saved
savePath = '/Library/Webserver/Documents/snellzone/weather/'
maxprecip = defaultdict(lambda: -99999)
diff = {}
today = datetime.date.today()
month = int(today.strftime('%m'))
monthstr = str(month + 100)[-2:]
day = today.strftime('%d')
year = today.strftime('%Y')
datelist = []
stormList = []
stormStart = []
stormEnd = []
theOutput = ''
newLine = '\n'
datapoint = re.compile(r't:([0-9]{2})[0-9]{4}')
rainpoint = re.compile(r'P:([0-9]{1,3}\.[0-9]{2})')
if month > 7:
monthStart = 7
else:
monthStart = -5
for i in range(monthStart, month+1, 1):
if i < 1 :
yearcode = str(int(year) - 1)
monthcode = 12 + i
else:
monthcode = i
yearcode = year
filepath = (weatherCatPath + f'{yearcode}/{monthcode}_WeatherCatData.cat')
file = open(filepath, 'r')
monthstring = str(monthcode + 100)[-2:]
for count, line in enumerate(file):
if count > 10:
theday = datapoint.search(line)
todayDay = (f'{yearcode}-{monthstring}-' + (theday.group(1)))
therain = rainpoint.search(line)
rainfloat = float(therain.group(1))
maxprecip[todayDay] = round(rainfloat * 0.03937007874, 2)
file.close()
# now loop through from monthstring + day
# plucking values for 7 days and putting them in a new list or dict
theRain = list(maxprecip.values())
theDates = list(maxprecip.keys())
theCounter = 0
totalRain = 0
# Loops through all rain days but the current day
for i in range(1,len(theRain)-1):
# If there was rain on this day, it updates the total rain count.
# If this is the first day of rain, it marks this as the start.
# It's marked as the end date, but that isn't used unless the
# next date has no rain.
if theRain[i] > 0 :
if totalRain == 0 :
sequenceStart = theDates[i]
totalRain += theRain[i]
if i == len(theRain)-1 :
pass
else:
sequenceEnd = theDates[i]
else:
# If there was no rain, but total rain is non-zero, mark this
# as the end of the rain and add all the results to the stack.
# Thus ends this storm entry.
if (totalRain > 0 ):
totalRain += theRain[i]
totalRain = round(totalRain,2)
if i != len(theRain)-1 :
# don't save storm total if rain continued on last day
stormList.append(totalRain)
stormEnd.append(sequenceEnd)
stormStart.append(sequenceStart)
totalRain = 0
# This handles the current day and wraps it all up.
if theRain[-1] > 0 :
if totalRain == 0 :
# If there was rain on the current day but not before
sequenceStart = theDates[-1]
stormStart.append(sequenceStart)
totalRain += theRain[-1]
sequenceEnd = theDates[-1]
totalRain = round(totalRain,2)
stormStart.append(sequenceStart)
stormList.append(totalRain)
stormEnd.append(f'{year}-{monthstr}-{day}')
else:
# there's no rain on the current day.
if (totalRain > 0 ):
# if there was an ongoing storm, close it out
totalRain = round(totalRain,2)
stormList.append(totalRain)
stormEnd.append(theDates[-2])
stormStart.append(sequenceStart)
# Now we're outputting the storm log, but removing low-precip storms.
for i in range((len(stormList)-1), 0, -1):
if stormList[i] > .09:
startDate = datetime.datetime.strptime(stormStart[i], '%Y-%m-%d')
endDate = datetime.datetime.strptime(stormEnd[i], '%Y-%m-%d')
difference = endDate - startDate
startDatePretty = startDate.strftime('%b %e')
endDatePretty = endDate.strftime('%b %e')
totalDays = difference.days + 1
if totalDays > 1 :
theOutput = theOutput + (f'<li>{stormList[i]}" {startDatePretty}-{endDatePretty} ({totalDays} days)</li>')
else:
theOutput = theOutput + (f'<li>{stormList[i]}" {startDatePretty}</li>')
lastStorm = datetime.datetime.strptime(stormEnd[-1], '%Y-%m-%d')
stormDifference = datetime.datetime.now() - lastStorm
if stormDifference.days < 2:
theOutputPrefix = (str(stormList[-1]) + ' inches in current storm.</p>' +
'<p><img width="400" src="/weather/rainhistory.png"></p>'
'<p><a href="https://abclocal.go.com/kgo/doppler?id=5750606&'
'mapnum=1&anim=true"><img src="https://cdn.abclocal.go.com/three/'
'kgo/weather/maps/nbay1_1280.jpg" width="400"></a></p>'
'<h3>Storm Log</h3>')
else:
theOutputPrefix = '</p><h3>Storm Log</h3>'
if stormDifference.days < 14:
theOutputPrefix = (theOutputPrefix +
'<p>Last two weeks of rain:</p><p><img '
'src="/weather/latestrain1.png" width="400" /></p><p><img '
'src="/weather/latestrain2.png" width="400" /></p>')
if theOutput:
theOutput = '<p>Rain events:</p><ul>' + theOutput + '</ul>'
outFile = open((savePath + 'stormlog.txt'), 'w')
outFile.write(theOutputPrefix + theOutput)
outFile.close()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment