mirror of
https://github.com/cnlimiter/codex-register.git
synced 2026-06-30 11:41:34 +08:00
Merge remote-tracking branch 'origin/master'
This commit is contained in:
@@ -36,6 +36,16 @@ STATIC_DIR = _RESOURCE_ROOT / "static"
|
||||
TEMPLATES_DIR = _RESOURCE_ROOT / "templates"
|
||||
|
||||
|
||||
def _build_static_asset_version(static_dir: Path) -> str:
|
||||
"""基于静态文件最后修改时间生成版本号,避免部署后浏览器继续使用旧缓存。"""
|
||||
latest_mtime = 0
|
||||
if static_dir.exists():
|
||||
for path in static_dir.rglob("*"):
|
||||
if path.is_file():
|
||||
latest_mtime = max(latest_mtime, int(path.stat().st_mtime))
|
||||
return str(latest_mtime or 1)
|
||||
|
||||
|
||||
def create_app() -> FastAPI:
|
||||
"""创建 FastAPI 应用实例"""
|
||||
settings = get_settings()
|
||||
@@ -80,6 +90,7 @@ def create_app() -> FastAPI:
|
||||
|
||||
# 模板引擎
|
||||
templates = Jinja2Templates(directory=str(TEMPLATES_DIR))
|
||||
templates.env.globals["static_version"] = _build_static_asset_version(STATIC_DIR)
|
||||
|
||||
def _auth_token(password: str) -> str:
|
||||
secret = get_settings().webui_secret_key.get_secret_value().encode("utf-8")
|
||||
|
||||
@@ -144,6 +144,7 @@ async def get_email_services_stats():
|
||||
'outlook_count': 0,
|
||||
'custom_count': 0,
|
||||
'temp_mail_count': 0,
|
||||
'duck_mail_count': 0,
|
||||
'tempmail_available': True, # 临时邮箱始终可用
|
||||
'enabled_count': enabled_count
|
||||
}
|
||||
@@ -155,6 +156,8 @@ async def get_email_services_stats():
|
||||
stats['custom_count'] = count
|
||||
elif service_type == 'temp_mail':
|
||||
stats['temp_mail_count'] = count
|
||||
elif service_type == 'duck_mail':
|
||||
stats['duck_mail_count'] = count
|
||||
|
||||
return stats
|
||||
|
||||
@@ -204,6 +207,17 @@ async def get_service_types():
|
||||
{"name": "domain", "label": "邮箱域名", "required": True, "placeholder": "example.com"},
|
||||
{"name": "enable_prefix", "label": "启用前缀", "required": False, "default": True},
|
||||
]
|
||||
},
|
||||
{
|
||||
"value": "duck_mail",
|
||||
"label": "DuckMail",
|
||||
"description": "DuckMail 接口邮箱服务,支持 API Key 私有域名访问",
|
||||
"config_fields": [
|
||||
{"name": "base_url", "label": "API 地址", "required": True, "placeholder": "https://api.duckmail.sbs"},
|
||||
{"name": "default_domain", "label": "默认域名", "required": True, "placeholder": "duckmail.sbs"},
|
||||
{"name": "api_key", "label": "API Key", "required": False, "secret": True},
|
||||
{"name": "password_length", "label": "随机密码长度", "required": False, "default": 12},
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -211,6 +211,9 @@ def _normalize_email_service_config(
|
||||
elif service_type == EmailServiceType.TEMP_MAIL:
|
||||
if 'default_domain' in normalized and 'domain' not in normalized:
|
||||
normalized['domain'] = normalized.pop('default_domain')
|
||||
elif service_type == EmailServiceType.DUCK_MAIL:
|
||||
if 'domain' in normalized and 'default_domain' not in normalized:
|
||||
normalized['default_domain'] = normalized.pop('domain')
|
||||
|
||||
if proxy_url and 'proxy_url' not in normalized:
|
||||
normalized['proxy_url'] = proxy_url
|
||||
@@ -341,6 +344,20 @@ def _run_sync_registration_task(task_uuid: str, email_service_type: str, proxy:
|
||||
logger.info(f"使用数据库 Outlook 账户: {selected_service.name}")
|
||||
else:
|
||||
raise ValueError("所有 Outlook 账户都已注册过 OpenAI 账号,请添加新的 Outlook 账户")
|
||||
elif service_type == EmailServiceType.DUCK_MAIL:
|
||||
from ...database.models import EmailService as EmailServiceModel
|
||||
|
||||
db_service = db.query(EmailServiceModel).filter(
|
||||
EmailServiceModel.service_type == "duck_mail",
|
||||
EmailServiceModel.enabled == True
|
||||
).order_by(EmailServiceModel.priority.asc()).first()
|
||||
|
||||
if db_service and db_service.config:
|
||||
config = _normalize_email_service_config(service_type, db_service.config, actual_proxy_url)
|
||||
crud.update_registration_task(db, task_uuid, email_service_id=db_service.id)
|
||||
logger.info(f"使用数据库 DuckMail 服务: {db_service.name}")
|
||||
else:
|
||||
raise ValueError("没有可用的 DuckMail 邮箱服务,请先在邮箱服务页面添加服务")
|
||||
else:
|
||||
config = email_service_config or {}
|
||||
|
||||
@@ -1069,6 +1086,11 @@ async def get_available_email_services():
|
||||
"available": False,
|
||||
"count": 0,
|
||||
"services": []
|
||||
},
|
||||
"duck_mail": {
|
||||
"available": False,
|
||||
"count": 0,
|
||||
"services": []
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1142,6 +1164,24 @@ async def get_available_email_services():
|
||||
result["temp_mail"]["count"] = len(temp_mail_services)
|
||||
result["temp_mail"]["available"] = len(temp_mail_services) > 0
|
||||
|
||||
duck_mail_services = db.query(EmailServiceModel).filter(
|
||||
EmailServiceModel.service_type == "duck_mail",
|
||||
EmailServiceModel.enabled == True
|
||||
).order_by(EmailServiceModel.priority.asc()).all()
|
||||
|
||||
for service in duck_mail_services:
|
||||
config = service.config or {}
|
||||
result["duck_mail"]["services"].append({
|
||||
"id": service.id,
|
||||
"name": service.name,
|
||||
"type": "duck_mail",
|
||||
"default_domain": config.get("default_domain"),
|
||||
"priority": service.priority
|
||||
})
|
||||
|
||||
result["duck_mail"]["count"] = len(duck_mail_services)
|
||||
result["duck_mail"]["available"] = len(duck_mail_services) > 0
|
||||
|
||||
return result
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user