面向日常使用 —— 查数据、写数据、做集成时看这份。
与
DMS_MAPPING.md的分工: 那份是迁移视角(源表→栏目怎么映射、建栏目踩了什么坑); 这份是使用视角(这五个栏目怎么用,字段叫什么)。 接口本身的通用约定见DMS_API.md。
服务:http://121.43.55.7:10081/dms
父栏目:营商助手 columnId=1883(分级栏目,tag=yszs)
最后核对:2026-09-16
📍 本文引用的 artifacts / RUNBOOK 不在本仓库,属于另一个项目
F:\yysk\AI_zhaoshang\DMS_Data_Migration\(本文从它的harness/docs/复制而来)。 链接已改为绝对路径指向那边。
| 栏目 | columnId | 当前内容数 |
|---|---|---|
| 助手页面浏览 | 1885 | 0 |
| 企业荣誉信息 | 1886 | 0 |
| 助手会话 | 1887 | 0 |
| 企业基础信息 | 1888 | 0 |
| 助手问答记录 | 1889 | 0 |
实测 selectContentList 五个栏目全部返回 code=202 数据不存在。
五张表的结构(栏目 + 字段)已就绪,但业务数据尚未写入。
数据迁移(F4-*)还没开始。所以现在查任何栏目都只会得到 202。
| 栏目 | columnId | tag(权限名) | 栏目模型 modelId | 字段数 | 源表 | 源行数 |
|---|---|---|---|---|---|---|
| 助手页面浏览 | 1885 | yszs_page_view |
2030 | 4 | assistant_page_view |
39,723 |
| 企业荣誉信息 | 1886 | yszs_qcc_honor |
2032 | 11 | qcc_honor |
7,118 |
| 助手会话 | 1887 | yszs_chat_session |
2034 | 7 | chat_session |
3,133 |
| 企业基础信息 | 1888 | yszs_qcc_enterprise |
2036 | 41 | qcc_enterprise |
81,980 |
| 助手问答记录 | 1889 | yszs_chat_record |
2038 | 13 | chat_record |
15,542 |
调 content 接口时用 columnId。 权限用 tag(已同步 OAuth permissionName)。
业务主线:c_credit_code(统一社会信用代码)串起 企业基础信息 ↔ 企业荣誉信息 ↔ 助手会话 ↔ 助手问答记录。
字段名以
c_开头。type是 DMS 存储类型,前端控件是 DMS 界面渲染用的控件名。 类型为text的字段用模糊查询(searchType=2),其余用精确(searchType=1)。
columnId=1885埋点数据。无企业关联(没有 credit_code),只有访客维度。
| 字段 | 别名 | 类型 | 前端控件 | 必填 |
|---|---|---|---|---|
c_id |
ID | integer | int_num | ✓ |
c_business_code |
业务编码 | text | varchar | |
c_visitor_id |
访客ID | text | varchar | |
c_created_at |
创建时间 | timestamp | date_time |
columnId=1886| 字段 | 别名 | 类型 | 前端控件 | 必填 |
|---|---|---|---|---|
c_id |
ID | integer | int_num | ✓ |
c_credit_code |
统一社会信用代码 | text | varchar | ✓ |
c_name |
企业名称 | text | varchar | |
c_level |
级别 | text | varchar | |
c_source |
来源 | text | varchar | |
c_publish_office |
发布机构 | text | varchar | |
c_publish_date |
发布日期 | text | varchar | |
c_beging_date |
起始日期 | text | varchar | |
c_dead_line |
截止日期 | text | varchar | |
c_certificate_code |
证书编号 | text | varchar | |
c_created_at |
创建时间 | timestamp | date_time | |
c_tag_name |
荣誉 | text | text |
c_tag_name由前端的企业信息分类同步写入(2026-09-18 DMS 侧新增,12 字段): 一行 = 一条真实荣誉(数据源是company_info.honors.records),荣誉名同时写进 这一列与系统字段title(DMS 列表用后者显示);别的列照抄后端记录:c_level=Level、c_source=Source、c_publish_office=PublishOffice、c_publish_date=PublishDate、c_beging_date=BegingDate、c_dead_line=DeadLine、c_certificate_code=CertificateCode。同步按「荣誉名+级别+来源」与库里该企业的行全量对齐:补新增、更新有差异的列、 删库里多出来的(仅当后端
honors.complete === true)。 灌入的行(09-17 那批,只有title没有c_tag_name)同样参与,首次对齐会补上这一列。 见../exec-plans/active/company-classify-dms-sync.md。
columnId=1887| 字段 | 别名 | 类型 | 前端控件 | 必填 |
|---|---|---|---|---|
c_id |
ID | integer | int_num | ✓ |
c_credit_code |
统一社会信用代码 | text | varchar | ✓ |
c_session_id |
会话ID | text | varchar | |
c_title |
标题 | text | varchar | |
c_source |
来源 | text | varchar | |
c_created_at |
创建时间 | timestamp | date_time | |
c_updated_at |
更新时间 | timestamp | date_time |
columnId=188847 字段(原 41 + 2026-09-18 新增的 6 个 c_tag_*)。
主键 c_credit_code(注意:没有 c_id);must 字段只有 c_credit_code(实测自 getModelById)。
分类标签字段(前端的企业信息分类同步写入;值是 JSON 数组字符串,空集存 "[]")
| 字段 | 别名 | 类型 | 前端控件 | 必填 |
|---|---|---|---|---|
c_tag_basic |
基本信息 | text | text | |
c_tag_honor |
资质荣誉 | text | content(富文本) | |
c_tag_sector |
产业信息 | text | text | |
c_tag_operation |
经营活动 | text | text | |
c_tag_industry |
行业信息 | text | text | |
c_tag_license |
许可认证 | text | text |
六个字段与分类接口的六个角度一一对应(字段名映射见
src/network/api/dms/classification-sync-utils.ts的ANGLE_TO_FIELD)。 ⚠️ 行业信息用c_tag_industry,别和原有的c_industry(源库行业分类 JSON)混了。 ⚠️c_tag_honor的控件类型是content(富文本),其余是 text——2026-09-18 实测 JSON 字符串逐字往返正常(见verify-company-classify-dms.mjs的专项断言)。 ⚠️ 空数组不落库:写[](空标签)时读回来是字段不存在——两者语义相同, 同步逻辑按集合比较,不会因此反复写(见diffEnterpriseRow)。 ⚠️c_created_at在这个栏目里不生效:写了也读不回来(实测;1887/1889 是正常的)。
主体字段
| 字段 | 别名 | 类型 |
|---|---|---|
c_credit_code |
统一社会信用代码 | text |
c_name |
企业名称 | text |
c_belong_org |
所属机构 | text |
c_oper_id |
经营者ID | text |
c_oper_name |
经营者名称 | text |
c_ent_type |
企业类型 | text |
c_econ_kind |
经济类型 | text |
c_status |
经营状态 | text |
c_province |
省份 | text |
c_area_code |
行政区划代码 | text |
c_address |
注册地址 | text |
c_phone_number |
联系电话 | text |
c_email |
邮箱 | text |
经营期限与资本
| 字段 | 别名 | 类型 |
|---|---|---|
c_start_date |
成立日期 | text |
c_end_date |
结束日期 | text |
c_term_start |
营业期限起 | text |
c_term_end |
营业期限止 | text |
c_check_date |
核准日期 | text |
c_updated_date |
更新日期 | text |
c_regist_capi |
注册资本 | text |
c_registered_capital |
注册资本数值 | text |
c_registered_capital_unit |
注册资本单位 | text |
c_registered_capital_ccy |
注册资本币种 | text |
c_rec_cap |
实收资本 | text |
c_paid_up_capital |
实缴资本 | text |
c_paid_up_capital_unit |
实缴资本单位 | text |
c_paid_up_capital_ccy |
实缴资本币种 | text |
上市与编码
| 字段 | 别名 | 类型 |
|---|---|---|
c_is_on_stock |
是否上市 | text |
c_stock_number |
股票代码 | text |
c_stock_type |
股票类型 | text |
c_org_no |
组织机构代码 | text |
c_no |
编号 | text |
c_image_url |
图片地址 | text |
长文本
| 字段 | 别名 | 类型 |
|---|---|---|
c_scope |
经营范围 | text |
c_scope_brief |
经营范围简述 | text |
JSON 存成 text 的字段(⚠️ 内容不可被 DMS search 检索,见 §5.3)
| 字段 | 别名 | 源 jsonb 内容 |
|---|---|---|
c_designated_representative_list |
法定代表人列表 | 法定代表人数组 |
c_original_name |
曾用名 | 曾用名数组 |
c_revoke_info |
撤销信息 | 撤销记录 |
c_area |
行政区划 | 行政区划对象 |
c_industry |
行业 | 行业分类对象 |
时间
| 字段 | 别名 | 类型 |
|---|---|---|
c_created_at |
创建时间 | timestamp |
columnId=1889| 字段 | 别名 | 类型 | 前端控件 | 必填 |
|---|---|---|---|---|
c_id |
ID | integer | int_num | ✓ |
c_credit_code |
统一社会信用代码 | text | varchar | ✓ |
c_session_id |
会话ID | text | varchar | |
c_record_id |
记录ID | text | varchar | |
c_question |
问题 | text | text | |
c_answer |
回答 | text | text | |
c_reason |
原因 | text | text | |
c_source |
来源 | text | varchar | |
c_feedback_status |
反馈状态 | integer | int_num | |
c_feedback_option |
反馈选项 | text | varchar | |
c_feedback_remark |
反馈备注 | text | text | |
c_created_at |
创建时间 | timestamp | date_time | |
c_feedback_at |
反馈时间 | timestamp | date_time |
所有查询共用:
export DMS_HOST=121.43.55.7:10081
export DMS_TOKEN='...'
curl -s -X POST "http://${DMS_HOST}/dms/content/selectContentList" \
-H "token: ${DMS_TOKEN}" \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "columnId=1888" \
-d "page=0" \
-d "pageSize=20" \
-d "search=[{\"field\":\"c_name\",\"searchType\":2,\"content\":{\"value\":\"科技\"}}]" \
-d "orderBy=[{\"field\":\"c_created_at\",\"orderByType\":2}]"
返回 content.data(数组)+ content.count(总数)。
page 从 0 开始。
-d 'search=[{"field":"c_name","searchType":2,"content":{"value":"上海某某"}}]'
-d 'search=[{"field":"c_credit_code","searchType":1,"content":{"value":"91310118MA1JLXXXXX"}}]'
curl -s -X POST "http://${DMS_HOST}/dms/content/selectContentList" \
-H "token: ${DMS_TOKEN}" \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "columnId=1886" \
-d 'search=[{"field":"c_credit_code","searchType":1,"content":{"value":"91310118MA1JLXXXXX"}}]' \
-d "page=0&pageSize=50"
-d "columnId=1889"
-d 'search=[{"field":"c_credit_code","searchType":1,"content":{"value":"91310118MA1JLXXXXX"}}]'
searchType=3)-d 'search=[{"field":"c_created_at","searchType":3,"content":{"start":"2026-01-01 00:00:00","end":"2026-12-31 23:59:59"}}]'
-d 'search=[
{"field":"c_credit_code","searchType":1,"content":{"value":"91310118MA1JLXXXXX"}},
{"field":"c_level","searchType":2,"content":{"value":"市级"}}
]'
| 值 | 含义 | content 写法 |
|---|---|---|
1 |
精确 | {"value":"..."} |
2 |
模糊 | {"value":"..."} |
3 |
区间 | {"start":"...","end":"..."} |
4 |
in 数组 | {"value":["a","b"]} |
5 |
between | {"start":..,"end":..} |
# columnId + contentId(contentId 是 UUID 字符串)
curl -s -X POST "http://${DMS_HOST}/dms/content/selectContentById" \
-H "token: ${DMS_TOKEN}" \
-d "columnId=1888&contentId={uuid}"
需要字典解析(把码值翻成文本)时用 selectContentListInfo,参数相同。
import sys; sys.path.insert(0, 'harness/tools')
from dms import Dms
import json
d = Dms()
r = d.call("POST", "/content/selectContentList", {
"columnId": 1888,
"page": 0,
"pageSize": 20,
"search": json.dumps([{"field": "c_name", "searchType": 2,
"content": {"value": "科技"}}], ensure_ascii=False),
"orderBy": json.dumps([{"field": "c_created_at", "orderByType": 2}]),
}, expect=None)
print(r["content"]["count"], "条")
for row in r["content"]["data"]:
print(row.get("c_credit_code"), row.get("c_name"))
写入前先读 §5.1(时间换算)和 §5.2(幂等) —— 这两条不注意会产生脏数据。
curl -s -X POST "http://${DMS_HOST}/dms/content/addContent" \
-H "token: ${DMS_TOKEN}" \
-d "columnId=1886" \
-d "modelId=2032" \
-d 'content={"c_id":1,"c_credit_code":"91310118MA1JLXXXXX","c_name":"某某公司","c_level":"市级"}'
content 是 JSON 字符串,字段名带 c_ 前缀。
modelId 用栏目模型 id(速查表里的那个)。
同 addContent,但 content 里必须带 id(记录 UUID,不是业务 id):
-d 'content={"id":"{记录uuid}","c_level":"国家级"}'
⚠️ 注意区分两个「id」:
c_id是业务 id(来自源库),id是 DMS 记录 UUID。 修改时要用后者。
POST /content/importJSON —— 服务端确认存在,但参数未文档化、本项目未实测。
大批量写入前先在测试栏目验证(见 DMS_API.md §4.7)。
源库的 created_at / updated_at / feedback_at 是 epoch 秒(不是毫秒),
栏目里存为 timestamp。
查询时用正常的时间字符串(DMS 已转好):
-d 'search=[{"field":"c_created_at","searchType":3,"content":{"start":"2026-09-01 00:00:00","end":"2026-09-30 23:59:59"}}]'
写入/换算时:datetime.fromtimestamp(v),不要除以 1000。
from datetime import datetime
datetime.fromtimestamp(1789450583) # 2026-09-15 13:36 ✅
datetime.fromtimestamp(1789450583/1000) # 1970-01-22 ❌
| 栏目 | 幂等键 | 说明 |
|---|---|---|
| 企业基础信息 1888 | c_credit_code |
源表主键,天然唯一 |
| 企业荣誉信息 1886 | c_id |
源表主键 |
| 助手会话 1887 | c_id |
源表主键 |
| 助手问答记录 1889 | c_id |
源表主键 |
| 助手页面浏览 1885 | c_id |
源表主键 |
写入前先按幂等键查一次:不存在则 addContent,已存在则 updateContent。
企业基础信息里这 5 个字段是 JSON 文本,DMS 的 search 无法检索其内部值:
c_designated_representative_list(法定代表人)、c_industry(行业)、
c_area(行政区划)、c_original_name(曾用名)、c_revoke_info(撤销信息)
例如「查法定代表人是张三的企业」做不到 —— 除非把 JSON 反序列化后另建字段/栏目。 如果这类查询有需求,需要单独提出来做。
c_credit_code 在企业基础信息里是主键;但在荣誉/会话/问答里可空c_credit_code 为空的行会被漏掉栏目 tag 已同步 OAuth permissionName:
| 栏目 | tag |
|---|---|
| 助手页面浏览 | yszs_page_view |
| 企业荣誉信息 | yszs_qcc_honor |
| 助手会话 | yszs_chat_session |
| 企业基础信息 | yszs_qcc_enterprise |
| 助手问答记录 | yszs_chat_record |
无权限访问返回 code=201,token 失效返回 212。
⚠️ 权限边界尚未验证(未用测试账号确认「有权限能读 / 没权限返回 201」)。
| 问题 | 影响 | 处置 |
|---|---|---|
c_updated_at(1887)显示名为 updated_at |
— | ✅ 已修复(2026-09-16),现显示「更新时间」。根因是建栏目脚本别名表漏配 updated_at,已同步修正 |
| 数据尚未迁移 | 5 个栏目全部 code=202 数据不存在 |
等 F4-* |
| 权限边界未验证 | 不知道无权限用户能否读到 | 等 F6-01 |
改字段别名的方法(实测可用):
python harness/tools/fix_field_alias.py --model 2034 --field c_updated_at --alias 更新时间 --apply
⚠️ 更新模型要用
POST /model/updateProperty。updateFields返回 HTTP 400、updateFieldList返回 HTTP 500 —— 名字最像的恰好不能用。
| code | 含义 | 排查 |
|---|---|---|
200 |
成功 | |
201 |
无权限 | 检查栏目 tag 与用户 OAuth 权限 |
202 |
数据不存在 | 栏目是空的 —— 当前 5 个栏目都会返回这个 |
205 |
无数据 / 模型不存在 | 查询条件无匹配;或 getModelList 没传 type |
212 |
token 无效/过期 | 重新获取 |
| 文档 | 用途 |
|---|---|
DMS_API.md |
DMS 接口通用约定与全部端点 |
DMS_MAPPING.md |
源表→栏目映射、建栏目实测契约 |
RUNBOOK.md |
操作手册 |
dms_column_fields.json |
本文档字段表的机器可读版(从 DMS 实时拉取) |