bbc7bc520e
Co-Authored-By: Claude Code <noreply@anthropic.com>
47 lines
2.1 KiB
Python
47 lines
2.1 KiB
Python
"""Task 10: /api/public/brand + /api/public/avatar——品牌白名单下发。
|
|
|
|
红线:
|
|
- 品牌端点**显式字段白名单**序列化(BRAND_FIELDS)——绝不序列化整个
|
|
config(api_key/smtp 等内部字段永不出现在响应);
|
|
- 响应头 Access-Control-Allow-Origin: *(挂件嵌在客户站,跨源加载);
|
|
- ?site=<slug> 站点覆盖(空域名站点如 es 靠嵌入代码 data-site 接入),
|
|
未知 site 回退租户默认门面;
|
|
- 头像按租户解析 seed_profiles/<slug>/assets/,两租户各归各。
|
|
"""
|
|
|
|
BRAND_EXPECTED = {"slug", "title", "color", "avatar", "welcome", "topics",
|
|
"placeholder", "whatsapp", "email", "privacy_url"}
|
|
|
|
|
|
def test_brand_whitelist_only(app_client):
|
|
r = app_client.get("/api/public/brand")
|
|
assert r.status_code == 200
|
|
assert set(r.json().keys()) == BRAND_EXPECTED # 白名单,绝不多吐
|
|
assert "api_key" not in r.text and "smtp" not in r.text.lower()
|
|
assert r.headers["access-control-allow-origin"] == "*"
|
|
|
|
|
|
def test_brand_site_overlay(app_client):
|
|
h = {"host": "chat2.agent.hnxinyouhe.com"}
|
|
r = app_client.get("/api/public/brand?site=es", headers=h)
|
|
assert r.json()["title"] == "HESUPIPE Soporte" # 站点覆盖生效
|
|
r2 = app_client.get("/api/public/brand", headers=h)
|
|
assert r2.json()["title"] == "HESUPIPE Support" # 不带 site = 租户默认门面
|
|
r3 = app_client.get("/api/public/brand?site=nope", headers=h)
|
|
assert r3.json()["title"] == "HESUPIPE Support" # 未知 site 回退
|
|
|
|
|
|
def test_brand_carries_tenant_slug(app_client):
|
|
# slug 供客户端拼租户化 key(host id / storage key),jiancai 域必回 jiancai
|
|
r = app_client.get("/api/public/brand")
|
|
assert r.json()["slug"] == "jiancai"
|
|
|
|
|
|
def test_avatar_served_per_tenant(app_client):
|
|
r = app_client.get("/api/public/avatar", headers={"host": "chat.agent.hnxinyouhe.com"})
|
|
assert r.status_code == 200 and r.headers["content-type"].startswith("image/")
|
|
# 两租户头像内容不同(字节级对比两租户的 avatar 响应)
|
|
r_jc = app_client.get("/api/public/avatar") # base_url = jiancai 域
|
|
assert r_jc.status_code == 200
|
|
assert r.content != r_jc.content
|