319 if (!DolibarrApiAccess::$user->hasRight(
'mrp',
'write')) {
320 throw new RestException(403,
'Not enough permission');
322 $result = $this->mo->fetch(
$id);
324 throw new RestException(404,
'MO not found');
327 if ($this->mo->status != Mo::STATUS_VALIDATED && $this->mo->status != Mo::STATUS_INPROGRESS) {
328 throw new RestException(405,
'Error bad status of MO');
332 require_once DOL_DOCUMENT_ROOT.
'/product/class/product.class.php';
333 require_once DOL_DOCUMENT_ROOT.
'/product/stock/class/mouvementstock.class.php';
334 require_once DOL_DOCUMENT_ROOT.
'/mrp/lib/mrp_mo.lib.php';
341 $arraytoconsume = array();
342 $arraytoproduce = array();
344 foreach ($request_data as $field => $value) {
345 if ($field ==
'inventorylabel') {
346 $labelmovement = $value;
348 if ($field ==
'inventorycode') {
349 $codemovement = $value;
351 if ($field ==
'autoclose') {
354 if ($field ==
'arraytoconsume') {
355 $arraytoconsume = $value;
357 if ($field ==
'arraytoproduce') {
358 $arraytoproduce = $value;
360 if ($field ===
'caller') {
362 $stockmove->context[
'caller'] =
sanitizeVal($request_data[
'caller'],
'aZ09');
367 if (empty($labelmovement)) {
368 throw new RestException(500,
"Field inventorylabel not provided");
370 if (empty($codemovement)) {
371 throw new RestException(500,
"Field inventorycode not provided");
374 $consumptioncomplete =
true;
375 $productioncomplete =
true;
377 if (!empty($arraytoconsume) && !empty($arraytoproduce)) {
379 $arrayofarrayname = array(
"arraytoconsume",
"arraytoproduce");
380 foreach ($arrayofarrayname as $arrayname) {
381 foreach (${$arrayname} as $value) {
382 $tmpproduct =
new Product($this->db);
383 if (empty($value[
"objectid"])) {
384 throw new RestException(500,
"Field objectid required in ".$arrayname);
386 $tmpproduct->fetch($value[
"qty"]);
387 if (empty($value[
"qty"])) {
388 throw new RestException(500,
"Field qty required in ".$arrayname);
390 if ($value[
"qty"] != 0) {
391 $qtytoprocess = $value[
"qty"];
392 if (isset($value[
"fk_warehouse"])) {
393 if (!($value[
"fk_warehouse"] > 0)) {
395 throw new RestException(500,
"Field fk_warehouse must be > 0 in ".$arrayname);
397 if ($tmpproduct->status_batch) {
399 throw new RestException(500,
"Product ".$tmpproduct->ref.
"must be in batch");
403 if (!$error && $value[
"fk_warehouse"] > 0) {
405 $id_product_batch = 0;
407 $stockmove->setOrigin($this->mo->element, $this->mo->id);
409 if ($arrayname ==
'arraytoconsume') {
410 $moline =
new MoLine($this->db);
411 $moline->fk_mo = $this->mo->id;
412 $moline->position = $pos;
413 $moline->fk_product = $value[
"objectid"];
414 $moline->fk_warehouse = $value[
"fk_warehouse"];
415 $moline->qty = $qtytoprocess;
416 $moline->batch = (string) $tmpproduct->status_batch;
417 $moline->role =
'toproduce';
418 $moline->fk_mrp_production = 0;
419 $moline->fk_stock_movement = $idstockmove;
420 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
422 $resultmoline = $moline->create(DolibarrApiAccess::$user);
423 if ($resultmoline <= 0) {
425 throw new RestException(500, $moline->error);
427 $idstockmove = $stockmove->livraison(DolibarrApiAccess::$user, $value[
"objectid"], $value[
"fk_warehouse"], $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
429 $moline =
new MoLine($this->db);
430 $moline->fk_mo = $this->mo->id;
431 $moline->position = $pos;
432 $moline->fk_product = $value[
"objectid"];
433 $moline->fk_warehouse = $value[
"fk_warehouse"];
434 $moline->qty = $qtytoprocess;
435 $moline->batch = (string) $tmpproduct->status_batch;
436 $moline->role =
'toconsume';
437 $moline->fk_mrp_production = 0;
438 $moline->fk_stock_movement = $idstockmove;
439 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
441 $resultmoline = $moline->create(DolibarrApiAccess::$user);
442 if ($resultmoline <= 0) {
444 throw new RestException(500, $moline->error);
446 $idstockmove = $stockmove->reception(DolibarrApiAccess::$user, $value[
"objectid"], $value[
"fk_warehouse"], $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
448 if ($idstockmove < 0) {
450 throw new RestException(500, $stockmove->error);
455 $moline =
new MoLine($this->db);
456 $moline->fk_mo = $this->mo->id;
457 $moline->position = $pos;
458 $moline->fk_product = $value[
"objectid"];
459 $moline->fk_warehouse = $value[
"fk_warehouse"];
460 $moline->qty = $qtytoprocess;
461 $moline->batch = (string) $tmpproduct->status_batch;
462 if ($arrayname ==
"arraytoconsume") {
463 $moline->role =
'consumed';
465 $moline->role =
'produced';
467 $moline->fk_mrp_production = 0;
468 $moline->fk_stock_movement = $idstockmove;
469 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
471 $resultmoline = $moline->create(DolibarrApiAccess::$user);
472 if ($resultmoline <= 0) {
474 throw new RestException(500, $moline->error);
483 if ($autoclose <= 0) {
484 $consumptioncomplete =
false;
485 $productioncomplete =
false;
490 foreach ($this->mo->lines as $line) {
491 if ($line->role ==
'toconsume') {
492 $tmpproduct =
new Product($this->db);
493 $tmpproduct->fetch($line->fk_product);
494 if ($line->qty != 0) {
495 $qtytoprocess = $line->qty;
496 if (isset($line->fk_warehouse)) {
497 if (!($line->fk_warehouse > 0)) {
498 $langs->load(
"errors");
500 throw new RestException(500, $langs->trans(
"ErrorFieldRequiredForProduct", $langs->transnoentitiesnoconv(
"Warehouse"), $tmpproduct->ref));
502 if ($tmpproduct->status_batch) {
503 $langs->load(
"errors");
505 throw new RestException(500, $langs->trans(
"ErrorFieldRequiredForProduct", $langs->transnoentitiesnoconv(
"Batch"), $tmpproduct->ref));
509 if (!$error && $line->fk_warehouse > 0) {
511 $id_product_batch = 0;
512 $stockmove->origin_type =
'mo';
513 $stockmove->origin_id = $this->mo->id;
514 if ($qtytoprocess >= 0) {
515 $idstockmove = $stockmove->livraison(DolibarrApiAccess::$user, $line->fk_product, $line->fk_warehouse, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
517 $idstockmove = $stockmove->reception(DolibarrApiAccess::$user, $line->fk_product, $line->fk_warehouse, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
519 if ($idstockmove < 0) {
521 throw new RestException(500, $stockmove->error);
526 $moline =
new MoLine($this->db);
527 $moline->fk_mo = $this->mo->id;
528 $moline->position = $pos;
529 $moline->fk_product = $line->fk_product;
530 $moline->fk_warehouse = $line->fk_warehouse;
531 $moline->qty = $qtytoprocess;
532 $moline->batch = (string) $tmpproduct->status_batch;
533 $moline->role =
'consumed';
534 $moline->fk_mrp_production = $line->id;
535 $moline->fk_stock_movement = $idstockmove;
536 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
538 $resultmoline = $moline->create(DolibarrApiAccess::$user);
539 if ($resultmoline <= 0) {
541 throw new RestException(500, $moline->error);
550 foreach ($this->mo->lines as $line) {
551 if ($line->role ==
'toproduce') {
552 $tmpproduct =
new Product($this->db);
553 $tmpproduct->fetch($line->fk_product);
554 if ($line->qty != 0) {
555 $qtytoprocess = $line->qty;
556 if (isset($line->fk_warehouse)) {
557 if (!($line->fk_warehouse > 0)) {
558 $langs->load(
"errors");
560 throw new RestException(500, $langs->trans(
"ErrorFieldRequiredForProduct", $langs->transnoentitiesnoconv(
"Warehouse"), $tmpproduct->ref));
562 if ($tmpproduct->status_batch) {
563 $langs->load(
"errors");
565 throw new RestException(500, $langs->trans(
"ErrorFieldRequiredForProduct", $langs->transnoentitiesnoconv(
"Batch"), $tmpproduct->ref));
569 if (!$error && $line->fk_warehouse > 0) {
571 $id_product_batch = 0;
572 $stockmove->origin_type =
'mo';
573 $stockmove->origin_id = $this->mo->id;
574 if ($qtytoprocess >= 0) {
575 $idstockmove = $stockmove->reception(DolibarrApiAccess::$user, $line->fk_product, $line->fk_warehouse, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
577 $idstockmove = $stockmove->livraison(DolibarrApiAccess::$user, $line->fk_product, $line->fk_warehouse, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
579 if ($idstockmove < 0) {
581 throw new RestException(500, $stockmove->error);
586 $moline =
new MoLine($this->db);
587 $moline->fk_mo = $this->mo->id;
588 $moline->position = $pos;
589 $moline->fk_product = $line->fk_product;
590 $moline->fk_warehouse = $line->fk_warehouse;
591 $moline->qty = $qtytoprocess;
592 $moline->batch = (string) $tmpproduct->status_batch;
593 $moline->role =
'produced';
594 $moline->fk_mrp_production = $line->id;
595 $moline->fk_stock_movement = $idstockmove;
596 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
598 $resultmoline = $moline->create(DolibarrApiAccess::$user);
599 if ($resultmoline <= 0) {
601 throw new RestException(500, $moline->error);
611 if ($autoclose > 0) {
612 foreach ($this->mo->lines as $line) {
613 if ($line->role ==
'toconsume') {
614 $arrayoflines = $this->mo->fetchLinesLinked(
'consumed', $line->id);
615 $alreadyconsumed = 0;
616 foreach ($arrayoflines as $line2) {
617 $alreadyconsumed += $line2[
'qty'];
620 if ($alreadyconsumed < $line->qty) {
621 $consumptioncomplete =
false;
624 if ($line->role ==
'toproduce') {
625 $arrayoflines = $this->mo->fetchLinesLinked(
'produced', $line->id);
626 $alreadyproduced = 0;
627 foreach ($arrayoflines as $line2) {
628 $alreadyproduced += $line2[
'qty'];
631 if ($alreadyproduced < $line->qty) {
632 $productioncomplete =
false;
637 $consumptioncomplete =
false;
638 $productioncomplete =
false;
644 dol_syslog(
"consumptioncomplete = ".json_encode($consumptioncomplete).
" productioncomplete = ".json_encode($productioncomplete));
645 if ($consumptioncomplete && $productioncomplete) {
646 $result = $this->mo->setStatut(Mo::STATUS_PRODUCED, 0,
'',
'MRP_MO_PRODUCED');
648 $result = $this->mo->setStatut(Mo::STATUS_INPROGRESS, 0,
'',
'MRP_MO_PRODUCED');
651 throw new RestException(500, $this->mo->error);
654 return $this->mo->id;
691 if (!DolibarrApiAccess::$user->hasRight(
"mrp",
"write")) {
692 throw new RestException(403,
'Not enough permission');
694 $result = $this->mo->fetch(
$id);
696 throw new RestException(404,
'MO not found');
699 if ($this->mo->status != Mo::STATUS_VALIDATED && $this->mo->status != Mo::STATUS_INPROGRESS) {
700 throw new RestException(405,
'Error bad status of MO');
704 require_once DOL_DOCUMENT_ROOT.
'/product/class/product.class.php';
705 require_once DOL_DOCUMENT_ROOT.
'/product/stock/class/mouvementstock.class.php';
706 require_once DOL_DOCUMENT_ROOT.
'/mrp/lib/mrp_mo.lib.php';
713 $arraytoconsume = array();
714 $arraytoproduce = array();
716 foreach ($request_data as $field => $value) {
717 if ($field ==
'inventorylabel') {
718 $labelmovement = $value;
720 if ($field ==
'inventorycode') {
721 $codemovement = $value;
723 if ($field ==
'autoclose') {
726 if ($field ==
'arraytoconsume') {
727 $arraytoconsume = $value;
729 if ($field ==
'arraytoproduce') {
730 $arraytoproduce = $value;
732 if ($field ===
'caller') {
734 $stockmove->context[
'caller'] = $request_data[
'caller'];
739 if (empty($labelmovement)) {
740 throw new RestException(500,
"Field inventorylabel not provided");
742 if (empty($codemovement)) {
743 throw new RestException(500,
"Field inventorycode not provided");
749 $arrayofarrayname = array(
"arraytoconsume",
"arraytoproduce");
750 foreach ($arrayofarrayname as $arrayname) {
751 foreach (${$arrayname} as $value) {
752 if (empty($value[
"objectid"])) {
753 throw new RestException(500,
"Field objectid required in " . $arrayname);
756 $molinetoprocess =
new MoLine($this->db);
757 $tmpmolineid = $molinetoprocess->fetch($value[
"objectid"]);
758 if ($tmpmolineid <= 0) {
759 throw new RestException(500,
"MoLine with rowid " . $value[
"objectid"] .
" not exist.");
762 $tmpproduct =
new Product($this->db);
763 $tmpproduct->fetch($molinetoprocess->fk_product);
764 if ($tmpproduct->status_batch) {
765 throw new RestException(500,
"Product " . $tmpproduct->ref .
" must be in batch, this API can't handle it currently.");
768 if (empty($value[
"qty"]) && $value[
"qty"] != 0) {
769 throw new RestException(500,
"Field qty with lower or higher then 0 required in " . $arrayname);
771 $qtytoprocess = $value[
"qty"];
773 $fk_warehousetoprocess = 0;
774 if ($molinetoprocess->disable_stock_change ==
false) {
775 if (isset($value[
"fk_warehouse"])) {
776 if (!($value[
"fk_warehouse"] > 0)) {
777 throw new RestException(500,
"Field fk_warehouse required in " . $arrayname);
780 $fk_warehousetoprocess = (int) $value[
"fk_warehouse"];
784 if (isset($value[
"pricetoproduce"])) {
785 if ($value[
"pricetoproduce"] > 0) {
786 $pricetoproduce = $value[
"pricetoproduce"];
792 if ($molinetoprocess->disable_stock_change ==
false) {
794 $id_product_batch = 0;
795 $stockmove->origin_type =
'mo';
796 $stockmove->origin_id = $this->mo->id;
797 if ($arrayname ==
"arraytoconsume") {
798 if ($qtytoprocess >= 0) {
799 $idstockmove = $stockmove->livraison(DolibarrApiAccess::$user, $molinetoprocess->fk_product, $fk_warehousetoprocess, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
801 $idstockmove = $stockmove->reception(DolibarrApiAccess::$user, $molinetoprocess->fk_product, $fk_warehousetoprocess, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
804 if ($qtytoprocess >= 0) {
805 $idstockmove = $stockmove->reception(DolibarrApiAccess::$user, $molinetoprocess->fk_product, $fk_warehousetoprocess, $qtytoprocess, $pricetoproduce, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
807 $idstockmove = $stockmove->livraison(DolibarrApiAccess::$user, $molinetoprocess->fk_product, $fk_warehousetoprocess, $qtytoprocess, 0, $labelmovement,
dol_now(),
'',
'', $tmpproduct->status_batch, $id_product_batch, $codemovement);
810 if ($idstockmove <= 0) {
811 throw new RestException(500, $stockmove->error);
816 $moline =
new MoLine($this->db);
817 $moline->fk_mo = $this->mo->id;
818 $moline->position = $pos;
819 $moline->fk_product = $tmpproduct->id;
820 $moline->fk_warehouse = $idstockmove > 0 ? $fk_warehousetoprocess :
null;
821 $moline->qty = $qtytoprocess;
823 $moline->fk_mrp_production = $molinetoprocess->id;
824 $moline->fk_stock_movement = $idstockmove > 0 ? $idstockmove :
null;
825 $moline->fk_user_creat = DolibarrApiAccess::$user->id;
827 if ($arrayname ==
"arraytoconsume") {
828 $moline->role =
'consumed';
830 $moline->role =
'produced';
833 $resultmoline = $moline->create(DolibarrApiAccess::$user);
834 if ($resultmoline <= 0) {
835 throw new RestException(500, $moline->error);
842 $consumptioncomplete =
true;
843 $productioncomplete =
true;
845 if ($autoclose > 0) {
847 $this->mo->fetchLines();
849 foreach ($this->mo->lines as $line) {
850 if ($line->role ==
'toconsume') {
851 $arrayoflines = $this->mo->fetchLinesLinked(
'consumed', $line->id);
852 $alreadyconsumed = 0;
853 foreach ($arrayoflines as $line2) {
854 $alreadyconsumed += $line2[
'qty'];
857 if ($alreadyconsumed < $line->qty) {
858 $consumptioncomplete =
false;
861 if ($line->role ==
'toproduce') {
862 $arrayoflines = $this->mo->fetchLinesLinked(
'produced', $line->id);
863 $alreadyproduced = 0;
864 foreach ($arrayoflines as $line2) {
865 $alreadyproduced += $line2[
'qty'];
868 if ($alreadyproduced < $line->qty) {
869 $productioncomplete =
false;
874 $consumptioncomplete =
false;
875 $productioncomplete =
false;
879 dol_syslog(
"consumptioncomplete = " . (
string) $consumptioncomplete .
" productioncomplete = " . (
string) $productioncomplete);
881 if ($consumptioncomplete && $productioncomplete) {
882 $result = $this->mo->setStatut(Mo::STATUS_PRODUCED, 0,
'',
'MRP_MO_PRODUCED');
884 $result = $this->mo->setStatut(Mo::STATUS_INPROGRESS, 0,
'',
'MRP_MO_PRODUCED');
887 throw new RestException(500, $this->mo->error);
891 return $this->mo->id;