Skip to content

Commit

Permalink
Added error handling. Should respond appropriately for invalid input …
Browse files Browse the repository at this point in the history
…or if the stop number returns no routes (bad stop number).
  • Loading branch information
nealf committed Jun 24, 2016
1 parent ecd529f commit fd036a3
Show file tree
Hide file tree
Showing 4 changed files with 107 additions and 23 deletions.
4 changes: 4 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
FROM jazzdd/alpine-flask
MAINTAINER [email protected]

COPY ./ /app
90 changes: 78 additions & 12 deletions bt_text/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,21 +28,61 @@ def create_app():

app = create_app()

class InvalidUsage(Exception):
status_code = 400

def __init__(self, message, status_code=None, payload=None):
Exception.__init__(self)
self.message = message
if status_code is not None:
self.status_code = status_code
self.payload = payload

def to_dict(self):
rv = dict(self.payload or ())
rv['message'] = self.message
return rv

@app.errorhandler(InvalidUsage)
def handle_invalid_usage(error):
#response = jsonify(error.to_dict())
#response.status_code = error.status_code
#return response
reply = """<?xml version="1.0" encoding="UTF-8" ?>
<Response>
{content}
</Response>""".format(content=error.message)
return reply

@app.route('/')
def index():
reply = "Welcome to the BT Text/Phone API"
return reply


@app.route('/sms', methods=['GET', 'POST'])
@app.route('/sms', methods=['POST'])
def handle_text():

data = request.form['Body']
rt_code = int(data)
try:
data = request.form['Body']
rt_code = int(data)
except:
raise InvalidUsage('<Message>Invalid stop number, please try again.</Message>')
times = bt_api.get_times_for_stop_code(stopCode=rt_code, requestShortNames=True)

if times['success'] == False:
raise InvalidUsage("""
<Message>We're sorry, there was a problem retrieving stop times, please try again later.</Message>
""")
elif times['success'] == "Invalid":
raise InvalidUsage("""
<Message>That appears to be an invalid stop number, please try again.</Message>
""")
if times['times'] is None:
raise InvalidUsage("""
<Message>There are no current bus times for that stop number.</Message>
""")

message = ""

for stop in times['times']:

for time in stop[1]:
Expand All @@ -62,22 +102,48 @@ def handle_voice_call():
reply = """<?xml version="1.0" encoding="UTF-8" ?>
<Response>
<Gather timeout="15" finishOnKey="*" action="/voice" method="POST">
<Say voice="woman">Thanks for calling Blacksburg transit. Please enter the bus stop code and then press star.</Say>
<Say>Thanks for calling Blacksburg transit. Please enter the bus stop code and then press star.</Say>
</Gather>
<Gather timeout="15" finishOnKey="*" action="/voice" method="POST">
<Say voice="woman">Please enter the bus stop code and then press star.</Say>
<Say>Please enter the bus stop code and then press star.</Say>
</Gather>
<Say voice="woman">We're sorry, we didn't receive any input. Goodbye!</Say>
<Say>We're sorry, we didn't receive any input. Goodbye!</Say>
</Response>
"""
return reply

@app.route('/voice', methods=['POST'])
def handle_voice_input():
print(request.form['Digits'])
data = request.form['Digits']
rt_code = int(data)
try:
data = request.form['Digits']
rt_code = int(data)
except:
raise InvalidUsage("""
<Gather timeout="15" finishOnKey="*" action="/voice" method="POST">
<Say>Not a valid stop number, please try again.</Say>
</Gather>
<Gather timeout="15" finishOnKey="*" action="/voice" method="POST">
<Say>Please enter the bus stop code and then press star.</Say>
</Gather>
<Say>We're sorry, we didn't receive any input. Goodbye!</Say>
""")
times = bt_api.get_times_for_stop_code(stopCode=rt_code, requestShortNames=False)

if times['success'] is False:
raise InvalidUsage("""
<Say>We're sorry, there was a problem retrieving stop times, please try again later.</Say>
""")
elif times['success'] == "Invalid":
raise InvalidUsage("""
<Gather timeout="15" finishOnKey="*" action="/voice" method="POST">
<Say>That appears to be an invalid stop number, please enter the stop number followed by the star key.</Say>
</Gather>
<Say>We're sorry, we didn't receive any input. Goodbye!</Say>
""")
if times['times'] is None:
raise InvalidUsage("""
<Say>There are no current bus times for that stop number. Goodbye!</Say>
""")

message = "The next bus arrival times are: "
for stop in times['times']:
Expand All @@ -88,7 +154,7 @@ def handle_voice_input():

reply = """<?xml version="1.0" encoding="UTF-8" ?>
<Response>
<Say voice="woman">{content}. Thank you, goodbye!</Say>
<Say>{content}. Thank you, goodbye!</Say>
</Response>
""".format(content=message)
return reply
Binary file removed bt_text/__pycache__/__init__.cpython-35.pyc
Binary file not shown.
36 changes: 25 additions & 11 deletions bt_text/bt_request/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -181,22 +181,31 @@ def get_next_departure_times_for_route_and_stop_code(routeShortName, stopCode, n
def get_buses_for_stop_code(stopCode):
resp = __req_get_scheduled_routes(stopCode)

success = True
route_short_names = []
route_names = []
routes = {}

# pudb.set_trace()
if len(resp["xml"].findall('.//Error')) > 0:
#Successful response from server, but likely a bad stop number. We'll see if there are any routes in the calling function to handle'
success = False

success = True
if resp["status_code"] != None and resp["status_code"] == 200:
for child in resp["xml"].iter('RouteShortName'):
route_short_names.append(child.text)
for child in resp["xml"].iter('RouteName'):
route_names.append(child.text)
for child in resp["xml"].iter('ScheduledRoutes'):
routes[child.find('RouteShortName').text] = child.find('RouteName').text
else:
success = False
# pudb.set_trace()

if resp["status_code"] != None and resp["status_code"] == 200:
for child in resp["xml"].iter('RouteShortName'):
route_short_names.append(child.text)
for child in resp["xml"].iter('RouteName'):
route_names.append(child.text)
for child in resp["xml"].iter('ScheduledRoutes'):
routes[child.find('RouteShortName').text] = child.find('RouteName').text
else:
success = False

if len(routes) == 0:
#Bad stop number likely
success = False

return { "success": success, "status_code": resp["status_code"], "route_short_names": route_short_names, "route_names": route_names, "routes": routes }

Expand All @@ -208,10 +217,12 @@ def get_times_for_stop_code(stopCode, requestShortNames):
success = buses_resp["success"]
if buses_resp["status_code"] != None and buses_resp["status_code"] == 200 and success == True:
buses = buses_resp["route_short_names"]
print(buses_resp["routes"])

numTimesToReturn = 1

if len(buses) == 0:
return { "success": True, "times": None}

if len(buses) <= 2:
numTimesToReturn = 3

Expand All @@ -226,6 +237,9 @@ def get_times_for_stop_code(stopCode, requestShortNames):
else:
success = False
break
elif buses_resp["status_code"] != None and buses_resp["status_code"] == 200 and success == False and len(buses_resp["routes"]) == 0:
#No routes were listed, so probably an invalid stop number
success = "Invalid"
else:
success = False

Expand Down

1 comment on commit fd036a3

@nealf
Copy link
Member Author

@nealf nealf commented on fd036a3 Jun 24, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Closes #3

Please sign in to comment.