I have two expressions. I need to try one expression, if it is raise an exception try another, but if the second raises an exception too - to raise the exception.
I tried this, but it is looks ugly and I am not sure it is the best way to solve this issue:
try:
image = self.images.order_by(func.random()).limit(1)
except:
try:
image = self.images.order_by(func.rand()).limit(1)
except ProgrammingError:
raise ProgrammingError(
'The database engine must be PostgtreSQL or MySQL')
How do you do it?
Use a loop:
for methname in ("random", "rand"):
try:
image = self.images.order_by(getattr(func, methname)()).limit(1)
break
except ProgrammingError:
continue
else:
raise ProgrammingError("The database engine must be PostgtreSQL or MySQL")
The loop's else
clause is executed only if the loop terminates normally (i.e., without a break
) which is why we break
after doing the image
assignment. If you consider this too tricksy, because the else
clause is so infrequently used with for
, then this would also work:
image = None
for methname in ("random", "rand"):
try:
image = self.images.order_by(getattr(func, methname)()).limit(1)
except ProgrammingError:
continue
if not image:
raise ProgrammingError("The database engine must be PostgtreSQL or MySQL")