Skip to content

Instantly share code, notes, and snippets.

@UnixSage
Last active Aug 1, 2020
Embed
What would you like to do?
Evenly split arbitrary groups of hours evenly across work days in a month
#!/usr/bin/env python3
import calendar, datetime, holidays
import math
import os, json
# hours.json format
#
# {
# "Client1": 116,
# "Client2": 36
# }
configFile = os.environ['HOME']+'/.config/CalcHours/hours.json'
fp = open(configFile)
clients=json.load(fp)
fp.close()
workdays = []
report = {}
totalClientHours=0
defaultClient = list(clients.keys())[0]
month_begin = 0
month_end = 0
year = datetime.date.today().year
month = datetime.date.today().month
workday_count = 0
cal = calendar.Calendar()
for week in cal.monthdayscalendar(year, month):
for i, day in enumerate(week):
# not this month's day or a weekend
if (
day == 0
or i >= 5
or datetime.date(year, month, day) in holidays.US(observed=True)
):
continue
# or some other control if desired...
workdays.append(day)
workday_count += 1
print(f"Total Days: {workday_count} Total Hours: {workday_count*8} Hours")
for client in clients:
print(f'{client}: {clients[client]}')
totalClientHours += clients[client]
if totalClientHours != workday_count*8:
print(f'Hours Mismatch: Calendar ({workday_count*8}) and Client ({totalClientHours})')
exit(1)
totalmonth = 0
for day in workdays:
daytotal = 0
for client in clients.keys():
if day not in report:
report[day] = {}
report[day][client] = math.trunc(clients[client] / workday_count)
clients[client] -= report[day][client]
daytotal += report[day][client]
while daytotal < 8:
clients[defaultClient] -= 1
report[day][defaultClient] += 1
daytotal += 1
workday_count -= 1
for day in workdays:
dow = datetime.date(year, month, day).strftime("%A")
print(f"{dow:10} {day:2} {report[day]}")
for day in workdays:
if day <= 15:
month_begin += 8
else:
month_end += 8
print(f"\nHours Split:\n1st - 15th: {month_begin}\n16th - EOM: {month_end}\n")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment