事實盤點,未做軸線判斷。URL prefix =
/api/1.0。@jwt_required 以 route method 上的裝飾器為準。 「現況守門」= app-service 層是否有 role/admin/manager guard(ForbiddenErroron role/is_admin/participant.role)。 盤點日期 2026-07-07,branchfix/v1.8.0-bugs。本檔涵蓋含 write method 或敏感 GET 的模組。 跳過(無 write / 無敏感 GET):
api/translate(POST 實為翻譯查詢、無寫入無敏感檔)、api/issue(僅 GET get_members)、api/label(僅 GET menu)—— 詳見末段「跳過模組」。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/integrations/google-drive |
DELETE | api/cloud_integration/routes/google_drive_integration_route.py:41 |
是 | google_drive_integration_service.disconnect(is_admin=...) |
已有: if not is_admin and not _is_super_admin → ForbiddenError(GRC_NOT_ADMIN) @ app/cloud_integration/service/google_drive_integration_service.py:189 |
admin/super-admin 守門 |
/api/1.0/integrations/google-drive/auth-url |
POST | api/cloud_integration/routes/google_drive_integration_route.py:58 |
是 | google_drive_integration_service.build_auth_url(is_admin=...) |
已有: if not is_admin → ForbiddenError(GRC_NOT_ADMIN) @ app/cloud_integration/service/google_drive_integration_service.py:66 |
admin 守門 |
/api/1.0/integrations/google-drive/callback |
GET | api/cloud_integration/routes/google_drive_integration_route.py:73 |
否 | google_drive_integration_service.handle_callback(code, state) |
無 JWT | 刻意公開(OAuth callback);auth 靠 state token(cloud-integrations#2/#4) |
/api/1.0/integrations/google-drive/sync-jobs/<uid>/retry |
POST | api/cloud_integration/routes/google_drive_sync_route.py:84 |
是 | drive_sync_admin_service.manual_retry(is_admin=...) |
已有: if not is_admin → ForbiddenError(GRC_NOT_ADMIN) @ app/cloud_integration/service/drive_sync_admin_service.py:110 |
admin 守門 |
/api/1.0/integrations/google-drive/projects/<project_uid>/init-folders |
POST | api/cloud_integration/routes/google_drive_sync_route.py:105 |
是 | drive_sync_admin_service.trigger_init_project_folders(...) |
僅 JWT | 刻意不加 is_admin gate(避免擋非 tenant-admin 的 project manager)— 註解 @ drive_sync_admin_service.py:127-129 |
/api/1.0/integrations/google-drive/projects/<project_uid>/verify-and-repair-folders |
POST | api/cloud_integration/routes/google_drive_sync_route.py:136 |
是 | drive_project_verify_service.verify_and_repair(...) |
已有: if participant is None or participant.role != "manager" → ForbiddenError(GRC_NOT_MANAGER) @ app/cloud_integration/service/drive_project_verify_service.py:129 |
project manager 守門 |
/api/1.0/integrations/google-drive/tenant/rebuild-all |
POST | api/cloud_integration/routes/google_drive_sync_route.py:164 |
是 | drive_sync_admin_service.rebuild_all_for_tenant(is_admin=...) |
已有: if not is_admin → ForbiddenError(GRC_NOT_ADMIN) @ app/cloud_integration/service/drive_sync_admin_service.py:157 |
admin 守門;破壞性操作 |
/api/1.0/integrations/google-drive/webhook/register |
POST | api/cloud_integration/routes/google_drive_sync_route.py:195 |
是 | webhook_channel_manager.register_for_tenant(...) + orchestration |
僅 JWT | doc 註明「admin only」但 service 端未見 is_admin guard — 僅 @jwt_required |
/api/1.0/webhooks/google-drive/<int:tenant_id> |
POST | api/cloud_integration/routes/google_drive_webhook_route.py:39 |
否 | google_drive_webhook_service.handle_notification(...) |
無 JWT | 刻意公開(Drive push webhook);auth 靠 X-Goog-Channel-Token header(永遠回 200) |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/feedbacks |
POST | api/feedback/routes/feedback_route.py:26 |
是 | feedback_service.get_feedbacks_and_pager(...) |
僅 JWT | POST 實為分頁查詢(讀) |
/api/1.0/feedback |
POST | api/feedback/routes/feedback_route.py:52 |
是 | feedback_service.add_feedback(...) |
僅 JWT | 建立 feedback |
/api/1.0/feedback/<uid> |
PUT | api/feedback/routes/feedback_route.py:70 |
是 | feedback_service.update_feedback(...) |
僅 JWT | 無 owner check |
/api/1.0/feedback/<uid> |
DELETE | api/feedback/routes/feedback_route.py:89 |
是 | feedback_service.delete_feedback(uid, login_name) |
僅 JWT | 傳 login_name 但無 owner/role gate |
/api/1.0/feedback/file/<uid>/<file_uid> |
DELETE | api/feedback/routes/feedback_route.py:99 |
是 | feedback_service.delete_feedback_file(uid, file_uid) |
僅 JWT | 無 owner check |
/api/1.0/feedback/export/<export_type> |
POST | api/feedback/routes/feedback_route.py:108 |
是 | feedback_service.export_feedbacks(export_type) |
僅 JWT | 敏感 GET 性質(匯出全站 feedback),但為 POST |
SystemConfigService = jedi 套件
jedi_system_config.app.service.system_config_service;全數 method 皆無 role/admin guard(僅 JWT)。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/system/configs/<group> |
GET | api/system_config/routes/system_config_route.py:25 |
是 | system_config_service.get_system_config_by_group(group) |
僅 JWT | 敏感 GET — value dict 含 secret 無遮罩,SMTP/LDAP/issue-integration token 明文回傳(jedi_system_config/.../system_config_service.py:43 無 mask) |
/api/1.0/system/config/<uid> |
GET | api/system_config/routes/system_config_route.py:44 |
是 | system_config_service.get_system_config(uid) |
僅 JWT | 敏感 GET;同上,secret 明文 |
/api/1.0/system/config |
POST | api/system_config/routes/system_config_route.py:58 |
是 | system_config_service.create_system_config(payload) |
僅 JWT | 系統級設定寫入,無 admin gate |
/api/1.0/system/config/<uid> |
PUT | api/system_config/routes/system_config_route.py:72 |
是 | system_config_service.update_system_config(uid, payload) |
僅 JWT | 系統級設定改寫,無 admin gate |
/api/1.0/system/config/<uid> |
DELETE | api/system_config/routes/system_config_route.py:86 |
是 | system_config_service.delete_system_config(uid) |
僅 JWT | 無 admin gate |
/api/1.0/system/config/<group>/<key> |
GET | api/system_config/routes/system_config_route.py:97 |
是 | system_config_service.get_system_config_by_key(group, key) |
僅 JWT | 敏感 GET;secret 明文回傳 |
/api/1.0/system/config/<group>/<key> |
PUT | api/system_config/routes/system_config_route.py:111 |
是 | system_config_service.update_config_by_group_key(group, key, payload) |
僅 JWT | 無 admin gate |
/api/1.0/system/config/<group>/<key> |
DELETE | api/system_config/routes/system_config_route.py:126 |
是 | system_config_service.delete_config_by_group_key(group, key) |
僅 JWT | 無 admin gate |
InformationSystemService / InformationSystemAppService = 本地
app/information_system/...;write method 無 role/owner guard(僅 JWT)。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/information-systems/list |
POST | api/information_system/routes/information_system_route.py:59 |
是 | information_system_app_service.get_information_systems_and_pager(...) |
僅 JWT | POST 實為分頁查詢(讀) |
/api/1.0/information-systems |
POST | api/information_system/routes/information_system_route.py:90 |
是 | information_system_service.add_information_system(...) |
僅 JWT | 建立,無 role gate |
/api/1.0/information-system/<uid> |
PUT | api/information_system/routes/information_system_route.py:137 |
是 | information_system_service.update_information_system(...) |
僅 JWT | 無 owner/role gate |
/api/1.0/information-system/<uid> |
DELETE | api/information_system/routes/information_system_route.py:161 |
是 | information_system_service.delete_information_system(uid, user) |
僅 JWT | 傳 login_name 但無 owner/role gate |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/project/<project_uid>/ap/<ap_uid>/classify-evidence |
POST | api/evidence_classification/routes/evidence_classification_route.py:42 |
是 | service.trigger_classify(...) |
已有: if participant is None or participant.role != "manager" → ForbiddenError(EC_NOT_MANAGER) @ app/evidence_classification/service/evidence_classification_service.py:167 |
project manager 守門 |
/api/1.0/classification-run/<run_folder_id>/state |
PUT | api/evidence_classification/routes/evidence_classification_route.py:141 |
是 | service.put_state(run_folder_id, body, user.id) |
僅 JWT | 僅 _resolve_tenant_for_run_folder(tenant 解析,非 role gate)@ evidence_classification_service.py:737 |
/api/1.0/classification-run/<run_folder_id>/archive |
POST | api/evidence_classification/routes/evidence_classification_route.py:161 |
是 | service.archive_run(run_folder_id, user.id) |
僅 JWT | 同上,僅 tenant 解析非 role gate |
/api/1.0/classification-ground-truth |
POST | api/evidence_classification/routes/evidence_classification_route.py:237 |
是 | service.import_ground_truth(...) |
僅 JWT | GT 灌入,無 admin/role gate |
敏感 GET(下載/報表/預覽)— 皆 @jwt_required,僅 tenant 解析非 role gate:
GET /classification-run/<id>/file/<file_drive_id>/preview(route:178,檔案 bytes 串流)GET /classification-run/<id>/report/validation(route:203)GET /classification-run/<id>/report/adjudication(route:220)
DeviceAppService = 本地
app/device/...;write method 無 owner check(context 已知坑「device has no owner check」)。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/devices |
POST | api/device/routes/device_route.py:27 |
是 | device_app_service.get_devices_and_pager(...) |
僅 JWT | POST 實為分頁查詢(讀) |
/api/1.0/device |
POST | api/device/routes/device_route.py:68 |
是 | device_app_service.add_device(user, **payload) |
僅 JWT | 建立 |
/api/1.0/device/<uid> |
PUT | api/device/routes/device_route.py:81 |
是 | device_app_service.update_device(uid, user, <strong>payload) |
僅 JWT | 無 owner check** |
/api/1.0/device/<uid> |
DELETE | api/device/routes/device_route.py:93 |
是 | device_app_service.delete_device(uid, user) |
僅 JWT | 無 owner check |
BulletinService = 本地
app/bulletin/...;write method 無 role/owner guard(裸奔)。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/bulletins |
POST | api/bulletin/routes/bulletin_route.py:27 |
是 | bulletin_service.get_bulletins_and_pager(...) |
僅 JWT | POST 實為分頁查詢(讀) |
/api/1.0/bulletin |
POST | api/bulletin/routes/bulletin_route.py:55 |
是 | bulletin_service.add_bulletin(user, **payload) |
僅 JWT | 建立公告,無 admin gate |
/api/1.0/bulletin/<uid> |
PUT | api/bulletin/routes/bulletin_route.py:67 |
是 | bulletin_service.update_bulletin(uid, user, **payload) |
僅 JWT | 無 owner/role gate |
/api/1.0/bulletin/<uid> |
DELETE | api/bulletin/routes/bulletin_route.py:78 |
是 | bulletin_service.delete_bulletin(uid) |
僅 JWT | 無 owner/role gate |
FileUploadService / UploadFileService = jedi 套件
jedi_file_upload;upload/delete 無 owner check(僅 JWT)。
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/file/upload |
POST | api/uploadfile/routes/uploadfile_route.py:34 |
是 | file_upload_service.upload_files([file], login_name, save_dir) |
僅 JWT | 單檔上傳 |
/api/1.0/file/upload/<uid> |
DELETE | api/uploadfile/routes/uploadfile_route.py:54 |
是 | file_upload_service.delete_file(uid) |
僅 JWT | 無 owner check(jedi_file_upload/.../file_upload_service.py:93) |
/api/1.0/file/uploads |
POST | api/uploadfile/routes/uploadfile_route.py:63 |
是 | file_upload_service.upload_files(files, login_name, save_dir) |
僅 JWT | 多檔上傳 |
/api/1.0/file/download/<uid> |
GET | api/uploadfile/routes/uploadfile_route.py:81 |
否 | upload_file_service.get_upload_file(uid) → send_file |
無 JWT | 敏感 GET — 檔案下載,無 JWT 且無 owner check(任意 uid 可下載) |
/api/1.0/file/pdf-preview/<uid> |
GET | api/uploadfile/routes/uploadfile_route.py:108 |
否 | file_upload_service.convert_to_pdf/get_upload_file(uid) → send_file |
無 JWT | 敏感 GET — PDF 預覽下載,無 JWT 且無 owner check |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/notification |
POST | api/notification/routes/notification_route.py:22 |
是 | notification_service.send_discord/telegram_notification("test...") |
僅 JWT | 測試發送端點(寫死 "test from Raymond"),無 admin gate |
/api/1.0/mail/test |
POST | api/notification/routes/mail_route.py:25 |
是 | test_mail_service.send_test_mail(mail_to, smtp_config, change_pwd) |
僅 JWT | 測試寄信,收 SMTP config,無 admin gate |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/notify-config/<channel>/test |
POST | api/notify_config/routes/notify_config_route.py:21 |
是 | notify_config_test_service.test_channel(...) |
已有: if not user or not user.is_admin → ForbiddenError(NOTIFY_CHANNEL_TEST_FORBIDDEN) @ app/notify_config/service/notify_config_test_service.py:56 |
admin 守門 |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/ai-chatbot |
POST | api/ai/routes/ai_bot_route.py:19 |
是 | AiBotService().chat(user.id, session_id, message) |
僅 JWT | 對話端點,作用於自身 user.id |
/api/1.0/ai-chatbot |
DELETE | api/ai/routes/ai_bot_route.py:45 |
是 | AiBotService().clear_history(user.id, session_id) |
僅 JWT | 清自身 session 記錄(scoped by user.id) |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/ai-dashboard/health |
GET | api/ai_dashboard/routes/ai_dashboard_route.py:56 |
否 | (無 service,回靜態 config) | 無 JWT | 刻意公開(health);前端 onMounted 呼叫;回靜態 provider/speed 清單 |
/api/1.0/ai-dashboard/auto-generate |
POST | api/ai_dashboard/routes/ai_dashboard_route.py:91 |
是 | ai_dashboard_app_service.generate_dashboard_auto(...) |
僅 JWT | 呼叫 LLM 生成,作用於自身 user context |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/schedule-report/file-list |
POST | api/report/routes/scheduler_report_route.py:21 |
是 | (route 內直接讀檔系統目錄,無 service) | 僅 JWT | POST 實為檔案清單查詢(讀);依 payload 拼 SCHEDULE_REPORT_DIR 路徑 |
/api/1.0/schedule-report/preview |
GET | api/report/routes/scheduler_report_route.py:42 |
否 | (route 內 send_file(report_path),無 service) |
無 JWT | 敏感 GET — 檔案下載/預覽,無 JWT;path 由 query param 拼接(report_name/type/file_name),無 owner/tenant 隔離 |
| Route path | Method | Route file:line | @jwt_required? | 呼叫的 service method | 現況守門 | 備註 |
|---|---|---|---|---|---|---|
/api/1.0/log/api-logs |
POST | api/log/routes/api_log_route.py:26 |
是 | api_log_service.get_devices_and_pager(...) |
僅 JWT | POST 實為分頁查詢(讀);操作日誌列表 |
/api/1.0/log/api-logs/export |
GET | api/log/routes/api_log_route.py:53 |
是 | api_log_service.export_api_log_file() |
僅 JWT | 敏感 GET — 匯出操作日誌 zip;@jwt_required() 已於 commit 182bb2f7 (SEC-001) 恢復,現況存在(route:52) |
| Module | 唯一端點 | Method | @jwt_required? | 說明 |
|---|---|---|---|---|
api/translate |
/api/1.0/translate |
POST | 是(translate_route.py:41) |
翻譯查詢(呼叫 OpenAI),非資料寫入、非敏感檔案匯出 — 依「write / sensitive GET」定義不列入,但 POST 實為查詢動作。若採嚴格 write 定義則歸此類跳過。 |
api/issue |
/api/1.0/issue/get_members |
GET | 否(issue_member_route.py:8,class/method 均無 @jwt_required) |
讀取成員清單。注意:無 JWT — 純讀但完全裸奔。 |
api/label |
/api/1.0/labels/menu/<scope> |
GET | 是(label_route.py:16) |
讀取 label menu,非敏感。 |