workshop-tasks.md 19 KB

工作坊任务输入

配套 VOC 研究结构库(2026-11-05)

ksf-voc-library 保存已采集底料,独立只读Python入口,不是ksf-secure的新子命令。读其SKILL.md和contract验实际代际,再按问题选search/facets/aggregate/get/source;未装不得声称可用。比如找份量反馈可用 {"entities":["reviews"],"filters":{"brand":"康师傅"},"text":{"concepts":["portion_size"]},"limit":20},只限定问题实际给出的字段,不要求补齐平台/品牌/品类。商品ID、正文、规格/价格区间、时间、原文与条款、覆盖和来源都按目录选择路径;明确约束AND、同义组内OR,先精确关联再核上下文。同文评价按条数/去重文本/商品数分别统计,不当独立消费者。旧query三维模板保留兼容,不作为通用查询方式。

2026-11-06统一规则 ksf.agent-data-rules.20261106.v1:明确“京东康师傅拌面”就用 filters={platform:jd,brand:ksf,category:banmian},三项同时满足;评论购买规格也需符合,不以同名商品或标题命中代替。contract先取generation,后续所有查询/统计/原文回读传 --generation;版本变更报错后重建受影响结果。运维绑定KSF_LIBRARY_REGISTRY到看板的当前库目录,Agent按同一current.json取新代际,不自行切到旧库。结构、分类、来源与排除口径以配套Skill的references/data-contract.md为准。

工作坊业务库先查报告/证据/项目;研究库先查采集底料,两者都按需查。研究库返回的 archiveSha256/source_record_id/实体ID/来源URL/原始时间随结论留在来源与证据里,再按实际业务合同查重入库。只有本地研究库文件不等于生产业务库已入库、公开 API 已投影或看板已显示。未知品牌/品类、默认评价、身份不明/错配、品类冲突、无时间、标题推导规格均按研究库合同分开,不以关键词过滤替代精确范围。

所有命令均由 ksf-secure.mjs 接收 --input 绝对路径及 --request-id。输入 JSON 不含凭据;同一操作重试保持 requestId 和原文件。当前 API 版本 ksf.workshop.v1。

业务写命令必须同时传 --agent-profile <当前Agent完整档案键>,读取已登记的自身身份。新员工、新数字人先按 identity.md 登记,任何名称都适用;仅 role=workshop 可课堂写入。只读命令可不传档案键。

看板称呼:employee-name

先从当前真实消息登记取得employeeProfileKey和Agent键,再核对已有会话。三种输入共用同一命令:

{"sessionId":"已有本人会话编号","participant":{"profileKey":"当前员工完整档案键"}}

上例只读返回 promptState=not_asked/provided/skipped、displayName、source、nameVerified,readOnly=true且databaseWrites=0。只在未询问且无称呼时问一句;用户明确回答后,在同一输入加 "displayName":"用户实际提供的姓名或昵称"(1至40字),保存并供看板显示。用户明确说跳过时改为加 "skip":true,不带displayName。不把未回复自动当跳过。

node /opt/data/skills/ksf-workshop-runtime/scripts/ksf-secure.mjs employee-name --agent-profile <当前Agent完整键> --input /opt/data/私有目录/employee-name.json --request-id <本次操作稳定标记>

加密入口调用 ksfEmployeeDisplayName。读取需data:read;保存需额外ingest:write,两者均核对当前员工及Agent。读取、保存、回读使用不同requestId;相同保存请求幂等,改称呼使用新requestId。成功保存返回persisted=true、readOnly=false、businessRecordsChanged=0,随后省略displayName/skip回读确认。昵称通常source=self_reported、nameVerified=false;已有有效通讯录实名会优先返回,不将昵称替换实名。skip不会清除已有称呼。

不改本地participant档案的name,不把昵称注入workshop-save/report/rawText,不重存旧报告。首次仅导入资料尚无session时,按SKILL.md临时记住本人回答,正常会话建立后同步;不为改名新建session。无目录配置也能使用本命令,不自动调用employee-read。

员工实名最小查询:employee-read

本命令虽只读,仍必须传当前workshop角色的 --agent-profile,并先调用 ksf_register_current_employee 取得本条真实消息的员工profile.key。输入仅为已有会话和员工档案引用,不含姓名、账号或密钥:

{"sessionId":"已核对归属的会话编号","participant":{"profileKey":"本条消息登记返回的员工完整档案键"}}
node /opt/data/skills/ksf-workshop-runtime/scripts/ksf-secure.mjs employee-read --agent-profile <本条消息登记返回的Agent完整键> --input /opt/data/实际私有目录/employee-read.json --request-id <本次查询标记>

入口先读取KfSession并核对Agent及工作坊参与键派生关系,再通过现有加密凭据调用 ksfReadWecomEmployee。后端只需 data:read,验证服务owner、员工与Agent后从会话私有快照查询企微;不写服务端身份档案、审计或业务记录,不需要identity:write,不改变已有身份/同步函数。未知姓名不能从公开看板或模型猜测补齐。

成功查看 entryResult.result 的 employee.name、source=wecom_directory、nameVerified=true、verifiedAt,以及 readOnly=true、databaseWrites=0、employeeIdentity.persisted=false。错误按真实回执报告:WECOM_DIRECTORY_NOT_CONFIGURED为服务端通讯录配置缺失,WECOM_SENDER_MAPPING_REQUIRED为映射缺失,FORBIDDEN为读取权限/归属受限。命令在本地失败和远端返回错误要区分;远端错误附 remoteFunction、remoteResponseReceived。不重试、不换键、不使用运维凭据;临时输入及回执位于 /opt/data/ 下私有目录。查询不更新看板,展示同步仍由运维或正常上传流程完成。

1. workshop-start

部署前可用 workshop-contract 输入 {} 只读读取合同;身份扩展标识应为 workshop.identitySchema: ksf.agent-self.v1。新版 start 会检查,不支持时在写入之前停止。本地身份登记不依赖该能力。

企微 aibot 若已有接入层可信 from.userid,优先按 identity.md 自动登记并取得 profileKey,无需员工填写账号。该类型还须 channelIdentitySchema=ksf.wecom-aibot-sender.v1,执行 Agent 的实际botid须与员工账号scopeId一致。没有接入层逐消息上下文时不要制造文件冒充已接通。

{
  "workshopKey": "实际工作坊标识",
  "participant": {"profileKey":"register-employee 返回的完整档案键"},
  "conversation": {"key":"实际会话键","channel":"wecom"},
  "groupId":"实际组号,没有则空字符串",
  "dataMode":"manual"
}

participant 不接收临时 key/account/userId;这些字段与 identityBasis 由员工档案注入。Agent 同样由所选自身档案注入。缺任一档案时创建前停止,账号格式和登记命令见 identity.md。员工登记中的 userId 仅能填写本应用已有 _User.objectId;企微 userId、工号另填 account。dataMode 描述材料:manual 为人工取得的实际资料,live 为实际在线采集,构造演示/待查清单为 sample;与身份如何登记无关。

启用通讯录扩展后,start 成功返回 sessionId、participantKey 以及 employee、employeeIdentity。员工姓名来自服务端查询,不在 start 输入中新增 employee 字段;核对规则见 identity.md。旧服务没有实名回执时,只能确认 session 已建,不能声明姓名已核验。

2. workshop-save

{
  "sessionId":"start 返回值",
  "projectId":"已有项目编号;尚未立项时省略",
  "taskKey":"稳定任务键",
  "version":1,
  "stageCode":"S3",
  "title":"阶段报告标题",
  "artifactType":"opportunity_card",
  "category":"拌面",
  "rawText":"本次阶段成果完整正文,不是消费者原话的替代品",
  "sourceIds":[],
  "pendingQuestions":["尚缺的证据或条件"],
  "report":{
    "executive":["摘要,明确事实、假设和缺口"],
    "chapters":[{"id":"c1","title":"机会分析","stage":"S3","sections":[{"kind":"para","title":"待验证问题","text":"实际内容"}]}]
  },
  "opportunity":{
    "key":"稳定机会系列键","title":"机会标题","demandSummary":"需求描述",
    "targetAudience":"待研究或已获证据的人群","usageScenario":"对应场景","fusionDefinition":"赛道×用户×场景,逐项说明依据与缺口"
  }
}

可用 artifactType:category_report / competitor_report / voc_report / pain_list / opportunity_card / assessment_report / concept。opportunity 可省略;存在时保存独立机会卡并关联报告。来源、报告、机会和进度在同一事务保存,冲突时回滚。报告输入不接受 HTML。

不在 save 里填写 dataMode,继承 start 建立的 session。待查清单无真实研究材料时从 start 使用 sample,并将缺项逐项放入 pendingQuestions。

report 采用现有看板结构:executive 数组,chapters 数组。小节支持 para/longpara(text)、table/matrix(data.cols、data.rows)、findings(data 为含 conclusion/attitude/evidence 的数组)、two、milestones 等现有类型。不要自造 kind: text。

引文放 report.evidence 对象,例如 e1:{sourceId:"已保存来源编号",claim:"待论证判断",quotes:[{text:"逐字原话",ref:"原始定位"}]}。sourceId 必须同时在 sourceIds;服务逐字检查引文是否存在于来源 rawText,不匹配就拒绝。来源链接不能代替已取得正文。构造样例即便文字匹配,也不会被升级成真实证据。

企微员工上传前用当前消息登记工具核对 session 所属员工,不能沿用同群其他人的 session。save 由服务端按 session 私有归属取得员工账号并查询实名,成功时附 employee 和 employeeIdentity;不要把员工账号、通讯录密钥写进 rawText/report,也不新增手工身份参数。保存成功但实名 pending/缺少回执时,保留 artifactId、原 requestId 并继续成果回读,单列实名待同步,不因姓名问题再次保存。服务报错或结果未知时保留原键核查。完整状态处理见 identity.md。

3. project-create / project-progress

create:{"sessionId":"…","opportunityId":"…","projectKey":"稳定项目键","title":"项目名称"}。

progress:{"sessionId":"…","projectId":"…","toStage":"S4","state":"in_progress","note":"本次推进依据"}。

项目从 S3 建立,只允许当前阶段或推进一阶段;当前阶段没有项目成果不能前进。state:in_progress / blocked / completed,completed 仅用于 S5 且须有方案。创建的是课堂项目,不是企业正式审批。

4. concept-save / project-status

{
  "sessionId":"…","projectId":"…","version":1,
  "concept":{
    "name":"拟定名称","targetAudience":"人群","usageScenario":"场景",
    "specification":{"packaging":"已知包装或明确待验证","netWeightG":null},
    "valueProposition":"用户买点","flavor":"风味方向",
    "sellingPoints":["待验证卖点"],"productionSteps":[],"pendingQuestions":["企业工艺资料未提供"]
  },
  "formulaItems":[]
}

配料有资料时每条为 {materialId,component,amount,unit,basis,note};materialId 必须实际存在。amount 未知时省略,不能用 0 冒充。basis 明确每份、每批、每 100g 等计算基准。productionSteps 保留路线、processId 和约束依据;缺资料时空数组并说明缺口。方案版本连续递增。

project-status:{"sessionId":"…","projectId":"…"},回读项目、成果、事件、当前方案及配料。

5. workshop-import / workshop-search

先 search 当前合同支持的表,避免重建已有实体。search 输入沿用 ksfSearchRecords:{className,keyword,filters,limit,cursor,noiseContext};raw/evidence 查询须指定真实研究范围与噪声规则,未判断资料选 pending/all,不能算作可用证据。

filters 仅支持 reportType/dataMode/platform/projectId/recordState/category/stageCode/dashboardState,不支持 sessionId。精确回读改用 workshop-read:{"className":"KfArtifact","objectId":"保存返回的 artifactId"};会话用 KfSession 和 sessionId。返回仍经服务鉴权,CLI 移除私有账号/会话键,不把内部身份资料复制进聊天。

VOC 采集前的检索与复用

  1. 从员工需求和上下文确定实际约束、证据类型和统计口径。商品/评论/价格/政策底料先查ksf-voc-library;报告/机会/证据/项目查工作坊业务库。附件或采集工具缓存不代表已入库。已知sourceId/对象编号先精确回读,不凭旧报告标题推断库里有原文。
  2. 研究库用contract支持的类型化条件、search正文、aggregate统计及get/source核原文,不向旧workshop-search添加不存在的精确筛选字段。业务库仍用workshop-contract核表与字段,再按下表映射workshop-search。分页只沿本次条件与代际继续;总量统计优先aggregate,未查完只报已查范围,不能声称全库没有或全量分析。
  3. 核对命中资料的相关性、覆盖、来源编号/原文、观察或有效时间、dataMode及审核/噪声状态。以员工要求的时段和实际资料性质判断时效,不统一写死有效天数;采集日期不等于价格观察日或政策生效日。未判断的 raw/evidence 保持 pending/all,只作待审素材;sample 不充作真实证据。访问失败的旧私有来源不能直接引用,也不扩大服务权限解锁。
  4. 够用且有效:复用真实编号与可追溯原文,注明适用时段,不调用 VOC。部分缺失或已过期:保留可用部分,列出具体缺口(如某店/规格、评论时间段或最新价格快照),仅对缺口发起已授权采集。查询成功且所需范围内确无命中:按本次研究范围安排采集。用户要求“最新/重新采集”时,已有记录用于定位与比较,仍获取满足要求的新快照,不拿旧记录阻止刷新。
  5. 查询失败、权限不足或分页不完整时,明确失败环节与实际已查范围;先解决查询问题,或由用户明确决定是否在该信息不足条件下继续采集,不悄悄改成全量抓取。VOC 的平台、分页、增量参数和覆盖能力以实际工具为准;工具不支持按缺口精确补采时先说明范围限制,不假称已做增量采集。
  6. 补采取得实际原文后,按原有 workshop-dedup → workshop-import → 编号回读流程处理。入库查重只避免重复存储,不能替代采集前检索。仅检索或复用不新建会话、不上传报告;进入实际入库/上传时再执行现有称呼与归属流程。

向员工简报“查了什么范围、实际命中及可复用什么、还缺什么、VOC 实际补采什么、保存/复用的编号与时间”。区分记录数、独立来源数、评论数,不把本地原件数量说成已入库数量,不把多条引文说成多人反馈。查询和采集仍使用各自实际权限,不新增接口或权限。

import 输入:{source:{title,sourceKind,dataMode,rawText,...实际来源信息},records:[{itemKey,className,externalKey,data,dependsOn?}]}。逐表字段以本次服务合同为准,先本地核对必填项、原文与单位。引用前面条目使用 {"$item":"前条 itemKey"},并在 dependsOn 声明;服务返回真实编号后才转换 Pointer。sourceRef 由入口补入;data.dataMode 必须与 source.dataMode 一致。

映射:

内容 表
面类分类、分类关系 KfCategory、KfCategoryRelation
竞品及具体规格 KfProduct、KfSku、KfRetailPriceSnapshot
用户原文、引用和洞察 平台原始表、KfEvidence、KfEvidenceLink、KfInsight
原料、工艺路线、工序、执行标准 KfMaterial、KfProcess、KfProcessStep、KfStandard
供应商、报价、成本依据 KfSupplier、KfSupplyQuote
指标、验证模型与结果 KfMarketMetric、KfAssessment

报告、机会卡、项目、方案和配料用各自工作坊命令,不用通用导入绕过归属和阶段规则。导入按依赖逐条预检、提交和回执核对;整批不是单一事务,失败时可能已落部分条目,保持业务键回读,不能自动清理或换键。

采集资料查重

workshop-dedup输入与workshop-import相同,包含source和records;只读,不登记来源、不建导入任务。source要求实际rawText、sourceKind和dataMode,不能只有URL。输出readOnly=true、schema=ksf.ingest-dedup.v1、source.operation以及items[].decision:reuse=精确命中;no-exact-match=当前未命中,仍须校验提交;deferred=来源尚未登记或依赖尚未解析,实际提交时再查。预检结果不是可跳过服务端校验的写入许可。

来源按原文内容SHA-256、来源类型、dataMode、原样sourceUrl/platform及当前服务owner作用域查重;标题和采集时间不作为原文内容。源记录保留首次来源元数据,后续采集执行/回执保留批次。不同URL暂不自动视为同源,不删URL参数,文件在原件验证后走服务端查重。

结构化资料比较完整已提交业务字段,不以名称作唯一键;有sourceRef的普通实体限定同一已复用来源,无sourceRef的分类/关系等按完整字段比较。原始平台记录有真实upstream ID时按表+platform+externalObjectId+dataMode查询,并比较完整载荷及业务内容;仅排除采集批次、索引、抓取时间和服务端审核/噪声状态,保留原始载荷中的数值与时间。无upstream ID只在同源、同索引、同载荷下复用。不同内容/报价/观察时间或SKU不合并。历史人工判断不被重采覆盖。超出扫描上限明确DEDUP_SCAN_LIMIT,不将未查完说成无重复。

workshop-import返回sourceOperation、counts.created/unchanged及真实逐条operation/objectId,引用后续实体必须用实际回执编号,不能坚持使用本次计划新建编号。数据不同且业务键已有内容时仍IDEMPOTENCY_CONFLICT,按新事实设计版本,不自动换键重试。新采集资料与正常审计会增加,精确重复不重复创建实体,旧历史重复不在本命令清理范围。

全部表字段(workshop-schema)

完整路线见full-schema-and-intake.md,离线逐字段字典为business-data-dictionary.json。workshop-schema使用data:read,不要求agent-profile或员工身份,不创建会话。input可为{}、{"table":"KfProduct"}或{"summary":true};实际结构与本地声明不同须报告差异,不能猜字段写入。返回的是元信息,入库允许项仍以workshop-contract和专用操作为准。