Files
suixinkan_uikit/suixinkan/Features/WildPhotographerReport/举报摄影师接口.md

15 KiB
Raw Blame History

举报摄影师接口文档

本文档记录 iOS WildPhotographerReport 模块当前使用的后端接口。

基础约定

  • 业务域:举报摄影师
  • API 封装:suixinkan/Features/WildPhotographerReport/API/WildPhotographerReportAPI.swift
  • 网络入口:NetworkServices.shared.wildPhotographerReportAPI
  • 后端成功码:100000
  • 响应包裹:工程统一 APIEnvelope<T>
  • 当前状态:“首页文案”、“举报类型”、“提交举报”、“我的举报列表”、“举报详情”、“微信小程序分享”、“补充证据提交”和“附近风险地图”已接接口;模块内生产 Mock 数据已移除。

首页文案

用途

“举报摄影师”首页进入时拉取举报须知和举报规则文案。

请求

GET /api/yf-handset-app/photog/report/copy

响应示例

{
  "code": 100000,
  "msg": "success",
  "data": {
    "notice": [
      "需实名登录",
      "请尽量上传清晰证据",
      "恶意举报将被追责"
    ],
    "rule_groups": [
      {
        "title": "可举报行为",
        "items": [
          "疑似打野摄影师主动揽客",
          "未佩戴工牌开展摄影服务",
          "引导游客线下付款或私下交易"
        ]
      }
    ]
  },
  "time": "2026-07-09 10:15:17"
}

UI 行为

  • notice 用于首页“举报须知”条目展示。
  • rule_groups 非空时显示“举报规则”按钮,点击后在举报规则页按分组展示 titleitems
  • noticerule_groups 都为空时,隐藏整个“举报须知”模块。
  • 接口失败时不展示本地写死兜底文案,并 toast 错误。

当前调用位置

  • WildPhotographerReportHomeViewController.viewDidLoad()
  • WildPhotographerReportHomeViewModel.loadReportCopy(api:)
  • WildPhotographerReportAPI.reportCopy()

1. 获取举报类型

用途

提交举报页面进入时拉取可选举报类型。举报类型由后台动态维护,客户端不能用枚举写死,也不展示图标。

请求

GET /api/yf-handset-app/photog/report/types

请求参数

无。

响应示例

{
  "code": 100000,
  "msg": "success",
  "data": {
    "list": [
      {
        "value": 1,
        "label": "私下收款"
      },
      {
        "value": 2,
        "label": "疑似打野"
      },
      {
        "value": 3,
        "label": "未戴工牌"
      },
      {
        "value": 4,
        "label": "其他"
      }
    ]
  },
  "time": "2026-07-08 14:21:21"
}

iOS 模型

struct WildReportType: Decodable, Hashable {
    let value: Int
    let label: String
}

struct WildReportTypeListResponse: Decodable, Hashable {
    let list: [WildReportType]
}

UI 行为

  • 页面加载时调用 WildPhotographerReportSubmitViewModel.loadReportTypes(api:)
  • 按接口返回顺序渲染举报类型。
  • 每行最多展示 3 个类型,超过 3 个自动换行。
  • label 展示文字,不展示图标。
  • 默认选中 value == 2 的类型;如果接口返回中不存在该类型,则选中列表第一项。
  • 接口失败时不展示本地默认类型,并 toast 错误。

当前调用位置

  • WildPhotographerReportSubmitViewController.viewDidLoad()
  • WildPhotographerReportSubmitViewModel.loadReportTypes(api:)
  • WildPhotographerReportAPI.reportTypes()

2. 提交举报

用途

提交页点击“提交举报”时调用。客户端会先把现场证据和支付截图上传到 OSS全部上传成功后再提交表单数据。

请求

POST /api/yf-handset-app/photog/report/submit

请求参数

{
  "scenic_id": 1,
  "report_type": 2,
  "desc": "疑似人员在观景台附近主动揽客,并引导游客线下转账。",
  "contact_phone": "13800138000",
  "location_name": "黄山风景区",
  "location_address": "光明顶景区",
  "lat": 30.12345,
  "lng": 120.12345,
  "evidences": [
    {
      "file_url": "https://example.com/photog_report/20260708/1/report_image.jpg",
      "file_type": 1,
      "file_name": "report_image.jpg"
    },
    {
      "file_url": "https://example.com/photog_report/20260708/1/report_video.mp4",
      "file_type": 2,
      "file_name": "report_video.mp4"
    }
  ],
  "payment_screenshots": [
    {
      "file_url": "https://example.com/photog_report/20260708/1/payment.jpg",
      "file_type": 1,
      "file_name": "payment.jpg"
    }
  ]
}

字段说明

  • scenic_id:当前景区 ID来自 AppStore.shared.currentScenicId,必须大于 0。
  • report_type:举报类型接口返回的 value
  • desc:举报说明,必填,最多 500 字。
  • store_user_id:被举报摄影师 ID当前页面无来源本轮暂不传。
  • contact_phone:当前联系方式输入值,非空才传。
  • location_name / location_address:从当前定位展示文案拆分;无法拆分时使用景区名和完整地址兜底。
  • lat / lng:当前定位快照坐标;定位失败时不提交举报,提示用户重新获取位置。
  • evidences:现场证据,必填,至少 1 项、最多 9 项。
  • payment_screenshots:线下微信、支付宝截图,选填,最多 3 张。
  • file_type:举报提交接口约定为 1 = 图片2 = 视频

iOS 模型

struct WildReportSubmitRequest: Encodable, Equatable {
    let scenicId: Int
    let reportType: Int
    let desc: String
    let storeUserId: Int?
    let contactPhone: String?
    let locationName: String?
    let locationAddress: String?
    let lat: Double
    let lng: Double
    let evidences: [WildReportEvidenceRequest]
    let paymentScreenshots: [WildReportEvidenceRequest]
}

struct WildReportEvidenceRequest: Encodable, Equatable {
    let fileURL: String
    let fileType: Int
    let fileName: String?
}

UI 与上传行为

  • 图片、视频和支付截图使用系统相册选择器。
  • 图片/视频选择后先保存到本地临时目录,点击附件 tile 可预览本地文件。
  • 提交时顺序上传附件到 OSS按钮展示上传进度并禁用重复提交。
  • 任一 OSS 上传失败时不调用提交接口,并保留用户已填写内容。
  • 支付截图通过 payment_screenshots 独立提交,不替代现场证据必填校验。

当前调用位置

  • WildPhotographerReportSubmitViewController.submitTapped()
  • WildPhotographerReportSubmitViewModel.submitReport(api:uploader:scenicId:scenicName:)
  • OSSUploadService.uploadWildReportAttachment(...)
  • WildPhotographerReportAPI.submitReport(_:)

3. 我的举报列表

用途

“我的举报”页面进入、切换状态筛选、滚动加载更多时调用。

请求

GET /api/yf-handset-app/photog/report/list

请求参数

参数 类型 说明
scenic_id integer 可选,当前景区 ID大于 0 时传
handle_status integer 可选,状态筛选;“全部”不传该参数,其他筛选 iOS 固定使用该参数
status integer 可选,与 handle_status 等价iOS 不传
page integer 可选,默认 1
page_size integer 可选,默认 10最大 50

状态码

  • 全部:不传 handle_status
  • 0:待处理
  • 1:处理中
  • 2:已处理

响应示例

{
  "code": 100000,
  "msg": "success",
  "data": {
    "list": [
      {
        "id": 32,
        "complaint_no": "JB20260708917",
        "title": "私下收款举报",
        "report_type": 1,
        "report_type_text": "私下收款",
        "desc": "我在",
        "scenic_id": 128,
        "scenic_name": "伊犁那拉提景区-5A",
        "location_name": "伊犁那拉提景区-5A",
        "latitude": "32.4299428",
        "longitude": "119.4403263",
        "handle_status": 0,
        "handle_status_text": "待处理",
        "created_at": "2026-07-08 16:06:59"
      }
    ],
    "total": 1,
    "page": 1,
    "page_size": 10
  },
  "time": "2026-07-08 16:07:30"
}

iOS 模型

struct WildReportListRequest: Equatable {
    let scenicId: Int?
    let handleStatus: Int?
    let page: Int
    let pageSize: Int
}

struct WildReportListResponse: Decodable, Equatable {
    let list: [WildReportListItem]
    let total: Int
    let page: Int
    let pageSize: Int
}

UI 行为

  • 页面首次进入请求 page=1&page_size=10,不传 handle_status
  • 切换筛选时重置为第一页,待处理传 handle_status=0,处理中传 handle_status=1,已处理传 handle_status=2
  • 滚动到底部时,如果仍有更多数据,则请求下一页并追加。
  • 首屏失败显示 toast 和空态;加载更多失败只 toast并保留已有列表。
  • 列表接口暂不返回媒体数量,WildReportRecord.imageCount/videoCount 暂按 0 处理,进入详情页后由详情接口补齐。

当前调用位置

  • WildPhotographerReportListViewController.viewDidLoad()
  • WildPhotographerReportListViewModel.loadInitial(api:scenicId:)
  • WildPhotographerReportListViewModel.loadMoreIfNeeded(api:scenicId:)
  • WildPhotographerReportAPI.reportList(_:)

4. 举报详情

用途

“举报详情”页面进入时调用。列表页传入 WildReportRecord.serverID,详情接口返回完整举报信息、现场证据、支付截图、补充内容、处理信息和处理时间线。

请求

GET /api/yf-handset-app/photog/report/detail?id=32

请求参数

参数 类型 说明
id integer 必填,举报记录数值 ID来自列表接口返回的 id

关键响应字段

  • complaint_no:页面展示的举报编号。
  • report_type / report_type_text:举报类型。
  • desc:初始举报说明。
  • evidences:初始现场证据,详情页“举报人材料”区域展示。
  • payment_screenshots:支付截图,详情页单独展示。
  • supplements / report_contents:补充内容记录,优先使用 supplements,为空时从 report_contents 过滤 type=supplement
  • location_name / location_address:详情页位置展示。
  • handle_status / handle_status_text处理状态iOS 支持 0 待处理、1 处理中、2 已处理、3 驳回。
  • handle_remark:处理备注;handler.remark 为空时作为“处理信息”卡的处理意见兜底。
  • handler:处理人结构,包含 namephonestarted_atfinished_atremark,详情页“处理信息”卡优先使用。
  • handler_name / handler_phone / handled_at:处理信息顶层兼容字段;handler 缺字段时作为兜底。
  • handle_evidences:处理凭证附件数组,字段同证据附件,并额外支持 evidence_kind / evidence_kind_text
  • timeline:处理进度时间线;为空时只展示列表记录中的当前处理状态,不生成本地模拟流程。

iOS 模型

struct WildReportDetailData: Decodable, Equatable, Hashable
struct WildReportDetailEvidence: Decodable, Equatable, Hashable
struct WildReportDetailHandler: Decodable, Equatable, Hashable
struct WildReportDetailContent: Decodable, Equatable, Hashable
struct WildReportDetailTimelineItem: Decodable, Equatable, Hashable

UI 行为

  • 详情页先展示列表带入的基础记录,再异步请求详情接口刷新完整数据。
  • 如果传入记录没有 serverID,说明来自本地提交成功页等临时记录,不请求详情接口。
  • 详情接口失败时保留现有基础信息,并 toast 错误。
  • 图片证据使用 Kingfisher 加载网络图;视频证据展示视频样式缩略块和文件信息。
  • 状态为已处理或驳回且存在处理信息时展示“处理信息”卡:处理人、处理人电话、处理时间、处理完成时间、处理意见。
  • “处理人电话”展示脱敏文案,点击使用接口原始 handler.phonehandler_phone 发起 tel://
  • handle_evidences 非空时在“处理信息”卡内展示“处理凭证”横向缩略图,file_type=2 按视频处理,其余按图片处理。

当前调用位置

  • WildPhotographerReportDetailViewController.viewDidLoad()
  • WildPhotographerReportDetailViewModel.loadDetailIfNeeded(api:)
  • WildPhotographerReportAPI.reportDetail(id:)

5. 举报微信小程序分享

用途

“我的举报”列表卡片和“举报详情”头部点击分享时调用,后端按举报 ID 返回微信小程序分享配置iOS 映射为 WeChatMiniProgramSharePayload 后调用 WeChatShareService.shareMiniProgram(...)

请求

GET /api/yf-handset-app/photog/report/share?id=32

请求参数

参数 类型 说明
id string 必填,举报记录服务端 IDiOS 使用 WildReportRecord.serverID

响应示例

{
  "code": 100000,
  "msg": "success",
  "data": {
    "userName": "wx8c85189bf3bdda29",
    "path": "pages/scenic/radar/report-detail/index?id=32",
    "title": "私下收款举报",
    "imagePath": "/assets/share/report-share-cover.png",
    "webpageUrl": "https://www.youfuntour.com",
    "withShareTicket": true,
    "miniprogramType": 0,
    "scene": 0
  },
  "time": "2026-07-09 15:42:19"
}

字段说明

  • title:微信分享卡片标题,不能为空。
  • webpageUrl:小程序打不开时的兼容网页地址,微信要求不超过 1024 字节。
  • userName:微信 SDK WXMiniProgramObject.userName 字段;请后端确认返回值是否应为小程序原始 ID gh_...
  • path:小程序页面路径,可携带举报 ID 或分享 token。
  • miniprogramType0 正式版、1 开发版、2 体验版;由后端按环境明确返回。
  • withShareTicket:是否携带群分享票据。
  • scene:当前仅支持 0 微信好友会话;非 0 会被通用微信分享模块拒绝。
  • imagePath当前返回的是小程序内资源路径iOS 不下载;微信小程序预览图暂使用 App 图标兜底。若后续需要定制卡片图,请返回可下载的 https 图片地址。

当前调用位置

  • WildPhotographerReportListViewController 列表卡片分享按钮
  • WildPhotographerReportDetailViewController 详情头部分享按钮
  • WildPhotographerReportAPI.reportShare(id:)

6. 补充证据提交

请求

POST /api/yf-handset-app/photog/report/supplement

请求体

{
  "id": 32,
  "desc": "补充说明",
  "evidences": [
    {
      "file_url": "https://example.com/supplement.jpg",
      "file_type": 1,
      "file_name": "supplement.jpg"
    }
  ]
}

字段说明

  • id:服务端举报 ID必填需大于等于 1本地临时记录没有 serverID 时不允许补充提交。
  • desc:补充说明,选填,最多 500 字;与 evidences 至少填写一项。
  • evidences:补充附件,选填,最多 9 项;附件先通过 OSS photog_report 模块上传后再提交 URL。
  • file_type沿用举报提交接口约定1 图片2 视频。

当前调用位置

  • WildReportSupplementEvidenceViewModel.submit(api:uploader:scenicId:)
  • WildPhotographerReportAPI.supplementReport(_:)
  • WildReportSupplementEvidenceViewController.submitTapped()

生产 Mock 清理

  • 已删除本地种子举报、种子风险点、种子补充证据及对应生产代码文件。
  • 举报类型、首页文案、列表、详情、补充证据和风险地图均不再使用本地写死数据兜底。
  • 提交接口当前无业务 data 返回;提交成功页只展示本次用户提交快照,不伪造服务端举报编号,也不写入“我的举报”本地列表。