2025-11-12
Python
00

目录

🔍 Problem Analysis
What are Environment Variables?
Characteristics of Windows Environment Variables
💡 Solutions
🌟 Solution 1: Using os Module (Basic Method)
🚀 Solution 2: Using python-dotenv (Recommended Method)
🔧 Solution 3: Type Conversion and Validation
🎯 Code Practice
Practical Case 1: Database Connection Management
Practical Case 2: Configuration Management in HMI Development
Practical Case 3: Dynamic Setting of Environment Variables
🎯 Summary of Key Points

In Python development, environment variables are a concept that is both important and easily overlooked. Whether configuring database connections, API keys, or distinguishing between development and production environments, environment variables play a crucial role. However, many developers' operations with environment variables remain at a basic level, lacking systematic understanding and practical skills.

This article will take you deep into the methods of reading environment variables in Python, from basic operations to advanced techniques, and then to practical project applications, allowing you to thoroughly master this important programming skill. Whether you are a Python beginner or an experienced developer, you can gain practical knowledge and best practices from this.

🔍 Problem Analysis

What are Environment Variables?

Environment variables are dynamic named values used in operating systems to store system configuration information. In Python development, we commonly use environment variables to:

  • Configuration Management: Store sensitive information such as database connection strings, API keys
  • Environment Distinction: Differentiate between development, testing, and production environments
  • Dynamic Configuration: Adjust program behavior without modifying code
  • Security: Avoid hardcoding sensitive information in code

Characteristics of Windows Environment Variables

In Windows systems, environment variables have the following characteristics:

  • Case-insensitive (but uppercase is recommended)
  • Can be set through command line, system settings, or programmatically
  • Divided into system-level and user-level scopes

💡 Solutions

🌟 Solution 1: Using os Module (Basic Method)

The os module is the basic tool for handling environment variables in Python's standard library:

Python
import os # Read environment variables def get_env_basic(): # Method 1: Direct reading, will raise KeyError if not exists try: db_host = os.environ['DB_HOST'] print(f"Database Host: {db_host}") except KeyError: print("DB_HOST environment variable not set") # Method 2: Use get method, provide default value db_port = os.environ.get('DB_PORT', '3306') print(f"Database Port: {db_port}") # Method 3: Get all environment variables all_env = os.environ print(f"Total environment variables: {len(all_env)}")

image.png

🚀 Solution 2: Using python-dotenv (Recommended Method)

For project development, it's recommended to use the python-dotenv library to manage environment variables:

Bash
pip install python-dotenv

Create .env file:

text
# Database configuration DB_HOST=127.0.0.1 DB_PORT=3306 DB_USER=admin DB_PASSWORD=secret123 # API configuration API_KEY=your_api_key_here DEBUG=True

Python code:

Python
from dotenv import load_dotenv import os # Load .env file load_dotenv() class Config: """Configuration class for unified environment variable management""" def __init__(self): self.db_host = os.getenv('DB_HOST', 'localhost') self.db_port = int(os.getenv('DB_PORT', 3306)) self.db_user = os.getenv('DB_USER', 'root') self.db_password = os.getenv('DB_PASSWORD', '') self.api_key = os.getenv('API_KEY', '') self.debug = os.getenv('DEBUG', 'False').lower() == 'true' def get_db_url(self): """Build database connection URL""" return f"mysql://{self.db_user}:{self.db_password}@{self.db_host}:{self.db_port}/mydb" def display_config(self): """Display configuration information (hide sensitive info)""" print(f"Database Host: {self.db_host}") print(f"Database Port: {self.db_port}") print(f"API Key: {'*' * len(self.api_key) if self.api_key else 'Not Set'}") print(f"Debug Mode: {self.debug}") # Use configuration config = Config() config.display_config()

image.png

🔧 Solution 3: Type Conversion and Validation

Environment variables are all string types, requiring type conversion for actual use:

Python
import os from typing import Optional, Union class EnvHelper: """Environment variable helper class""" @staticmethod def get_str(key: str, default: str = '') -> str: """Get string type environment variable""" return os.getenv(key, default) @staticmethod def get_int(key: str, default: int = 0) -> int: """Get integer type environment variable""" value = os.getenv(key) if value is None: return default try: return int(value) except ValueError: print(f"Warning: {key} is not a valid integer, using default value {default}") return default @staticmethod def get_bool(key: str, default: bool = False) -> bool: """Get boolean type environment variable""" value = os.getenv(key, '').lower() if value in ('true', '1', 'yes', 'on'): return True elif value in ('false', '0', 'no', 'off'): return False else: return default @staticmethod def get_list(key: str, separator: str = ',', default: list = None) -> list: """Get list type environment variable""" if default is None: default = [] value = os.getenv(key) if value is None: return default return [item.strip() for item in value.split(separator) if item.strip()] @staticmethod def validate_required(required_vars: list) -> dict: """Validate whether required environment variables exist""" missing = [] present = {} for var in required_vars: value = os.getenv(var) if value is None: missing.append(var) else: present[var] = value if missing: raise ValueError(f"Missing required environment variables: {', '.join(missing)}") return present # Usage example if __name__ == "__main__": # Type conversion example port = EnvHelper.get_int('SERVER_PORT', 8080) debug = EnvHelper.get_bool('DEBUG', False) allowed_hosts = EnvHelper.get_list('ALLOWED_HOSTS', ',', ['localhost']) driver_data = EnvHelper.get_str('DriverData', '') print(f"Server Port: {port} (Type: {type(port)})") print(f"Debug Mode: {debug} (Type: {type(debug)})") print(f"Allowed Hosts: {allowed_hosts} (Type: {type(allowed_hosts)})") print(f"Driver Data: {driver_data} (Type: {type(driver_data)})") # Validate required variables try: required = EnvHelper.validate_required(['DB_HOST', 'API_KEY']) print("All required variables are set") except ValueError as e: print(f"Configuration error: {e}")

image.png

🎯 Code Practice

Practical Case 1: Database Connection Management

Python
import os from dotenv import load_dotenv import mysql.connector from mysql.connector import Error load_dotenv() class DatabaseManager: """Database management class""" def __init__(self): self.host = os.getenv('DB_HOST', 'localhost') self.port = int(os.getenv('DB_PORT', 3306)) self.user = os.getenv('DB_USER', 'root') self.password = os.getenv('DB_PASSWORD', '') self.database = os.getenv('DB_NAME', 'test') self.connection = None def connect(self): """Establish database connection""" try: self.connection = mysql.connector.connect( host=self.host, port=self.port, user=self.user, password=self.password, database=self.database ) if self.connection.is_connected(): print(f"Successfully connected to MySQL database: {self.database}") return True except Error as e: print(f"Database connection failed: {e}") return False def disconnect(self): """Disconnect database connection""" if self.connection and self.connection.is_connected(): self.connection.close() print("Database connection disconnected") def execute_query(self, query: str): """Execute query""" if not self.connection or not self.connection.is_connected(): print("Please establish database connection first") return None try: cursor = self.connection.cursor() cursor.execute(query) result = cursor.fetchall() cursor.close() return result except Error as e: print(f"Query execution failed: {e}") return None # Usage example db_manager = DatabaseManager() if db_manager.connect(): # Execute query operations results = db_manager.execute_query("SELECT VERSION()") if results: print(f"Database version: {results[0][0]}") db_manager.disconnect()

image.png

Practical Case 2: Configuration Management in HMI Development

Python
import os from dotenv import load_dotenv import json from dataclasses import dataclass from typing import Dict, Any load_dotenv() @dataclass class SerialConfig: """Serial port configuration""" port: str baudrate: int timeout: float @classmethod def from_env(cls): return cls( port=os.getenv('SERIAL_PORT', 'COM1'), baudrate=int(os.getenv('SERIAL_BAUDRATE', 9600)), timeout=float(os.getenv('SERIAL_TIMEOUT', 1.0)) ) @dataclass class ModbusConfig: """Modbus configuration""" host: str port: int slave_id: int @classmethod def from_env(cls): return cls( host=os.getenv('MODBUS_HOST', '192.168.1.100'), port=int(os.getenv('MODBUS_PORT', 502)), slave_id=int(os.getenv('MODBUS_SLAVE_ID', 1)) ) class HMIConfig: """HMI configuration management""" def __init__(self): self.serial = SerialConfig.from_env() self.modbus = ModbusConfig.from_env() self.scan_interval = float(os.getenv('SCAN_INTERVAL', 1.0)) self.log_level = os.getenv('LOG_LEVEL', 'INFO') self.data_storage_path = os.getenv('DATA_STORAGE_PATH', './data') def to_dict(self) -> Dict[str, Any]: """Convert to dictionary format""" return { 'serial': { 'port': self.serial.port, 'baudrate': self.serial.baudrate, 'timeout': self.serial.timeout }, 'modbus': { 'host': self.modbus.host, 'port': self.modbus.port, 'slave_id': self.modbus.slave_id }, 'scan_interval': self.scan_interval, 'log_level': self.log_level, 'data_storage_path': self.data_storage_path } def save_to_file(self, filename: str = 'config.json'): """Save configuration to file""" with open(filename, 'w', encoding='utf-8') as f: json.dump(self.to_dict(), f, indent=2, ensure_ascii=False) print(f"Configuration saved to {filename}") def display_config(self): """Display current configuration""" print("=== HMI Configuration Information ===") print(f"Serial Port: {self.serial.port}") print(f"Baud Rate: {self.serial.baudrate}") print(f"Modbus Host: {self.modbus.host}:{self.modbus.port}") print(f"Slave ID: {self.modbus.slave_id}") print(f"Scan Interval: {self.scan_interval} seconds") print(f"Log Level: {self.log_level}") print(f"Data Storage Path: {self.data_storage_path}") # Usage example if __name__ == "__main__": config = HMIConfig() config.display_config() config.save_to_file()

image.png

Practical Case 3: Dynamic Setting of Environment Variables

Python
import os import subprocess import platform class EnvManager: """Environment variable manager""" @staticmethod def set_env_var(key: str, value: str, permanent: bool = False): """Set environment variable""" # Temporary setting (effective only for current process) os.environ[key] = value print(f"Temporary environment variable {key} set to: {value}") # Permanent setting (Windows system) if permanent and platform.system() == 'Windows': try: # Set user-level environment variable subprocess.run([ 'setx', key, value ], check=True, capture_output=True) print(f"Permanent environment variable {key} has been set") except subprocess.CalledProcessError as e: print(f"Failed to set permanent environment variable: {e}") @staticmethod def delete_env_var(key: str): """Delete environment variable""" if key in os.environ: del os.environ[key] print(f"Environment variable {key} deleted") else: print(f"Environment variable {key} does not exist") @staticmethod def backup_env_vars(keys: list, filename: str = 'env_backup.txt'): """Backup specified environment variables""" backup_data = [] for key in keys: value = os.getenv(key) if value is not None: backup_data.append(f"{key}={value}") with open(filename, 'w', encoding='utf-8') as f: f.write('\n'.join(backup_data)) print(f"Environment variables backed up to {filename}") @staticmethod def restore_env_vars(filename: str = 'env_backup.txt'): """Restore environment variables from backup file""" try: with open(filename, 'r', encoding='utf-8') as f: for line in f: line = line.strip() if '=' in line: key, value = line.split('=', 1) os.environ[key] = value print(f"Restored environment variable: {key}") except FileNotFoundError: print(f"Backup file {filename} does not exist") except Exception as e: print(f"Error occurred while restoring environment variables: {e}") # Usage example if __name__ == "__main__": env_manager = EnvManager() # Set environment variables env_manager.set_env_var('MY_APP_VERSION', '1.0.0') env_manager.set_env_var('MY_APP_DEBUG', 'true', permanent=True) # Backup environment variables env_manager.backup_env_vars(['MY_APP_VERSION', 'MY_APP_DEBUG']) # Read set environment variables print(f"Application Version: {os.getenv('MY_APP_VERSION')}") print(f"Debug Mode: {os.getenv('MY_APP_DEBUG')}")

image.png

🎯 Summary of Key Points

Through the in-depth explanation in this article, we have comprehensively mastered the skills of reading and managing environment variables in Python. Let's review three key points:

1. Flexible Application of Multiple Reading Methods: From basic os.environ to professional python-dotenv library, and then to custom type conversion tools, choosing appropriate methods for different scenarios can greatly improve development efficiency.

2. Type Conversion and Validation Cannot Be Ignored: Environment variables are essentially all strings, and in actual projects, appropriate type conversion and validation must be performed to ensure program robustness and reliability.

3. Practical Application is Key: Whether it's database connection management, HMI development configuration, or dynamic management of environment variables, mastering these practical skills can make your Python development more professional and efficient.

Environment variable management is a fundamental skill in modern software development. By mastering these techniques, you can write more flexible, secure, and maintainable Python applications. It is recommended to practice more in actual projects and deepen understanding by combining specific business scenarios.

本文作者:技术老小子

本文链接:

版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!