最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

從環(huán)境變量到配置中心帶你掌握Python多環(huán)境配置

 更新時(shí)間:2026年03月03日 09:45:31   作者:銘淵老黃  
這篇文章主要為大家詳細(xì)介紹了Python中配置管理的藝術(shù),本文會(huì)從環(huán)境變量到配置中心帶你優(yōu)雅駕馭多環(huán)境配置,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以了解下

引言:一次慘痛的線上事故

凌晨?jī)牲c(diǎn),手機(jī)突然震動(dòng)。

“生產(chǎn)環(huán)境數(shù)據(jù)庫(kù)連接失敗,核心業(yè)務(wù)全部中斷!”

我從睡夢(mèng)中驚醒,打開電腦,定睛一看——有人提交了一行代碼,把 config.py 里的數(shù)據(jù)庫(kù)地址從生產(chǎn)環(huán)境硬編碼成了開發(fā)環(huán)境的地址。這一個(gè)低級(jí)錯(cuò)誤,導(dǎo)致整個(gè)系統(tǒng)停擺了四十分鐘。

這是我職業(yè)生涯中刻骨銘心的一次教訓(xùn)。從那以后,我對(duì) Python 配置管理的重視程度,不亞于對(duì)核心業(yè)務(wù)邏輯的重視。

配置管理,是大型 Python 項(xiàng)目中最容易被忽視、卻最容易引發(fā)生產(chǎn)事故的環(huán)節(jié)之一。

今天,我將結(jié)合多年 Python 實(shí)戰(zhàn)經(jīng)驗(yàn),系統(tǒng)講解配置管理的三個(gè)層次:環(huán)境變量、配置文件、配置中心,以及如何在不同場(chǎng)景下選擇合適的方案,構(gòu)建穩(wěn)定、安全、可維護(hù)的配置體系。

一、配置管理的核心矛盾

在深入技術(shù)細(xì)節(jié)之前,先來理解配置管理要解決的根本問題。

1.1 三個(gè)環(huán)境,三張面孔

任何一個(gè)稍具規(guī)模的 Python 項(xiàng)目,都會(huì)面對(duì)至少三套環(huán)境:

  • 開發(fā)環(huán)境(Development):本地調(diào)試,連接本地?cái)?shù)據(jù)庫(kù),開啟詳細(xì)日志
  • 測(cè)試環(huán)境(Staging):接近生產(chǎn),用于集成測(cè)試和驗(yàn)收
  • 生產(chǎn)環(huán)境(Production):真實(shí)用戶訪問,嚴(yán)格權(quán)限,關(guān)閉調(diào)試信息

同一份代碼,在三套環(huán)境里運(yùn)行時(shí),數(shù)據(jù)庫(kù)地址、API 密鑰、日志級(jí)別、第三方服務(wù) URL,都可能截然不同。如何讓代碼在不修改的情況下,自動(dòng)適應(yīng)不同環(huán)境?這是配置管理要解決的第一個(gè)核心問題。

1.2 安全與便利的博弈

把密碼寫在代碼里,方便但危險(xiǎn);把密碼加密存儲(chǔ),安全但復(fù)雜。配置管理始終在安全與便利之間尋找平衡點(diǎn)。

1.3 配置管理的黃金原則

在討論具體方案之前,先記住這個(gè)原則:"The Twelve-Factor App"第三條:將配置存儲(chǔ)在環(huán)境中,而不是代碼里。

二、第一層:環(huán)境變量——最簡(jiǎn)單的隔離

2.1 為什么首選環(huán)境變量

環(huán)境變量是配置管理的基石,理由有三:

  • 天然隔離:不同環(huán)境設(shè)置不同的環(huán)境變量,代碼無需修改
  • 安全存儲(chǔ):密鑰不會(huì)出現(xiàn)在版本控制系統(tǒng)中
  • 云原生友好:Kubernetes、Docker、各大云平臺(tái)都原生支持

2.2 最簡(jiǎn)單的用法

import os

# 基礎(chǔ)用法:讀取環(huán)境變量
DATABASE_URL = os.environ["DATABASE_URL"]  # 不存在則拋出 KeyError
DATABASE_URL = os.environ.get("DATABASE_URL", "sqlite:///dev.db")  # 提供默認(rèn)值

# 類型轉(zhuǎn)換:環(huán)境變量都是字符串
DEBUG = os.environ.get("DEBUG", "false").lower() == "true"
PORT = int(os.environ.get("PORT", "8000"))
MAX_WORKERS = int(os.environ.get("MAX_WORKERS", "4"))

2.3 使用 python-dotenv 管理本地開發(fā)配置

生產(chǎn)環(huán)境通過 CI/CD 注入環(huán)境變量,但本地開發(fā)怎么辦?總不能每次都手動(dòng) export。python-dotenv 優(yōu)雅地解決了這個(gè)問題。

安裝:

pip install python-dotenv

項(xiàng)目根目錄創(chuàng)建 .env 文件:

# .env(絕對(duì)不能提交到 Git?。?
DATABASE_URL=postgresql://user:password@localhost:5432/devdb
REDIS_URL=redis://localhost:6379/0
SECRET_KEY=your-local-secret-key-never-use-in-production
DEBUG=true
LOG_LEVEL=DEBUG

.gitignore 中添加:

.env
.env.local
.env.*.local

代碼中加載:

from dotenv import load_dotenv
import os

# 加載 .env 文件(生產(chǎn)環(huán)境中 .env 文件不存在,不影響運(yùn)行)
load_dotenv()

DATABASE_URL = os.environ["DATABASE_URL"]
DEBUG = os.environ.get("DEBUG", "false").lower() == "true"

提供 .env.example 模板(可以提交到 Git):

# .env.example — 復(fù)制為 .env 并填寫真實(shí)值
DATABASE_URL=postgresql://user:password@host:5432/dbname
REDIS_URL=redis://host:6379/0
SECRET_KEY=your-secret-key-here
DEBUG=false
LOG_LEVEL=INFO

2.4 環(huán)境變量的局限性

環(huán)境變量適合存儲(chǔ)少量、簡(jiǎn)單的鍵值對(duì),但面對(duì)復(fù)雜的嵌套配置時(shí),它開始力不從心:

# 嘗試用環(huán)境變量表達(dá)嵌套配置——丑陋且難以維護(hù)
DATABASE_PRIMARY_HOST=db1.example.com
DATABASE_PRIMARY_PORT=5432
DATABASE_REPLICA_HOST=db2.example.com
DATABASE_REPLICA_PORT=5432

這時(shí)候,就需要第二層方案:配置文件。

三、第二層:配置文件——結(jié)構(gòu)化的力量

3.1 常見配置文件格式對(duì)比

格式優(yōu)點(diǎn)缺點(diǎn)適用場(chǎng)景
INI簡(jiǎn)單易讀不支持嵌套簡(jiǎn)單項(xiàng)目
JSON結(jié)構(gòu)清晰不支持注釋API 配置
YAML可讀性強(qiáng),支持注釋縮進(jìn)敏感大多數(shù)項(xiàng)目
TOML語義明確生態(tài)較新Python 項(xiàng)目(pyproject.toml)

3.2 使用 YAML 配置文件

YAML 是目前最流行的配置文件格式,兼具可讀性和表達(dá)能力。

項(xiàng)目配置文件結(jié)構(gòu):

config/
├── base.yaml          # 所有環(huán)境共享的基礎(chǔ)配置
├── development.yaml   # 開發(fā)環(huán)境覆蓋配置
├── staging.yaml       # 測(cè)試環(huán)境覆蓋配置
└── production.yaml    # 生產(chǎn)環(huán)境覆蓋配置

base.yaml:

# 所有環(huán)境共享的默認(rèn)配置
app:
  name: "My Application"
  version: "1.0.0"
  timezone: "Asia/Shanghai"

server:
  host: "0.0.0.0"
  port: 8000
  workers: 4

logging:
  level: "INFO"
  format: "json"
  
cache:
  ttl: 3600
  max_size: 1000

development.yaml:

# 僅覆蓋開發(fā)環(huán)境特有的配置
server:
  port: 8080
  
logging:
  level: "DEBUG"
  format: "console"  # 開發(fā)環(huán)境用人類可讀格式

database:
  url: "postgresql://dev:dev@localhost:5432/myapp_dev"
  pool_size: 2
  echo: true  # 打印 SQL 語句

cache:
  ttl: 60  # 開發(fā)環(huán)境緩存時(shí)間短

production.yaml:

server:
  workers: 16  # 生產(chǎn)環(huán)境更多 worker

logging:
  level: "WARNING"  # 生產(chǎn)環(huán)境減少日志量

database:
  pool_size: 20
  pool_timeout: 30
  echo: false

3.3 實(shí)現(xiàn)配置合并加載器

import yaml
import os
from pathlib import Path
from typing import Any


def deep_merge(base: dict, override: dict) -> dict:
    """
    深度合并兩個(gè)字典,override 的值會(huì)覆蓋 base 的值
    支持嵌套字典的遞歸合并
    """
    result = base.copy()
    for key, value in override.items():
        if key in result and isinstance(result[key], dict) and isinstance(value, dict):
            result[key] = deep_merge(result[key], value)
        else:
            result[key] = value
    return result


def load_config() -> dict:
    """
    按優(yōu)先級(jí)加載配置:
    base.yaml < {env}.yaml < 環(huán)境變量
    """
    config_dir = Path(__file__).parent / "config"
    env = os.environ.get("APP_ENV", "development")
    
    # 1. 加載基礎(chǔ)配置
    base_path = config_dir / "base.yaml"
    with open(base_path) as f:
        config = yaml.safe_load(f)
    
    # 2. 加載環(huán)境特定配置(覆蓋基礎(chǔ)配置)
    env_path = config_dir / f"{env}.yaml"
    if env_path.exists():
        with open(env_path) as f:
            env_config = yaml.safe_load(f) or {}
        config = deep_merge(config, env_config)
    
    # 3. 環(huán)境變量中的配置優(yōu)先級(jí)最高
    # 支持 APP__DATABASE__URL 形式的嵌套鍵
    for key, value in os.environ.items():
        if key.startswith("APP__"):
            keys = key[5:].lower().split("__")
            nested = config
            for k in keys[:-1]:
                nested = nested.setdefault(k, {})
            nested[keys[-1]] = value
    
    return config


# 全局配置單例
_config = None

def get_config() -> dict:
    global _config
    if _config is None:
        _config = load_config()
    return _config

使用示例:

from config_loader import get_config

config = get_config()

# 訪問配置
db_url = config["database"]["url"]
log_level = config["logging"]["level"]
server_port = config["server"]["port"]

3.4 使用 Pydantic 實(shí)現(xiàn)類型安全的配置

原始字典沒有類型檢查,容易出錯(cuò)。用 Pydantic 定義強(qiáng)類型配置模型,在應(yīng)用啟動(dòng)時(shí)就能發(fā)現(xiàn)配置錯(cuò)誤:

from pydantic import BaseModel, validator, Field
from pydantic_settings import BaseSettings
from typing import Optional
import os


class DatabaseConfig(BaseModel):
    url: str
    pool_size: int = 10
    pool_timeout: int = 30
    echo: bool = False
    
    @validator("pool_size")
    def validate_pool_size(cls, v):
        if v < 1 or v > 100:
            raise ValueError("pool_size 必須在 1-100 之間")
        return v


class ServerConfig(BaseModel):
    host: str = "0.0.0.0"
    port: int = Field(8000, ge=1, le=65535)
    workers: int = Field(4, ge=1)


class LoggingConfig(BaseModel):
    level: str = "INFO"
    format: str = "json"
    
    @validator("level")
    def validate_level(cls, v):
        valid_levels = {"DEBUG", "INFO", "WARNING", "ERROR", "CRITICAL"}
        if v.upper() not in valid_levels:
            raise ValueError(f"日志級(jí)別必須是 {valid_levels} 之一")
        return v.upper()


class AppConfig(BaseSettings):
    """
    頂層配置模型
    自動(dòng)從環(huán)境變量讀取(優(yōu)先級(jí)高于默認(rèn)值)
    """
    env: str = Field("development", env="APP_ENV")
    
    database: DatabaseConfig
    server: ServerConfig = ServerConfig()
    logging: LoggingConfig = LoggingConfig()
    
    class Config:
        env_prefix = "APP_"
        env_nested_delimiter = "__"


# 使用方式
def create_config() -> AppConfig:
    raw_config = load_config()  # 從 YAML 文件加載
    return AppConfig(**raw_config)


# 全局配置
settings = create_config()

# 類型安全的訪問
print(settings.database.url)       # str
print(settings.server.port)        # int,不需要類型轉(zhuǎn)換
print(settings.logging.level)      # 已驗(yàn)證為合法值

四、第三層:配置中心——分布式系統(tǒng)的救星

當(dāng)系統(tǒng)演進(jìn)為微服務(wù)架構(gòu),配置文件方案開始暴露短板:

  • 配置變更需要重新部署:改一個(gè)參數(shù),所有服務(wù)都要重啟
  • 多服務(wù)配置不一致:十個(gè)服務(wù),十套配置,維護(hù)噩夢(mèng)
  • 敏感信息難以集中管控:數(shù)據(jù)庫(kù)密碼散落各處

這時(shí),配置中心登場(chǎng)了。

4.1 HashiCorp Vault:密鑰管理的王者

Vault 專門用于管理敏感配置(密鑰、證書、API Token):

import hvac
import os
from functools import lru_cache


class VaultConfigProvider:
    """從 HashiCorp Vault 讀取敏感配置"""
    
    def __init__(self):
        self.client = hvac.Client(
            url=os.environ["VAULT_ADDR"],
            token=os.environ["VAULT_TOKEN"]
        )
    
    def get_secret(self, path: str) -> dict:
        """讀取 KV v2 格式的密鑰"""
        response = self.client.secrets.kv.v2.read_secret_version(
            path=path,
            mount_point="secret"
        )
        return response["data"]["data"]
    
    def get_database_credentials(self) -> dict:
        """獲取動(dòng)態(tài)數(shù)據(jù)庫(kù)憑證(每次調(diào)用都獲取新的臨時(shí)憑證)"""
        response = self.client.secrets.database.generate_credentials(
            name="my-app-role"
        )
        return {
            "username": response["data"]["username"],
            "password": response["data"]["password"],
            "lease_id": response["lease_id"],
            "lease_duration": response["lease_duration"]
        }


@lru_cache(maxsize=None)
def get_vault_provider() -> VaultConfigProvider:
    return VaultConfigProvider()


# 在應(yīng)用啟動(dòng)時(shí)獲取敏感配置
vault = get_vault_provider()

# 獲取數(shù)據(jù)庫(kù)密碼(不再硬編碼)
db_secret = vault.get_secret("myapp/database")
DATABASE_URL = f"postgresql://{db_secret['username']}:{db_secret['password']}@{db_secret['host']}/myapp"

4.2 動(dòng)態(tài)配置:運(yùn)行時(shí)熱更新

某些配置需要在不重啟服務(wù)的情況下動(dòng)態(tài)調(diào)整(如限流閾值、功能開關(guān))。使用 Redis 或 etcd 實(shí)現(xiàn)動(dòng)態(tài)配置:

import redis
import json
import threading
from typing import Any, Callable


class DynamicConfig:
    """
    基于 Redis 的動(dòng)態(tài)配置,支持熱更新
    
    使用 Redis Pub/Sub 監(jiān)聽配置變更
    """
    
    def __init__(self, redis_url: str):
        self.redis = redis.from_url(redis_url)
        self._cache = {}
        self._listeners: dict[str, list[Callable]] = {}
        self._start_listener()
    
    def get(self, key: str, default: Any = None) -> Any:
        """獲取配置值(優(yōu)先從本地緩存讀?。?""
        if key not in self._cache:
            value = self.redis.get(f"config:{key}")
            if value:
                self._cache[key] = json.loads(value)
            else:
                return default
        return self._cache.get(key, default)
    
    def set(self, key: str, value: Any) -> None:
        """設(shè)置配置值,并通知所有實(shí)例"""
        self.redis.set(f"config:{key}", json.dumps(value))
        self.redis.publish("config:changes", json.dumps({"key": key, "value": value}))
    
    def on_change(self, key: str, callback: Callable) -> None:
        """注冊(cè)配置變更回調(diào)"""
        if key not in self._listeners:
            self._listeners[key] = []
        self._listeners[key].append(callback)
    
    def _start_listener(self) -> None:
        """在后臺(tái)線程監(jiān)聽配置變更"""
        def listen():
            pubsub = self.redis.pubsub()
            pubsub.subscribe("config:changes")
            for message in pubsub.listen():
                if message["type"] == "message":
                    data = json.loads(message["data"])
                    key = data["key"]
                    self._cache[key] = data["value"]
                    # 觸發(fā)回調(diào)
                    for callback in self._listeners.get(key, []):
                        callback(data["value"])
        
        thread = threading.Thread(target=listen, daemon=True)
        thread.start()


# 使用示例
dynamic_config = DynamicConfig(redis_url="redis://localhost:6379/1")

# 注冊(cè)限流閾值變更回調(diào)
def on_rate_limit_change(new_value):
    print(f"限流閾值已更新為: {new_value} 次/分鐘")
    # 實(shí)時(shí)更新限流器配置

dynamic_config.on_change("rate_limit_per_minute", on_rate_limit_change)

# 讀取動(dòng)態(tài)配置
rate_limit = dynamic_config.get("rate_limit_per_minute", default=100)
feature_enabled = dynamic_config.get("feature_new_ui", default=False)

# 運(yùn)維人員可以在不重啟服務(wù)的情況下調(diào)整
# dynamic_config.set("rate_limit_per_minute", 200)

五、綜合實(shí)戰(zhàn):構(gòu)建完整的配置管理體系

5.1 分層配置架構(gòu)圖

┌─────────────────────────────────────────────────┐
│                  應(yīng)用配置層次                     │
├─────────────────────────────────────────────────┤
│  優(yōu)先級(jí)(從高到低)                               │
│                                                  │
│  1. 命令行參數(shù)    --port=8080                    │
│                        ↓                         │
│  2. 環(huán)境變量     APP__SERVER__PORT=8080          │
│                        ↓                         │
│  3. 配置中心     Vault / etcd / Redis            │
│                        ↓                         │
│  4. 環(huán)境配置文件  config/production.yaml          │
│                        ↓                         │
│  5. 基礎(chǔ)配置文件  config/base.yaml               │
│                        ↓                         │
│  6. 代碼默認(rèn)值   port: int = 8000                │
└─────────────────────────────────────────────────┘

5.2 完整的配置管理類

import os
import yaml
from pathlib import Path
from functools import lru_cache
from pydantic import BaseModel, validator
from pydantic_settings import BaseSettings
from typing import Optional


class DatabaseSettings(BaseModel):
    url: str = "sqlite:///./dev.db"
    pool_size: int = 5
    echo: bool = False


class RedisSettings(BaseModel):
    url: str = "redis://localhost:6379/0"
    max_connections: int = 10


class AppSettings(BaseSettings):
    # 基礎(chǔ)信息
    app_name: str = "MyApp"
    app_env: str = "development"
    debug: bool = False
    secret_key: str = "change-this-in-production"
    
    # 子配置
    database: DatabaseSettings = DatabaseSettings()
    redis: RedisSettings = RedisSettings()
    
    # 功能開關(guān)
    feature_new_dashboard: bool = False
    
    class Config:
        env_file = ".env"
        env_prefix = "APP_"
        env_nested_delimiter = "__"
    
    @validator("secret_key")
    def validate_secret_key(cls, v, values):
        env = values.get("app_env", "development")
        if env == "production" and v == "change-this-in-production":
            raise ValueError("生產(chǎn)環(huán)境必須設(shè)置真實(shí)的 SECRET_KEY!")
        return v
    
    @validator("app_env")
    def validate_env(cls, v):
        allowed = {"development", "staging", "production", "test"}
        if v not in allowed:
            raise ValueError(f"app_env 必須是 {allowed} 之一")
        return v
    
    def is_production(self) -> bool:
        return self.app_env == "production"
    
    def is_development(self) -> bool:
        return self.app_env == "development"


@lru_cache(maxsize=1)
def get_settings() -> AppSettings:
    """
    獲取全局配置單例(使用 lru_cache 確保只初始化一次)
    在測(cè)試中可以通過 get_settings.cache_clear() 重置
    """
    return AppSettings()


# 在應(yīng)用的任何地方使用
settings = get_settings()

print(f"運(yùn)行環(huán)境: {settings.app_env}")
print(f"數(shù)據(jù)庫(kù): {settings.database.url}")
print(f"調(diào)試模式: {settings.debug}")

5.3 測(cè)試中的配置隔離

# tests/conftest.py
import pytest
from unittest.mock import patch
from config import get_settings, AppSettings


@pytest.fixture
def test_settings():
    """提供測(cè)試專用的配置"""
    test_config = AppSettings(
        app_env="test",
        debug=True,
        database={"url": "sqlite:///./test.db", "echo": True},
        secret_key="test-secret-key"
    )
    return test_config


@pytest.fixture(autouse=True)
def override_settings(test_settings):
    """自動(dòng)替換所有測(cè)試中的配置"""
    # 清除 lru_cache 并替換
    get_settings.cache_clear()
    with patch("config.get_settings", return_value=test_settings):
        yield
    get_settings.cache_clear()

六、最佳實(shí)踐清單

在我經(jīng)歷過數(shù)十個(gè) Python 項(xiàng)目之后,總結(jié)出以下配置管理鐵律:

安全規(guī)范:

  • 敏感信息(密碼、API Key)只能通過環(huán)境變量或配置中心注入,絕不寫入代碼或配置文件
  • .env 文件必須加入 .gitignore,倉(cāng)庫(kù)中只保留 .env.example
  • 定期輪換密鑰,使用 Vault 的動(dòng)態(tài)憑證功能減少泄露風(fēng)險(xiǎn)

結(jié)構(gòu)規(guī)范:

  • 使用 Pydantic 定義配置模型,應(yīng)用啟動(dòng)時(shí)進(jìn)行驗(yàn)證,讓配置錯(cuò)誤在部署階段就暴露
  • 配置文件按環(huán)境分層,base → 環(huán)境專屬,使用深度合并
  • 配置值通過依賴注入傳遞,避免在代碼深處直接調(diào)用 os.environ

運(yùn)維規(guī)范:

  • 提供 APP_ENV 變量明確標(biāo)識(shí)環(huán)境,防止誤操作
  • 關(guān)鍵配置加載失敗時(shí),應(yīng)用應(yīng)拒絕啟動(dòng)并給出明確錯(cuò)誤信息
  • 建立配置變更審計(jì)日志,每次生產(chǎn)配置修改都有記錄

七、總結(jié)與展望

配置管理是 Python 工程化體系中的基礎(chǔ)設(shè)施,它的質(zhì)量直接影響系統(tǒng)的安全性、可維護(hù)性和團(tuán)隊(duì)協(xié)作效率。

我們從三個(gè)層次進(jìn)行了深入探討:環(huán)境變量適合簡(jiǎn)單鍵值對(duì)和敏感信息的隔離;配置文件適合結(jié)構(gòu)化的靜態(tài)配置,通過 Pydantic 實(shí)現(xiàn)類型安全;配置中心適合分布式系統(tǒng)中需要集中管控或動(dòng)態(tài)更新的配置。

三者不是互斥的,而是互補(bǔ)的。成熟的項(xiàng)目往往三者并用,根據(jù)配置的性質(zhì)選擇合適的存儲(chǔ)方式。

配置管理沒有銀彈,但有一條永恒的原則:讓配置錯(cuò)誤盡早暴露,而不是在凌晨?jī)牲c(diǎn)讓你從睡夢(mèng)中驚醒。

你在項(xiàng)目中是如何管理不同環(huán)境的配置的?有沒有遇到過因?yàn)榕渲没靵y引發(fā)的生產(chǎn)事故?歡迎在評(píng)論區(qū)分享你的經(jīng)驗(yàn)和教訓(xùn),讓我們一起把這道坎踩實(shí)。

以上就是從環(huán)境變量到配置中心帶你掌握Python多環(huán)境配置的詳細(xì)內(nèi)容,更多關(guān)于Python多環(huán)境配置的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • 詳解Python的字符串格式化

    詳解Python的字符串格式化

    這篇文章主要介紹了Python的字符串格式化,python的format函數(shù)怎么用,這篇文章向大家介紹format函數(shù)用法,需要的朋友可以參考下
    2023-04-04
  • Python獲取瀏覽器Cookies的方法總結(jié)

    Python獲取瀏覽器Cookies的方法總結(jié)

    在現(xiàn)代網(wǎng)絡(luò)應(yīng)用和開發(fā)中,使用Cookies是一種常見的方式,它們用于存儲(chǔ)用戶信息、會(huì)話狀態(tài)等,本文為大家整理了多種Python獲取瀏覽器Cookies的方法,希望對(duì)大家有所幫助
    2023-12-12
  • 讓python json encode datetime類型

    讓python json encode datetime類型

    python2.6+ 自帶的json模塊,不支持datetime的json encode,每次都需要手動(dòng)轉(zhuǎn)為字符串,很累人,我們可以自己封裝一個(gè)簡(jiǎn)單的方法處理此問題。
    2010-12-12
  • python異步的ASGI與Fast Api實(shí)現(xiàn)

    python異步的ASGI與Fast Api實(shí)現(xiàn)

    本文主要介紹了python異步的ASGI與Fast Api實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-07-07
  • 基于Python+OpenCV制作屏幕錄制工具

    基于Python+OpenCV制作屏幕錄制工具

    這篇文章主要介紹了如何利用Python?OpenCV實(shí)現(xiàn)屏幕錄制工具的制作,文中的示例代碼講解詳細(xì),對(duì)我們的學(xué)習(xí)和工作有一定的價(jià)值,感興趣的可以學(xué)習(xí)一下
    2022-01-01
  • python中的錯(cuò)誤處理

    python中的錯(cuò)誤處理

    異常是指程序中的例外,違例情況。異常機(jī)制是指程序出現(xiàn)錯(cuò)誤后,程序的處理方法。當(dāng)出現(xiàn)錯(cuò)誤后,程序的執(zhí)行流程發(fā)生改變,程序的控制權(quán)轉(zhuǎn)移到異常處理。
    2016-04-04
  • Python使用asyncio實(shí)現(xiàn)異步操作的示例

    Python使用asyncio實(shí)現(xiàn)異步操作的示例

    本文主要介紹了Python使用asyncio實(shí)現(xiàn)異步操作的示例,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2025-01-01
  • Python greenlet實(shí)現(xiàn)原理和使用示例

    Python greenlet實(shí)現(xiàn)原理和使用示例

    這篇文章主要介紹了Python greenlet實(shí)現(xiàn)原理和使用示例,greenlet是Python中的一個(gè)并行處理庫(kù),需要的朋友可以參考下
    2014-09-09
  • python中如何正確使用正則表達(dá)式的詳細(xì)模式(Verbose mode expression)

    python中如何正確使用正則表達(dá)式的詳細(xì)模式(Verbose mode expression)

    許多程序設(shè)計(jì)語言都支持利用正則表達(dá)式進(jìn)行字符串操作,python自然也不例外,下面這篇文章主要給大家介紹了關(guān)于在python中如何正確使用正則表達(dá)式的詳細(xì)模式(Verbose mode expression)的相關(guān)資料,需要的朋友可以參考借鑒,下面來一起看看吧。
    2017-11-11
  • Python字符串詳細(xì)介紹

    Python字符串詳細(xì)介紹

    這篇文章主要介紹了Python字符串詳解,本文講解了字符串相關(guān)知識(shí)、字符串的一些特性、原始字符串、unicode字符串、字符串的常用操作方法、內(nèi)建函數(shù)列表等內(nèi)容,需要的朋友可以參考下
    2015-05-05

最新評(píng)論

晋宁县| 分宜县| 浑源县| 桦甸市| 白沙| 龙山县| 苗栗县| 青神县| 营口市| 周口市| 沙田区| 成安县| 精河县| 河津市| 西乌珠穆沁旗| 万盛区| 融水| 和龙市| 漳平市| 宁德市| 肃北| 错那县| 富裕县| 杨浦区| 伊春市| 峨边| 武冈市| 耒阳市| 东阿县| 静安区| 华宁县| 杭锦后旗| 嘉定区| 汶川县| 晋州市| 墨脱县| 嘉定区| 渑池县| 永年县| 秦皇岛市| 池州市|