# 竞价系统-数据对接
# 概述
目前竞价系统与高校其它系统对接的方式有三种方式:统一数据接口,中间库对接,竞价系统调用对方接口。 可以通过参数order.dataInterchange.type.value进行控制, 数据对接类型(0:无数据对接;1:数据接口;2:中间库;3:对方提供接口),开启多种时以逗号隔开。
# 统一数据接口
- 验签机制
- 数据接口使用CXF Webservice实现,传参和返回均为JSON格式
- 处理验签是在拦截器WebServiceInInterceptor中。
- 这些接口都有两个POST参数,jsonData和signKey,其中,signKey = SHA1(jsonData + 接口密钥),
- 程序会对signKey的提交值和计算值进行比较,如果不一致,则验证失败。
- 提供的接口
- 提交申购需求 /college/services/operation/submitOrderNew
- 获取成交结果 /college/services/queryBid/getOrderResultNew
- 按条件查询申购单(竞价公告、结果公告) /college/services/queryBid/getOrdersAll
- 查询终止申购单 /college/services/queryBid/getAborts
- 查询再成交申购单 /college/services/queryBid/getReOrders
- 以上接口,操作类(/operation)的实现在OperationWebServiceImpl, 查询类(/queryBid)的实现在QueryBidWebServiceImpl
- 接口文档已上传SVN svn://39.108.127.82/manager/竞价/接口文档/高校网上竞价采购平台
- 接口调用记录 每一次接口调用,无论成功还是失败,都会记录在log_inter_fail中 (由于之前只记录失败记录,所以表名是这个名称,该表的时间字段是CALL_TIME)
# 中间库对接
实现机制
- 高校端通过定时任务DataInterchangeJob来执行数据对接(含中间库对接、调用对方接口获取)
- 在定时任务中会调用C8001(从对接系统获取申购信息)和C8002(推送竞价结果到对接系统)操作
- 如果高校在这基础上还要推送其它的(比如南昌大学需要把申购单当前节点同步到采购系统), 则可以写一个高校个性化的操作类,然后配置到对应的操作上
属性转换
- 在order.dataInterchange.config.database.sql.getOrderInfo.propertyConvert.value中进行配置,
配置格式为a=field1,b=filed2,等号左边是中间库字段名,右边是java字段名(如果是明细属性,则加上detail前缀),例如如果某个java字段需要多个中间库字段组成,则可以配置为以下形式,${xxx}中的xxx为中间库字段
CgID=otherId,orderTitle=orderTitle,detail.deviceType=deviceType,foundsSubject=foundsSubject,foundsCode=foundsCode,usingCorrentcy=usingCorrency,budget=budget,deliverTime=deliverTime,deliverPlace=deliverPlace,orderPerson=orderPerson,orderUnit=orderUnit,orderTime=orderTime,personPhone=personPhone,remark=remark,createUsername=createUsername,isTax=isTax
如果某个java字段需要很复杂的判断,则可以通过 .order.dataInterchange.config.database.sql.getOrderDetail.jsonTemplate.value进行配置, 配置内容为JSON,key都是java字段名,只是value变成了FreeMarker的模板, 其中出现的${xxx}都是中间库字段。${a}-${b}=remark
(通过JSON可视化工具配置不需要手动转义双引号,但直接改数据库就要手动转义了){ "deviceSpec": " <#switch TYPE> <#case 1>${GG}<#break> <#case 2>${GG};材质:${CZ}<#break> <#case 3>出版社:${CBS};出版日期:${CBRQ}<#break> <#case 4>纲属科:${GSK};产地:${CD}<#break> </#switch>" }
- 明细的属性转换在order.dataInterchange.config.database.sql.getOrderDetail.propertyConvert.value 中配置,配置格式和上面相同
- 推送结果回去的字段在order.dataInterchange.config.database.sql.pushBidResult.targetProperties.value
中进行配置,如(前缀的意义为 main:主单;detail:明细;bid:竞价信息;company:成交企业信息;sync:中间库同步表信息)
detail.status,detail.bidPrice,detail.bidAmount,detail.bidAmountRenminbi,detail.companyName,company.realName,company.authorizedPhone,detail.otherDetailId
- 在order.dataInterchange.config.database.sql.getOrderInfo.propertyConvert.value中进行配置,
配置格式为a=field1,b=filed2,等号左边是中间库字段名,右边是java字段名(如果是明细属性,则加上detail前缀),例如
数据获取流程
- 从中间库获取未获取的采购计划(未记录在同步表中,一般用联表或者not exists来实现)
- 根据该采购计划生成申购单,随后再同步表插入一条记录,表示该采购计划已经获取过了
结果推送流程
- 查询同步表中尚未推送结果的采购计划对应的申购单
- 根据参数的属性转换后,插入中间库的成交结果表中
# 竞价系统调用对方接口
- 这种方式的对接需要单独实现代码,可以通过操作来实现,然后将该操作配置到 C8001操作(从对接系统获取申购信息)。
- 之前宁波大学是采用这种方式(DataInterchangeGetOperationNbu),但其更换采购系统后, 改为使用统一数据接口对接,目前暂时没有高校使用这种对接方式。
# 默认值
- 通过order.dataInterchange.config.common.defaultValue.simpleProperty.value 可以配置主单字段的默认值,配置格式为a=val1,b=val2,示例如下
orderType=1,budgetIsOpen=N,isTax=A,priceType=1,isImplemented=Y,isInvoice=Y,invoiceType=1,isDeliver=Y,deliverType=1,usingCorrency=人民币,payType=货到验收合格后付款,remark=不接受快递送货
- 明细字段的默认值可以通过order.dataInterchange.config.common.defaultValue.detailProperty.value 来配置,格式与上面一样。
# 附件对接
- 将附件下载到输出流中,转换为字节数组,通过oss微服务进行上传
- 对于获取附件失败的情况,依然插入附件信息(没有路径),在备注设置附件地址
- 由于获取附件耗时较长,因此采用异步操作,这就需要提前生成明细ID和主单ID,否则附件信息将无法绑定申购单。 因此在对应的DTO中增加了预设置ID值preDetailId和preOrderMainId,在生成ID时优先使用预设值ID