我想在我的 Django 应用程序数据库中保留一些“签入”事件的记录。如果客户端/用户在超过 X 分钟内没有发布签入(通过对我的应用程序的 HTTP 请求完成),那么我想向客户端发出一条 socketIO 消息。客户可以根据需要随时发布签到信息。我从 Kubernetes Pod 运行此应用程序,数据库用户名和密码在 Pod 部署时导出为环境变量。
我的解决方案是在应用程序启动时启动一个线程,并让该线程每 10 分钟轮询一次 Django 数据库。如果最近10分钟内没有在数据库中找到签到记录,则调用我的套接字发射函数。否则,再睡10分钟。不幸的是,当我尝试从我的线程内轮询数据库时,我遇到了:
django.db.utils.ProgrammingError: permission denied for table check_in_table
一些简化的代码片段:
# WatchCheckIn().start() is called from my apps.py file within my `AppConfig`'s `ready()`
class WatchCheckIn(threading.Thread):
def run(self) -> None:
logging.info('Querying database for check-ins.')
try:
latest_record = models.CheckIn.objects.last()
check_in_period = datetime.datetime.now(
tz=datetime.timezone.utc) - datetime.timedelta(minutes=10)
if latest_record.check_in_time < check_in_period:
socket_views.notify_need_check_in()
except IndexError:
logging.warning('No previous check-ins found.')
finally:
time.sleep(600)
在我的应用程序的
settings.py
中,我从 K8s 部署中导出的内容中获取用户名和密码,正如我上面提到的:
DATABASES = {
'default': {
# <other items>
'USER': os.environ.get('DB_USER'),
'PASSWORD': os.environ.get('DB_PASSWORD'),
}
}
我的应用程序确实有相应的
models.py
、views.py
和 serializers.py
文件,当客户提出请求时,我使用它们工作得很好,但我不确定是否/如何应该在我自己的应用程序中使用这些文件应用程序。我通常只是对如何授予我的应用程序定期查询其数据库的权限感到困惑。
我知道除此之外还有其他解决方案,例如 Celery,但我真的很想看看这种方法是否可行(如果可能的话)。预先感谢您的帮助!
看起来该用户没有权限访问该
check_in_table
所在的数据库。
你能做到吗?执行到 POD 并尝试从 Django shell 运行相同的 SQL 命令。不会成功的。
然后使用psql命令,以便任何用户都可以访问数据库。您始终可以细粒度许可。但这看起来是根本原因。
sudo -u postgres psql <database_name>
GRANT CREATE ON SCHEMA public TO <your_dbuser>;
您可以执行类似的操作来授予权限。
顺便说一句,这与 kubernetes 无关。