Приложение Heroku может взаимодействовать с Heroku-postgres локально, но не при развертывании в Heroku

Я делаю приложение Flask для очень простой игры, которую размещаю на Heroku, и оно взаимодействует с базой данных Heroku-Postgres уровня хобби-разработчика. При локальном размещении приложение может отлично взаимодействовать с базой данных (. Однако, когда я развертываю его на Heroku, оно обычно аварийно завершает работу вскоре после попытки взаимодействия с базой данных. Страницы, которые не требуют этого взаимодействия, работают нормально. В частности, , я получаю следующие две ошибки в журналах Heroku:

2021-05-19T19:23:20.943811+00:00 app[web.1]:cur = db.cursor() 
2021-05-19T19:23:20.943812+00:00 app[web.1]: psycopg2.InterfaceError: connection already closed

и...

2021-05-19T19:20:35.682211+00:00 app[web.1]:     cur.execute("select * from mock_table;")
2021-05-19T19:20:35.682211+00:00 app[web.1]: psycopg2.OperationalError: SSL error: decryption failed or bad record mac

У меня есть несколько теорий, основанных на исследованиях, но я не уверен:

  • Соединение с базой данных создается только один раз в самом начале приложения Flask.
  • Я храню код Python для взаимодействия с базой данных в отдельном модуле. Я создаю исходное соединение один раз, используя psycopg2.connect(...) в модуле приложения Flask, но передаю его другому модулю и его методам для фактического взаимодействия с базой данных.
  • Что-то еще приводит к завершению соединения с базой данных

Кто-нибудь из них близок, и кто-нибудь понимает, что мне не хватает? Я могу предоставить больше информации, если это необходимо, но я не хотел помещать слишком много.


person Lee    schedule 19.05.2021    source источник


Ответы (1)


Согласно этой статье Одной из возможных причин ошибок, которые я получаю, является тайм-аут соединения с базой данных. Таким образом, все, что мне нужно было сделать, это поместить методы вызова базы данных в блок try-except и восстановить соединение в случае возникновения ошибки. Например,

cur.execute("select * from mock_table;")

можно заменить на...

try:
    cur.execute("select * from mock_table;")
except:
    #remake connection here
    db.connect(host=host, database=database, user=user, password=password)
    cur.execute("select * from mock_table;")

Это не самое элегантное решение, и у него могут быть некоторые недостатки, но до сих пор оно успешно устраняло проблему, поэтому я решил поделиться им.

person Lee    schedule 20.05.2021