Created
September 7, 2018 17:26
-
-
Save ftobia/e7040792bf6f86d35dd58a887d6d258a to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
""" | |
FSEND standup bot script. | |
Calls on people via MacOS's "say" command. | |
Tracks timings for how long different parts of the standup take. | |
Code is written in Python 3 | |
""" | |
import datetime | |
import random | |
import json | |
import subprocess | |
class Standup: | |
prompt_strings = [ | |
'Status time, {}!', | |
"{}, why don't you go ahead?", | |
"{}, what's up?", | |
"How's it going {}?", | |
"{}, how's it going?", | |
'{}, can you give your status please?', | |
'{}, could you please give your status?', | |
'Could you please give your status, {}?', | |
'Would you go ahead {}?', | |
"{}, you're up.", | |
] | |
def doit(self): | |
timer = Timer() | |
timer.start() | |
# Prompt for attendance. | |
missing = input('Is anyone missing? ') | |
timer.event('Standup intro') | |
print() | |
if 'no' not in missing.strip().lower(): | |
missing_peeps = [p.strip().lower() for p in missing.split(',')] | |
else: | |
missing_peeps = [] | |
attendees = Attendees(missing_peeps) | |
# Say what the schedule is. | |
print('First up: pass-up pass-down') | |
print('Second: QA status') | |
print('Lastly: Dev status') | |
potential_arrivals = input('Are you done with pass-up pass-down yet? ') | |
print() | |
print("Here's the order for today:") | |
print('\n'.join([a.capitalize() for a in attendees.remaining()])) | |
attendees.parse_potential_arrivals(potential_arrivals) | |
while attendees.remaining(): | |
print() | |
prompt_fmt = random.choice(self.prompt_strings) | |
self.prompt_strings.remove(prompt_fmt) | |
next_attendee = attendees.next().capitalize() | |
prompt_str = prompt_fmt.format(next_attendee) | |
subprocess.Popen(['say', '-v', 'Samantha', '-r', '250', prompt_str]) | |
timer.event(next_attendee) | |
potential_arrivals = input(prompt_str + ' ') | |
attendees.parse_potential_arrivals(potential_arrivals) | |
timer.event('OUTRO') | |
print("I think that's it!") | |
input('Is there anything else?') | |
timer.stop() | |
timer.write() | |
class Attendees: | |
qa = ['renuka', 'scott', 'yidie'] | |
devs = ['ian', 'rob', 'dennis', | |
'casey', 'charlie', | |
'frank'] | |
def __init__(self, missing_peeps=None): | |
self.ordered_peeps = \ | |
sorted(self.qa, key=lambda x: random.random()) + \ | |
sorted(self.devs, key=lambda x: random.random()) | |
self.statuses_given = [] | |
for person in (missing_peeps or []): | |
try: | |
self.ordered_peeps.remove(person) | |
except ValueError: | |
... | |
def parse_potential_arrivals(self, potential_arrivals): | |
if 'arrived' in potential_arrivals: | |
s = potential_arrivals[:-len('arrived')] | |
late_arrivals = [r.strip().lower() for r in s.split(',')] | |
for person in late_arrivals: | |
self.late_arrival(person) | |
def remaining(self): | |
return list(self.ordered_peeps) | |
def next(self): | |
person = self.ordered_peeps.pop(0) | |
self.statuses_given.append(person) | |
return person | |
def late_arrival(self, person): | |
self.ordered_peeps.append(person) | |
class Timer: | |
def __init__(self): | |
self._events = [] | |
self._ongoing_event = 'PRE' | |
self._time = datetime.datetime.now() | |
def start(self): | |
self.event('START') | |
def stop(self): | |
self.event('STOP') | |
self.event(None) | |
def event(self, event): | |
""" | |
Log an "event" string and keep track of how | |
long each event is going on for. | |
""" | |
now = datetime.datetime.now() | |
self._events.append((self._ongoing_event, self._time, now)) | |
self._ongoing_event = event | |
self._time = now | |
def write(self): | |
filename = '{}.json'.format(datetime.datetime.now().strftime('%Y-%m-%d')) | |
with open(filename, 'w') as f: | |
f.write(json.dumps(self._events, indent=2, cls=DatetimeEncoder)) | |
class DatetimeEncoder(json.JSONEncoder): | |
def default(self, obj): | |
if isinstance(obj, datetime.datetime): | |
return obj.strftime("%Y-%m-%dT%H:%M:%S.%f%z") | |
return super().default(obj) | |
if __name__ == '__main__': | |
Standup().doit() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment