Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Iss pass error handling #7

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
67 changes: 34 additions & 33 deletions app.py
Original file line number Diff line number Diff line change
Expand Up @@ -74,39 +74,40 @@ def tle_info():
@jsonp
@json
def iss_pass():

# Sanitize inputs
lat = request.args.get('lat', False)
if lat:
lat = safe_float(lat, (-90.0, 90.0))
if not lat:
return {"message": "failure", "reason": "Latitude must be number between -90.0 and 90.0"}, 400
else:
return {"message": "failure", "reason": "Latitude must be specified"}, 400

lon = request.args.get('lon', False)
if lon:
lon = safe_float(lon, (-180.0, 180.0))
if not lon:
return {"message": "failure", "reason": "Longitue must be number between -180.0 and 180.0"}, 400
else:
return {"message": "failure", "reason": "Longitude must be specified"}, 400

alt = request.args.get('alt', False)
if alt:
alt = safe_float(alt, (0, 10000))
if not alt:
return {"message": "failure", "reason": "Altitude must be number between 0 and 10,000"}, 400
else:
alt = 100

n = request.args.get('n', False)
if n:
n = safe_float(n, (1, 100))
if not n:
return {"message": "failure", "reason": "Number of passes must be number between 1 and 100"}, 400
else:
n = 5
try:
# Sanitize inputs
lat = request.args.get('lat', False)
if lat:
lat = safe_float(lat, (-90.0, 90.0))
if not lat:
raise ValueError("Latitude must be number between -90.0 and 90.0")
else:
raise ValueError("Latitude must be specified.")
lon = request.args.get('lon', False)
if lon:
lon = safe_float(lon, (-180.0, 180.0))
if not lon:
ValueError("Longitude must be number between -180.0 and 180.0")
else:
raise ValueError("Longitude must be specified.")
alt = request.args.get('alt', False)
if alt:
alt = safe_float(alt, (0, 10000))
if not alt:
raise ValueError("Altitude must be number between 0 and 10,000")
else:
alt = 100

n = request.args.get('n', False)
if n:
n = safe_float(n, (1, 100))
if not n:
raise ValueError("Number of passes must be number between 1 and 100")
else:
n = 5
except ValueError as e:
error_response = {"message": "failure", "reason": e.message, "request": request.args}
return error_response, 400

# Calculate data and return
d = iss.get_passes(lon, lat, alt, int(n))
Expand Down
15 changes: 6 additions & 9 deletions iss.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,30 +43,29 @@ def get_tle_update():


def get_passes(lon, lat, alt, n):
"""Compute n number of passes of the ISS for a location"""

"""Compute up to n number of passes of the ISS for a location"""
# Get latest TLE from redis
tle = json.loads(r.get("iss_tle"))
iss = ephem.readtle(str(tle[0]), str(tle[1]), str(tle[2]))

# Set location
location = ephem.Observer()
location.lat = str(lat)
location.long = str(lon)
location.elevation = alt

# Override refration calculation
location.pressure = 0
location.horizon = '10:00'

# Set time now
now = datetime.datetime.utcnow()
location.date = now

# Predict passes
passes = []
for p in xrange(n):
tr, azr, tt, altt, ts, azs = location.next_pass(iss)
try:
tr, azr, tt, altt, ts, azs = location.next_pass(iss)
except ValueError as e:
# next_pass returns "that satellite seems to stay always below your horizon"
break
duration = int((ts - tr) * 60 * 60 * 24)
year, month, day, hour, minute, second = tr.tuple()
dt = datetime.datetime(year, month, day, hour, minute, int(second))
Expand All @@ -76,7 +75,6 @@ def get_passes(lon, lat, alt, n):

# Increase the time by more than a pass and less than an orbit
location.date = tr + 25*ephem.minute

# Return object
obj = {"request": {
"datetime": timegm(now.timetuple()),
Expand All @@ -87,5 +85,4 @@ def get_passes(lon, lat, alt, n):
},
"response": passes,
}

return obj
31 changes: 30 additions & 1 deletion testsuite/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,35 @@
import json
from app import app

class IssPassTest(TestCase):
"""Test ISS-pass API"""
def setUp(self):
self.app = app
self.w = TestApp(self.app)
self.endpoint = '/iss-pass.json'

def format_uri(self, lat, lon):
return self.endpoint + '?lat={0}&lon={1}'.format(lat, lon)

def test_berkeley(self):
berkeley = self.format_uri(37.8715926, -122.27274699999998)
r = self.w.get(berkeley)
r.charset = 'utf8'
data = json.loads(r.text)
self.assertEqual(r.status_code, 200)

def test_no_passes_found(self):
mcmurdo_station = self.format_uri(-77.8418779, 166.6863449)
r = self.w.get(mcmurdo_station)
self.assertEqual(r.status_code, 200)
data = r.json
self.assertEqual(len(data['response']), 0)

def test_bad_lat(self):
bad_lat = self.format_uri(-91, 50)
r = self.w.get(bad_lat, expect_errors=True)
self.assertEqual(r.status_code, 400)


class IssNowTest(TestCase):
"""Test the ISS-now API"""
Expand All @@ -26,7 +55,7 @@ def test_data(self):
try:
data = json.loads(r.text)
except:
self.fail("ISS API not a valid JSON responce")
self.fail("ISS API not a valid JSON response")

# Success message
self.assertEqual(data['message'], "success", "ISS API Did not return 'sucess' message")
Expand Down