bitcreed

Linux & Systems

Python Decouple: Config from Command Line, Env or .env

· updated

This is a short read on simplifying configuration and launch management with Python’s decouple library.

Python Decouple is a lightweight library that separates configuration from code. It reads startup options from environment variables or a .env (dot-env) file, and it combines well with argparse for command-line arguments.

Why use Python Decouple?

The idea is simple: your code should be independent of its configuration. That keeps sensitive values like tokens out of the codebase and makes the application environment-agnostic. Dockerized applications in particular benefit from reading their launch arguments from environment variables or a mounted .env file.

Key features:

  1. Several configuration sources. Combined with argparse, settings can come from command-line arguments, environment variables or a .env file, whichever suits the deployment.
  2. Type casting. Values can be converted to Python types, which simplifies numeric, boolean and other settings.
  3. Simple syntax. It’s easy to drop into an existing Python project.
  4. Fallback values. You can define defaults so the application still runs when a setting is missing.

How to use Python Decouple

1. Install it

Install it with pip, or better, add it to your requirements.txt or setup.py:

pip install python-decouple

2. Put settings in a .env file

Create a .env file in a folder of your deployment and add your settings:

LOGLEVEL=DEBUG
TELEGRAM_BOT_TOKEN=yourbottoken123

3. Read the settings in code

Import config from decouple and use it to read your settings. Here’s decouple and argparse working together: a command-line flag wins, otherwise the value comes from the environment or the .env file.

import argparse
import sys

from decouple import config
# from myapp import MyApp
# from myapp.logger import set_log_level

class AppStarter:
    def __init__(self):
        self.app = None

    def run(self, argv):
        options = argparse.ArgumentParser()
        options.add_argument('-b', '--telegram-bot-token',
                             help="Telegram bot token. Also via env TELEGRAM_BOT_TOKEN or .env")
        options.add_argument('-c', '--telegram-chat-id',
                             help="Telegram chat ID (negative number for channel). Also via env TELEGRAM_CHAT_ID or .env")
        options.add_argument('-l', '--loglevel',
                             help="Log level. Also via env LOGLEVEL or .env. Valid values are DEBUG, INFO, WARN, ERROR etc.")

        args = options.parse_args(argv[1:])

        args.telegram_bot_token = args.telegram_bot_token or config('TELEGRAM_BOT_TOKEN')
        args.telegram_chat_id = args.telegram_chat_id or config('TELEGRAM_CHAT_ID')
        args.loglevel = args.loglevel or config('LOGLEVEL')
        # if args.loglevel:
        #     set_log_level(args.loglevel)

        # self.app = MyApp(args)
        # ret = self.app.run()
        sys.exit(ret)


def main():
    app = AppStarter()
    app.run(sys.argv)

The commented-out lines stand in for your own application; uncomment and adapt them so ret is set.

4. Or use environment variables

Instead of a .env file, you can set the same settings as environment variables, and the code above reads them the same way:

LOGLEVEL=INFO myapp

Here myapp is the generated Python project binary.

5. Command-line arguments

Python Decouple itself focuses on .env files and environment variables. For command-line arguments it integrates well with argparse, as the example shows.

Summary

Python Decouple together with argparse is a straightforward, flexible way to handle configuration and launch settings in Python applications. Separating configuration from code keeps the codebase cleaner, more secure and easier to manage, whether it’s a small script or a large application.