Aravinda S Holla
Posted on December 5, 2020
In the Court of Judiciary, the loser is the one who has won, dead is the one who has lost. - Boothayyana Maga Ayyu, Kannada Cinema.
In real-world projects, sensitive and important data such as server IP address, credentials, etc, must be kept secret as much as possible.
For doing so, we have lots of tools, utilities, packages, etc. But while using such a facility, there may be problems of another kind.
Let's have an illustration.
Django Twangy:
The cookie-cutter
tool is a commonly used project template starter. And provides us with a clean folder structure, .envs
, for storing the data.
These data are supplied to python code via environment variables, something like:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': 'ecommerce-portal',
'USER': 'postgres',
'PASSWORD': os.environ.get('DATABASE_PASSWORD'),,
'HOST': os.environ.get('DATABASE_HOST', default='localhost'),
'PORT': '5432',
}
}
Here secrets such as DATABASE_PASSWORD
, DATABASE_HOST
can be stored at .envs
.
The Case:
In the above scenario, if Supervisor
(a process control system) is used: While restarting sub-processes,
sudo supervisorctl restart ecommerce_celery
the result maybe something like:
ecommerce_celery: ERROR (not running)
ecommerce_celery: ERROR (spawn error)
If subprocess worker log is checked:
django.db.utils.OperationalError: could not connect to server: No such file or directory
Is the server running locally and accepting
connections on Unix domain socket "/var/run/postgresql/.s.PGSQL.5432"?
-
supervisor
runs outside the context of the virtual environment, detached from environment variables - In the above error case, the
supervisor
has not received the database name to connect.
A possible try is to pass the database name in the config file as an environment variable, like:
environment = DATABASE_HOST="255.254.253.252", .....
at /etc/supervisor/conf.d/ecommerce_celery.conf
.
This does not seem to work but continues to persist with the same error.
Saviour:
python-decouple
is a smart and simple solution that solves the above problem in a painless manner.
from decouple import config
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': 'ecommerce-portal',
'USER': 'postgres',
'PASSWORD': config('DATABASE_PASSWORD'),,
'HOST': config('DATABASE_HOST', default='localhost'),
'PORT': '5432',
}
}
The restart does not produce the errors but runs successfully.
Links:
Posted on December 5, 2020
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.