Commit e1e633fa76c9c57431445a0e8806c6952023e6c9

Authored by Antoine Goutenoir
1 parent 9c034dd2
Exists in master

chore: improve error handling in production env

Showing 2 changed files with 43 additions and 34 deletions   Show diff stats
flaskr/controllers/main_controller.py
@@ -254,7 +254,6 @@ def estimate(): # register new estimation request, more accurately @@ -254,7 +254,6 @@ def estimate(): # register new estimation request, more accurately
254 public_id=estimation.public_id, 254 public_id=estimation.public_id,
255 extension='html' 255 extension='html'
256 )) 256 ))
257 - # return render_template("estimate-debrief.html", form=form)  
258 257
259 return show_form() 258 return show_form()
260 259
@@ -720,9 +719,6 @@ def compute(): # process the queue of estimation requests @@ -720,9 +719,6 @@ def compute(): # process the queue of estimation requests
720 return _respond(errmsg) 719 return _respond(errmsg)
721 720
722 721
723 -unavailable_statuses = [StatusEnum.pending, StatusEnum.working]  
724 -  
725 -  
726 @main.route("/estimation/<public_id>.<extension>") 722 @main.route("/estimation/<public_id>.<extension>")
727 def consult_estimation(public_id, extension): 723 def consult_estimation(public_id, extension):
728 try: 724 try:
@@ -741,13 +737,16 @@ def consult_estimation(public_id, extension): @@ -741,13 +737,16 @@ def consult_estimation(public_id, extension):
741 737
742 if extension in ['xhtml', 'html', 'htm']: 738 if extension in ['xhtml', 'html', 'htm']:
743 739
744 - if estimation.status in unavailable_statuses: 740 + if estimation.status in estimation.unavailable_statuses:
745 return render_template( 741 return render_template(
746 "estimation-queue-wait.html", 742 "estimation-queue-wait.html",
747 estimation=estimation 743 estimation=estimation
748 ) 744 )
749 else: 745 else:
750 - estimation_output = estimation.get_output_dict() 746 + try:
  747 + estimation_output = estimation.get_output_dict()
  748 + except Exception as e:
  749 + return abort(404)
751 estimation_sum = 0 750 estimation_sum = 0
752 if estimation_output: 751 if estimation_output:
753 for city in estimation_output['cities']: 752 for city in estimation_output['cities']:
@@ -762,16 +761,16 @@ def consult_estimation(public_id, extension): @@ -762,16 +761,16 @@ def consult_estimation(public_id, extension):
762 761
763 elif extension in ['yaml', 'yml']: 762 elif extension in ['yaml', 'yml']:
764 763
765 - if estimation.status in unavailable_statuses:  
766 - abort(404) 764 + if not estimation.is_available():
  765 + return abort(404)
767 766
768 return u"%s" % yaml_dump(estimation.get_output_dict()) 767 return u"%s" % yaml_dump(estimation.get_output_dict())
769 # return estimation.output_yaml 768 # return estimation.output_yaml
770 769
771 elif 'csv' == extension: 770 elif 'csv' == extension:
772 771
773 - if estimation.status in unavailable_statuses:  
774 - abort(404) 772 + if not estimation.is_available():
  773 + return abort(404)
775 774
776 si = StringIO() 775 si = StringIO()
777 cw = csv.writer(si, quoting=csv.QUOTE_ALL) 776 cw = csv.writer(si, quoting=csv.QUOTE_ALL)
@@ -811,7 +810,7 @@ def consult_estimation(public_id, extension): @@ -811,7 +810,7 @@ def consult_estimation(public_id, extension):
811 ) 810 )
812 811
813 else: 812 else:
814 - abort(404) 813 + return abort(404)
815 814
816 815
817 def get_locations(addresses): 816 def get_locations(addresses):
@@ -877,8 +876,8 @@ def get_trips_csv(public_id, destination_index=0): @@ -877,8 +876,8 @@ def get_trips_csv(public_id, destination_index=0):
877 except Exception as e: 876 except Exception as e:
878 return abort(500) 877 return abort(500)
879 878
880 - if estimation.status in unavailable_statuses:  
881 - abort(404) 879 + if not estimation.is_available():
  880 + return abort(404)
882 881
883 si = StringIO() 882 si = StringIO()
884 cw = csv.writer(si, quoting=csv.QUOTE_ALL) 883 cw = csv.writer(si, quoting=csv.QUOTE_ALL)
@@ -891,12 +890,12 @@ def get_trips_csv(public_id, destination_index=0): @@ -891,12 +890,12 @@ def get_trips_csv(public_id, destination_index=0):
891 results = estimation.get_output_dict() 890 results = estimation.get_output_dict()
892 891
893 if not 'cities' in results: 892 if not 'cities' in results:
894 - abort(500) 893 + return abort(500)
895 894
896 cities_length = len(results['cities']) 895 cities_length = len(results['cities'])
897 896
898 if 0 == cities_length: 897 if 0 == cities_length:
899 - abort(500, Response("No cities in results.")) 898 + return abort(500, Response("No cities in results."))
900 899
901 destination_index = min(destination_index, cities_length - 1) 900 destination_index = min(destination_index, cities_length - 1)
902 destination_index = max(destination_index, 0) 901 destination_index = max(destination_index, 0)
flaskr/models.py
@@ -42,6 +42,8 @@ class Estimation(db.Model): @@ -42,6 +42,8 @@ class Estimation(db.Model):
42 default=lambda: generate_unique_id(), 42 default=lambda: generate_unique_id(),
43 unique=True 43 unique=True
44 ) 44 )
  45 +
  46 + unavailable_statuses = [StatusEnum.pending, StatusEnum.working]
45 status = db.Column(db.Enum(StatusEnum), default=StatusEnum.pending) 47 status = db.Column(db.Enum(StatusEnum), default=StatusEnum.pending)
46 48
47 email = db.Column(db.Unicode(1024)) 49 email = db.Column(db.Unicode(1024))
@@ -121,8 +123,6 @@ class Estimation(db.Model): @@ -121,8 +123,6 @@ class Estimation(db.Model):
121 return join(runs_dir, self.public_id) 123 return join(runs_dir, self.public_id)
122 124
123 def set_output_dict(self, output): 125 def set_output_dict(self, output):
124 - # with shelve.open(filename=self.get_output_filename(), protocol=2) as shelf:  
125 - # shelf['output'] = output  
126 shelf = shelve.open( 126 shelf = shelve.open(
127 filename=self.get_output_filename(), 127 filename=self.get_output_filename(),
128 flag='c', # read/write, create if needed 128 flag='c', # read/write, create if needed
@@ -139,21 +139,25 @@ class Estimation(db.Model): @@ -139,21 +139,25 @@ class Estimation(db.Model):
139 output_filename = self.get_output_filename() 139 output_filename = self.get_output_filename()
140 if isfile(output_filename): 140 if isfile(output_filename):
141 141
142 - # Perhaps we'll need a mutex around here  
143 - # from threading import Lock  
144 - # mutex = Lock()  
145 - # mutex.acquire()  
146 -  
147 - # Not using the `with …` syntax, but we may in python3  
148 - shelf = shelve.open(  
149 - filename=output_filename,  
150 - flag='r',  
151 - protocol=2  
152 - )  
153 - self._output_dict = shelf['output']  
154 - shelf.close()  
155 -  
156 - # mutex.release() 142 + try:
  143 + # Perhaps we'll need a mutex around here
  144 + # from threading import Lock
  145 + # mutex = Lock()
  146 + # mutex.acquire()
  147 +
  148 + # Not using the `with …` syntax, but we may in python3
  149 + shelf = shelve.open(
  150 + filename=output_filename,
  151 + flag='r',
  152 + protocol=2
  153 + )
  154 + self._output_dict = shelf['output']
  155 + shelf.close()
  156 +
  157 + # mutex.release()
  158 + except Exception as e:
  159 +
  160 + return None
157 else: 161 else:
158 self._output_dict = None 162 self._output_dict = None
159 else: 163 else:
@@ -176,10 +180,16 @@ class Estimation(db.Model): @@ -176,10 +180,16 @@ class Estimation(db.Model):
176 180
177 def get_models(self): 181 def get_models(self):
178 if self._models is None: 182 if self._models is None:
179 - mdl_slugs = self.models_slugs.split("\n")  
180 - self._models = [m for m in models if m.slug in mdl_slugs] 183 + slugs = self.models_slugs.split("\n")
  184 + self._models = [m for m in models if m.slug in slugs]
181 return self._models 185 return self._models
182 186
  187 + def is_available(self):
  188 + if self.status in self.unavailable_statuses:
  189 + return False
  190 + # We might add more conditions here, such as file data availability
  191 + return True
  192 +
183 193
184 # BACKOFFICE CONFIGURATION #################################################### 194 # BACKOFFICE CONFIGURATION ####################################################
185 195