HeiHuOrderServiceImpl.java 126 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206
  1. package com.malk.fenggefushi.service.Impl;
  2. import cn.hutool.core.util.ObjectUtil;
  3. import com.alibaba.fastjson.JSON;
  4. import com.alibaba.fastjson.JSONArray;
  5. import com.alibaba.fastjson.JSONObject;
  6. import com.fasterxml.jackson.core.JacksonException;
  7. import com.fasterxml.jackson.core.JsonProcessingException;
  8. import com.fasterxml.jackson.databind.JsonNode;
  9. import com.fasterxml.jackson.databind.ObjectMapper;
  10. import com.malk.fenggefushi.service.HeiHuOrderService;
  11. import com.malk.server.aliwork.YDConf;
  12. import com.malk.server.aliwork.YDParam;
  13. import com.malk.server.aliwork.YDSearch;
  14. import com.malk.server.common.McR;
  15. import com.malk.server.dingtalk.DDConf;
  16. import com.malk.service.aliwork.YDClient;
  17. import com.malk.service.aliwork.YDService;
  18. import com.malk.utils.UtilHttp;
  19. import com.malk.utils.UtilMap;
  20. import lombok.SneakyThrows;
  21. import lombok.extern.slf4j.Slf4j;
  22. import org.springframework.beans.factory.annotation.Autowired;
  23. import org.springframework.stereotype.Service;
  24. import java.math.BigDecimal;
  25. import java.time.Instant;
  26. import java.time.LocalDate;
  27. import java.time.LocalDateTime;
  28. import java.time.ZoneId;
  29. import java.time.format.DateTimeFormatter;
  30. import java.util.*;
  31. import java.util.concurrent.ConcurrentHashMap;
  32. import java.util.stream.Collectors;
  33. @Slf4j
  34. @Service
  35. public class HeiHuOrderServiceImpl implements HeiHuOrderService {
  36. @Autowired
  37. private YDClient ydClient;
  38. @Autowired
  39. private YDConf ydConf;
  40. @Autowired
  41. private YDService ydService;
  42. @Autowired
  43. private DDConf ddConf;
  44. private ConcurrentHashMap<String, LocalDateTime> tokenStore = new ConcurrentHashMap<>();
  45. /*登录获取黑湖登录token*/
  46. @Override
  47. public McR HeiHuAccessToken() throws JacksonException {
  48. final String[] token = {""};
  49. final boolean[] isHave = {false};
  50. tokenStore.forEach((k, v) -> {
  51. if (validateToken(k)) {
  52. token[0] = k;
  53. isHave[0] = true;
  54. }
  55. });
  56. if (!isHave[0]) {
  57. HashMap body = new HashMap();
  58. body.put("type",1);//type=1,登录方式为工厂代号+账号+密码
  59. body.put("code","648910");//工厂代号
  60. body.put("username","FGJK");//账号
  61. body.put("password","b715db070346a8a59e0eba5da27f8e4938536bb7867e09592326fde2");//密码加密
  62. HashMap header = new HashMap();
  63. header.put("X-CLIENT","lite-web");//固定
  64. header.put("Content-Type","application/json");
  65. String s = UtilHttp.doPost("https://liteweb.blacklake.cn/api/user/v1/users/_login", header, null, body);
  66. // String data = new ObjectMapper().readTree(s).get("data").asText();
  67. token[0] = new ObjectMapper().readTree(s).get("data").asText();
  68. addToken(token[0],70);
  69. }
  70. return McR.success(token[0]);
  71. }
  72. /**
  73. * token存储
  74. * @param token
  75. * @param expireHours
  76. */
  77. public void addToken(String token, int expireHours) {
  78. LocalDateTime expirationTime = LocalDateTime.now().plusHours(expireHours);
  79. tokenStore.put(token, expirationTime);
  80. }
  81. /**
  82. * 清理过期token
  83. * @param token
  84. * @return
  85. */
  86. public boolean validateToken(String token) {
  87. LocalDateTime expirationTime = tokenStore.get(token);
  88. if (expirationTime == null || expirationTime.isBefore(LocalDateTime.now())) {
  89. tokenStore.remove(token); // 清理过期 Token
  90. return false;
  91. }
  92. return true;
  93. }
  94. /*抓取黑湖工单发起宜搭审批流程*/
  95. @Override
  96. public McR StartYidaAproval(String OrderNo,String fromUuid) throws JacksonException {
  97. HashMap header = new HashMap();
  98. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  99. header.put("Content-Type","application/json");
  100. HashMap body = new HashMap();
  101. body.put("orderNo",OrderNo);//订单编码
  102. /*TODO:对json进行处理*/
  103. String jsonString = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", header, null, body);
  104. JSONObject jsonObject = JSONObject.parseObject(jsonString);
  105. JSONArray dataArray = jsonObject.getJSONArray("data");
  106. //基础信息字段
  107. String orderNo = ""; String customerName = "";Long orderTime = null;Long arrivalPlanTime = null;String contractNo = "";
  108. String operatorName = "";double orderDiscount = 0;String customerCode = "";
  109. // 提取自定义字段
  110. String productPhoto = "";//产品照片:182852
  111. String sampleType = "";//样品类型:69230
  112. String processType = "";//工艺类型:47768
  113. String productType = "";//产品类型:47770
  114. String orderType = "";//订单类型:47771
  115. String department = "";//部门:47777
  116. String season = "";//季节:47778
  117. String expectedOrderQty = "";//预计下单量:59314
  118. double estimatedUnitPrice = 0;//辅料预估单价:161769
  119. String purchaseOrderNumber = "";//对应预采购单号:113495
  120. String qualityConfirmation = "";//品质确认:113119
  121. String materialCycle = "";//物料周期:113086
  122. //产品详情字段
  123. String productCode = "";String productName = "";String productSpec = "";int productStockQty;int qty;
  124. String productUnitName = "";double unitPrice;double amount;double discount;double taxInclusiveAmount;
  125. double taxRate;String productArrivalPlanTime = "";String productOriginType = "";
  126. //其他信息
  127. String contactName = "";String contactNumbers = "";String contactAddress = "";
  128. for (int i = 0; i < dataArray.size(); i++) {
  129. JSONObject data = dataArray.getJSONObject(i);
  130. // 提取订单基本信息
  131. orderNo = data.getString("orderNo");//订单编号:orderNo
  132. customerName = data.getString("customerName");//客户:customerName
  133. orderTime = data.getLong("orderTime");//下单日期:orderTime
  134. arrivalPlanTime = data.getLong("arrivalPlanTime");//计划交货日期:arrivalPlanTime
  135. contractNo = data.getString("contractNo");//合同号:contractNo
  136. operatorName = data.getString("operatorName");//业务员:operatorName
  137. orderDiscount = data.getDoubleValue("orderDiscount")*100;//整单折扣:orderDiscount
  138. customerCode = data.getString("customerCode");//客户名称:customerCode
  139. //提取其他信息
  140. contactName = data.getString("contactName");//联系人
  141. contactNumbers = data.getString("contactNumbers");//联系电话
  142. contactAddress = data.getString("contactAddress");//联系地址
  143. JSONArray customFields = data.getJSONArray("customFieldValues");
  144. if (customFields != null) {
  145. for (int j = 0; j < customFields.size(); j++) {
  146. JSONObject field = customFields.getJSONObject(j);
  147. long fieldId = field.getLongValue("fieldId");
  148. String value = field.getString("value");
  149. switch ((int)fieldId) {
  150. case 70931: productPhoto = value; break;
  151. case 69230: sampleType = value; break;
  152. case 47768: processType = value; break;
  153. case 47770: productType = value; break;
  154. case 47771: orderType = value; break;
  155. case 47777: department = value; break;
  156. case 47778: season = value; break;
  157. case 59314: expectedOrderQty = value;break;
  158. case 161769: estimatedUnitPrice = Double.parseDouble(value);break;
  159. case 113495:purchaseOrderNumber = value;break;
  160. case 113119:qualityConfirmation = value;break;
  161. case 113086:materialCycle = value;break;
  162. }
  163. }
  164. }
  165. }
  166. /*判断订单类型来封装数据*/
  167. HashMap formdata = new HashMap();
  168. /*主表*/
  169. formdata.put("textField_mfqgmwcw",orderNo);
  170. formdata.put("textField_mfqgmwcx",customerName);
  171. formdata.put("dateField_mfqgmwcy",orderTime);
  172. formdata.put("dateField_mfqgmwcz",arrivalPlanTime);
  173. formdata.put("textField_mfqgmwd5",contractNo);
  174. formdata.put("textField_mgc0kc5u",operatorName);
  175. formdata.put("numberField_mfqgmwd7",orderDiscount);
  176. formdata.put("selectField_mg5y3rcr",orderType);
  177. formdata.put("textField_mfqgmwdn",processType);
  178. formdata.put("textField_mfqgmwdo",productType);
  179. formdata.put("textField_mg5y3rda",department);
  180. formdata.put("textField_mfqgmwdx",season);
  181. formdata.put("textField_mfqi6ui8",contactName);
  182. formdata.put("textField_mfqi6ui9",contactNumbers);
  183. formdata.put("textField_mfqi6uia",contactAddress);
  184. List<Map<String, Object>> imageAttachments = new ArrayList<>();
  185. //处理多照片
  186. if(productPhoto != null && productPhoto.contains(",")){
  187. String[] photoUrls = productPhoto.split(",");
  188. for (String url : photoUrls){
  189. String trimmedUrl = url.trim();
  190. if(!trimmedUrl.isEmpty()){
  191. Map<String, Object> imageInfo = new HashMap<>();
  192. imageInfo.put("name",productType);
  193. imageInfo.put("downloadUrl",trimmedUrl);
  194. imageInfo.put("previewUrl",trimmedUrl);
  195. imageInfo.put("url",trimmedUrl);
  196. imageInfo.put("ext","png");
  197. imageAttachments.add(imageInfo);
  198. }
  199. }
  200. }else {
  201. HashMap<String,Object> imageInfo = new HashMap();
  202. imageInfo.put("name",productType);
  203. imageInfo.put("downloadUrl",productPhoto);
  204. imageInfo.put("previewUrl",productPhoto);
  205. imageInfo.put("url",productPhoto);
  206. imageInfo.put("ext","png");
  207. imageAttachments.add(imageInfo);
  208. }
  209. formdata.put("imageField_mfqgmwde",imageAttachments);
  210. if(orderType.equals("样品订单")){
  211. formdata.put("textField_mfqgmwdh",customerCode);
  212. formdata.put("textField_mg5y3rdd",sampleType);
  213. formdata.put("textField_mgc1xl62",expectedOrderQty);
  214. }else if(orderType.equals("贸易公司订单")){
  215. formdata.put("numberField_mg5y3rcx",estimatedUnitPrice);
  216. formdata.put("textField_mg5y3rcy",purchaseOrderNumber);
  217. formdata.put("textField_mg5y3rcz",qualityConfirmation);
  218. formdata.put("textField_mg5y3rd0",materialCycle);
  219. formdata.put("textField_mfqgmwdh",customerCode);
  220. }else{
  221. formdata.put("textField_mfqgmwdh",customerCode);
  222. }
  223. /*子表*/
  224. JSONArray products = jsonObject.getJSONArray("data").getJSONObject(0).getJSONArray("saleManageOrderDetailRowApiVOList");
  225. List<Map<String,Object>> tableData = new ArrayList();
  226. if (products != null) {
  227. for (int i = 0; i < products.size(); i++) {
  228. JSONObject detail = products.getJSONObject(i);
  229. HashMap row = new HashMap();
  230. //
  231. String color = "";
  232. JSONArray array1 = detail.getJSONArray("customFieldValues");
  233. color = array1.stream()
  234. .map(obj -> (JSONObject) obj)
  235. .filter(item -> item.getIntValue("fieldId") == 82259)
  236. .map(item -> item.getString("value"))
  237. .findFirst()
  238. .orElse(null);
  239. ArrayList colorList = new ArrayList();
  240. colorList.add(color);
  241. String color_AAA = getProductColor(colorList);
  242. row.put("textField_mk0jz9i1",color_AAA);//中文颜色
  243. row.put("textField_mfqgmwe1",detail.getString("productCode"));//产品编号
  244. row.put("textField_mfqgmwe2",detail.getString("productName"));//产品名称
  245. row.put("textField_mfqgmwe3",detail.getString("productSpec"));//产品规格
  246. row.put("textField_mfqgmwe4","0".equals(detail.getString("productOriginType")) ? "自制" : "其它");//产品属性
  247. row.put("numberField_mfqgmwe5",detail.getIntValue("productStockQty"));//库存数量
  248. row.put("numberField_mfqgmwe6",detail.getIntValue("qty"));//数量
  249. row.put("textField_mfqgmwe7",detail.getString("productUnitName"));//单位
  250. row.put("numberField_mfqgmwe8",detail.getDoubleValue("unitPrice"));//单价
  251. row.put("numberField_mfqgmwe9",detail.getDoubleValue("amount"));//报价金额
  252. row.put("numberField_mfqgmwea",detail.getDoubleValue("discount")*100);//折扣
  253. row.put("numberField_mfqgmweb",detail.getDoubleValue("taxInclusiveAmount"));//折扣
  254. row.put("numberField_mfqgmwec",detail.getDoubleValue("taxRate"));//税率
  255. row.put("dateField_mfqgmwed",detail.getLong("arrivalPlanTime"));//产品交货日期
  256. tableData.add(row);
  257. }
  258. }
  259. formdata.put("tableField_mfqgmwe0",tableData);
  260. System.out.println(formdata);
  261. /*发起流程*/
  262. String userid = getDDToken(operatorName);
  263. String dd = ydClient.operateData(YDParam.builder()
  264. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  265. .formUuid(fromUuid)
  266. .userId(userid)
  267. .formDataJson(JSON.toJSONString(formdata))
  268. .build(), YDConf.FORM_OPERATION.start).toString();
  269. log.info("----------【销售订单】已发起----------");
  270. return McR.success(dd);
  271. }
  272. @Override
  273. public String getDDToken(String Name) {
  274. HashMap body = new HashMap();
  275. body.put("appKey","dingie28nalt6tcnzizl");
  276. body.put("appSecret","Ss7na86M_BWPEXhKffiQDA-8jXvuBhBklfD8C-ot7xGwiDKfFMIf9y00mXYutfCB");
  277. String s = UtilHttp.doPost("https://api.dingtalk.com/v1.0/oauth2/accessToken", null, null, body);
  278. String accessToken = JSONObject.parseObject(s).getString("accessToken");
  279. HashMap header = new HashMap();
  280. header.put("x-acs-dingtalk-access-token",accessToken);
  281. HashMap bodyy = new HashMap();
  282. bodyy.put("queryWord", Name);
  283. bodyy.put("offset",0);
  284. bodyy.put("size",10);
  285. String s1 = UtilHttp.doPost("https://api.dingtalk.com/v1.0/contact/users/search", header, null, bodyy);
  286. List<String> list = JSONObject.parseObject(s1).getJSONArray("list").toJavaList(String.class);
  287. String userId = "";
  288. if(list!= null && !list.isEmpty()){
  289. userId = list.get(0);
  290. }
  291. return userId;
  292. }
  293. @SneakyThrows
  294. @Override
  295. public McR startYidaProcurementAproval(String OrderNo,String FormUuType) throws JsonProcessingException {
  296. HashMap header = new HashMap();
  297. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  298. header.put("Content-Type","application/json");
  299. HashMap body = new HashMap();
  300. body.put("orderCode",OrderNo);//订单编号
  301. String jsonString = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//todo:查询采购订单
  302. JSONArray dataArray = JSONObject.parseObject(jsonString).getJSONArray("data");
  303. //基础信息字段
  304. String orderCode = "";String shortName = "";Long purchaseTime = null;Long planArrivalTime = null;String purchaserName = "";
  305. String gysnumber = "";
  306. double orderDiscount = 0;
  307. //自定义信息
  308. String department = "";//部门:186341
  309. String add = "";//地址:32869
  310. String SalesOrderNumber = "";//销售订单号:59332
  311. String PaymentStatus = "";//付款情况:55674
  312. String PortOfShipment = "";//出运地:42003
  313. String ShippingStatus = "";//出运状态:42002
  314. //产品详情字段
  315. String productCode = "";String productName = "";String productSpec = "";int purchaseNum;
  316. String unitName = "";double purchasePrice;double purchaseAmount;double discount;double taxInclusiveAmount;
  317. double taxRate;Long productArrivalPlanTime = null;
  318. //其他信息
  319. String contactName = "";String contactNumber = "";String contactAddress = "";
  320. for (int i=0;i<dataArray.size();i++){
  321. JSONObject data = dataArray.getJSONObject(i);
  322. //提取订单基本信息
  323. orderCode = data.getString("orderCode");//订单编号:orderCode
  324. shortName = data.getString("shortName");//供应商:shortName
  325. gysnumber = data.getString("vendorCode");//供应商编码:gysnumber
  326. purchaseTime = data.getLong("purchaseTime");//采购日期:purchaseTime
  327. planArrivalTime = data.getLong("planArrivalTime");//计划到货日期:planArrivalTime
  328. purchaserName = data.getString("purchaserName");//采购员:purchaserName
  329. orderDiscount = data.getDouble("orderDiscount");//整单折扣:orderDiscount
  330. //其他信息
  331. contactName = data.getString("contactName");//联系人
  332. contactNumber = data.getString("contactNumber");//联系电话
  333. contactAddress = data.getString("contactAddress");//联系地址
  334. //自定义信息
  335. JSONArray customFields = data.getJSONArray("customFieldValues");
  336. if(customFields != null){
  337. for (int j = 0; j < customFields.size(); j++) {
  338. JSONObject field = customFields.getJSONObject(j);
  339. long fieldId = field.getLongValue("fieldId");
  340. String value = field.getString("value");
  341. switch ((int)fieldId){
  342. case 186341: department = value;break;
  343. case 59391:
  344. JSONObject associatedDetail = field.getJSONObject("associatedObjectValueDetail");
  345. if(associatedDetail != null && !associatedDetail.isEmpty()) {
  346. add = associatedDetail.getString("vendorContactAddress");
  347. }
  348. break;
  349. case 59332: SalesOrderNumber = value;break;
  350. case 55674: PaymentStatus = value;break;
  351. case 42003: PortOfShipment = value;break;
  352. case 42002: ShippingStatus = value;break;
  353. }
  354. }
  355. }
  356. }
  357. /*开始封装数据*/
  358. //采购订单-基础信息
  359. HashMap formdata = new HashMap();
  360. formdata.put("textField_mfqia327",orderCode);
  361. formdata.put("textField_mfqia328",shortName);
  362. formdata.put("textField_mkaudmn6",gysnumber);
  363. formdata.put("dateField_mfqia329",purchaseTime);
  364. formdata.put("dateField_mfqia32a",planArrivalTime);
  365. formdata.put("employeeField_mfqia32g",getDDToken(purchaserName));
  366. formdata.put("numberField_mfqia32h",orderDiscount*100);
  367. //采购订单-自定义
  368. formdata.put("textField_mfqia32o",department);
  369. formdata.put("textField_mfqia32q",add);
  370. formdata.put("textField_mfqia32r",SalesOrderNumber);
  371. formdata.put("textField_mfqia32x",PaymentStatus);
  372. formdata.put("textField_mfqia32y",PortOfShipment);
  373. formdata.put("textField_mfqia32z",ShippingStatus);
  374. //采购订单-其他信息
  375. formdata.put("textField_mg4gqve0",contactName);
  376. formdata.put("textField_mg4gqve1",contactNumber);
  377. formdata.put("textareaField_mg4gqve2",contactAddress);
  378. //采购订单-子表
  379. JSONArray products = JSONObject.parseObject(jsonString).getJSONArray("data").getJSONObject(0).getJSONArray("purchaseSubOrderVOS");
  380. ArrayList<Map<String,Object>> tableData = new ArrayList();
  381. if(products != null){
  382. for (int i = 0; i < products.size(); i++) {
  383. JSONObject detail = products.getJSONObject(i);
  384. HashMap row = new HashMap();
  385. row.put("textField_mfqia332",detail.getString("productCode"));//产品编码
  386. row.put("textField_mfqia333",detail.getString("productName"));//产品名称
  387. row.put("textField_mfqia334",detail.getString("productSpec"));//产品规格
  388. row.put("numberField_mfqia335",detail.getInteger("purchaseNum"));//采购数量
  389. row.put("textField_mfqia336",detail.getString("unitName"));//单位
  390. row.put("numberField_mfqia337",detail.getDouble("purchasePrice"));//单价
  391. row.put("numberField_mg4gqvdm",detail.getDouble("purchaseAmount"));//报价金额
  392. row.put("numberField_mg4gqvdn",detail.getDouble("discount"));//折扣
  393. row.put("numberField_mg4gqvdo",detail.getDouble("taxInclusiveAmount"));//含税金额
  394. row.put("numberField_mg4gqvdp",detail.getDouble("taxRate"));//税率
  395. row.put("dateField_mg4gqvdq",detail.getLong("productArrivalTime"));//产品到货日期
  396. tableData.add(row);
  397. }
  398. }
  399. /*todo:新版栏目:客户、订单号、款号、产品描述、颜色、数量、销售单价、销售金额、币别、生产工厂、采购单价、采购金额、利润率、美金汇率、辅料预估成本*/
  400. String customerName = "",styleNumber = "",productDescription = "",color = "",currency = "";
  401. Double number,unitPrice,salesAmount;
  402. Double rate = 1.00;Double saletotalAmount = 0.00;Double procuretotalAmount = 0.00;Double saletotalnum =0.00;
  403. Double estimatedtotalAmount = 0.00;Double estimatedPrice = 0.00;
  404. Double USDrate = 0.00;Double flygcb = 0.00;
  405. ObjectMapper objectMapper = new ObjectMapper();
  406. JsonNode rootNode = objectMapper.readTree(jsonString);
  407. JsonNode dataNode = rootNode.get("data");
  408. String orderNumber = "";//销售订单编号
  409. if(dataNode != null && dataNode.isArray()){
  410. for(JsonNode item : dataNode){
  411. JsonNode orderNoNode = item.get("orderCode");
  412. JsonNode saleOrders = item.get("relationSaleOrders");
  413. if(saleOrders != null && saleOrders.isArray() && saleOrders.size() > 0){
  414. orderNumber = saleOrders.get(0).asText();
  415. }
  416. }
  417. }
  418. HashMap body_A = new HashMap();
  419. body_A.put("orderNo",orderNumber);
  420. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", header, null, body_A);//todo:查询销售订单,获取客户、订单号、款号、产品描述、颜色、数量、销售单价、销售金额、币别
  421. JSONArray array = JSONObject.parseObject(jsonString2).getJSONArray("data");//主表数据
  422. for(int i=0;i<array.size();i++){
  423. JSONObject data = array.getJSONObject(i);
  424. customerName = data.getString("customerCode");//客户名称
  425. }
  426. ObjectMapper objectMapper2 = new ObjectMapper();
  427. JsonNode dataNode2 = objectMapper2.readTree(jsonString2).get("data");//主表数据
  428. for (JsonNode item : dataNode2){
  429. JsonNode customFieldValues = item.get("customFieldValues");
  430. for (JsonNode field : customFieldValues){
  431. JsonNode fieldIdNode = field.get("fieldId");
  432. if(fieldIdNode != null && fieldIdNode.asInt() == 161769){
  433. JsonNode valueNode = field.get("value");
  434. if(valueNode != null){
  435. estimatedPrice = valueNode.asDouble();//辅料预估单价
  436. break;
  437. }
  438. }
  439. }
  440. }
  441. JSONArray products_A = JSONObject.parseObject(jsonString2).getJSONArray("data").getJSONObject(0).getJSONArray("saleManageOrderDetailRowApiVOList");//销售订单明细数据
  442. List<Map<String,String>> tabledata = new ArrayList();
  443. if(products_A != null){
  444. for (int i=0;i<products_A.size();i++){
  445. JSONObject detail = products_A.getJSONObject(i);
  446. HashMap row = new HashMap();
  447. row.put("textField_mhsj6gtn",customerName);//todo:客户
  448. row.put("textField_mhsj6gto",orderNumber);//todo:订单号
  449. styleNumber = detail.getString("productCode");//款号
  450. row.put("textField_mhsj6gtp",styleNumber);//todo:款号
  451. productDescription = detail.getString("productName");//产品描述
  452. row.put("textField_mhsj6gtq",productDescription);//todo:产品描述
  453. JSONArray array1 = detail.getJSONArray("customFieldValues");
  454. color = array1.stream()
  455. .map(obj -> (JSONObject) obj)
  456. .filter(item -> item.getIntValue("fieldId") == 82259)
  457. .map(item -> item.getString("value"))
  458. .findFirst()
  459. .orElse(null);
  460. ArrayList colorList = new ArrayList();
  461. colorList.add(color);
  462. String color_AAA = getProductColor(colorList);
  463. row.put("textField_mhsj6gtr",color_AAA);//todo:颜色
  464. number = detail.getDoubleValue("qty");//数量
  465. row.put("numberField_mhsj6gts",number);//todo:数量
  466. saletotalnum = saletotalnum + number;
  467. unitPrice = detail.getDoubleValue("unitPrice");//销售单价
  468. row.put("numberField_mhsj6gtt",unitPrice);//todo:销售单价
  469. salesAmount = number * unitPrice;//销售金额
  470. row.put("numberField_mhsj6gtu",salesAmount);//todo:销售金额
  471. String customFieldValues = detail.getString("customFieldValues");
  472. ObjectMapper mapper = new ObjectMapper();
  473. JsonNode jsonarray = mapper.readTree(customFieldValues);
  474. for (JsonNode node : jsonarray){
  475. if(node.get("fieldId").asInt() == 47919){
  476. currency = node.get("value").asText();
  477. }else if (node.get("fieldId").asInt() == 165251){
  478. rate = node.get("value").asDouble();
  479. USDrate = rate;
  480. }else if (node.get("fieldId").asInt() == 161783) {
  481. flygcb = node.get("value").asDouble();
  482. }
  483. }
  484. row.put("textField_mhtxft3p",currency);//todo:币别
  485. row.put("numberField_ml85btkc",USDrate);//todo:美金汇率
  486. row.put("numberField_ml85btkd",flygcb);//todo:辅料预估成本
  487. //下面是采购订单的明细数据
  488. row.put("textField_mhsj6gtv",shortName);//todo:生产工厂
  489. for(int j=0;j<products.size();j++){
  490. if(styleNumber.equals(products.getJSONObject(j).getString("productCode"))){
  491. //找到对应的采购一行数据
  492. row.put("numberField_mhsj6gtw",products.getJSONObject(j).getDouble("purchasePrice"));//todo:采购单价
  493. row.put("numberField_mhtxft3q",products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购数量
  494. row.put("numberField_mhsj6gtx",products.getJSONObject(j).getDouble("purchasePrice") * products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购金额
  495. }
  496. }
  497. //销售总金额 币别:人民币 数量*单价 美元:数量*单价*美元汇率
  498. saletotalAmount = (currency.equals("CNY") ? number*unitPrice : number*unitPrice*rate) + saletotalAmount;
  499. //采购订单总金额 均为人民币不存在汇率
  500. procuretotalAmount = products.getJSONObject(i).getDouble("purchasePrice") * products.getJSONObject(i).getDouble("purchaseNum") + procuretotalAmount;
  501. tabledata.add(row);
  502. }
  503. }
  504. //预估辅料总成本 订单总数量*辅料预估单价
  505. estimatedtotalAmount = saletotalnum * estimatedPrice;
  506. //毛利率 (销售总金额-采购订单总金额-辅料预估总成本)/(销售总金额)
  507. double margin = (saletotalAmount - procuretotalAmount - estimatedtotalAmount) / saletotalAmount;
  508. formdata.put("numberField_mhvp9qy0",margin);
  509. formdata.put("tableField_mhsj6gtm",tabledata);
  510. System.out.println(formdata);
  511. /*发起流程*/
  512. String userId = getDDToken(purchaserName);
  513. String dd = ydClient.operateData(YDParam.builder()
  514. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  515. .formUuid(FormUuType)
  516. .userId(userId)
  517. .formDataJson(JSON.toJSONString(formdata))
  518. .build(), YDConf.FORM_OPERATION.start).toString();
  519. log.info("------------【采购订单】审批已发起-----------");
  520. return McR.success(dd);
  521. }
  522. @SneakyThrows
  523. @Override
  524. public McR SyncOrderStatus(String formInstanceId,String Approvalresult) throws JsonProcessingException {
  525. HashMap header = new HashMap();
  526. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  527. header.put("Content-Type","application/json");
  528. Map formdata = ydClient.queryData(YDParam.builder().formInstId(formInstanceId)
  529. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  530. .userId(ddConf.getOperator()).build(), YDConf.FORM_QUERY.retrieve_id).getFormData();
  531. HashMap body = new HashMap();
  532. body.put("orderNo",formdata.get("textField_mfqgmwcw"));//订单编号
  533. body.put("customerCode",formdata.get("textField_mfqgmwdh"));//客户编号(名称)
  534. String aa = formdata.get("dateField_mfqgmwcy").toString();
  535. String xdrq = Instant.ofEpochMilli(Long.parseLong(aa))
  536. .atZone(ZoneId.of("Asia/Shanghai"))
  537. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  538. body.put("orderTime",xdrq);//下单日期
  539. String bb = formdata.get("dateField_mfqgmwcz").toString();
  540. String jhjfrq = Instant.ofEpochMilli(Long.parseLong(bb))
  541. .atZone(ZoneId.of("Asia/Shanghai"))
  542. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  543. body.put("arrivalPlanTime",jhjfrq);//计划交付日期
  544. body.put("operatorName",formdata.get("textField_mgc0kc5u"));//业务人员名称
  545. ArrayList<Map<String,String>> customFiled = new ArrayList();
  546. HashMap field = new HashMap();
  547. field.put("name","销售订单钉钉审批状态");
  548. field.put("value",Approvalresult);//审批状态
  549. customFiled.add(field);
  550. body.put("saleOrderCustomFieldsValue",customFiled);//订单状态明细
  551. String dd = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/update", header, null, body);
  552. log.info("---------【回传销售订单状态完成】----------");
  553. return McR.success(dd);
  554. }
  555. @SneakyThrows
  556. @Override
  557. public McR SyncPurchaseOrderStatus(String formInstanceId,String Approvalresult) throws JsonProcessingException {
  558. HashMap header = new HashMap();
  559. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  560. header.put("Content-Type","application/json");
  561. Map formdata = ydClient.queryData(YDParam.builder().formInstId(formInstanceId)
  562. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  563. .userId(ddConf.getOperator()).build(), YDConf.FORM_QUERY.retrieve_id).getFormData();
  564. String jsonString = formdata.get("tableField_ml7ch2pj").toString();
  565. JSONArray tableField_ml7ch2pj = JSON.parseArray(jsonString);
  566. for (int i=0;i<tableField_ml7ch2pj.size();i++){
  567. String poNumber = tableField_ml7ch2pj.getJSONObject(i).getString("textField_ml7ch2pk");//拿到采购订单号
  568. HashMap body = new HashMap();
  569. body.put("orderCode",poNumber);//订单编号
  570. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//todo:查询采购订单
  571. JSONArray dataArray = JSONObject.parseObject(jsonString2).getJSONArray("data");
  572. for (int k=0;k<dataArray.size();k++) {
  573. JSONObject data = dataArray.getJSONObject(k);
  574. //提取订单基本信息 并赋值
  575. HashMap body1 = new HashMap();
  576. body1.put("orderCode",data.getString("orderCode"));//订单编号:orderCode
  577. body1.put("vendorCode",data.getString("vendorCode"));//供应商编码:gysnumber
  578. String aa = data.getLong("purchaseTime").toString();
  579. String purchaseTime = Instant.ofEpochMilli(Long.parseLong(aa))
  580. .atZone(ZoneId.of("Asia/Shanghai"))
  581. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  582. body1.put("purchaseTime",purchaseTime);//采购日期:purchaseTime
  583. String bb = data.getLong("planArrivalTime").toString();
  584. String planArrivalTime = Instant.ofEpochMilli(Long.parseLong(bb))
  585. .atZone(ZoneId.of("Asia/Shanghai"))
  586. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  587. body1.put("planArrivalTime",planArrivalTime);//计划到货日期:planArrivalTime
  588. ArrayList<Map<String,String>> customFiled = new ArrayList();
  589. HashMap field = new HashMap();
  590. field.put("name","采购订单钉钉审批状态");
  591. field.put("value",Approvalresult);//审批状态
  592. customFiled.add(field);
  593. body1.put("purchaseOrderCustomFieldsValue",customFiled);
  594. UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/update", header, null, body1);
  595. log.info("---------【回传,{},采购订单状态完成】-----------",data.getString("orderCode"));
  596. }
  597. }
  598. return McR.success();
  599. }
  600. @Override
  601. @SneakyThrows
  602. public McR salesAproval(Map body) throws JacksonException {
  603. StartYidaAproval(body.get("order").toString(),"FORM-472F0C1BD8DF41FA965A0B4525779B67S421");//todo:发起销售订单流程档案
  604. HashMap formdata = new HashMap();
  605. formdata.put("textField_mgq90lwf",body.get("order").toString());
  606. Instant now = Instant.now();
  607. long timestampMillis = now.toEpochMilli();
  608. formdata.put("dateField_mgq90lwg",timestampMillis);
  609. ydClient.operateData(YDParam.builder()
  610. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  611. .formUuid("FORM-1693380A673E498C827CD0A4C2D8214CIK90")
  612. .userId("3320511511-1158713155")
  613. .formDataJson(JSON.toJSONString(formdata))
  614. .build(), YDConf.FORM_OPERATION.create).toString();//todo:销售合同档案
  615. log.info("[销售订单流程发起,销售汇总表已同步]");
  616. return McR.success();
  617. }
  618. @Override
  619. @SneakyThrows
  620. public McR Procurement(Map body_new) throws JacksonException {
  621. //1、每次创建的时候才去查询宜搭采购订单底表
  622. log.info("【开始查询宜搭采购订单汇总】");
  623. String formUuid = "FORM-56E11C4FAB6E4FB594169BB779736FF0ZG91";
  624. YDParam ydParam = YDParam.builder().formUuid(formUuid).build();
  625. ydParam.setPageSize(1);
  626. long totalCount = ydClient.queryData(ydParam, YDConf.FORM_QUERY.retrieve_search_form).getTotalCount();
  627. List<Map> dataList = new ArrayList<>();
  628. ydParam.setCurrentPage(1);
  629. ydParam.setPageSize(100);
  630. int totalPages = (int) Math.ceil((double) totalCount / ydParam.getPageSize());
  631. for (int page = 1; page <= totalPages; page++) {
  632. ydParam.setCurrentPage(page);
  633. dataList.addAll((List<Map>) ydClient.queryData(ydParam, YDConf.FORM_QUERY.retrieve_search_form).getData());
  634. }
  635. int i =0;
  636. String jsonStr = "";
  637. ArrayList<String> procureList = new ArrayList();//采购订单汇总-订单号
  638. for (Map li : dataList) {
  639. i++;
  640. jsonStr = li.get("formData").toString();
  641. String orderNumber = new ObjectMapper().readTree(jsonStr).get("textField_mgq932hi").asText();
  642. procureList.add(orderNumber);
  643. }
  644. //2、其次就是在查询下黑湖工单,时间为当前时间
  645. HashMap header = new HashMap();
  646. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  647. header.put("Content-Type","application/json");
  648. HashMap body = new HashMap();
  649. DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
  650. LocalDateTime todayMidnight = LocalDate.now().atStartOfDay();
  651. String formattedToday = todayMidnight.format(formatter);
  652. body.put("createdAtGte",formattedToday);//创建时间大于等于
  653. /*TODO:对json进行处理*/
  654. String jsonString = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//TODO:查询采购订单
  655. List<String> orderNoList = new ArrayList<>();//存在这个orderList里面
  656. ObjectMapper objectMapper = new ObjectMapper();
  657. JsonNode rootNode = objectMapper.readTree(jsonString);
  658. JsonNode dataNode = rootNode.get("data");
  659. String orderNumber = "";//销售订单编号
  660. List<String> orderNumberList = new ArrayList<>();//todo:存在关联多个销售订单
  661. String purchaseOrderNo = "";//采购订单编号
  662. String orderType = "";//销售订单类型
  663. if (dataNode != null && dataNode.isArray()) {
  664. for (JsonNode item : dataNode) {
  665. JsonNode orderNoNode = item.get("orderCode");
  666. if (orderNoNode != null) {
  667. purchaseOrderNo = orderNoNode.asText();
  668. }
  669. JsonNode saleOrders = item.get("relationSaleOrders");
  670. if (saleOrders != null && saleOrders.isArray() && saleOrders.size() > 0) {
  671. for (int j = 0; j < saleOrders.size(); j++) {
  672. orderNumberList.add(saleOrders.get(j).asText());
  673. }
  674. orderNumber = saleOrders.get(0).asText();
  675. }
  676. //每次查询下是否为“样品订单”推过来的采购订单
  677. HashMap body2 = new HashMap();
  678. body2.put("orderNo",orderNumber);
  679. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", header, null, body2);//TODO: 查询销售订单
  680. ObjectMapper objectMapper2 = new ObjectMapper();
  681. JsonNode dataNode2 = objectMapper2.readTree(jsonString2).get("data");
  682. if(dataNode2 != null && dataNode2.isArray()){
  683. for (JsonNode item2 : dataNode2){
  684. JsonNode customFieldValues = item2.get("customFieldValues");
  685. if (customFieldValues != null && customFieldValues.isArray()) {
  686. for (JsonNode field : customFieldValues) {
  687. JsonNode fieldIdNode = field.get("fieldId");
  688. // 查找fieldId为47771的字段:订单类型
  689. if (fieldIdNode != null && fieldIdNode.asInt() == 47771) {
  690. JsonNode valueNode = field.get("value");
  691. if (valueNode != null) {
  692. orderType = valueNode.asText();
  693. break;
  694. }
  695. }
  696. }
  697. }
  698. }
  699. }
  700. if (orderNoNode != null && !orderType.equals("样品订单") ) {
  701. orderNoList.add(orderNoNode.asText());
  702. }
  703. }
  704. }
  705. //3、两者比较[procureList\orderList],差别的一个发起审批流程,排除订单类型为“样品订单”外
  706. Set<String> orderNoSet = new HashSet<>(orderNoList);
  707. Set<String> procureSet = new HashSet<>(procureList);
  708. List<String> onlyInSalesList = new ArrayList<>();
  709. for (String item : procureList) {
  710. if (!orderNoSet.contains(item)) {
  711. onlyInSalesList.add(item);
  712. }
  713. }
  714. List<String> onlyInOrderNoList = new ArrayList<>();
  715. for (String item : orderNoList) {
  716. if (!procureSet.contains(item)) {
  717. onlyInOrderNoList.add(item);
  718. }
  719. }
  720. System.out.println("要发起的采购订单: " + onlyInOrderNoList);//这里的orderNoList中的元素可能为[],为空的话就不发起流程
  721. //4、非样品订单发起宜搭审批流程
  722. if(orderType.equals("样品订单")){
  723. HashMap formdata2 = new HashMap();
  724. formdata2.put("textField_mgq932hi",purchaseOrderNo);
  725. formdata2.put("textField_mhyh7ues",orderNumber);
  726. Instant now = Instant.now();
  727. long timestampMillis = now.toEpochMilli();
  728. formdata2.put("dateField_mgq932hj",timestampMillis);
  729. ydClient.operateData(YDParam.builder()
  730. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  731. .formUuid("FORM-56E11C4FAB6E4FB594169BB779736FF0ZG91")
  732. .userId("3320511511-1158713155")
  733. .formDataJson(JSON.toJSONString(formdata2))
  734. .build(),YDConf.FORM_OPERATION.create).toString();
  735. log.info("[样品订单流程不发起,采购汇总表已同步]");
  736. }
  737. for (int j=0;j< onlyInOrderNoList.size();j++){
  738. String orderNo = onlyInOrderNoList.get(j);
  739. startYidaProcurementAproval(orderNo,"FORM-5BD5B7F6C8B249A5ADD6E1C82DEAA2C086FY");
  740. //5、发起流程写入采购订单汇总表
  741. HashMap formdata = new HashMap();
  742. formdata.put("textField_mgq932hi",orderNo);
  743. formdata.put("textField_mhyh7ues",orderNumber);
  744. Instant now = Instant.now();
  745. long timestampMillis = now.toEpochMilli();
  746. formdata.put("dateField_mgq932hj",timestampMillis);
  747. ydClient.operateData(YDParam.builder()
  748. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  749. .formUuid("FORM-56E11C4FAB6E4FB594169BB779736FF0ZG91")
  750. .userId("3320511511-1158713155")
  751. .formDataJson(JSON.toJSONString(formdata))
  752. .build(), YDConf.FORM_OPERATION.create).toString();
  753. log.info("[采购订单流程发起,采购汇总表已同步]");
  754. }
  755. //6、样品订单也要写入采购订单汇总表内
  756. if(orderType.equals("样品订单")){
  757. HashMap formdata2 = new HashMap();
  758. formdata2.put("textField_mgq932hi",purchaseOrderNo);
  759. formdata2.put("textField_mhyh7ues",orderNumber);
  760. Instant now = Instant.now();
  761. long timestampMillis = now.toEpochMilli();
  762. formdata2.put("dateField_mgq932hj",timestampMillis);
  763. ydClient.operateData(YDParam.builder()
  764. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  765. .formUuid("FORM-56E11C4FAB6E4FB594169BB779736FF0ZG91")
  766. .userId("3320511511-1158713155")
  767. .formDataJson(JSON.toJSONString(formdata2))
  768. .build(),YDConf.FORM_OPERATION.create).toString();
  769. log.info("[样品订单流程不发起,采购汇总表已同步]");
  770. }
  771. return McR.success();
  772. }
  773. // 定义核心字段KEY数组
  774. private static final List<String> CORE_KEY_LIST=Arrays.asList("numberField_mfqgmwe6","numberField_mfqgmwe8","textField_mk0jz9i1");//数量 单价 中文颜色
  775. private static final String MATCH_KEY = "textField_mhsj6gtp";
  776. @Override
  777. public McR salesUpdate(Map body_new) throws JacksonException {
  778. /*todo:1、修改销售明细的颜色、数量、单价(已实现) 2、修改计划交货日期(进行中)*/
  779. // 查询销售订单明细
  780. HashMap head = new HashMap();
  781. head.put("X-AUTH",HeiHuAccessToken().getData().toString());
  782. head.put("Content-Type","application/json");
  783. HashMap bodyy = new HashMap();
  784. bodyy.put("orderNo",body_new.get("order").toString());
  785. String saleDetails = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", head, null, bodyy);
  786. JSONArray datas = JSONObject.parseObject(saleDetails).getJSONArray("data");
  787. JSONArray prods = JSONObject.parseObject(saleDetails).getJSONArray("data").getJSONObject(0).getJSONArray("saleManageOrderDetailRowApiVOList");
  788. List<Map<String,Object>> tabledata = new ArrayList();
  789. String customerCode = "";String orderNo = "";
  790. String arrivalPlanTime_New = "";
  791. for (int b=0;b< datas.size();b++){
  792. JSONObject object = datas.getJSONObject(b);
  793. customerCode = object.getString("customerCode");//客户
  794. orderNo = object.getString("orderNo");//订单号
  795. arrivalPlanTime_New = object.getString("arrivalPlanTime");//计划交货日期
  796. }
  797. for (int a=0;a< prods.size();a++){
  798. JSONObject detail = prods.getJSONObject(a);
  799. HashMap row = new HashMap();
  800. String productCode = detail.getString("productCode");//款号
  801. String productName = detail.getString("productName");//产品描述
  802. Double qty = detail.getDouble("qty");//数量
  803. Double unitPrice = detail.getDouble("unitPrice");//单价
  804. double saleamount = detail.getDouble("qty") * detail.getDouble("unitPrice");//销售金额
  805. String color = "";
  806. JSONArray array1 = detail.getJSONArray("customFieldValues");
  807. color = array1.stream()
  808. .map(obj -> (JSONObject) obj)
  809. .filter(item -> item.getIntValue("fieldId") == 82259)
  810. .map(item -> item.getString("value"))
  811. .findFirst()
  812. .orElse(null);
  813. String currency = "";
  814. currency = array1.stream()
  815. .map(obj -> (JSONObject) obj)
  816. .filter(item -> item.getIntValue("fieldId") == 47919)
  817. .map(item -> item.getString("value"))
  818. .findFirst()
  819. .orElse(null); //币别
  820. ArrayList colorList = new ArrayList();
  821. colorList.add(color);
  822. String color_AAA = getProductColor(colorList);//颜色
  823. row.put("textField_mhsj6gtn",customerCode);
  824. row.put("textField_mhsj6gto",orderNo);
  825. row.put("textField_mhsj6gtp",productCode);
  826. row.put("textField_mhsj6gtq",productName);
  827. row.put("textField_mk4rrk35",color_AAA);//
  828. row.put("numberField_mk4rrk3b",qty);//
  829. row.put("numberField_mk4rrk3d",unitPrice);//
  830. row.put("numberField_mk4rrk3e",saleamount);//
  831. row.put("textField_mhtxft3p",currency);
  832. tabledata.add(row);
  833. }
  834. // 销售订单明细转换为宜搭表单字段的 formData
  835. HashMap fromdata = new HashMap();
  836. fromdata.put("tableField_mhsj6gtm",tabledata);
  837. log.info("[修改后的销售明细值],{}",tabledata);
  838. // 查询修改前的宜搭数据 formData
  839. List<Map<String,Object>> tabledata_yida = new ArrayList();
  840. List<Map> list = (List<Map>) ydClient.queryData(YDParam.builder()
  841. .formUuid("FORM-472F0C1BD8DF41FA965A0B4525779B67S421")
  842. .searchCondition(JSONObject.toJSONString(Arrays.asList(new YDSearch(
  843. "textField_mfqgmwcw", orderNo, "订单编号", YDSearch.Type.TEXT_FIELD, YDSearch.Operator.EQ))))
  844. .build()
  845. ,YDConf.FORM_QUERY.retrieve_list).getData();
  846. String formInstanceId = (String) list.get(0).get("formInstanceId");
  847. Map data = (Map) ydClient.queryData(YDParam.builder().formInstId(formInstanceId)
  848. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  849. .userId(ddConf.getOperator()).build(), YDConf.FORM_QUERY.retrieve_id).getFormData();
  850. String arrivalPlanTime_Old = data.get("dateField_mfqgmwcz").toString();
  851. List<Map<String, Object>> table = (List<Map<String, Object>>) data.get("tableField_mfqgmwe0");
  852. for (Map<String, Object> row : table) {
  853. HashMap row_yida = new HashMap();
  854. row_yida.put("textField_mhsj6gtn",data.get("textField_mfqgmwcx"));
  855. row_yida.put("textField_mhsj6gto",data.get("textField_mfqgmwcw"));
  856. row_yida.put("textField_mhsj6gtp",row.get("textField_mfqgmwe1"));
  857. row_yida.put("textField_mhsj6gtq",row.get("textField_mfqgmwe2"));
  858. row_yida.put("textField_mk4rrk35",row.get("textField_mk0jz9i1"));
  859. row_yida.put("numberField_mk4rrk3b",row.get("numberField_mfqgmwe6"));
  860. row_yida.put("numberField_mk4rrk3d",row.get("numberField_mfqgmwe8"));
  861. row_yida.put("numberField_mk4rrk3e",row.get("numberField_mfqgmweb"));
  862. row_yida.put("textField_mhtxft3p",row.get("textField_mk0xio3b"));
  863. tabledata_yida.add(row_yida);
  864. }
  865. HashMap fromdata_yida = new HashMap();
  866. fromdata_yida.put("tableField_mhsj6gtm",tabledata_yida);
  867. log.info("[修改前的销售明细值],{}",tabledata_yida);
  868. // 对比获取变更的KEY列表 AI
  869. List<Map<String, Object>> result = compareAndGetChanges(tabledata_yida, tabledata);
  870. log.info("[变更的值],{}",result);
  871. // 包含 发起宜搭审批
  872. StartYidaAproval(orderNo,"FORM-9A44F1DA0F5B4D319A6D06692767564CFHDS");
  873. //查找销售订单变更审批的实例id
  874. List<Map> lis = (List<Map>) ydClient.queryData(YDParam.builder()
  875. .formUuid("FORM-9A44F1DA0F5B4D319A6D06692767564CFHDS")
  876. .searchCondition(JSONObject.toJSONString(Arrays.asList(new YDSearch(
  877. "textField_mfqgmwcw", orderNo, "订单编号", YDSearch.Type.TEXT_FIELD, YDSearch.Operator.EQ))))
  878. .build()
  879. ,YDConf.FORM_QUERY.retrieve_list).getData();
  880. String instanceId = (String) lis.get(0).get("formInstanceId");
  881. log.info("[销售订单审批变更的实例id],{}",instanceId);
  882. //把变更的数据整理去走operateData方法
  883. Map<String, List<Map<String, Object>>> grouped = result.stream()
  884. .collect(Collectors.groupingBy(m -> (String) m.get("billNo")));
  885. List<Map<String, Object>> ret = new ArrayList<>();
  886. for (List<Map<String, Object>> group : grouped.values()) {
  887. Map<String, Object> merged = new LinkedHashMap<>(); // 保持插入顺序(可选)
  888. for (Map<String, Object> item : group) {
  889. String field = (String) item.get("field");
  890. Object oldValue = item.get("oldValue");
  891. merged.put(field, oldValue);
  892. }
  893. ret.add(merged);
  894. }
  895. System.out.println("即将插入的数据" + ret);
  896. Map formdata = new HashMap();
  897. if(!arrivalPlanTime_New.equals(arrivalPlanTime_Old)){
  898. formdata.put("textareaField_mjghnmvv",AAAA(arrivalPlanTime_Old));
  899. }
  900. formdata.put("tableField_mk4rrk3k",ret);
  901. ydClient.operateData(YDParam.builder()
  902. .formInstanceId(instanceId)
  903. .updateFormDataJson(JSONObject.toJSONString(formdata))
  904. .build(),YDConf.FORM_OPERATION.update);
  905. return McR.success();
  906. }
  907. /**
  908. * 对比新旧列表,返回所有变更项(Java 8 兼容)
  909. *
  910. * 返回格式:List<Map<String, Object>>
  911. * 每个 Map 包含:
  912. * - "billNo": 单号(textField_mhsj6gtp 的值)
  913. * - "field": 变更的字段名
  914. * - "oldValue": 旧值
  915. * - "newValue": 新值
  916. */
  917. public static List<Map<String, Object>> compareAndGetChanges(
  918. List<Map<String, Object>> oldList,
  919. List<Map<String, Object>> newList) {
  920. Map<String, Map<String, Object>> oldIndex = toIndex(oldList);
  921. Map<String, Map<String, Object>> newIndex = toIndex(newList);
  922. List<Map<String, Object>> changes = new ArrayList<>();
  923. for (String billNo : oldIndex.keySet()) {
  924. Map<String, Object> oldRow = oldIndex.get(billNo);
  925. Map<String, Object> newRow = newIndex.get(billNo);
  926. if (newRow == null) {
  927. continue;
  928. }
  929. for (Map.Entry<String, Object> entry : oldRow.entrySet()) {
  930. String field = entry.getKey();
  931. Object oldValue = entry.getValue();
  932. Object newValue = newRow.get(field);
  933. if (!Objects.equals(oldValue, newValue)) {
  934. Map<String, Object> change = new HashMap<>();
  935. change.put("billNo", billNo);
  936. change.put("field", field);
  937. change.put("oldValue", oldValue);
  938. change.put("newValue", newValue);
  939. changes.add(change);
  940. }
  941. }
  942. }
  943. return changes;
  944. }
  945. // 构建以 textField_mhsj6gtp 为 key 的索引
  946. private static Map<String, Map<String, Object>> toIndex(List<Map<String, Object>> list) {
  947. Map<String, Map<String, Object>> index = new HashMap<>();
  948. for (Map<String, Object> row : list) {
  949. if (row.containsKey(MATCH_KEY)) {
  950. String key = String.valueOf(row.get(MATCH_KEY));
  951. // 避免重复 key 覆盖(保留第一个)
  952. if (!index.containsKey(key)) {
  953. index.put(key, row);
  954. }
  955. }
  956. }
  957. return index;
  958. }
  959. /*返回备注信息*/
  960. public static String AAAA(String ccc){
  961. String aa = "";
  962. String dd = Instant.ofEpochMilli(Long.parseLong(ccc))
  963. .atZone(ZoneId.of("Asia/Shanghai"))
  964. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
  965. aa = "{\"dateField_mfqgmwcz\":\"<article class=\\\"4ever-xarticle\\\"><p style=\\\"text-align:left;text-indent:0;margin-left:0;margin-top:0;margin-bottom:0\\\"><span style=\\\"color:#FE0300\\\">" + dd +"</span></p></article>\"}";
  966. return aa;
  967. }
  968. @Override
  969. public String getProductColor(List list) throws JacksonException {
  970. HashMap header = new HashMap();
  971. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  972. header.put("Content-Type","application/json");
  973. HashMap body = new HashMap();
  974. body.put("type","PRODUCT");
  975. body.put("ids",list);
  976. String doPost = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/customField/associatedBusinessObject/entity/queryList", header, null, body);
  977. JSONObject jsonObject = JSONObject.parseObject(doPost);
  978. JSONArray dataArray = jsonObject.getJSONArray("data");
  979. System.out.println(dataArray);
  980. /* String productName = "";
  981. for (int i = 0; i < dataArray.size(); i++) {
  982. JSONObject data = dataArray.getJSONObject(i);
  983. productName = data.getString("productName");
  984. }*/
  985. String colorValue = "";
  986. if (dataArray != null && dataArray.size() > 0) {
  987. JSONObject data = dataArray.getJSONObject(0);
  988. JSONObject customFieldValues = data.getJSONObject("customFieldValues");
  989. if (customFieldValues != null) {
  990. // 直接获取指定字段的值
  991. colorValue = customFieldValues.getString("product1741831360685211");
  992. }
  993. }
  994. return colorValue;
  995. }
  996. @SneakyThrows
  997. @Override
  998. public McR purchaseSchedule(List<Map<String, Object>> dataList) {
  999. HashMap header = new HashMap();
  1000. header.put("X-AUTH", HeiHuAccessToken().getData().toString());
  1001. header.put("Content-Type", "application/json");
  1002. String targetValue = "合同确认,提交审批";
  1003. String targetValueUpdate = "合同修改,修改审批";
  1004. // 定义一个字符串集合,默认包含两个值:"默认值1"、"默认值2"
  1005. List<String> targetValues = new ArrayList() {{
  1006. add("合同确认,提交审批");
  1007. add("合同修改,修改审批");
  1008. }};
  1009. Map<String, List<String>> purchaserOrderCodes = new HashMap<>();
  1010. if (ObjectUtil.isNotNull(dataList) && dataList.size() > 0) {
  1011. for (Map<String, Object> item : dataList) {
  1012. String purchaserName = (String) item.get("purchaserName");
  1013. if (purchaserName == null) purchaserName = "未知";
  1014. // boolean hasTargetStatus = false;
  1015. List<Map<String, Object>> customFieldValues = (List<Map<String, Object>>) item.get("customFieldValues");
  1016. if (customFieldValues != null) {
  1017. for (Map<String, Object> field : customFieldValues) {
  1018. if (targetValue.equals(field.get("value") ) || targetValueUpdate.equals(field.get("value"))) {
  1019. System.out.println("合同状态类型:"+field.get("value"));
  1020. // if (targetValue.equals(field.get("value"))) {
  1021. // hasTargetStatus = true;
  1022. String orderCode = (String) item.get("orderCode");
  1023. if (orderCode != null) {
  1024. purchaserOrderCodes.computeIfAbsent(purchaserName + "-" + field.get("value"), k -> new ArrayList<>()).add(orderCode);
  1025. }
  1026. break;
  1027. }
  1028. }
  1029. }
  1030. }
  1031. }
  1032. // 输出所有采购员的待审批订单
  1033. System.out.println("========== 所有采购员的待审批订单统计 ==========");
  1034. if (purchaserOrderCodes.isEmpty()) {
  1035. System.out.println("没有找到钉钉审批状态为'" + targetValue + "'的订单");
  1036. } else {
  1037. int totalPurchasers = purchaserOrderCodes.size();
  1038. int totalOrders = purchaserOrderCodes.values().stream().mapToInt(List::size).sum();
  1039. System.out.println("共找到 " + totalOrders + " 个待审批订单");
  1040. System.out.println("涉及 " + totalPurchasers + " 位采购员");
  1041. System.out.println();
  1042. // 输出每个采购员的情况
  1043. for (Map.Entry<String, List<String>> entry : purchaserOrderCodes.entrySet()) {
  1044. String[] split = entry.getKey().split("-");
  1045. String purchaserName = split[0];
  1046. String type = split[1];
  1047. List<String> orderCodes = entry.getValue();
  1048. int orderCount = orderCodes.size();
  1049. System.out.println("采购员: " + purchaserName);
  1050. System.out.println("待审批订单数量: " + orderCount);
  1051. System.out.println("审批类型: " + type);
  1052. if (orderCount > 1) {
  1053. System.out.println("⚠️ 注意:该采购员有 " + orderCount + " 个待审批订单");
  1054. }
  1055. System.out.println("订单编号: " + String.join(", ", orderCodes));
  1056. }
  1057. // 按订单数量排序输出
  1058. System.out.println("========== 按待审批订单数量排序 ==========");
  1059. purchaserOrderCodes.entrySet().stream()
  1060. .sorted((e1, e2) -> Integer.compare(e2.getValue().size(), e1.getValue().size()))
  1061. .forEach(entry -> {
  1062. String[] split = entry.getKey().split("-");
  1063. String purchaserName = split[0];
  1064. String type = split[1];
  1065. List<String> orderCodes = entry.getValue();
  1066. System.out.println(purchaserName + " (" + orderCodes.size() + "个): " +
  1067. String.join(", ", orderCodes));
  1068. // ========== 修改点1:声明两个列表分别存储不同毛利率的订单数据 ==========
  1069. // 针对同一个采购员,遍历下面的订单编号
  1070. System.out.println("开始处理采购员 " + purchaserName + " 的 " + orderCodes.size() + " 个待审批订单");
  1071. // 高毛利率表单数据 (mlv >= 0.15)
  1072. HashMap formdataHigh = new HashMap();
  1073. List<Map<String,String>> tabledataHigh = new ArrayList();
  1074. // 低毛利率表单数据 (mlv < 0.15)
  1075. HashMap formdataLow = new HashMap();
  1076. List<Map<String,String>> tabledataLow = new ArrayList();
  1077. // ========== 修改点2:为每个订单创建临时存储列表 ==========
  1078. // 用于暂存每个订单的明细数据,等计算出毛利率后再决定添加到哪个列表
  1079. // Map<String, List<Map<String, String>>> tempOrderDataMap = new HashMap<>();
  1080. // 用于存储每个订单的汇总数据,用于计算毛利率
  1081. // Map<String, Map<String, Double>> orderSummaryForMlv = new HashMap<>();
  1082. List<String> oldIds = new ArrayList<>();
  1083. for (String orderCode : orderCodes) {
  1084. System.out.println("正在处理订单: " + orderCode);
  1085. if (type.equals(targetValueUpdate)){
  1086. oldIds.add(orderCode);
  1087. }
  1088. // ========== 修改点3:为当前订单创建临时数据存储 ==========
  1089. List<Map<String, String>> currentOrderRows = new ArrayList<>();
  1090. double orderTotalSalesAmount = 0.0;
  1091. double orderTotalPurchaseAmount = 0.0;
  1092. double orderTotalFlygcb = 0.0;
  1093. //todo:查询订单的销售订单 | 客户 销售订单号 款式 产品描述 颜色 | 数量 销售单价 销售金额 | 币别 美金汇率 辅料预估成本 销售总金额
  1094. String customerName = "",orderNumber ="",styleNumber ="",productDescription = "",color = "";
  1095. Double number,unitPrice,salesAmount;
  1096. String currency = ""; Double USDrate = 0.00; Double flygcb = 0.00; Double saletotalAmount = 0.00;
  1097. Double estimatedPrice = 0.00;//辅料预估单价
  1098. HashMap body = new HashMap();
  1099. body.put("orderCode",orderCode);//订单编号
  1100. String jsonString = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);
  1101. //todo:查询采购订单 生产工厂(供应商)
  1102. String shortName = "";
  1103. JSONArray dataArray = JSONObject.parseObject(jsonString).getJSONArray("data");
  1104. for (int i=0;i<dataArray.size();i++) {
  1105. JSONObject data = dataArray.getJSONObject(i);
  1106. shortName = data.getString("shortName");//供应商:shortName
  1107. }
  1108. JSONArray products = JSONObject.parseObject(jsonString).getJSONArray("data").getJSONObject(0).getJSONArray("purchaseSubOrderVOS");
  1109. ObjectMapper objectMapper = new ObjectMapper();
  1110. JsonNode rootNode = null;
  1111. try {
  1112. rootNode = objectMapper.readTree(jsonString);
  1113. } catch (JsonProcessingException e) {
  1114. throw new RuntimeException(e);
  1115. }
  1116. JsonNode dataNode = rootNode.get("data");
  1117. if(dataNode != null && dataNode.isArray()){
  1118. for(JsonNode item : dataNode){
  1119. JsonNode orderNoNode = item.get("orderCode");
  1120. JsonNode saleOrders = item.get("relationSaleOrders");
  1121. if(saleOrders != null && saleOrders.isArray() && saleOrders.size() > 0){
  1122. orderNumber = saleOrders.get(0).asText();//销售订单号
  1123. }
  1124. }
  1125. }
  1126. HashMap body_A = new HashMap();
  1127. body_A.put("orderNo",orderNumber);
  1128. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", header, null, body_A);//todo:查询销售订单,获取客户、订单号、款号、产品描述、颜色、数量、销售单价、销售金额、币别
  1129. JSONArray array = JSONObject.parseObject(jsonString2).getJSONArray("data");//主表数据
  1130. boolean isSample = false;//销售订单若为样品订单则不发起钉钉流程
  1131. for(int i=0;i<array.size();i++){
  1132. JSONObject data = array.getJSONObject(i);
  1133. customerName = data.getString("customerCode");//客户
  1134. }
  1135. ObjectMapper objectMapper2 = new ObjectMapper();
  1136. JsonNode dataNode2 = null;//主表数据
  1137. try {
  1138. dataNode2 = objectMapper2.readTree(jsonString2).get("data");
  1139. } catch (JsonProcessingException e) {
  1140. throw new RuntimeException(e);
  1141. }
  1142. for (JsonNode item : dataNode2){
  1143. JsonNode customFieldValues = item.get("customFieldValues");
  1144. for (JsonNode field : customFieldValues){
  1145. JsonNode fieldIdNode = field.get("fieldId");
  1146. if(fieldIdNode != null && fieldIdNode.asInt() == 161769){
  1147. JsonNode valueNode = field.get("value");
  1148. if(valueNode != null){
  1149. estimatedPrice = valueNode.asDouble();//辅料预估单价
  1150. }
  1151. }
  1152. else if(fieldIdNode != null && fieldIdNode.asInt() == 47771){
  1153. JsonNode valueNode = field.get("value");
  1154. log.info("销售订单类型:{}",valueNode.asText());
  1155. if("样品订单".equals(valueNode.asText())){
  1156. isSample = true;
  1157. }
  1158. }
  1159. }
  1160. }
  1161. if (!isSample){
  1162. JSONArray products_A = JSONObject.parseObject(jsonString2).getJSONArray("data").getJSONObject(0).getJSONArray("saleManageOrderDetailRowApiVOList");//销售订单明细数据
  1163. if(products_A != null) {
  1164. for (int i = 0; i < products_A.size(); i++) {
  1165. JSONObject detail = products_A.getJSONObject(i);
  1166. HashMap row = new HashMap();
  1167. row.put("textField_mm2t71jm",orderCode);//todo:采购订单单号
  1168. row.put("textField_ml6g7k5e", customerName);//todo:客户
  1169. row.put("textField_ml6g7k5f", orderNumber);//todo:订单号
  1170. styleNumber = detail.getString("productCode");//款号
  1171. row.put("textField_ml7c3yhq", styleNumber);//todo:款号
  1172. productDescription = detail.getString("productName");//产品描述
  1173. row.put("textField_ml7c3yhr", productDescription);//todo:产品描述
  1174. JSONArray array1 = detail.getJSONArray("customFieldValues");
  1175. color = array1.stream()
  1176. .map(obj -> (JSONObject) obj)
  1177. .filter(item -> item.getIntValue("fieldId") == 82259)
  1178. .map(item -> item.getString("value"))
  1179. .findFirst()
  1180. .orElse(null);
  1181. ArrayList colorList = new ArrayList();
  1182. colorList.add(color);
  1183. String color_AAA = null;
  1184. try {
  1185. color_AAA = getProductColor(colorList);
  1186. } catch (JacksonException e) {
  1187. throw new RuntimeException(e);
  1188. }
  1189. row.put("textField_ml7c3yhs", color_AAA);//todo:颜色
  1190. number = detail.getDoubleValue("qty");//数量
  1191. row.put("numberField_ml7c3yht", number);//todo:数量
  1192. unitPrice = detail.getDoubleValue("unitPrice");//销售单价
  1193. row.put("numberField_ml7c3yhu", unitPrice);//todo:销售单价
  1194. salesAmount = number * unitPrice;//销售金额
  1195. row.put("numberField_ml7c3yhv", salesAmount);//todo:销售金额
  1196. String customFieldValues = detail.getString("customFieldValues");
  1197. ObjectMapper mapper = new ObjectMapper();
  1198. JsonNode jsonarray = null;
  1199. try {
  1200. jsonarray = mapper.readTree(customFieldValues);
  1201. } catch (JsonProcessingException e) {
  1202. throw new RuntimeException(e);
  1203. }
  1204. for (JsonNode node : jsonarray) {
  1205. if (node.get("fieldId").asInt() == 47919) {
  1206. currency = node.get("value").asText();
  1207. } else if (node.get("fieldId").asInt() == 165251) {
  1208. USDrate = node.get("value").asDouble();
  1209. } else if (node.get("fieldId").asInt() == 161783) {
  1210. flygcb = node.get("value").asDouble();
  1211. }
  1212. }
  1213. row.put("textField_ml7c3yhw", currency);//todo:币别
  1214. row.put("numberField_ml86221y", USDrate);//todo:美金汇率
  1215. row.put("numberField_ml86221z", flygcb);//todo:辅料预估成本
  1216. if(currency.equals("USD")){
  1217. saletotalAmount = salesAmount * USDrate;
  1218. }else {
  1219. saletotalAmount = salesAmount;
  1220. }
  1221. row.put("numberField_ml862220",saletotalAmount);
  1222. //下面是采购订单的明细数据
  1223. row.put("textField_ml7c3yhx",shortName);//todo:生产工厂
  1224. for(int j=0;j<products.size();j++){
  1225. if(styleNumber.equals(products.getJSONObject(j).getString("productCode"))){
  1226. //找到对应的采购一行数据
  1227. row.put("numberField_ml7c3yhy",products.getJSONObject(j).getDouble("purchasePrice"));//todo:采购单价
  1228. row.put("numberField_ml7c3yhz",products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购数量
  1229. row.put("numberField_ml7c3yi0",products.getJSONObject(j).getDouble("purchasePrice") * products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购金额
  1230. }
  1231. }
  1232. // ========== 修改点4:将当前行转换为Map<String,String>并暂存 ==========
  1233. Map<String, String> rowMap = new HashMap<>();
  1234. for (Object key : row.keySet()) {
  1235. Object value = row.get(key);
  1236. rowMap.put(key.toString(), value != null ? value.toString() : "");
  1237. }
  1238. currentOrderRows.add(rowMap);
  1239. // ========== 修改点5:累加当前订单的汇总数据用于计算毛利率 ==========
  1240. orderTotalSalesAmount += saletotalAmount;
  1241. orderTotalPurchaseAmount += (Double)row.get("numberField_ml7c3yi0");
  1242. orderTotalFlygcb += flygcb;
  1243. }
  1244. }
  1245. // ========== 修改点6:计算当前订单的毛利率 ==========
  1246. double mlv = 0.0;
  1247. if (orderTotalSalesAmount > 0) {
  1248. mlv = (orderTotalSalesAmount - orderTotalPurchaseAmount - orderTotalFlygcb) / orderTotalSalesAmount;
  1249. }
  1250. System.out.println("订单 " + orderCode + " 毛利率: " + String.format("%.2f%%", mlv * 100));
  1251. // ========== 修改点7:根据毛利率决定添加到哪个列表 ==========
  1252. if (mlv >= 0.15) {
  1253. // 高毛利率订单
  1254. tabledataHigh.addAll(currentOrderRows);
  1255. System.out.println("订单 " + orderCode + " 归类到高毛利率审批(>=15%)");
  1256. } else {
  1257. // 低毛利率订单
  1258. tabledataLow.addAll(currentOrderRows);
  1259. System.out.println("订单 " + orderCode + " 归类到低毛利率审批(<15%)");
  1260. }
  1261. } else {
  1262. try {
  1263. log.info("采购订单编号:{}将不发起钉钉审批",orderCode);
  1264. HashMap body1 = new HashMap();
  1265. body1.put("orderCode",orderCode);//订单编号:orderCode
  1266. body1.put("vendorCode",dataArray.getJSONObject(0).getString("vendorCode"));//供应商编码:gysnumber
  1267. String aa = dataArray.getJSONObject(0).getLong("purchaseTime").toString();
  1268. String purchaseTime = Instant.ofEpochMilli(Long.parseLong(aa))
  1269. .atZone(ZoneId.of("Asia/Shanghai"))
  1270. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  1271. body1.put("purchaseTime",purchaseTime);//采购日期:purchaseTime
  1272. String bb = dataArray.getJSONObject(0).getLong("planArrivalTime").toString();
  1273. String planArrivalTime = Instant.ofEpochMilli(Long.parseLong(bb))
  1274. .atZone(ZoneId.of("Asia/Shanghai"))
  1275. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  1276. body1.put("planArrivalTime",planArrivalTime);//计划到货日期:planArrivalTime
  1277. ArrayList<Map<String,String>> customFiled = new ArrayList();
  1278. HashMap field = new HashMap();
  1279. field.put("name","采购订单钉钉审批状态");
  1280. field.put("value","审批完成");//审批状态
  1281. customFiled.add(field);
  1282. body1.put("purchaseOrderCustomFieldsValue",customFiled);
  1283. UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/update", header, null, body1);
  1284. log.info("---------【回传,{},采购订单状态完成】-----------",dataArray.getJSONObject(0).getString("orderCode"));
  1285. } catch (Exception e) {
  1286. log.info("样品订单的采购订单自动通过审批失败,采购订单编号为:{}",orderCode);
  1287. e.printStackTrace();
  1288. }
  1289. }
  1290. }
  1291. List<Map<String, Object>> oldList = new ArrayList<>();
  1292. List<Map<String, Object>> faxList = new ArrayList<>();
  1293. if (type.equals(targetValueUpdate)){
  1294. oldIds.forEach(h->{
  1295. List<Map> oldDataList = ydService.queryFormData_all(YDParam.builder()
  1296. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1297. .formUuid("FORM-278D56A5065641F8AC95BCA0A8CE8447D8QY")
  1298. .searchFieldJson(JSON.toJSONString(UtilMap.map("textField_mmx9gyct", h)))
  1299. .build());
  1300. if (ObjectUtil.isNotNull(oldDataList) && oldDataList.size()>0){
  1301. List<Map> sonList = ydService.queryDetails(YDParam.builder()
  1302. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1303. .formInstanceId(UtilMap.getString(oldDataList.get(0),"textField_mmx9gycu"))
  1304. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2")
  1305. .tableFieldId("tableField_ml6g7k5d")
  1306. .build());
  1307. if (ObjectUtil.isNotNull(sonList) && sonList.size() > 0){
  1308. sonList.forEach(s->{
  1309. Map<String, Object> map = new HashMap<>();
  1310. TABLEFIELD_ENUM.forEach((k,v)->{
  1311. map.put(v,UtilMap.getString(s,k));
  1312. });
  1313. oldList.add(map);
  1314. });
  1315. }
  1316. List<Map> sonFaxList = ydService.queryDetails(YDParam.builder()
  1317. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1318. .formInstanceId(UtilMap.getString(oldDataList.get(0),"textField_mmx9gycu"))
  1319. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2")
  1320. .tableFieldId("tableField_ml7ch2pj")
  1321. .build());
  1322. if (ObjectUtil.isNotNull(sonFaxList) && sonFaxList.size() > 0){
  1323. sonFaxList.forEach(s->{
  1324. Map<String, Object> map = new HashMap<>();
  1325. TABLEFIELD_ENUM2.forEach((k,v)->{
  1326. map.put(v,UtilMap.getString(s,k));
  1327. });
  1328. faxList.add(map);
  1329. });
  1330. }
  1331. }
  1332. });
  1333. log.info("oldList:{}",oldList.toString());
  1334. log.info("faxList:{}",faxList.toString());
  1335. }
  1336. // ========== 修改点8:分别处理高低毛利率的审批 ==========
  1337. // 处理高毛利率的审批 (mlv >= 0.15)
  1338. if (!tabledataHigh.isEmpty()) {
  1339. System.out.println("\n========== 开始处理高毛利率审批(>=15%),共 " + tabledataHigh.size() + " 条明细 ==========");
  1340. //组装数据塞到采购明细表
  1341. formdataHigh.put("tableField_ml6g7k5d", tabledataHigh);
  1342. //组装数据塞到采购审批单号明细
  1343. List<Map<String, String>> orderSummaryListHigh = calculateOrderSummary(tabledataHigh);
  1344. formdataHigh.put("tableField_ml7ch2pj", orderSummaryListHigh);
  1345. formdataHigh.put("tableField_mmx6gata", oldList);
  1346. formdataHigh.put("tableField_mnekj8oq", faxList);
  1347. //数值统计毛利率
  1348. int szHigh = 0;
  1349. for (Map map : orderSummaryListHigh) {
  1350. Object numberFieldMm2t71jo = map.get("numberField_mm2t71jo");
  1351. log.info((String) numberFieldMm2t71jo);
  1352. szHigh += Integer.parseInt((String) numberFieldMm2t71jo);
  1353. }
  1354. formdataHigh.put("numberField_mm2t71jp", szHigh);
  1355. /*发起流程 - 高毛利率审批*/
  1356. String userId = getDDToken(purchaserName);
  1357. ydClient.operateData(YDParam.builder()
  1358. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1359. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2") // 高毛利率使用原表单
  1360. .userId(userId)
  1361. .formDataJson(JSON.toJSONString(formdataHigh))
  1362. .build(), YDConf.FORM_OPERATION.start).toString();
  1363. /*修改采购订单为审批中*/
  1364. for (Map map : orderSummaryListHigh) {
  1365. String textFieldMl7ch2pk = (String) map.get("textField_ml7ch2pk");
  1366. callback(textFieldMl7ch2pk);
  1367. }
  1368. System.out.println("高毛利率审批流程发起完成");
  1369. }
  1370. // 处理低毛利率的审批 (mlv < 0.15)
  1371. if (!tabledataLow.isEmpty()) {
  1372. System.out.println("\n========== 开始处理低毛利率审批(<15%),共 " + tabledataLow.size() + " 条明细 ==========");
  1373. //组装数据塞到采购明细表
  1374. formdataLow.put("tableField_ml6g7k5d", tabledataLow);
  1375. formdataLow.put("tableField_mmx6gata", oldList);
  1376. formdataLow.put("tableField_mnekj8oq", faxList);
  1377. //组装数据塞到采购审批单号明细
  1378. List<Map<String, String>> orderSummaryListLow = calculateOrderSummary(tabledataLow);
  1379. formdataLow.put("tableField_ml7ch2pj", orderSummaryListLow);
  1380. //数值统计毛利率
  1381. int szLow = 0;
  1382. for (Map map : orderSummaryListLow) {
  1383. Object numberFieldMm2t71jo = map.get("numberField_mm2t71jo");
  1384. log.info((String) numberFieldMm2t71jo);
  1385. szLow += Integer.parseInt((String) numberFieldMm2t71jo);
  1386. }
  1387. formdataLow.put("numberField_mm2t71jp", szLow);
  1388. /*发起流程 - 低毛利率审批*/
  1389. String userId = getDDToken(purchaserName);
  1390. // ========== 修改点9:如果低毛利率需要不同表单,可以在这里修改formUuid ==========
  1391. ydClient.operateData(YDParam.builder()
  1392. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1393. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2") // 如果需要不同流程,替换这里的UUID
  1394. .userId(userId)
  1395. .formDataJson(JSON.toJSONString(formdataLow))
  1396. .build(), YDConf.FORM_OPERATION.start).toString();
  1397. /*修改采购订单为审批中*/
  1398. for (Map map : orderSummaryListLow) {
  1399. String textFieldMl7ch2pk = (String) map.get("textField_ml7ch2pk");
  1400. callback(textFieldMl7ch2pk);
  1401. }
  1402. System.out.println("低毛利率审批流程发起完成");
  1403. }
  1404. });
  1405. }
  1406. return null;
  1407. }
  1408. @SneakyThrows
  1409. @Override
  1410. public List<Map<String, Object>> queryAllPurchase() {
  1411. HashMap header = new HashMap();
  1412. header.put("X-AUTH", HeiHuAccessToken().getData().toString());
  1413. header.put("Content-Type", "application/json");
  1414. boolean hasMoreData = true;
  1415. int pageNum = 1;
  1416. int pageSize = 100;
  1417. List<Map<String, Object>> dataList = new ArrayList<>();
  1418. while (hasMoreData) {
  1419. HashMap body = new HashMap();
  1420. Map<String, Integer> page = new HashMap<>();
  1421. page.put("pageNum", pageNum);
  1422. page.put("pageSize", pageSize);
  1423. List<Integer> status = Arrays.asList(1);
  1424. body.put("page", page);
  1425. body.put("status", status);
  1426. String doPost = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//查询采购订单
  1427. log.info("header:{}",header.toString());
  1428. System.out.println("header:" + header.toString());
  1429. ObjectMapper mapper = new ObjectMapper();
  1430. Map<String, Object> response = mapper.readValue(doPost, Map.class);
  1431. if (!"01000000".equals(response.get("code"))) {
  1432. System.out.println("请求失败: " + response.get("msg"));
  1433. break;
  1434. }
  1435. // dataList.addAll(UtilMap.getList(response,"data"));
  1436. List<Map<String, Object>> mapList = (List<Map<String, Object>>) response.get("data");
  1437. if (ObjectUtil.isNotNull(mapList) && mapList.size() > 0){
  1438. dataList.addAll(mapList);
  1439. hasMoreData = mapList.size() >= pageSize;
  1440. } else {
  1441. hasMoreData = false;
  1442. }
  1443. pageNum++;
  1444. }
  1445. try {
  1446. Thread.sleep(200);
  1447. } catch (InterruptedException e) {
  1448. e.printStackTrace();
  1449. }
  1450. return dataList;
  1451. }
  1452. @Override
  1453. public McR purchaseUpdateSchedule() throws JacksonException {
  1454. HashMap header = new HashMap();
  1455. header.put("X-AUTH", HeiHuAccessToken().getData().toString());
  1456. header.put("Content-Type", "application/json");
  1457. String targetValue = "合同修改,修改审批";
  1458. Map<String, List<String>> purchaserOrderCodes = new HashMap<>();
  1459. int pageNum = 1;
  1460. int pageSize = 100;
  1461. boolean hasMoreData = true;
  1462. while (hasMoreData) {
  1463. HashMap body = new HashMap();
  1464. Map<String, Integer> page = new HashMap<>();
  1465. page.put("pageNum", pageNum);
  1466. page.put("pageSize", pageSize);
  1467. List<Integer> status = Arrays.asList(1);
  1468. body.put("page", page);
  1469. body.put("status", status);
  1470. String doPost = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//查询采购订单
  1471. ObjectMapper mapper = new ObjectMapper();
  1472. Map<String, Object> response = mapper.readValue(doPost, Map.class);
  1473. if (!"01000000".equals(response.get("code"))) {
  1474. log.info("请求失败: {}" , response.get("msg"));
  1475. break;
  1476. }
  1477. List<Map<String, Object>> dataList = (List<Map<String, Object>>) response.get("data");
  1478. if (dataList != null) {
  1479. for (Map<String, Object> item : dataList) {
  1480. String purchaserName = (String) item.get("purchaserName");
  1481. if (purchaserName == null) purchaserName = "未知";
  1482. boolean hasTargetStatus = false;
  1483. List<Map<String, Object>> customFieldValues = (List<Map<String, Object>>) item.get("customFieldValues");
  1484. if (customFieldValues != null) {
  1485. for (Map<String, Object> field : customFieldValues) {
  1486. if (targetValue.equals(field.get("value"))) {
  1487. hasTargetStatus = true;
  1488. break;
  1489. }
  1490. }
  1491. }
  1492. if (hasTargetStatus) {
  1493. String orderCode = (String) item.get("orderCode");
  1494. if (orderCode != null) {
  1495. purchaserOrderCodes.computeIfAbsent(purchaserName, k -> new ArrayList<>()).add(orderCode);
  1496. }
  1497. }
  1498. }
  1499. hasMoreData = dataList.size() >= pageSize;
  1500. } else {
  1501. hasMoreData = false;
  1502. }
  1503. pageNum++;
  1504. try {
  1505. Thread.sleep(200);
  1506. } catch (InterruptedException e) {
  1507. e.printStackTrace();
  1508. }
  1509. }
  1510. // 输出所有采购员的待审批订单
  1511. System.out.println("========== 所有采购员的待审批订单统计 ==========");
  1512. if (purchaserOrderCodes.isEmpty()) {
  1513. System.out.println("没有找到钉钉审批状态为'" + targetValue + "'的订单");
  1514. } else {
  1515. int totalPurchasers = purchaserOrderCodes.size();
  1516. int totalOrders = purchaserOrderCodes.values().stream().mapToInt(List::size).sum();
  1517. System.out.println("共找到 " + totalOrders + " 个待审批订单");
  1518. System.out.println("涉及 " + totalPurchasers + " 位采购员");
  1519. System.out.println();
  1520. // 输出每个采购员的情况
  1521. for (Map.Entry<String, List<String>> entry : purchaserOrderCodes.entrySet()) {
  1522. String purchaserName = entry.getKey();
  1523. List<String> orderCodes = entry.getValue();
  1524. int orderCount = orderCodes.size();
  1525. System.out.println("采购员: " + purchaserName);
  1526. System.out.println("待审批订单数量: " + orderCount);
  1527. if (orderCount > 1) {
  1528. System.out.println("⚠️ 注意:该采购员有 " + orderCount + " 个待审批订单");
  1529. }
  1530. System.out.println("订单编号: " + String.join(", ", orderCodes));
  1531. System.out.println();
  1532. }
  1533. // 按订单数量排序输出
  1534. System.out.println("========== 按待审批订单数量排序 ==========");
  1535. purchaserOrderCodes.entrySet().stream()
  1536. .sorted((e1, e2) -> Integer.compare(e2.getValue().size(), e1.getValue().size()))
  1537. .forEach(entry -> {
  1538. String purchaserName = entry.getKey();
  1539. List<String> orderCodes = entry.getValue();
  1540. System.out.println(purchaserName + " (" + orderCodes.size() + "个): " +
  1541. String.join(", ", orderCodes));
  1542. // ========== 修改点1:声明两个列表分别存储不同毛利率的订单数据 ==========
  1543. // 针对同一个采购员,遍历下面的订单编号
  1544. System.out.println("开始处理采购员 " + purchaserName + " 的 " + orderCodes.size() + " 个待审批订单");
  1545. // 高毛利率表单数据 (mlv >= 0.15)
  1546. HashMap formdataHigh = new HashMap();
  1547. List<Map<String,String>> tabledataHigh = new ArrayList();
  1548. // 低毛利率表单数据 (mlv < 0.15)
  1549. HashMap formdataLow = new HashMap();
  1550. List<Map<String,String>> tabledataLow = new ArrayList();
  1551. // ========== 修改点2:为每个订单创建临时存储列表 ==========
  1552. // 用于暂存每个订单的明细数据,等计算出毛利率后再决定添加到哪个列表
  1553. Map<String, List<Map<String, String>>> tempOrderDataMap = new HashMap<>();
  1554. // 用于存储每个订单的汇总数据,用于计算毛利率
  1555. Map<String, Map<String, Double>> orderSummaryForMlv = new HashMap<>();
  1556. List<String> oldHighIds = new ArrayList<>();
  1557. List<String> oldLowIds = new ArrayList<>();
  1558. for (String orderCode : orderCodes) {
  1559. System.out.println("正在处理订单: " + orderCode);
  1560. // ========== 修改点3:为当前订单创建临时数据存储 ==========
  1561. List<Map<String, String>> currentOrderRows = new ArrayList<>();
  1562. double orderTotalSalesAmount = 0.0;
  1563. double orderTotalPurchaseAmount = 0.0;
  1564. double orderTotalFlygcb = 0.0;
  1565. //todo:查询订单的销售订单 | 客户 销售订单号 款式 产品描述 颜色 | 数量 销售单价 销售金额 | 币别 美金汇率 辅料预估成本 销售总金额
  1566. String customerName = "",orderNumber ="",styleNumber ="",productDescription = "",color = "";
  1567. Double number,unitPrice,salesAmount;
  1568. String currency = ""; Double USDrate = 0.00; Double flygcb = 0.00; Double saletotalAmount = 0.00;
  1569. Double estimatedPrice = 0.00;//辅料预估单价
  1570. HashMap body = new HashMap();
  1571. body.put("orderCode",orderCode);//订单编号
  1572. String jsonString = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);
  1573. //todo:查询采购订单 生产工厂(供应商)
  1574. String shortName = "";
  1575. JSONArray dataArray = JSONObject.parseObject(jsonString).getJSONArray("data");
  1576. for (int i=0;i<dataArray.size();i++) {
  1577. JSONObject data = dataArray.getJSONObject(i);
  1578. shortName = data.getString("shortName");//供应商:shortName
  1579. }
  1580. JSONArray products = JSONObject.parseObject(jsonString).getJSONArray("data").getJSONObject(0).getJSONArray("purchaseSubOrderVOS");
  1581. ObjectMapper objectMapper = new ObjectMapper();
  1582. JsonNode rootNode = null;
  1583. try {
  1584. rootNode = objectMapper.readTree(jsonString);
  1585. } catch (JsonProcessingException e) {
  1586. throw new RuntimeException(e);
  1587. }
  1588. JsonNode dataNode = rootNode.get("data");
  1589. if(dataNode != null && dataNode.isArray()){
  1590. for(JsonNode item : dataNode){
  1591. JsonNode orderNoNode = item.get("orderCode");
  1592. JsonNode saleOrders = item.get("relationSaleOrders");
  1593. if(saleOrders != null && saleOrders.isArray() && saleOrders.size() > 0){
  1594. orderNumber = saleOrders.get(0).asText();//销售订单号
  1595. }
  1596. }
  1597. }
  1598. HashMap body_A = new HashMap();
  1599. body_A.put("orderNo",orderNumber);
  1600. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/saleOrder/queryList2", header, null, body_A);//todo:查询销售订单,获取客户、订单号、款号、产品描述、颜色、数量、销售单价、销售金额、币别
  1601. JSONArray array = JSONObject.parseObject(jsonString2).getJSONArray("data");//主表数据
  1602. for(int i=0;i<array.size();i++){
  1603. JSONObject data = array.getJSONObject(i);
  1604. customerName = data.getString("customerCode");//客户
  1605. }
  1606. ObjectMapper objectMapper2 = new ObjectMapper();
  1607. JsonNode dataNode2 = null;//主表数据
  1608. try {
  1609. dataNode2 = objectMapper2.readTree(jsonString2).get("data");
  1610. } catch (JsonProcessingException e) {
  1611. throw new RuntimeException(e);
  1612. }
  1613. for (JsonNode item : dataNode2){
  1614. JsonNode customFieldValues = item.get("customFieldValues");
  1615. for (JsonNode field : customFieldValues){
  1616. JsonNode fieldIdNode = field.get("fieldId");
  1617. if(fieldIdNode != null && fieldIdNode.asInt() == 161769){
  1618. JsonNode valueNode = field.get("value");
  1619. if(valueNode != null){
  1620. estimatedPrice = valueNode.asDouble();//辅料预估单价
  1621. break;
  1622. }
  1623. }
  1624. }
  1625. }
  1626. JSONArray products_A = JSONObject.parseObject(jsonString2).getJSONArray("data").getJSONObject(0).getJSONArray("saleManageOrderDetailRowApiVOList");//销售订单明细数据
  1627. if(products_A != null) {
  1628. for (int i = 0; i < products_A.size(); i++) {
  1629. JSONObject detail = products_A.getJSONObject(i);
  1630. HashMap row = new HashMap();
  1631. row.put("textField_mm2t71jm",orderCode);//todo:采购订单单号
  1632. row.put("textField_ml6g7k5e", customerName);//todo:客户
  1633. row.put("textField_ml6g7k5f", orderNumber);//todo:订单号
  1634. styleNumber = detail.getString("productCode");//款号
  1635. row.put("textField_ml7c3yhq", styleNumber);//todo:款号
  1636. productDescription = detail.getString("productName");//产品描述
  1637. row.put("textField_ml7c3yhr", productDescription);//todo:产品描述
  1638. JSONArray array1 = detail.getJSONArray("customFieldValues");
  1639. color = array1.stream()
  1640. .map(obj -> (JSONObject) obj)
  1641. .filter(item -> item.getIntValue("fieldId") == 82259)
  1642. .map(item -> item.getString("value"))
  1643. .findFirst()
  1644. .orElse(null);
  1645. ArrayList colorList = new ArrayList();
  1646. colorList.add(color);
  1647. String color_AAA = null;
  1648. try {
  1649. color_AAA = getProductColor(colorList);
  1650. } catch (JacksonException e) {
  1651. throw new RuntimeException(e);
  1652. }
  1653. row.put("textField_ml7c3yhs", color_AAA);//todo:颜色
  1654. number = detail.getDoubleValue("qty");//数量
  1655. row.put("numberField_ml7c3yht", number);//todo:数量
  1656. unitPrice = detail.getDoubleValue("unitPrice");//销售单价
  1657. row.put("numberField_ml7c3yhu", unitPrice);//todo:销售单价
  1658. salesAmount = number * unitPrice;//销售金额
  1659. row.put("numberField_ml7c3yhv", salesAmount);//todo:销售金额
  1660. String customFieldValues = detail.getString("customFieldValues");
  1661. ObjectMapper mapper = new ObjectMapper();
  1662. JsonNode jsonarray = null;
  1663. try {
  1664. jsonarray = mapper.readTree(customFieldValues);
  1665. } catch (JsonProcessingException e) {
  1666. throw new RuntimeException(e);
  1667. }
  1668. for (JsonNode node : jsonarray) {
  1669. if (node.get("fieldId").asInt() == 47919) {
  1670. currency = node.get("value").asText();
  1671. } else if (node.get("fieldId").asInt() == 165251) {
  1672. USDrate = node.get("value").asDouble();
  1673. } else if (node.get("fieldId").asInt() == 161783) {
  1674. flygcb = node.get("value").asDouble();
  1675. }
  1676. }
  1677. row.put("textField_ml7c3yhw", currency);//todo:币别
  1678. row.put("numberField_ml86221y", USDrate);//todo:美金汇率
  1679. row.put("numberField_ml86221z", flygcb);//todo:辅料预估成本
  1680. if(currency.equals("USD")){
  1681. saletotalAmount = salesAmount * USDrate;
  1682. }else {
  1683. saletotalAmount = salesAmount;
  1684. }
  1685. row.put("numberField_ml862220",saletotalAmount);
  1686. //下面是采购订单的明细数据
  1687. row.put("textField_ml7c3yhx",shortName);//todo:生产工厂
  1688. for(int j=0;j<products.size();j++){
  1689. if(styleNumber.equals(products.getJSONObject(j).getString("productCode"))){
  1690. //找到对应的采购一行数据
  1691. row.put("numberField_ml7c3yhy",products.getJSONObject(j).getDouble("purchasePrice"));//todo:采购单价
  1692. row.put("numberField_ml7c3yhz",products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购数量
  1693. row.put("numberField_ml7c3yi0",products.getJSONObject(j).getDouble("purchasePrice") * products.getJSONObject(j).getDouble("purchaseNum"));//todo:采购金额
  1694. }
  1695. }
  1696. // ========== 修改点4:将当前行转换为Map<String,String>并暂存 ==========
  1697. Map<String, String> rowMap = new HashMap<>();
  1698. for (Object key : row.keySet()) {
  1699. Object value = row.get(key);
  1700. rowMap.put(key.toString(), value != null ? value.toString() : "");
  1701. }
  1702. currentOrderRows.add(rowMap);
  1703. // ========== 修改点5:累加当前订单的汇总数据用于计算毛利率 ==========
  1704. orderTotalSalesAmount += saletotalAmount;
  1705. orderTotalPurchaseAmount += (Double)row.get("numberField_ml7c3yi0");
  1706. orderTotalFlygcb += flygcb;
  1707. }
  1708. }
  1709. // ========== 修改点6:计算当前订单的毛利率 ==========
  1710. double mlv = 0.0;
  1711. if (orderTotalSalesAmount > 0) {
  1712. mlv = (orderTotalSalesAmount - orderTotalPurchaseAmount - orderTotalFlygcb) / orderTotalSalesAmount;
  1713. }
  1714. System.out.println("订单 " + orderCode + " 毛利率: " + String.format("%.2f%%", mlv * 100));
  1715. // ========== 修改点7:根据毛利率决定添加到哪个列表 ==========
  1716. if (mlv >= 0.15) {
  1717. // 高毛利率订单
  1718. tabledataHigh.addAll(currentOrderRows);
  1719. oldHighIds.add(orderCode);
  1720. System.out.println("订单 " + orderCode + " 归类到高毛利率审批(>=15%)");
  1721. } else {
  1722. // 低毛利率订单
  1723. tabledataLow.addAll(currentOrderRows);
  1724. oldLowIds.add(orderCode);
  1725. System.out.println("订单 " + orderCode + " 归类到低毛利率审批(<15%)");
  1726. }
  1727. }
  1728. // ========== 修改点8:分别处理高低毛利率的审批 ==========
  1729. // 处理高毛利率的审批 (mlv >= 0.15)
  1730. if (!tabledataHigh.isEmpty()) {
  1731. System.out.println("\n========== 开始处理高毛利率审批(>=15%),共 " + tabledataHigh.size() + " 条明细 ==========");
  1732. List<Map<String, Object>> oldList = new ArrayList<>();
  1733. oldHighIds.forEach(h->{
  1734. List<Map> dataList = ydService.queryFormData_all(YDParam.builder()
  1735. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1736. .formUuid("FORM-278D56A5065641F8AC95BCA0A8CE8447D8QY")
  1737. .searchFieldJson(JSON.toJSONString(UtilMap.map("textField_mmx9gyct", h)))
  1738. .build());
  1739. if (ObjectUtil.isNotNull(dataList) && dataList.size()>0){
  1740. List<Map> sonList = ydService.queryDetails(YDParam.builder()
  1741. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1742. .formInstanceId(UtilMap.getString(dataList.get(0),"textField_mmx9gycu"))
  1743. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2")
  1744. .tableFieldId("tableField_ml6g7k5d")
  1745. .build());
  1746. if (ObjectUtil.isNotNull(sonList) && sonList.size() > 0){
  1747. sonList.forEach(s->{
  1748. Map<String, Object> map = new HashMap<>();
  1749. TABLEFIELD_ENUM.forEach((k,v)->{
  1750. map.put(v,UtilMap.getString(s,k));
  1751. });
  1752. oldList.add(map);
  1753. });
  1754. }
  1755. }
  1756. });
  1757. //组装数据塞到采购明细表
  1758. formdataHigh.put("tableField_ml6g7k5d", tabledataHigh);
  1759. formdataHigh.put("tableField_mmx6gata", oldList);
  1760. //组装数据塞到采购审批单号明细
  1761. List<Map<String, String>> orderSummaryListHigh = calculateOrderSummary(tabledataHigh);
  1762. formdataHigh.put("tableField_ml7ch2pj", orderSummaryListHigh);
  1763. //数值统计毛利率
  1764. int szHigh = 0;
  1765. for (Map map : orderSummaryListHigh) {
  1766. Object numberFieldMm2t71jo = map.get("numberField_mm2t71jo");
  1767. log.info((String) numberFieldMm2t71jo);
  1768. szHigh += Integer.parseInt((String) numberFieldMm2t71jo);
  1769. }
  1770. formdataHigh.put("numberField_mm2t71jp", szHigh);
  1771. /*发起流程 - 高毛利率审批*/
  1772. String userId = getDDToken(purchaserName);
  1773. ydClient.operateData(YDParam.builder()
  1774. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1775. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2") // 高毛利率使用原表单
  1776. .userId(userId)
  1777. .formDataJson(JSON.toJSONString(formdataHigh))
  1778. .build(), YDConf.FORM_OPERATION.start).toString();
  1779. /*修改采购订单为审批中*/
  1780. for (Map map : orderSummaryListHigh) {
  1781. String textFieldMl7ch2pk = (String) map.get("textField_ml7ch2pk");
  1782. callback(textFieldMl7ch2pk);
  1783. }
  1784. System.out.println("高毛利率审批流程发起完成");
  1785. }
  1786. // 处理低毛利率的审批 (mlv < 0.15)
  1787. if (!tabledataLow.isEmpty()) {
  1788. System.out.println("\n========== 开始处理低毛利率审批(<15%),共 " + tabledataLow.size() + " 条明细 ==========");
  1789. List<Map<String, Object>> oldList = new ArrayList<>();
  1790. oldLowIds.forEach(h->{
  1791. List<Map> dataList = ydService.queryFormData_all(YDParam.builder()
  1792. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1793. .formUuid("FORM-278D56A5065641F8AC95BCA0A8CE8447D8QY")
  1794. .searchFieldJson(JSON.toJSONString(UtilMap.map("textField_mmx9gyct", h)))
  1795. .build());
  1796. if (ObjectUtil.isNotNull(dataList) && dataList.size()>0){
  1797. List<Map> sonList = ydService.queryDetails(YDParam.builder()
  1798. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1799. .formInstanceId(UtilMap.getString(dataList.get(0),"textField_mmx9gycu"))
  1800. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2")
  1801. .tableFieldId("tableField_ml6g7k5d")
  1802. .build());
  1803. if (ObjectUtil.isNotNull(sonList) && sonList.size() > 0){
  1804. sonList.forEach(s->{
  1805. Map<String, Object> map = new HashMap<>();
  1806. TABLEFIELD_ENUM.forEach((k,v)->{
  1807. map.put(v,UtilMap.getString(s,k));
  1808. });
  1809. oldList.add(map);
  1810. });
  1811. }
  1812. }
  1813. });
  1814. //组装数据塞到采购明细表
  1815. formdataLow.put("tableField_mmx6gata", oldList);
  1816. //组装数据塞到采购明细表
  1817. formdataLow.put("tableField_ml6g7k5d", tabledataLow);
  1818. //组装数据塞到采购审批单号明细
  1819. List<Map<String, String>> orderSummaryListLow = calculateOrderSummary(tabledataLow);
  1820. formdataLow.put("tableField_ml7ch2pj", orderSummaryListLow);
  1821. //数值统计毛利率
  1822. int szLow = 0;
  1823. for (Map map : orderSummaryListLow) {
  1824. Object numberFieldMm2t71jo = map.get("numberField_mm2t71jo");
  1825. log.info((String) numberFieldMm2t71jo);
  1826. szLow += Integer.parseInt((String) numberFieldMm2t71jo);
  1827. }
  1828. formdataLow.put("numberField_mm2t71jp", szLow);
  1829. /*发起流程 - 低毛利率审批*/
  1830. String userId = getDDToken(purchaserName);
  1831. // ========== 修改点9:如果低毛利率需要不同表单,可以在这里修改formUuid ==========
  1832. ydClient.operateData(YDParam.builder()
  1833. .appType(ydConf.getAppType()).systemToken(ydConf.getSystemToken())
  1834. .formUuid("FORM-3A54B12BE3D241218A75242B935F2987YWV2") // 如果需要不同流程,替换这里的UUID
  1835. .userId(userId)
  1836. .formDataJson(JSON.toJSONString(formdataLow))
  1837. .build(), YDConf.FORM_OPERATION.start).toString();
  1838. /*修改采购订单为审批中*/
  1839. for (Map map : orderSummaryListLow) {
  1840. String textFieldMl7ch2pk = (String) map.get("textField_ml7ch2pk");
  1841. callback(textFieldMl7ch2pk);
  1842. }
  1843. System.out.println("低毛利率审批流程发起完成");
  1844. }
  1845. });
  1846. }
  1847. return null;
  1848. }
  1849. private static final Map<String,String> TABLEFIELD_ENUM =new HashMap<>();
  1850. static {
  1851. TABLEFIELD_ENUM.put("textField_mm2t71jm","textField_mmx6gast");
  1852. TABLEFIELD_ENUM.put("textField_ml6g7k5e","textField_mmx6gasu");
  1853. TABLEFIELD_ENUM.put("textField_ml6g7k5f","textField_mmx6gasv");
  1854. TABLEFIELD_ENUM.put("textField_ml7c3yhq","textField_mmx6gasw");
  1855. TABLEFIELD_ENUM.put("textField_ml7c3yhr","textField_mmx6gasx");
  1856. TABLEFIELD_ENUM.put("textField_ml7c3yhs","textField_mmx6gasy");
  1857. TABLEFIELD_ENUM.put("numberField_ml7c3yht","numberField_mmx6gasz");
  1858. TABLEFIELD_ENUM.put("numberField_ml7c3yhu","numberField_mmx6gat0");
  1859. TABLEFIELD_ENUM.put("numberField_ml7c3yhv","numberField_mmx6gat1");
  1860. TABLEFIELD_ENUM.put("textField_ml7c3yhw","textField_mmx6gat2");
  1861. TABLEFIELD_ENUM.put("numberField_ml86221y","numberField_mmx6gat3");
  1862. TABLEFIELD_ENUM.put("numberField_ml86221z","numberField_mmx6gat4");
  1863. TABLEFIELD_ENUM.put("numberField_ml862220","numberField_mmx6gat5");
  1864. TABLEFIELD_ENUM.put("textField_ml7c3yhx","textField_mmx6gat6");
  1865. TABLEFIELD_ENUM.put("numberField_ml7c3yhy","numberField_mmx6gat7");
  1866. TABLEFIELD_ENUM.put("numberField_ml7c3yhz","numberField_mmx6gat8");
  1867. TABLEFIELD_ENUM.put("numberField_ml7c3yi0","numberField_mmx6gat9");
  1868. }
  1869. private static final Map<String,String> TABLEFIELD_ENUM2 =new HashMap<>();//修改后:修改前
  1870. static {
  1871. TABLEFIELD_ENUM2.put("textField_ml7ch2pk","textField_mnekj8ok");
  1872. TABLEFIELD_ENUM2.put("numberField_ml862225","numberField_mnekj8ol");
  1873. TABLEFIELD_ENUM2.put("numberField_ml862226","numberField_mnekj8om");
  1874. TABLEFIELD_ENUM2.put("numberField_ml862228","numberField_mnekj8on");
  1875. TABLEFIELD_ENUM2.put("numberField_ml86222d","numberField_mnekj8oo");
  1876. }
  1877. /**
  1878. * 根据orderCode对tabledata进行分类求和
  1879. * @param tableData 原始明细数据
  1880. * @return 按orderCode汇总后的数据列表(只包含求和结果)
  1881. */
  1882. private List<Map<String, String>> calculateOrderSummary(List<Map<String, String>> tableData) {
  1883. // 使用Map暂存每个orderCode的汇总数据
  1884. Map<String, Map<String, Double>> summaryMap = new LinkedHashMap<>();
  1885. for (Map<String, String> row : tableData) {
  1886. String orderCode = row.get("textField_mm2t71jm"); // 采购订单号
  1887. if (orderCode == null || orderCode.isEmpty()) {
  1888. continue;
  1889. }
  1890. // 获取或创建该订单的汇总Map
  1891. Map<String, Double> orderSum = summaryMap.computeIfAbsent(orderCode,
  1892. k -> {
  1893. Map<String, Double> newMap = new HashMap<>();
  1894. newMap.put("salesAmount", 0.0); // 销售金额总和
  1895. newMap.put("purchaseAmount", 0.0); // 采购金额总和
  1896. newMap.put("flygcb", 0.0); // 辅料预估成本总和
  1897. return newMap;
  1898. });
  1899. // 累加各项金额
  1900. String salesAmountStr = UtilMap.getString(row,"numberField_ml862220");
  1901. String purchaseAmountStr = UtilMap.getString(row,"numberField_ml7c3yi0");
  1902. String flygcbStr = UtilMap.getString(row,"numberField_ml86221z");
  1903. try {
  1904. if (salesAmountStr != null && !salesAmountStr.isEmpty()) {
  1905. orderSum.put("salesAmount",
  1906. orderSum.get("salesAmount") + Double.parseDouble(salesAmountStr));
  1907. }
  1908. if (purchaseAmountStr != null && !purchaseAmountStr.isEmpty()) {
  1909. orderSum.put("purchaseAmount",
  1910. orderSum.get("purchaseAmount") + Double.parseDouble(purchaseAmountStr));
  1911. }
  1912. if (flygcbStr != null && !flygcbStr.isEmpty()) {
  1913. orderSum.put("flygcb",
  1914. orderSum.get("flygcb") + Double.parseDouble(flygcbStr));
  1915. }
  1916. } catch (NumberFormatException e) {
  1917. System.err.println("数字格式错误: " + e.getMessage());
  1918. }
  1919. }
  1920. // 转换为最终的List<Map<String, String>>
  1921. List<Map<String, String>> result = new ArrayList<>();
  1922. for (Map.Entry<String, Map<String, Double>> entry : summaryMap.entrySet()) {
  1923. String orderCode = entry.getKey();
  1924. Map<String, Double> sums = entry.getValue();
  1925. double salesAmount = sums.get("salesAmount");
  1926. double purchaseAmount = sums.get("purchaseAmount");
  1927. double flygcb = sums.get("flygcb");
  1928. // 构建结果行
  1929. Map<String, String> summaryRow = new LinkedHashMap<>();
  1930. summaryRow.put("textField_ml7ch2pk", orderCode);//orderCode:采购审批单单号
  1931. summaryRow.put("numberField_ml862225", formatNumber(salesAmount));//salesAmount:销售总金额
  1932. summaryRow.put("numberField_ml862226", formatNumber(purchaseAmount));//purchaseAmount:采购订单总金额
  1933. summaryRow.put("numberField_ml862228", formatNumber(flygcb));//flygcb:辅料预估总成本
  1934. summaryRow.put("numberField_ml86222d",formatNumber((salesAmount - purchaseAmount - flygcb) / salesAmount));//毛利率
  1935. Double mlv = (salesAmount - purchaseAmount - flygcb) / salesAmount;
  1936. if(mlv >= 0.15){
  1937. summaryRow.put("numberField_mm2t71jo", String.valueOf(1));
  1938. }else {
  1939. summaryRow.put("numberField_mm2t71jo", String.valueOf(0));
  1940. }
  1941. result.add(summaryRow);
  1942. }
  1943. return result;
  1944. }
  1945. /**
  1946. * 格式化数字,去除多余的.0
  1947. */
  1948. private String formatNumber(double number) {
  1949. if (Math.abs(number - Math.round(number)) < 0.000001) {
  1950. return String.valueOf((long) number);
  1951. } else {
  1952. return String.format("%.2f", number);
  1953. }
  1954. }
  1955. /*采购订单发起更新状态*/
  1956. @SneakyThrows
  1957. public McR callback(String orderNum){
  1958. HashMap header = new HashMap();
  1959. header.put("X-AUTH",HeiHuAccessToken().getData().toString());
  1960. header.put("Content-Type","application/json");
  1961. HashMap body = new HashMap();
  1962. body.put("orderCode",orderNum);//订单编号
  1963. String jsonString2 = UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/queryList2", header, null, body);//todo:查询采购订单
  1964. JSONArray dataArray = JSONObject.parseObject(jsonString2).getJSONArray("data");
  1965. for (int k=0;k<dataArray.size();k++) {
  1966. JSONObject data = dataArray.getJSONObject(k);
  1967. //提取订单基本信息 并赋值
  1968. HashMap body1 = new HashMap();
  1969. body1.put("orderCode",data.getString("orderCode"));//订单编号:orderCode
  1970. body1.put("vendorCode",data.getString("vendorCode"));//供应商编码:gysnumber
  1971. String aa = data.getLong("purchaseTime").toString();
  1972. String purchaseTime = Instant.ofEpochMilli(Long.parseLong(aa))
  1973. .atZone(ZoneId.of("Asia/Shanghai"))
  1974. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  1975. body1.put("purchaseTime",purchaseTime);//采购日期:purchaseTime
  1976. String bb = data.getLong("planArrivalTime").toString();
  1977. String planArrivalTime = Instant.ofEpochMilli(Long.parseLong(bb))
  1978. .atZone(ZoneId.of("Asia/Shanghai"))
  1979. .format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
  1980. body1.put("planArrivalTime",planArrivalTime);//计划到货日期:planArrivalTime
  1981. ArrayList<Map<String,String>> customFiled = new ArrayList();
  1982. HashMap field = new HashMap();
  1983. field.put("name","采购订单钉钉审批状态");
  1984. field.put("value","审批中");//审批状态
  1985. customFiled.add(field);
  1986. body1.put("purchaseOrderCustomFieldsValue",customFiled);
  1987. UtilHttp.doPost("https://liteweb.blacklake.cn/api/dytin/external/purchaseOrder/update", header, null, body1);
  1988. }
  1989. return McR.success();
  1990. }
  1991. /*获取宜搭采购订单汇总*/
  1992. @SneakyThrows
  1993. McR getPurchaseList(){
  1994. log.info("开始查询宜搭采购订单汇总表");
  1995. String formUuid = "FORM-56E11C4FAB6E4FB594169BB779736FF0ZG91";
  1996. YDParam ydParam = YDParam.builder().formUuid(formUuid).build();
  1997. ydParam.setPageSize(1);
  1998. long totalCount = ydClient.queryData(ydParam, YDConf.FORM_QUERY.retrieve_search_form).getTotalCount();
  1999. List<Map> datalist = new ArrayList<>();
  2000. ydParam.setCurrentPage(1);
  2001. ydParam.setPageSize(100);
  2002. int totalPages = (int)Math.ceil((double) totalCount / ydParam.getPageSize());
  2003. for (int page = 1;page <= totalPages;page++){
  2004. ydParam.setCurrentPage(page);
  2005. datalist.addAll((List<Map>) ydClient.queryData(ydParam, YDConf.FORM_QUERY.retrieve_search_form).getData());
  2006. }
  2007. int i =0;
  2008. String jsonStr = "";
  2009. Map<String, String> orderMap = new HashMap<>();//格式:采购订单/关联销售订单
  2010. for(Map li : datalist){
  2011. i++;
  2012. // log.info("{}/{}",i,datalist.size());
  2013. jsonStr = li.get("formData").toString();
  2014. String orderNum = new ObjectMapper().readTree(jsonStr).get("textField_mgq932hi").asText();
  2015. String relatedOrderNum = new ObjectMapper().readTree(jsonStr).get("textField_mhyh7ues").asText();
  2016. orderMap.put(orderNum, relatedOrderNum);
  2017. }
  2018. return McR.success(orderMap);
  2019. }
  2020. }