GluingReport.php 55 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639
  1. <?php
  2. namespace app\api\controller;
  3. use app\common\controller\Api;
  4. use think\Db;
  5. use think\Request;
  6. class GluingReport extends Api
  7. {
  8. protected $noNeedLogin = ['*'];
  9. protected $noNeedRight = ['*'];
  10. /**
  11. * 设备角色菜单
  12. * @return void
  13. */
  14. public function getGluingcoleTab()
  15. {
  16. if ($this->request->isGet() === false){
  17. $this->error('请求错误');
  18. }
  19. $data = [];
  20. $sist = ['印后糊盒车间','精品自动化车间','数字化车间'];
  21. $department = \db('设备_基本资料')
  22. ->distinct(true)
  23. ->where('使用部门','in',$sist)
  24. ->where('设备编组','<>','')
  25. ->order('设备编组')
  26. ->column('rtrim(使用部门) as 使用部门');
  27. if (empty($department)){
  28. $this->success('未获取到机台数据');
  29. }
  30. foreach ($department as $value){
  31. $machine = \db('设备_基本资料')
  32. ->where('使用部门',$value)
  33. ->field('rtrim(设备编号) as 设备编号,rtrim(设备名称) as 设备名称')
  34. ->order('设备编号')
  35. ->select();
  36. foreach ($machine as $k=>$v){
  37. $data[rtrim($value)][] = $v['设备编号'].'-->'.$v['设备名称'];
  38. }
  39. }
  40. $this->success('成功',$data);
  41. }
  42. /**
  43. * 设备角色列表
  44. * @return void
  45. * @throws \think\db\exception\DataNotFoundException
  46. * @throws \think\db\exception\ModelNotFoundException
  47. * @throws \think\exception\DbException
  48. */
  49. public function getGluingcoleList()
  50. {
  51. if ($this->request->isGet() === false){
  52. $this->error('请求错误');
  53. }
  54. $param = $this->request->param();
  55. if (empty($param)){
  56. $this->error('参数错误');
  57. }
  58. $list = db('设备_糊盒班组角色')
  59. ->where('jtbh',$param['machine'])
  60. ->select();
  61. if (empty($list)){
  62. $this->error('未找到数据');
  63. }else{
  64. $this->success('成功',$list);
  65. }
  66. }
  67. /**
  68. * 设备角色资料详情
  69. * @return void
  70. * @throws \think\db\exception\DataNotFoundException
  71. * @throws \think\db\exception\ModelNotFoundException
  72. * @throws \think\exception\DbException
  73. */
  74. public function getGluingcoleDetail()
  75. {
  76. if ($this->request->isGet() === false){
  77. $this->error('请求错误');
  78. }
  79. $param = $this->request->param();
  80. if (empty($param)){
  81. $this->error('参数错误');
  82. }
  83. $list = db('设备_糊盒班组角色')
  84. ->where('id',$param['id'])
  85. ->find();
  86. if (empty($list)){
  87. $this->error('未找到数据详情');
  88. }else{
  89. $this->success('成功',$list);
  90. }
  91. }
  92. /**
  93. * 新增机台班组角色
  94. * @return void
  95. */
  96. public function saveGluingcoleDetail(){
  97. if ($this->request->isPost() === false){
  98. $this->error('请求错误');
  99. }
  100. $param = Request::instance()->post();
  101. if (empty($param)){
  102. $this->error('参数错误');
  103. }
  104. $param['sys_rq'] = date('Y-m-d H:i:s',time());
  105. $res = db('设备_糊盒班组角色')->insert($param);
  106. if (empty($res)){
  107. $this->error('新增失败');
  108. }else{
  109. $this->success('新增成功');
  110. }
  111. }
  112. /**
  113. * 修改设备角色资料
  114. * @return void
  115. * @throws \think\Exception
  116. * @throws \think\exception\PDOException
  117. */
  118. public function getGluingcoleDetaiEdit()
  119. {
  120. if ($this->request->isPost() === false){
  121. $this->error('请求错误');
  122. }
  123. $param = Request::instance()->post();
  124. if (empty($param['id'])){
  125. $this->error('参数错误');
  126. }
  127. $id = intval($param['id']);
  128. $param['mod_rq'] = date('Y-m-d H:i:s',time());
  129. unset($param['id']);
  130. $res = db('设备_糊盒班组角色')
  131. ->where('id',$id)
  132. ->update($param);
  133. if ($res === false){
  134. $this->error('修改失败');
  135. }else{
  136. $this->success('修改成功');
  137. }
  138. }
  139. /**
  140. * 设备当前班组角色
  141. * @return void
  142. * @throws \think\Exception
  143. * @throws \think\exception\PDOException
  144. */
  145. public function UpdateGluingcoleStatus()
  146. {
  147. if ($this->request->isGet() === false){
  148. $this->error('请求错误');
  149. }
  150. $param = $this->request->param();
  151. if (empty($param['id']) || empty($param['jtbh'])){
  152. $this->error('参数错误');
  153. }
  154. $updateRes = db('设备_糊盒班组角色')
  155. ->where('jtbh',$param['jtbh'])
  156. ->update(['status' => 0]);
  157. $res = db('设备_糊盒班组角色')
  158. ->where('id',$param['id'])
  159. ->update(['status' => 1]);
  160. if ($updateRes === false || $res === false){
  161. $this->error('更新失败');
  162. }else{
  163. $this->success('更新成功');
  164. }
  165. }
  166. /**
  167. * 设备班组资料列表
  168. * @return void
  169. * @throws \think\db\exception\DataNotFoundException
  170. * @throws \think\db\exception\ModelNotFoundException
  171. * @throws \think\exception\DbException
  172. */
  173. public function getGluingClassLList()
  174. {
  175. if ($this->request->isGet() === false){
  176. $this->error('请求错误');
  177. }
  178. $param = $this->request->param();
  179. if (empty($param)){
  180. $this->error('参数错误');
  181. }
  182. $list = db('设备_糊盒班组资料')
  183. ->where('jtbh',$param['machine'])
  184. ->select();
  185. foreach ($list as $k=>$v){
  186. for ($i = 1; $i <= 15; $i++){
  187. $bh = $v['bh'.$i];
  188. $list[$k]['name'.$i] = '';
  189. if (!empty($bh) && $bh !== ''){
  190. $name = \db('人事_基本资料')
  191. ->where('员工编号',$bh)
  192. ->value('员工姓名');
  193. $list[$k]['name'.$i] = $name;
  194. }
  195. }
  196. }
  197. if (empty($list)){
  198. $this->error('未找到数据');
  199. }else{
  200. $this->success('成功',$list);
  201. }
  202. }
  203. /**
  204. * 获取设备角色数据
  205. * @return void
  206. * @throws \think\db\exception\DataNotFoundException
  207. * @throws \think\db\exception\ModelNotFoundException
  208. * @throws \think\exception\DbException
  209. */
  210. public function getGluingcole()
  211. {
  212. if ($this->request->isGet() === false){
  213. $this->error('请求错误');
  214. }
  215. $param = $this->request->param();
  216. if (empty($param)){
  217. $this->error('参数错误');
  218. }
  219. $list = db('设备_糊盒班组角色')
  220. ->where('jtbh',$param['machine'])
  221. ->where('status',1)
  222. ->find();
  223. if (empty($list)){
  224. $this->error('未找到角色资料');
  225. }else{
  226. $this->success('成功',$list);
  227. }
  228. }
  229. /**
  230. * 新增糊盒机台班组资料
  231. * @return void
  232. */
  233. public function AddGluingClass()
  234. {
  235. if ($this->request->isPost() === false){
  236. $this->error('请求错误');
  237. }
  238. $param = Request::instance()->post();
  239. if (empty($param)){
  240. $this->error('参数错误');
  241. }
  242. $param['sys_rq'] = date('Y-m-d H:i:s',time());
  243. $res = db('设备_糊盒班组资料')->insert($param);
  244. if ($res === false){
  245. $this->error('新增失败');
  246. }else{
  247. $this->success('新增成功');
  248. }
  249. }
  250. /**
  251. * 修改设备糊盒班组资料
  252. * @return void
  253. * @throws \think\Exception
  254. * @throws \think\exception\PDOException
  255. */
  256. public function UpdateGluingClass()
  257. {
  258. if ($this->request->isPost() === false){
  259. $this->error('请求错误');
  260. }
  261. $param = Request::instance()->post();
  262. if (empty($param['id'])){
  263. $this->error('参数错误');
  264. }
  265. $id = intval($param['id']);
  266. $param['mod_rq'] = date('Y-m-d H:i:s',time());
  267. unset($param['id']);
  268. $res = db('设备_糊盒班组资料')
  269. ->where('id',$id)
  270. ->update($param);
  271. if ($res === false){
  272. $this->error('修改失败');
  273. }else{
  274. $this->success('修改成功');
  275. }
  276. }
  277. /**
  278. * 糊盒机台报工
  279. * @return void
  280. * @throws \think\db\exception\BindParamException
  281. * @throws \think\exception\PDOException
  282. */
  283. public function addGluingReportData()
  284. {
  285. // 1. 请求方式验证(严格限制POST请求)
  286. if (!$this->request->isPost()) {
  287. $this->error('仅支持POST请求');
  288. }
  289. // 2. 获取并验证参数(重点适配含#字符的sczl_jtbh字段)
  290. $param = $this->request->post();
  291. // 核心修复:验证规则调整,明确允许#字符,兼容特殊字符
  292. $validate = new \think\Validate([
  293. 'sczl_jtbh' => 'require|regex:/^[\w#\x{4e00}-\x{9fa5}]+$/u', // 允许字母、数字、下划线、#、中文
  294. 'sczl_gdbh' => 'require',
  295. 'sczl_gxmc' => 'require',
  296. 'sys_id' => 'require',
  297. 'sczl_rq' => 'require|dateFormat:Y-m-d H:i:s',
  298. ], [
  299. 'sczl_jtbh.require' => '机组编号不能为空',
  300. 'sczl_jtbh.regex' => '机组编号仅支持字母、数字、下划线、#号和中文',
  301. 'sczl_gdbh.require' => '工单号不能为空',
  302. 'sczl_gxmc.require' => '工序名称不能为空',
  303. 'sys_id.require' => '系统ID不能为空',
  304. 'sczl_rq.require' => '报工日期不能为空',
  305. 'sczl_rq.dateFormat' => '报工日期格式错误(需为Y-m-d H:i:s)',
  306. ]);
  307. // 验证前处理:仅去除前后空格(不影响#字符)
  308. foreach (['sczl_jtbh', 'sczl_gdbh', 'sczl_gxmc', 'sys_id', 'sczl_rq'] as $field) {
  309. if (isset($param[$field]) && is_string($param[$field])) {
  310. $param[$field] = trim($param[$field]); // 只去空格,保留#等特殊字符
  311. }
  312. }
  313. // 执行验证
  314. if (!$validate->check($param)) {
  315. $this->error($validate->getError());
  316. }
  317. if ($this->isEmptyReportPrice($param['price'] ?? null)) {
  318. $resolvedPrice = $this->resolveReportPrice($param);
  319. if ($resolvedPrice !== null) {
  320. $param['price'] = $resolvedPrice;
  321. } else {
  322. unset($param['price']);
  323. }
  324. }
  325. // 3. 事务处理(确保数据一致性)
  326. $currentTime = date('Y-m-d H:i:s');
  327. $tableClass = '糊盒报工班组';
  328. $tableDevice = '设备_糊盒报工资料';
  329. // 4. 构建班组数据(保留#字符,无需额外处理)
  330. $classData = [
  331. 'sys_rq' => $currentTime,
  332. 'jtbh' => $param['sczl_jtbh'], // 直接保留含#的原始值
  333. 'gdbh' => $param['sczl_gdbh'],
  334. 'gxmc' => $param['sczl_gxmc'],
  335. 'sys_id' => $param['sys_id'],
  336. 'sczl_rq' => $param['sczl_rq'],
  337. 'sczl_bzdh' => $param['sczl_bzdh'],
  338. ];
  339. // 处理动态字段(1-30组bh/rate)
  340. $dynamicFields = [];
  341. for ($i = 1; $i <= 30; $i++) {
  342. $dynamicFields['bh' . $i] = isset($param['bh' . $i]) ? $param['bh' . $i] : '';
  343. $dynamicFields['rate' . $i] = isset($param['rate' . $i]) ? $param['rate' . $i] : '';
  344. }
  345. $classData = array_merge($classData, $dynamicFields);
  346. // 5. 保存班组数据(框架会自动处理特殊字符转义,避免SQL注入)
  347. $classId = Db::name($tableClass)->insertGetId($classData);
  348. if (empty($classId)) {
  349. throw new \Exception("{$tableClass}数据保存失败");
  350. }
  351. // 6. 构建设备数据(适配PHP7.2)
  352. $filteredParam = array_filter($param, function ($key) {
  353. return !preg_match('/^(bh|rate)\d+$/', $key);
  354. }, ARRAY_FILTER_USE_KEY);
  355. $deviceData = array_merge([
  356. 'role' => $classId,
  357. 'sys_rq' => $currentTime,
  358. ], $filteredParam);
  359. // 7. 保存设备数据(含#字符的字段会被自动转义,安全插入)
  360. $sql = Db::name($tableDevice)->fetchSql(true)->insert($deviceData);
  361. $saveResult = db()->query($sql);
  362. if ($saveResult !== false) {
  363. $this->success('报工提交成功');
  364. }else{
  365. $this->error('报工提交失败');
  366. }
  367. }
  368. /**
  369. * 糊盒机台报工数据菜单
  370. * @return void
  371. * @throws \think\db\exception\DataNotFoundException
  372. * @throws \think\db\exception\ModelNotFoundException
  373. * @throws \think\exception\DbException
  374. */
  375. public function getTab()
  376. {
  377. if ($this->request->isGet() === false){
  378. $this->error('请求错误');
  379. }
  380. $data = [];
  381. $date = date('Y-m-d 00:00:00',time()-3888000);
  382. $sist = ['印后糊盒车间','精品自动化车间','精品手工车间','数字化车间'];
  383. $department = \db('设备_基本资料')
  384. ->distinct(true)
  385. ->where('使用部门','in',$sist)
  386. ->where('设备编组','<>','')
  387. ->order('设备编组')
  388. ->column('rtrim(使用部门) as 使用部门');
  389. if (empty($department)){
  390. $this->success('未获取到机台数据');
  391. }
  392. $list = \db('设备_糊盒报工资料')
  393. ->field([
  394. 'DISTINCT(sczl_rq)' => '时间',
  395. 'rtrim(sczl_jtbh)' => '机台编号'
  396. ])
  397. ->where('sczl_rq','>',$date)
  398. ->order('sczl_rq desc')
  399. ->select();
  400. foreach ($department as $value){
  401. $machine = \db('设备_基本资料')
  402. ->where('使用部门',$value)
  403. ->field('rtrim(设备编号) as 设备编号,rtrim(设备名称) as 设备名称')
  404. ->order('设备编号')
  405. ->select();
  406. foreach ($machine as $k=>$v){
  407. $data[rtrim($value)][$v['设备编号'].'-->'.$v['设备名称']] = [];
  408. foreach ($list as $kk=>$vv){
  409. if ($v['设备编号'] === $vv['机台编号']){
  410. array_push($data[rtrim($value)][$v['设备编号'].'-->'.$v['设备名称']],date('Y-m-d',strtotime($vv['时间'])));
  411. }
  412. }
  413. }
  414. }
  415. $this->success('成功',$data);
  416. }
  417. /**
  418. * 获取当前生产工单
  419. * @return void
  420. * @throws \think\db\exception\DataNotFoundException
  421. * @throws \think\db\exception\ModelNotFoundException
  422. * @throws \think\exception\DbException
  423. */
  424. public function GetProduction()
  425. {
  426. if (Request::instance()->isGet() == false) {
  427. $this->error('非法请求');
  428. }
  429. $params = Request::instance()->param();
  430. if (!isset($params['machine']) || empty($params['machine'])) {
  431. $this->error('参数错误');
  432. }
  433. $machine = $params['machine'];
  434. $machineCode = \db('dic_lzde')->where('适用机型',$machine)->value('sys_bh');
  435. $data = \db('设备_糊盒报工采集')->where('sczl_jtbh',$machine)->order('UID desc')->find();
  436. if (empty($data)){
  437. $this->success('未找到数据');
  438. }
  439. $list = [];
  440. $list['班组ID'] = $data['班组ID'];
  441. $row = [];
  442. if (!empty($data['sczl_gdbh'])){
  443. $endTime = \db('工单_工艺资料')
  444. ->where('Gy0_gdbh',$data['sczl_gdbh'])
  445. ->where('Gy0_yjno',$data['sczl_yjno'])
  446. ->where('Gy0_gxh',$data['sczl_gxh'])
  447. ->find();
  448. $list['工单编号'] = $data['sczl_gdbh'];
  449. if (!empty($endTime)){
  450. $list['印件号'] = $data['sczl_yjno'];
  451. $name = \db('工单_基本资料')->where('Gd_Gdbh',$data['sczl_gdbh'])->value('成品名称');
  452. $code = \db('工单_基本资料')->where('Gd_Gdbh',$data['sczl_gdbh'])->value('成品代号');
  453. $list['产品名称'] = rtrim($name);
  454. $list['产品代号'] = rtrim($code);
  455. $list['工序名称'] = $data['sczl_gxmc'];
  456. $list['联数'] = $endTime['Gy0_ls'];
  457. }
  458. $list['状态'] = rtrim($data['status']);
  459. $list['开工时间'] = $data['sczl_kgsj'];
  460. }else{
  461. $list['工单编号'] = '';
  462. $list['印件号'] = 0;
  463. $list['产品名称'] = '';
  464. $list['工序名称'] = '';
  465. $list['产品代号'] = '';
  466. $list['状态'] = '';
  467. $list['开工时间'] = '';
  468. $list['联数'] = '';
  469. }
  470. $list['班组编号'] = rtrim($data['sczl_bzbh']);
  471. $idList = explode(',',$data['班组ID']);
  472. foreach ($idList as $k=>$v){
  473. $class = \db('设备_糊盒班组资料')
  474. ->where('id',$v)
  475. ->field("role,rate,bh1,bh2,bh3,bh4,bh5,bh6,bh7,bh8,bh9,bh10,bh11,bh12,bh13,bh14,bh15")
  476. ->find();
  477. if (!empty($class)){
  478. for ($i=1;$i<16;$i++) {
  479. if ($class['bh' . $i] != '' && $class['bh' . $i] != '000000') {
  480. $name = \db('人事_基本资料')->where('员工编号', $class['bh' . $i])->field('rtrim(员工姓名) as 姓名')->find();
  481. $row[] = [
  482. '编号' => $class['bh' . $i],
  483. '姓名' => $name['姓名'],
  484. '比例' => $class['rate'],
  485. '角色' => $class['role'],
  486. ];
  487. }
  488. }
  489. $row = array_values($row);
  490. }
  491. }
  492. $list['班组成员'] = $row;
  493. $list['定额代号'] = $machineCode;
  494. $this->success('成功',$list);
  495. }
  496. /**
  497. * 设置当前工单和当前班组
  498. * @return void
  499. */
  500. public function setMachineTeam()
  501. {
  502. if (Request::instance()->isPost() == false) {
  503. $this->error('非法请求');
  504. }
  505. $params = Request::instance()->post();
  506. if (!isset($params['machine']) || empty($params['machine'] )) {
  507. $this->error('参数不能为空');
  508. }
  509. if (empty($params['team_id']) || empty($params['sczl_bzdh'])){
  510. $this->error('请先选择班组成员');
  511. }
  512. $machine = $params['machine'] . '#';
  513. $data = [];
  514. $data['status'] = $params['status'];
  515. $data['sczl_sj'] = date('Y-m-d H:i:s');
  516. $data['sczl_jtbh'] = $machine;
  517. $data['sczl_gdbh'] = empty($params['order']) ? '':$params['order'];
  518. $data['sczl_yjno'] = empty($params['yjno']) ? '':$params['yjno'];
  519. $data['sczl_gxh'] = empty($params['gy_name']) ? '' : (int)substr($params['gy_name'], 0, 2);
  520. $data['sczl_gxmc'] = empty($params['gy_name']) ? '' : $params['gy_name'];
  521. $data['sczl_bzbh'] = $params['sczl_bzdh'];
  522. $data['班组ID'] = $params['team_id'];
  523. // 获取当前时间
  524. $current_time = time();
  525. // 设置时间范围
  526. $start_time1 = strtotime(date('Y-m-d') . ' 08:30:00');
  527. $end_time1 = strtotime(date('Y-m-d') . ' 20:30:00');
  528. $end_time2 = strtotime(date('Y-m-d') . ' 24:00:00');
  529. $start_time3 = strtotime(date('Y-m-d', strtotime('+1 day')) . ' 08:30:00');
  530. $start_time4 = strtotime(date('Y-m-d', strtotime('+1 day')) . ' 00:00:00');
  531. // 判断当前时间属于哪个时间范围
  532. if ($current_time >= $start_time1 && $current_time <= $end_time1) {
  533. $data['sczl_kgsj'] = date('Y-m-d') . ' 08:30:00';
  534. } elseif ($current_time > $end_time1 && $current_time <= $end_time2) {
  535. $data['sczl_kgsj'] = date('Y-m-d') . ' 20:30:00';
  536. } elseif ($current_time > $end_time1 && $current_time <= $start_time3) {
  537. $data['sczl_kgsj'] = date('Y-m-d', strtotime('+1 day')) . ' 08:30:00';
  538. }elseif ($current_time > $start_time4 && $current_time <= $start_time3){
  539. $data['sczl_kgsj'] = date('Y-m-d') . ' 20:30:00';
  540. }
  541. if (!empty($params['order']) && !empty($params['yjno'])){
  542. $option['Gy0_gdbh'] = $params['order'];
  543. $option['Gy0_yjno'] = $params['yjno'];
  544. $option['Gy0_gxh'] = $data['sczl_gxh'];
  545. $data['任务ID'] = \db('工单_工艺资料')->where($option)->value('UniqId');
  546. }else{
  547. $data['任务ID'] = '';
  548. }
  549. $sql = \db('设备_糊盒报工采集')->fetchSql(true)->insert($data);
  550. $res = Db::query($sql);
  551. if ($res === false) {
  552. $this->error('设置失败');
  553. } else {
  554. $this->success('设置成功');
  555. }
  556. }
  557. /**
  558. * 糊盒设备运行跟踪数据页面显示
  559. * @return void
  560. * @throws \think\db\exception\DataNotFoundException
  561. * @throws \think\db\exception\ModelNotFoundException
  562. * @throws \think\exception\DbException
  563. */
  564. public function getGluingReportDataList()
  565. {
  566. if ($this->request->isGet() === false){
  567. $this->error('请求错误');
  568. }
  569. $params = $this->request->param();
  570. if (empty($params['machine']) || empty($params['day'])){
  571. $this->error('参数错误');
  572. }
  573. $where = [
  574. 'a.sczl_jtbh' => $params['machine'],
  575. 'a.sczl_rq' => ['like',$params['day'].'%']
  576. ];
  577. $field = ['a.sczl_gdbh as 工单编号','a.sczl_gxmc as 工序名称','a.来料数量','a.sczl_cl as 产量',
  578. 'a.sczl_zcfp as 制程废品','a.startTime as 开始时间','a.endTime as 结束时间','a.sczl_ls as 联数','a.sczl_rq as 日期',
  579. 'a.sczl_dedh as 定额代号','a.工价系数','a.保养工时','a.装版工时','a.异常工时','a.异常类型','a.设备运行工时','a.role',
  580. 'a.sys_id as 创建人员','a.sys_rq as 上报时间','a.mod_rq as 修改时间','a.Uid','a.sczl_jtbh as 机台编号','a.price',
  581. 'b.Gd_cpdh as 产品代号','b.Gd_cpmc as 产品名称','a.sczl_bzdh as 班组','a.来料异常'];
  582. $list = \db('设备_糊盒报工资料')
  583. ->alias('a')
  584. ->join('工单_基本资料 b','a.sczl_gdbh = b.Gd_gdbh','left')
  585. ->field($field)
  586. ->where($where)
  587. ->group('a.Uid')
  588. ->select();
  589. if (empty($list)){
  590. $this->error('未找到报工数据');
  591. }
  592. foreach ($list as $key=>$value) {
  593. $list[$key]['class'] = [];
  594. $class = \db('糊盒报工班组')
  595. ->where('id', $value['role'])
  596. ->field("bh1,bh2,bh3,bh4,bh5,bh6,bh7,bh8,bh9,bh10,bh11,bh12,bh13,bh14,bh15,bh16,bh17,bh18,bh19,bh20,bh21,bh22,bh23,
  597. bh24,bh25,bh26,bh27,bh28,bh29,bh30,rate1,rate2,rate3,rate4,rate5,rate6,rate7,rate8,rate9,rate10,rate11,rate12,rate13,rate14,
  598. rate15,rate16,rate17,rate18,rate19,rate20,rate21,rate22,rate23,rate24,rate25,rate26,rate27,rate28,rate29,rate30")
  599. ->find();
  600. if (!empty($class)) {
  601. for ($i = 1; $i <=30; $i++) {
  602. if ($class['bh' . $i] != '' && $class['bh' . $i] != '000000') {
  603. $name = \db('人事_基本资料')->where('员工编号', $class['bh' . $i])->field('rtrim(员工姓名) as 姓名')->find();
  604. $list[$key]['class'][] = [
  605. '编号' => $class['bh' . $i],
  606. '姓名' => $name['姓名'],
  607. '比例' => $class['rate'.$i],
  608. ];
  609. }
  610. }
  611. $list[$key]['class'] = array_values($list[$key]['class']);
  612. }
  613. }
  614. $this->success('成功',$list);
  615. }
  616. /**
  617. * 报工数据详情显示
  618. * @return void
  619. * @throws \think\db\exception\DataNotFoundException
  620. * @throws \think\db\exception\ModelNotFoundException
  621. * @throws \think\exception\DbException
  622. */
  623. public function getGluingReportDataDetail()
  624. {
  625. if ($this->request->isGet() === false){
  626. $this->error('请求错误');
  627. }
  628. $params = $this->request->param();
  629. if(!isset($params['id']) || empty($params['id'])){
  630. $this->error('参数错误');
  631. }
  632. $where = ['Uid'=>$params['id']];
  633. $field = ['a.sczl_gdbh as 工单编号','a.sczl_gxmc as 工序名称','a.来料数量','a.sczl_cl as 产量',
  634. 'a.sczl_zcfp as 制程废品','a.startTime as 开始时间','a.endTime as 结束时间','a.sczl_ls as 联数','a.sczl_rq as 日期',
  635. 'a.sczl_dedh as 定额代号','a.工价系数','a.保养工时','a.装版工时','a.异常工时','a.异常类型','a.设备运行工时','a.role',
  636. 'a.sys_id as 创建人员','a.sys_rq as 上报时间','a.mod_rq as 修改时间','a.Uid','a.sczl_jtbh as 机台编号','a.price',
  637. 'b.Gd_cpdh as 产品代号','b.Gd_cpmc as 产品名称','a.sczl_bzdh as 班组','a.来料异常'];
  638. $list = \db('设备_糊盒报工资料')
  639. ->alias('a')
  640. ->join('工单_基本资料 b','a.sczl_gdbh = b.Gd_gdbh','left')
  641. ->where($where)
  642. ->field($field)
  643. ->find();
  644. $list['class'] = [];
  645. $class = \db('糊盒报工班组')
  646. ->where('id', $list['role'])
  647. ->field("bh1,bh2,bh3,bh4,bh5,bh6,bh7,bh8,bh9,bh10,bh11,bh12,bh13,bh14,bh15,bh16,bh17,bh18,bh19,bh20,bh21,bh22,bh23,
  648. bh24,bh25,bh26,bh27,bh28,bh29,bh30,rate1,rate2,rate3,rate4,rate5,rate6,rate7,rate8,rate9,rate10,rate11,rate12,rate13,rate14,
  649. rate15,rate16,rate17,rate18,rate19,rate20,rate21,rate22,rate23,rate24,rate25,rate26,rate27,rate28,rate29,rate30")
  650. ->find();
  651. if (!empty($class)) {
  652. for ($i = 1; $i <=30; $i++) {
  653. if ($class['bh' . $i] != '' && $class['bh' . $i] != '000000') {
  654. $name = \db('人事_基本资料')->where('员工编号', $class['bh' . $i])->field('rtrim(员工姓名) as 姓名')->find();
  655. $list['class'][] = [
  656. '编号' => $class['bh' . $i],
  657. '姓名' => $name['姓名'],
  658. '比例' => $class['rate'.$i],
  659. ];
  660. }
  661. }
  662. $list['class'] = array_values($list['class']);
  663. }
  664. $this->success('成功',$list);
  665. }
  666. /**
  667. * 修改糊盒班组报工资料
  668. * @return void
  669. * @throws \think\Exception
  670. * @throws \think\db\exception\BindParamException
  671. * @throws \think\exception\PDOException
  672. */
  673. public function getGluingReportDetailUpdate()
  674. {
  675. if ($this->request->isPost() === false){
  676. $this->error('请求错误');
  677. }
  678. $param = Request::instance()->post();
  679. if(!isset($param['id']) || empty($param['id'])){
  680. $this->error('参数错误');
  681. }
  682. $id = $param['id'];
  683. $role = $param['role'];
  684. unset($param['id']);
  685. // 核心修复:验证规则调整,明确允许#字符,兼容特殊字符
  686. $validate = new \think\Validate([
  687. 'sczl_jtbh' => 'require|regex:/^[\w#\x{4e00}-\x{9fa5}]+$/u', // 允许字母、数字、下划线、#、中文
  688. 'sczl_gdbh' => 'require',
  689. 'sczl_gxmc' => 'require',
  690. 'sczl_rq' => 'require|dateFormat:Y-m-d H:i:s',
  691. ], [
  692. 'sczl_jtbh.require' => '机组编号不能为空',
  693. 'sczl_jtbh.regex' => '机组编号仅支持字母、数字、下划线、#号和中文',
  694. 'sczl_gdbh.require' => '工单号不能为空',
  695. 'sczl_gxmc.require' => '工序名称不能为空',
  696. 'sczl_rq.require' => '报工日期不能为空',
  697. 'sczl_rq.dateFormat' => '报工日期格式错误(需为Y-m-d H:i:s)',
  698. ]);
  699. // 验证前处理:仅去除前后空格(不影响#字符)
  700. foreach (['sczl_jtbh', 'sczl_gdbh', 'sczl_gxmc', 'sczl_rq'] as $field) {
  701. if (isset($param[$field]) && is_string($param[$field])) {
  702. $param[$field] = trim($param[$field]); // 只去空格,保留#等特殊字符
  703. }
  704. }
  705. // 执行验证
  706. if (!$validate->check($param)) {
  707. $this->error($validate->getError());
  708. }
  709. // 3. 事务处理(确保数据一致性)
  710. $currentTime = date('Y-m-d H:i:s');
  711. $tableClass = '糊盒报工班组';
  712. $tableDevice = '设备_糊盒报工资料';
  713. // 4. 构建班组数据(保留#字符,无需额外处理)
  714. $classData = [
  715. 'jtbh' => $param['sczl_jtbh'], // 直接保留含#的原始值
  716. 'gdbh' => $param['sczl_gdbh'],
  717. 'gxmc' => $param['sczl_gxmc'],
  718. 'sczl_rq' => $param['sczl_rq'],
  719. 'sczl_bzdh' => $param['sczl_bzdh'],
  720. ];
  721. // 处理动态字段(1-30组bh/rate)
  722. $dynamicFields = [];
  723. for ($i = 1; $i <= 30; $i++) {
  724. $dynamicFields['bh' . $i] = isset($param['bh' . $i]) ? $param['bh' . $i] : '';
  725. $dynamicFields['rate' . $i] = isset($param['rate' . $i]) ? $param['rate' . $i] : '';
  726. }
  727. $classData = array_merge($classData, $dynamicFields);
  728. // 5. 保存班组数据(框架会自动处理特殊字符转义,避免SQL注入)
  729. $classId = Db::name($tableClass)->where('id',$role)->update($classData);
  730. // 6. 构建设备数据(适配PHP7.2)
  731. $filteredParam = array_filter($param, function ($key) {
  732. return !preg_match('/^(bh|rate)\d+$/', $key);
  733. }, ARRAY_FILTER_USE_KEY);
  734. $deviceData = array_merge([
  735. 'mod_rq' => $currentTime,
  736. ], $filteredParam);
  737. // 7. 保存设备数据(含#字符的字段会被自动转义,安全插入)
  738. $sql = Db::name($tableDevice)->where('Uid',$id)->fetchSql(true)->update($deviceData);
  739. $saveResult = db()->query($sql);
  740. if ($saveResult !== false) {
  741. $this->success('修改成功');
  742. }else{
  743. $this->error('修改失败');
  744. }
  745. }
  746. /**
  747. * 修改报工数据班组
  748. * @return void
  749. * @throws \think\Exception
  750. * @throws \think\exception\PDOException
  751. */
  752. public function UpdateGluingReportClass()
  753. {
  754. if ($this->request->isPost() === false){
  755. $this->error('请求错误');
  756. }
  757. $params = Request::instance()->post();
  758. if(!isset($params['id']) || empty($params['id'])){
  759. $this->error('参数错误');
  760. }
  761. $id = $params['id'];
  762. $data['role'] = $params['role'];
  763. $res = \db('设备_糊盒报工资料')->where('Uid',$id)->update($data);
  764. if ($res === false) {
  765. $this->error('修改失败');
  766. }else{
  767. $this->success('修改成功');
  768. }
  769. }
  770. /**
  771. * 当班产量
  772. * @return void
  773. * @throws \think\db\exception\DataNotFoundException
  774. * @throws \think\db\exception\ModelNotFoundException
  775. * @throws \think\exception\DbException
  776. */
  777. public function GluingReportList()
  778. {
  779. if ($this->request->isGet() === false){
  780. $this->error('请求错误');
  781. }
  782. $params = $this->request->param();
  783. if (!isset($params['machine']) || empty($params['machine'])){
  784. $this->error('参数错误');
  785. }
  786. $machine = $params['machine'];
  787. $sczlTime = date('Y-m-d H:i:s',time());
  788. if ($sczlTime>date('Y-m-d 00:00:00') && $sczlTime<date('Y-m-d 08:30:00')){
  789. $time = date('Y-m-d 00:00:00',time()-86400);
  790. }else{
  791. $time = date('Y-m-d 00:00:00');
  792. }
  793. $where = [
  794. 'sczl_jtbh' => $machine,
  795. 'sczl_rq' => $time,
  796. ];
  797. $field = 'rtrim(sczl_gdbh) as 工单编号,rtrim(sczl_yjno) as yjno,rtrim(sczl_dedh) as dedh,rtrim(sczl_gxmc) as gxmc,
  798. rtrim(sczl_cl) as 产量,rtrim(sczl_zcfp) as 制程废品,rtrim(装版工时) as 装版工时,rtrim(保养工时) as 保养工时,
  799. rtrim(异常工时) as 异常工时,rtrim(设备运行工时) as 通电工时,startTime,endTime,Uid,rtrim(sczl_ls) as ls,来料数量,来料异常';
  800. $list = \db('设备_糊盒报工资料')->where($where)->field($field)->order('Uid desc')->select();
  801. if (!empty($list)){
  802. foreach ($list as $k=>$v){
  803. $name = \db('工单_印件资料')->where('Yj_Gdbh',$v['工单编号'])->where('yj_Yjno',$v['yjno'])->field('rtrim(yj_yjmc) as cpmc')->find();
  804. if ($v['yjno']<10){
  805. $list[$k]['yjno'] = '0'.$v['yjno'];
  806. }
  807. $list[$k]['印件及工序'] = $list[$k]['yjno'].'-'.$v['gxmc'];
  808. $list[$k]['生产时间段'] = substr($v['startTime'],5,5).' '.substr($v['startTime'],11,5).'<-->'.substr($v['endTime'],5,5).' '.substr($v['endTime'],11,5);
  809. $list[$k]['产品名称'] = $name['cpmc'];
  810. }
  811. }
  812. $this->success('成功',$list);
  813. }
  814. /**
  815. * 工单查询
  816. * @return void
  817. * @throws \think\db\exception\DataNotFoundException
  818. * @throws \think\db\exception\ModelNotFoundException
  819. * @throws \think\exception\DbException
  820. */
  821. public function getWorkOrderList()
  822. {
  823. if ($this->request->isGet() === false){
  824. $this->error('请求错误');
  825. }
  826. $params = $this->request->param();
  827. if (!isset($params['search']) || empty($params['search'])){
  828. $this->error('参数错误');
  829. }
  830. $search = $params['search'];
  831. $list = \db('工单_基本资料')
  832. ->where('Gd_gdbh|Gd_cpmc','like','%'.$search.'%')
  833. ->field('Gd_gdbh as 工单编号,Gd_cpdh as 产品代号,Gd_cpmc as 产品名称')
  834. ->order('Gd_gdbh desc')
  835. ->select();
  836. if (empty($list)){
  837. $this->error('未找到数据');
  838. }else{
  839. $this->success('成功',$list);
  840. }
  841. }
  842. /**
  843. * 查询机台编号
  844. * @return void
  845. */
  846. public function getMachineList()
  847. {
  848. if ($this->request->isGet() === false){
  849. $this->error('请求错误');
  850. }
  851. $params = $this->request->param();
  852. if (!isset($params['search']) || empty($params['search'])){
  853. $this->error('参数错误');
  854. }
  855. $search = $params['search'];
  856. $list = \db('设备_基本资料')
  857. ->where('使用部门',$search)
  858. ->order('设备编号')
  859. ->column('设备名称','设备编号');
  860. if (empty($list)){
  861. $this->error('未找到数据');
  862. }else{
  863. $this->success('成功',$list);
  864. }
  865. }
  866. /**
  867. * 查询工艺名称
  868. * @return void
  869. * @throws \think\db\exception\DataNotFoundException
  870. * @throws \think\db\exception\ModelNotFoundException
  871. * @throws \think\exception\DbException
  872. */
  873. public function gitProcessList()
  874. {
  875. if ($this->request->isGet() === false){
  876. $this->error('请求错误');
  877. }
  878. $params = $this->request->param();
  879. if (!isset($params['search']) || empty($params['search'])){
  880. $this->error('参数错误');
  881. }
  882. $search = $params['search'];
  883. $list = \db('erp_常用字典')
  884. ->where('分类','糊盒工艺')
  885. ->where('名称','like','%'.$search.'%')
  886. ->field('名称')
  887. ->select();
  888. $data = [];
  889. if (empty($list)){
  890. $this->error('未找到工艺数据');
  891. }
  892. foreach ($list as $k=>$v){
  893. $name = explode('_',$v['名称']);
  894. $data[] = $name[2];
  895. }
  896. $this->success('成功',$data);
  897. }
  898. //最新糊盒班组查询
  899. public function classifyList()
  900. {
  901. // 1. 请求方法验证
  902. if (!$this->request->isGet()) {
  903. $this->error('请使用GET请求');
  904. }
  905. // 2. 参数验证
  906. $params = $this->request->param();
  907. // 验证必需参数
  908. $requiredParams = ['sczl_jtbh', 'sczl_bzdh'];
  909. foreach ($requiredParams as $param) {
  910. if (empty($params[$param] ?? null)) {
  911. $this->error("缺少必要参数: {$param}");
  912. }
  913. }
  914. $jtbh = trim($params['sczl_jtbh']);
  915. $bzdh = trim($params['sczl_bzdh']);
  916. // 3. 查询糊盒报工资料
  917. $role = \db('设备_糊盒报工资料')
  918. ->where('sczl_jtbh', $jtbh)
  919. ->where('sczl_bzdh', $bzdh)
  920. ->order('Uid', 'desc')
  921. ->value('role');
  922. if (empty($role)) {
  923. $this->error('未找到对应的报工班组信息');
  924. }
  925. // 4. 动态生成字段列表
  926. $fields = [];
  927. for ($i = 1; $i <= 30; $i++) {
  928. $fields[] = "bh{$i}";
  929. $fields[] = "rate{$i}";
  930. }
  931. // 5. 查询班组信息
  932. $class = \db('糊盒报工班组')
  933. ->where('id', $role)
  934. ->field($fields)
  935. ->find();
  936. if (empty($class)) {
  937. $this->error('班组信息不存在');
  938. }
  939. // 6. 处理班组成员信息
  940. $members = [];
  941. $employeeIds = [];
  942. // 收集所有有效的员工编号
  943. for ($i = 1; $i <= 30; $i++) {
  944. $bh = $class["bh{$i}"] ?? '';
  945. $rate = $class["rate{$i}"] ?? 0;
  946. // 验证员工编号是否有效
  947. $bh = trim($bh);
  948. if (!empty($bh) && $bh !== '000000') {
  949. $employeeIds[$bh] = [
  950. 'index' => $i,
  951. 'rate' => $rate
  952. ];
  953. }
  954. }
  955. // 如果有有效的员工编号,批量查询员工信息
  956. if (!empty($employeeIds)) {
  957. $employeeNames = [];
  958. $ids = array_keys($employeeIds);
  959. // 批量查询员工信息(减少数据库查询次数)
  960. $result = \db('人事_基本资料')
  961. ->whereIn('员工编号', $ids)
  962. ->field('员工编号, rtrim(员工姓名) as 姓名')
  963. ->select();
  964. foreach ($result as $item) {
  965. $employeeNames[$item['员工编号']] = $item['姓名'];
  966. }
  967. // 组装返回数据
  968. foreach ($employeeIds as $employeeId => $info) {
  969. $members[] = [
  970. '编号' => $employeeId,
  971. '姓名' => $employeeNames[$employeeId] ?? '未知',
  972. '比例' => $info['rate']
  973. ];
  974. }
  975. }
  976. $this->success('获取成功', array_values($members));
  977. }
  978. /**
  979. * 判断报工单价是否为空
  980. * @param mixed $price
  981. * @return bool
  982. */
  983. protected function isEmptyReportPrice($price)
  984. {
  985. return $price === null || $price === '';
  986. }
  987. /**
  988. * 报工时自动解析单价
  989. * @param array $param
  990. * @return float|null
  991. */
  992. protected function resolveReportPrice(array $param)
  993. {
  994. $machine = trim($param['sczl_jtbh']);
  995. $gxmc = trim($param['sczl_gxmc']);
  996. $count = $this->extractManualProcessCountSilent($param);
  997. $machinePrices = $this->collectMachinePriceValues($machine);
  998. if (!empty($machinePrices)) {
  999. return (float)$machinePrices[0];
  1000. }
  1001. $manualPrice = $this->resolveManualProcessPriceSilent($gxmc, $count);
  1002. if ($manualPrice !== null) {
  1003. return $manualPrice;
  1004. }
  1005. $aiService = new Aicompute();
  1006. $rates = $aiService->fetchWorkshopRatesByMachine($machine);
  1007. if (empty($rates)) {
  1008. return null;
  1009. }
  1010. $productName = db('工单_基本资料')
  1011. ->where('Gd_gdbh', trim($param['sczl_gdbh']))
  1012. ->value('Gd_cpmc');
  1013. $productName = $productName ? trim($productName) : '';
  1014. if ($productName !== '') {
  1015. $matched = $aiService->matchWorkshopRateByProductName($rates, $productName);
  1016. if (!empty($matched)) {
  1017. return (float)$matched['piece_price'];
  1018. }
  1019. }
  1020. $aiPrice = $aiService->resolvePiecePriceByAi(trim($param['sczl_gdbh']), $machine);
  1021. if ($aiPrice !== null) {
  1022. return $aiPrice;
  1023. }
  1024. return (float)$rates[0]['piece_price'];
  1025. }
  1026. /**
  1027. * 收集机台单价列表
  1028. * @param string $machine
  1029. * @return array
  1030. */
  1031. protected function collectMachinePriceValues($machine)
  1032. {
  1033. $list = db('machine_price')
  1034. ->where('machine_id', $machine)
  1035. ->field('price1,price2,price3,price4,price5,price6,price7,price8,price9,price10')
  1036. ->select();
  1037. $result = [];
  1038. foreach ($list as $item) {
  1039. foreach ($item as $value) {
  1040. if ($value !== '' && $value !== null) {
  1041. $result[] = $value;
  1042. }
  1043. }
  1044. }
  1045. return $result;
  1046. }
  1047. /**
  1048. * 静默解析手工工序单价(报工场景,不中断请求)
  1049. * @param string $gxmc
  1050. * @param int|null $count
  1051. * @return float|null
  1052. */
  1053. protected function resolveManualProcessPriceSilent($gxmc, $count)
  1054. {
  1055. if (strpos($gxmc, '割围条') !== false) {
  1056. $row = db('machine_price')->where('machine_id', '手工割围条')->find();
  1057. return $row ? (float)$row['price1'] : null;
  1058. }
  1059. if (strpos($gxmc, '打孔') !== false) {
  1060. if ($count === null) {
  1061. return null;
  1062. }
  1063. return $this->resolvePunchHolePrice($count);
  1064. }
  1065. if (strpos($gxmc, '拆片') !== false) {
  1066. $rows = db('machine_price')->where('machine_id', '手工拆片')->select();
  1067. if (empty($rows)) {
  1068. return null;
  1069. }
  1070. return $this->resolveManualStripPriceSilent($rows, $gxmc, $count);
  1071. }
  1072. if (strpos($gxmc, '贴磁铁') !== false) {
  1073. return $this->resolveManualCountPriceFromDb('手工贴磁铁', $count, false);
  1074. }
  1075. if (strpos($gxmc, '贴片') !== false) {
  1076. return $this->resolveManualCountPriceFromDb('手工贴片', $count, false);
  1077. }
  1078. $row = db('machine_price')
  1079. ->where('machine_id', $gxmc)
  1080. ->whereOr('machine_name', 'like', '%' . $gxmc . '%')
  1081. ->find();
  1082. return $row ? (float)$row['price1'] : null;
  1083. }
  1084. /**
  1085. * 静默提取孔数/拼数
  1086. * @param array $params
  1087. * @return int|null
  1088. */
  1089. protected function extractManualProcessCountSilent(array $params)
  1090. {
  1091. if (!isset($params['count']) || $params['count'] === '') {
  1092. return null;
  1093. }
  1094. if (!is_numeric($params['count']) || (int)$params['count'] != $params['count'] || (int)$params['count'] <= 0) {
  1095. return null;
  1096. }
  1097. return (int)$params['count'];
  1098. }
  1099. /**
  1100. * 静默解析手工拆片单价
  1101. * @param array $rows
  1102. * @param string $gxmc
  1103. * @param int|null $count
  1104. * @return float|null
  1105. */
  1106. protected function resolveManualStripPriceSilent(array $rows, $gxmc, $count)
  1107. {
  1108. $gxmc = trim($gxmc);
  1109. if ($gxmc === '手工拆片' || $gxmc === '拆片') {
  1110. if ($count === null) {
  1111. return null;
  1112. }
  1113. return $this->resolveDefaultStripPriceByCount($count);
  1114. }
  1115. if ($gxmc !== '') {
  1116. $row = $this->matchManualPriceRow($rows, $gxmc);
  1117. if (empty($row)) {
  1118. return null;
  1119. }
  1120. return $this->calculateStripPriceByRowSilent($row, $count);
  1121. }
  1122. if ($count === null) {
  1123. return null;
  1124. }
  1125. return $this->resolveDefaultStripPriceByCount($count);
  1126. }
  1127. /**
  1128. * 静默计算拆片规格单价
  1129. * @param array $row
  1130. * @param int|null $count
  1131. * @return float|null
  1132. */
  1133. protected function calculateStripPriceByRowSilent(array $row, $count)
  1134. {
  1135. $name = $row['machine_name'];
  1136. $basePrice = (float)$row['price1'];
  1137. if (strpos($name, '1-4拼(特种纸') !== false) {
  1138. if ($count === null) {
  1139. return null;
  1140. }
  1141. if ($count <= 4) {
  1142. return $basePrice;
  1143. }
  1144. return floatval(number_format($basePrice + ($count - 4) * 0.001, 4, '.', ''));
  1145. }
  1146. if (strpos($name, '1-4拼(小盒二次拆片') !== false) {
  1147. if ($count === null) {
  1148. return null;
  1149. }
  1150. if ($count === 8) {
  1151. return 0.01;
  1152. }
  1153. if ($count === 10) {
  1154. return 0.012;
  1155. }
  1156. return $basePrice;
  1157. }
  1158. if (strpos($name, '5-6拼(小盒二次拆片') !== false) {
  1159. return $basePrice;
  1160. }
  1161. if (strpos($name, '6拼及以上') !== false) {
  1162. return $basePrice;
  1163. }
  1164. if (preg_match('/^(\d+)拼/u', $name) && $count === null) {
  1165. return null;
  1166. }
  1167. return $basePrice;
  1168. }
  1169. /**
  1170. * 获取机台报工单价数据
  1171. * 参数:machine(机台编号)、gxmc(工序名称)、count(孔数/拼数,纯数字)
  1172. * 优先按机台编号查询;查不到则按手工工序(gxmc + count)匹配单价
  1173. * @return void
  1174. * @throws \think\db\exception\DataNotFoundException
  1175. * @throws \think\db\exception\ModelNotFoundException
  1176. * @throws \think\exception\DbException
  1177. */
  1178. public function getMachinePriceData()
  1179. {
  1180. if ($this->request->isGet() === false) {
  1181. $this->error('请求错误');
  1182. }
  1183. $params = $this->request->param();
  1184. if (!isset($params['machine']) || $params['machine'] === '') {
  1185. $this->error('参数错误');
  1186. }
  1187. $machine = trim($params['machine']);
  1188. // 1. 优先按机台编号查询
  1189. $list = db('machine_price')
  1190. ->where('machine_id', $machine)
  1191. ->field('price1,price2,price3,price4,price5,price6,price7,price8,price9,price10')
  1192. ->select();
  1193. $result = [];
  1194. foreach ($list as $item) {
  1195. foreach ($item as $value) {
  1196. if ($value !== '' && $value !== null) {
  1197. $result[] = $value;
  1198. }
  1199. }
  1200. }
  1201. if (!empty($result)) {
  1202. $this->success('获取成功', $result);
  1203. }
  1204. // 2. 机台编号查不到,按手工工序查询
  1205. $gxmc = trim((string)($params['gxmc'] ?? ''));
  1206. if ($gxmc === '') {
  1207. $this->error('未找到机台单价,请传入工序名称');
  1208. }
  1209. $price = $this->resolveManualProcessPriceByGxmc($gxmc, $params);
  1210. if ($price === null) {
  1211. $this->error('未找到匹配的单价');
  1212. }
  1213. $this->success('获取成功', [$price]);
  1214. }
  1215. /**
  1216. * 按工序名称解析手工工序单价
  1217. * @param string $gxmc 工序名称
  1218. * @param array $params count=孔数/拼数(纯数字)
  1219. * @return float|null
  1220. */
  1221. protected function resolveManualProcessPriceByGxmc($gxmc, array $params)
  1222. {
  1223. $count = $this->extractManualProcessCount($params);
  1224. if (strpos($gxmc, '割围条') !== false) {
  1225. $row = db('machine_price')->where('machine_id', '手工割围条')->find();
  1226. return $row ? (float)$row['price1'] : null;
  1227. }
  1228. if (strpos($gxmc, '打孔') !== false) {
  1229. if ($count === null) {
  1230. $this->error('请传入孔数(纯数字)');
  1231. }
  1232. return $this->resolvePunchHolePrice($count);
  1233. }
  1234. if (strpos($gxmc, '拆片') !== false) {
  1235. $rows = db('machine_price')->where('machine_id', '手工拆片')->select();
  1236. if (empty($rows)) {
  1237. return null;
  1238. }
  1239. return $this->resolveManualStripPrice($rows, $gxmc, $count);
  1240. }
  1241. if (strpos($gxmc, '贴磁铁') !== false) {
  1242. return $this->resolveManualCountPriceFromDb('手工贴磁铁', $count, true);
  1243. }
  1244. if (strpos($gxmc, '贴片') !== false) {
  1245. return $this->resolveManualCountPriceFromDb('手工贴片', $count, true);
  1246. }
  1247. // 其他手工工序:按 machine_id 或 machine_name 匹配
  1248. $row = db('machine_price')
  1249. ->where('machine_id', $gxmc)
  1250. ->whereOr('machine_name', 'like', '%' . $gxmc . '%')
  1251. ->find();
  1252. return $row ? (float)$row['price1'] : null;
  1253. }
  1254. /**
  1255. * 按拼数查询手工工序单价(machine_name 存拼数)
  1256. * @param string $machineId
  1257. * @param int|null $count
  1258. * @param bool $errorOnMissingCount
  1259. * @return float|null
  1260. */
  1261. protected function resolveManualCountPriceFromDb($machineId, $count, $errorOnMissingCount = false)
  1262. {
  1263. if ($count === null) {
  1264. if ($errorOnMissingCount) {
  1265. $this->error('请传入拼数(纯数字)');
  1266. }
  1267. return null;
  1268. }
  1269. $row = db('machine_price')
  1270. ->where('machine_id', $machineId)
  1271. ->where('machine_name', (string)$count)
  1272. ->find();
  1273. return $row ? (float)$row['price1'] : null;
  1274. }
  1275. /**
  1276. * 提取孔数/拼数(前端传入纯数字)
  1277. * @param array $params
  1278. * @return int|null
  1279. */
  1280. protected function extractManualProcessCount(array $params)
  1281. {
  1282. if (!isset($params['count']) || $params['count'] === '') {
  1283. return null;
  1284. }
  1285. if (!is_numeric($params['count']) || (int)$params['count'] != $params['count'] || (int)$params['count'] <= 0) {
  1286. $this->error('孔数/拼数必须为大于0的整数');
  1287. }
  1288. return (int)$params['count'];
  1289. }
  1290. /**
  1291. * 手工打孔单价(按孔数区间)
  1292. * @param int $holeCount
  1293. * @return float
  1294. */
  1295. protected function resolvePunchHolePrice($holeCount)
  1296. {
  1297. $holeCount = (int)$holeCount;
  1298. if ($holeCount === 1) {
  1299. return 0.0055;
  1300. }
  1301. if ($holeCount >= 2 && $holeCount <= 4) {
  1302. return 0.007;
  1303. }
  1304. if ($holeCount >= 5 && $holeCount <= 8) {
  1305. return 0.012;
  1306. }
  1307. if ($holeCount >= 9 && $holeCount <= 12) {
  1308. return 0.016;
  1309. }
  1310. if ($holeCount >= 13 && $holeCount <= 18) {
  1311. return 0.025;
  1312. }
  1313. return floatval(number_format(0.025 + ($holeCount - 18) * 0.001, 4, '.', ''));
  1314. }
  1315. /**
  1316. * 手工拆片单价(按规格名称 + 拼数)
  1317. * @param array $rows
  1318. * @param string $gxmc 工序规格名称(文字)
  1319. * @param int|null $count 拼数(纯数字)
  1320. * @return float|null
  1321. */
  1322. protected function resolveManualStripPrice(array $rows, $gxmc, $count)
  1323. {
  1324. $gxmc = trim($gxmc);
  1325. // 通用拆片工序,仅按拼数数字匹配默认单价
  1326. if ($gxmc === '手工拆片' || $gxmc === '拆片') {
  1327. if ($count === null) {
  1328. $this->error('请传入拼数(纯数字)');
  1329. }
  1330. return $this->resolveDefaultStripPriceByCount($count);
  1331. }
  1332. if ($gxmc !== '') {
  1333. $row = $this->matchManualPriceRow($rows, $gxmc);
  1334. if (empty($row)) {
  1335. return null;
  1336. }
  1337. return $this->calculateStripPriceByRow($row, $count);
  1338. }
  1339. if ($count === null) {
  1340. $this->error('请传入拼数(纯数字)');
  1341. }
  1342. return $this->resolveDefaultStripPriceByCount($count);
  1343. }
  1344. /**
  1345. * 默认拆片单价(1.0厚以上灰白板,按拼数数字匹配)
  1346. * @param int $count
  1347. * @return float
  1348. */
  1349. protected function resolveDefaultStripPriceByCount($count)
  1350. {
  1351. $prices = [
  1352. 1 => 0.008,
  1353. 2 => 0.01,
  1354. 3 => 0.013,
  1355. 4 => 0.017,
  1356. 5 => 0.022,
  1357. 6 => 0.028,
  1358. ];
  1359. $pieceCount = min((int)$count, 6);
  1360. return $prices[$pieceCount];
  1361. }
  1362. /**
  1363. * 按 machine_name 匹配手工单价行
  1364. * @param array $rows
  1365. * @param string $gxmc
  1366. * @return array|null
  1367. */
  1368. protected function matchManualPriceRow(array $rows, $gxmc)
  1369. {
  1370. $gxmc = trim($gxmc);
  1371. foreach ($rows as $row) {
  1372. if ($row['machine_name'] === $gxmc) {
  1373. return $row;
  1374. }
  1375. }
  1376. $best = null;
  1377. $bestLen = 0;
  1378. foreach ($rows as $row) {
  1379. $name = $row['machine_name'];
  1380. if (strpos($name, $gxmc) !== false || strpos($gxmc, $name) !== false) {
  1381. $len = mb_strlen($name);
  1382. if ($len > $bestLen) {
  1383. $best = $row;
  1384. $bestLen = $len;
  1385. }
  1386. }
  1387. }
  1388. return $best;
  1389. }
  1390. /**
  1391. * 根据拆片规格行及拼数计算单价
  1392. * @param array $row
  1393. * @param int|null $count 拼数(纯数字)
  1394. * @return float|null
  1395. */
  1396. protected function calculateStripPriceByRow(array $row, $count)
  1397. {
  1398. $name = $row['machine_name'];
  1399. $basePrice = (float)$row['price1'];
  1400. if (strpos($name, '1-4拼(特种纸') !== false) {
  1401. if ($count === null) {
  1402. $this->error('请传入拼数(纯数字)');
  1403. }
  1404. if ($count <= 4) {
  1405. return $basePrice;
  1406. }
  1407. return floatval(number_format($basePrice + ($count - 4) * 0.001, 4, '.', ''));
  1408. }
  1409. if (strpos($name, '1-4拼(小盒二次拆片') !== false) {
  1410. if ($count === null) {
  1411. $this->error('请传入拼数(纯数字)');
  1412. }
  1413. if ($count === 8) {
  1414. return 0.01;
  1415. }
  1416. if ($count === 10) {
  1417. return 0.012;
  1418. }
  1419. return $basePrice;
  1420. }
  1421. if (strpos($name, '5-6拼(小盒二次拆片') !== false) {
  1422. return $basePrice;
  1423. }
  1424. if (strpos($name, '6拼及以上') !== false) {
  1425. return $basePrice;
  1426. }
  1427. if (preg_match('/^(\d+)拼/u', $name, $matches)) {
  1428. if ($count === null) {
  1429. $this->error('请传入拼数(纯数字)');
  1430. }
  1431. }
  1432. return $basePrice;
  1433. }
  1434. /**
  1435. * 报工数据删除
  1436. * @return void
  1437. * @throws \Exception
  1438. * @throws \think\db\exception\DataNotFoundException
  1439. * @throws \think\db\exception\ModelNotFoundException
  1440. * @throws \think\exception\DbException
  1441. * @throws \think\exception\PDOException
  1442. */
  1443. public function deleteGluingReportData()
  1444. {
  1445. if ($this->request->isPost() === false){
  1446. $this->error('请求错误');
  1447. }
  1448. $params = $this->request->param();
  1449. if (!isset($params['id']) || empty($params['id'])){
  1450. $this->error('参数错误');
  1451. }
  1452. $ids = explode(',', $params['id']);
  1453. $roleIds = \db('设备_糊盒报工资料')
  1454. ->where('Uid', 'in', $ids)
  1455. ->column('role');
  1456. $roleIds = array_filter(array_unique($roleIds));
  1457. db()->startTrans();
  1458. try {
  1459. $res = \db('设备_糊盒报工资料')->where('Uid', 'in', $ids)->delete();
  1460. if ($res === false) {
  1461. throw new \Exception('删除报工数据失败');
  1462. }
  1463. if (!empty($roleIds)) {
  1464. $classRes = \db('糊盒报工班组')->where('id', 'in', $roleIds)->delete();
  1465. if ($classRes === false) {
  1466. throw new \Exception('删除班组数据失败');
  1467. }
  1468. }
  1469. db()->commit();
  1470. } catch (\Exception $e) {
  1471. db()->rollback();
  1472. $this->error($e->getMessage());
  1473. }
  1474. $this->success('删除成功');
  1475. }
  1476. }