"""机构名录栏目文章:工作人员写入 → 门户公开读取。""" import pytest from fastapi.testclient import TestClient from app.core.config import get_settings from app.core.security import create_access_token @pytest.fixture def client(monkeypatch): monkeypatch.setenv("JWT_SECRET", "test-secret-must-be-32-characters!") monkeypatch.setenv("API_PAYLOAD_ENCRYPT", "false") get_settings.cache_clear() if not get_settings().database_url.strip(): pytest.skip("DATABASE_URL 为空") from app.main import create_app with TestClient(create_app()) as api: yield api get_settings.cache_clear() def _headers(token_type: str) -> dict[str, str]: return {"Authorization": f"Bearer {create_access_token('1', token_type)}"} def _minio_ready() -> bool: try: from app.services.storage import ensure_buckets ensure_buckets() return True except Exception: return False def _clear_category(client, staff: dict[str, str]) -> None: listed = client.get("/api/admin/about/articles/institution_directories", headers=staff) assert listed.status_code == 200, listed.text for item in listed.json().get("items") or []: deleted = client.delete(f"/api/admin/home/articles/{item['id']}", headers=staff) assert deleted.status_code in (200, 204), deleted.text def test_institution_directory_publish_filter_placeholder_and_attachment(client): if not _minio_ready(): pytest.skip("MinIO 不可达") staff = _headers("staff") article_ids: list[int] = [] file_ids: list[int] = [] try: _clear_category(client, staff) empty = client.get("/api/site/about/articles/institution_directories") assert empty.status_code == 200, empty.text assert "暂无机构名录" in empty.text pdf = client.post( "/api/admin/files", headers=staff, data={"bucket": "public"}, files={"file": ("名录.pdf", b"%PDF-1.4\nroster", "application/pdf")}, ) assert pdf.status_code == 200, pdf.text file_ids.append(pdf.json()["id"]) created = client.post( "/api/admin/home/articles", headers=staff, json={ "category": "institution_directories", "title": "甘肃省房地产价格评估行业协会单位会员名录(2025年6月)", "publishedAt": "2025-06-05T08:00:00", "published": True, "bodyHtml": ( "
兰州市
| 甘肃中瑞房地产资产评估有限公司 |
未发布名录
", "attachmentFileIds": [], }, ) assert draft.status_code == 200, draft.text article_ids.append(draft.json()["id"]) listed = client.get("/api/site/about/articles/institution_directories") assert listed.status_code == 200, listed.text assert "甘肃省房地产价格评估行业协会单位会员名录(2025年6月)" in listed.text assert "未发布名录" not in listed.text assert "暂无机构名录" not in listed.text detail = client.get(f"/api/site/home/articles/{article_ids[0]}") assert detail.status_code == 200, detail.text body = detail.json()["bodyHtml"] assert "甘肃中瑞房地产资产评估有限公司" in body assert "table" in body.lower() lowered = body.lower() assert "script" not in lowered assert "alert" not in lowered assert [item["filename"] for item in detail.json()["attachments"]] == ["名录.pdf"] hidden = client.get(f"/api/site/home/articles/{article_ids[1]}") assert hidden.status_code == 404 editor = client.get("/api/admin/home", headers=staff) assert editor.status_code == 200, editor.text categories = {item["category"] for item in editor.json()["articles"]} assert "institution_directories" not in categories before = client.get("/api/site/about/articles/institution_directories").text rejected = client.post( "/api/admin/home/articles", headers=_headers("member"), json={ "category": "institution_directories", "title": "会员不得发布名录", "published": True, "bodyHtml": "会员不得发布名录
", "attachmentFileIds": [], }, ) assert rejected.status_code in (401, 403) after = client.get("/api/site/about/articles/institution_directories") assert after.text == before assert "会员不得发布名录" not in after.text renamed = client.put( f"/api/admin/home/articles/{article_ids[0]}", headers=staff, json={ "category": "institution_directories", "title": "甘肃省房地产价格评估行业协会单位会员名录(2025年6月修订)", "publishedAt": "2025-06-05T08:00:00", "published": True, "bodyHtml": "兰州市
| 甘肃中瑞房地产资产评估有限公司 |
名录分页样例-{index:02d}
", "attachmentFileIds": [], }, ) assert created.status_code == 200, created.text article_ids.append(created.json()["id"]) page1 = client.get("/api/site/about/articles/institution_directories?current=1&size=10") assert page1.status_code == 200, page1.text body1 = page1.json() assert body1["total"] == 11 assert body1["current"] == 1 assert body1["size"] == 10 assert len(body1["items"]) == 10 assert body1["items"][0]["title"] == "名录分页样例-10" page2 = client.get("/api/site/about/articles/institution_directories?current=2&size=10") assert page2.status_code == 200, page2.text body2 = page2.json() assert body2["total"] == 11 assert body2["current"] == 2 assert len(body2["items"]) == 1 assert body2["items"][0]["title"] == "名录分页样例-00" size20 = client.get("/api/site/about/articles/institution_directories?current=1&size=20") assert size20.status_code == 200, size20.text assert size20.json()["size"] == 20 assert len(size20.json()["items"]) == 11 bad_size = client.get("/api/site/about/articles/institution_directories?current=1&size=15") assert bad_size.status_code == 200, bad_size.text assert bad_size.json()["size"] == 10 assert len(bad_size.json()["items"]) == 10 finally: for article_id in article_ids: client.delete(f"/api/admin/home/articles/{article_id}", headers=staff) PUBLISHED_TITLES = [ "甘肃省房地产价格评估行业协会单位会员名录(2025年6月)", "甘肃省房地产价格评估行业协会个人会员名录(2025年5月)", "甘肃省房地产价格评估行业协会个人会员名录(2023年6月)", "甘肃省房地产价格评估行业协会单位会员名录(2023年6月)", "甘肃省房地产价格评估行业协会估价师个人会员名录(2022年4月)", "甘肃省房地产价格评估行业协会单位会员名录(2022年4月)", "甘肃省房地产价格评估行业协会估价师个人会员名录(2021年7月)", "甘肃省房地产价格评估行业协会估价师单位会员名录(2021年7月)", "甘肃省房地产价格评估行业协会估价师个人会员名录(2021年5月)", "甘肃省房地产价格评估行业协会单位会员名录(2021年5月)", "甘肃省房地产价格评估行业协会估价师个人会员名录(2020年)", "甘肃省房地产价格评估行业协会单位会员名录(2020年)", "甘肃省最低收费备案标准名单", "甘肃省住房和城乡建设厅关于公布甘肃省房地产估价机构名录的通知", "甘肃省房地产价格评估行业协会单位会员名录", "甘肃省房地产价格评估行业协会估价师个人会员名录(2019年)", ] def test_institution_directory_import_keeps_titles_and_is_idempotent(client): staff = _headers("staff") from app.commands.import_institution_directories import import_institution_directories from app.db import SessionLocal db = SessionLocal() try: _clear_category(client, staff) import_institution_directories(db) listed = client.get("/api/site/about/articles/institution_directories?current=1&size=20") assert listed.status_code == 200, listed.text body = listed.json() assert body["total"] == 16 assert [item["title"] for item in body["items"]] == PUBLISHED_TITLES detail = client.get(f"/api/site/home/articles/{body['items'][0]['id']}") assert detail.status_code == 200, detail.text assert "甘肃中瑞房地产资产评估有限公司" in detail.json()["bodyHtml"] assert "table" in detail.json()["bodyHtml"].lower() import_institution_directories(db) again = client.get("/api/site/about/articles/institution_directories?current=1&size=20") assert again.status_code == 200, again.text titles = [item["title"] for item in again.json()["items"]] assert titles == PUBLISHED_TITLES assert len(titles) == len(set(titles)) finally: db.close() _clear_category(client, staff)