|
@@ -98,7 +98,7 @@ class Mo extends CommonObject
|
|
|
'rowid' => array('type'=>'integer', 'label'=>'TechnicalID', 'enabled'=>1, 'visible'=>-2, 'position'=>1, 'notnull'=>1, 'index'=>1, 'comment'=>"Id",),
|
|
|
'entity' => array('type'=>'integer', 'label'=>'Entity', 'enabled'=>1, 'visible'=>0, 'position'=>5, 'notnull'=>1, 'default'=>'1', 'index'=>1),
|
|
|
'ref' => array('type'=>'varchar(128)', 'label'=>'Ref', 'enabled'=>1, 'visible'=>4, 'position'=>10, 'notnull'=>1, 'default'=>'(PROV)', 'index'=>1, 'searchall'=>1, 'comment'=>"Reference of object", 'showoncombobox'=>'1', 'noteditable'=>1),
|
|
|
- 'fk_bom' => array('type'=>'integer:Bom:bom/class/bom.class.php:0:(t.status:=:1)', 'filter'=>'active=1', 'label'=>'BOM', 'enabled'=>'$conf->bom->enabled', 'visible'=>1, 'position'=>33, 'notnull'=>-1, 'index'=>1, 'comment'=>"Original BOM", 'css'=>'minwidth100 maxwidth300', 'csslist'=>'nowraponall', 'picto'=>'bom'),
|
|
|
+ 'fk_bom' => array('type'=>'integer:Bom:bom/class/bom.class.php:0:(t.status:=:1)', 'filter'=>'active=1', 'label'=>'BOM', 'enabled'=>'$conf->bom->enabled', 'visible'=>1, 'position'=>33, 'notnull'=>-1, 'index'=>1, 'comment'=>"Original BOM", 'css'=>'minwidth100 maxwidth500', 'csslist'=>'tdoverflowmax150', 'picto'=>'bom'),
|
|
|
'mrptype' => array('type'=>'integer', 'label'=>'Type', 'enabled'=>1, 'visible'=>1, 'position'=>34, 'notnull'=>1, 'default'=>'0', 'arrayofkeyval'=>array(0=>'Manufacturing', 1=>'Disassemble'), 'css'=>'minwidth150', 'csslist'=>'minwidth150 center'),
|
|
|
'fk_product' => array('type'=>'integer:Product:product/class/product.class.php:0', 'label'=>'Product', 'enabled'=>'isModEnabled("product")', 'visible'=>1, 'position'=>35, 'notnull'=>1, 'index'=>1, 'comment'=>"Product to produce", 'css'=>'maxwidth300', 'csslist'=>'tdoverflowmax100', 'picto'=>'product'),
|
|
|
'qty' => array('type'=>'real', 'label'=>'QtyToProduce', 'enabled'=>1, 'visible'=>1, 'position'=>40, 'notnull'=>1, 'comment'=>"Qty to produce", 'css'=>'width75', 'default'=>1, 'isameasure'=>1),
|
|
@@ -283,26 +283,23 @@ class Mo extends CommonObject
|
|
|
*/
|
|
|
public function create(User $user, $notrigger = false)
|
|
|
{
|
|
|
- global $conf;
|
|
|
-
|
|
|
$error = 0;
|
|
|
$idcreated = 0;
|
|
|
|
|
|
- $this->db->begin();
|
|
|
-
|
|
|
- // Check that product is not a kit/virtual product
|
|
|
- if (empty($conf->global->ALLOW_USE_KITS_INTO_BOM_AND_MO) && $this->fk_product > 0) {
|
|
|
+ // If kits feature is enabled and we don't allow kits into BOM and MO, we check that the product is not a kit/virtual product
|
|
|
+ if (getDolGlobalString('PRODUIT_SOUSPRODUITS') && !getDolGlobalString('ALLOW_USE_KITS_INTO_BOM_AND_MO') && $this->fk_product > 0) {
|
|
|
include_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
|
|
|
$tmpproduct = new Product($this->db);
|
|
|
$tmpproduct->fetch($this->fk_product);
|
|
|
if ($tmpproduct->hasFatherOrChild(1) > 0) {
|
|
|
$this->error = 'ErrorAVirtualProductCantBeUsedIntoABomOrMo';
|
|
|
$this->errors[] = $this->error;
|
|
|
- $this->db->rollback();
|
|
|
return -1;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+ $this->db->begin();
|
|
|
+
|
|
|
if ($this->fk_bom > 0) {
|
|
|
// If there is a nown BOM, we force the type of MO to the type of BOM
|
|
|
include_once DOL_DOCUMENT_ROOT.'/bom/class/bom.class.php';
|
|
@@ -320,7 +317,7 @@ class Mo extends CommonObject
|
|
|
}
|
|
|
|
|
|
if (!$error) {
|
|
|
- $result = $this->updateProduction($user, $notrigger); // Insert lines from BOM
|
|
|
+ $result = $this->createProduction($user, $notrigger); // Insert lines from BOM
|
|
|
if ($result <= 0) {
|
|
|
$error++;
|
|
|
}
|
|
@@ -640,6 +637,12 @@ class Mo extends CommonObject
|
|
|
$error++;
|
|
|
}
|
|
|
|
|
|
+ // Update the lines (the qty) to consume or to produce
|
|
|
+ $result = $this->updateProduction($user, $notrigger);
|
|
|
+ if ($result <= 0) {
|
|
|
+ $error++;
|
|
|
+ }
|
|
|
+
|
|
|
if (!$error) {
|
|
|
$this->db->commit();
|
|
|
return 1;
|
|
@@ -649,6 +652,7 @@ class Mo extends CommonObject
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
/**
|
|
|
* Erase and update the line to consume and to produce.
|
|
|
*
|
|
@@ -656,6 +660,114 @@ class Mo extends CommonObject
|
|
|
* @param bool $notrigger false=launch triggers after, true=disable triggers
|
|
|
* @return int <0 if KO, >0 if OK
|
|
|
*/
|
|
|
+ public function createProduction(User $user, $notrigger = true)
|
|
|
+ {
|
|
|
+ $error = 0;
|
|
|
+ $role = "";
|
|
|
+
|
|
|
+ if ($this->status != self::STATUS_DRAFT) {
|
|
|
+ return -1;
|
|
|
+ }
|
|
|
+
|
|
|
+ $this->db->begin();
|
|
|
+
|
|
|
+ // Insert lines in mrp_production table from BOM data
|
|
|
+ if (!$error) {
|
|
|
+ $sql = 'DELETE FROM '.MAIN_DB_PREFIX.'mrp_production WHERE fk_mo = '.((int) $this->id);
|
|
|
+ $this->db->query($sql);
|
|
|
+
|
|
|
+ $moline = new MoLine($this->db);
|
|
|
+
|
|
|
+ // Line to produce
|
|
|
+ $moline->fk_mo = $this->id;
|
|
|
+ $moline->qty = $this->qty;
|
|
|
+ $moline->fk_product = $this->fk_product;
|
|
|
+ $moline->position = 1;
|
|
|
+
|
|
|
+ if ($this->fk_bom > 0) { // If a BOM is defined, we know what to produce.
|
|
|
+ include_once DOL_DOCUMENT_ROOT.'/bom/class/bom.class.php';
|
|
|
+ $bom = new Bom($this->db);
|
|
|
+ $bom->fetch($this->fk_bom);
|
|
|
+ if ($bom->bomtype == 1) {
|
|
|
+ $role = 'toproduce';
|
|
|
+ $moline->role = 'toconsume';
|
|
|
+ } else {
|
|
|
+ $role = 'toconsume';
|
|
|
+ $moline->role = 'toproduce';
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ if ($this->mrptype == 1) {
|
|
|
+ $moline->role = 'toconsume';
|
|
|
+ } else {
|
|
|
+ $moline->role = 'toproduce';
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ $resultline = $moline->create($user, false); // Never use triggers here
|
|
|
+ if ($resultline <= 0) {
|
|
|
+ $error++;
|
|
|
+ $this->error = $moline->error;
|
|
|
+ $this->errors = $moline->errors;
|
|
|
+ dol_print_error($this->db, $moline->error, $moline->errors);
|
|
|
+ }
|
|
|
+
|
|
|
+ if ($this->fk_bom > 0) { // If a BOM is defined, we know what to consume.
|
|
|
+ if ($bom->id > 0) {
|
|
|
+ // Lines to consume
|
|
|
+ if (!$error) {
|
|
|
+ foreach ($bom->lines as $line) {
|
|
|
+ $moline = new MoLine($this->db);
|
|
|
+
|
|
|
+ $moline->fk_mo = $this->id;
|
|
|
+ $moline->origin_id = $line->id;
|
|
|
+ $moline->origin_type = 'bomline';
|
|
|
+ if ($line->qty_frozen) {
|
|
|
+ $moline->qty = $line->qty; // Qty to consume does not depends on quantity to produce
|
|
|
+ } else {
|
|
|
+ $moline->qty = price2num(($line->qty / ( !empty($bom->qty) ? $bom->qty : 1 ) ) * $this->qty / ( !empty($line->efficiency) ? $line->efficiency : 1 ), 'MS'); // Calculate with Qty to produce and more presition
|
|
|
+ }
|
|
|
+ if ($moline->qty <= 0) {
|
|
|
+ $error++;
|
|
|
+ $this->error = "BadValueForquantityToConsume";
|
|
|
+ break;
|
|
|
+ } else {
|
|
|
+ $moline->fk_product = $line->fk_product;
|
|
|
+ $moline->role = $role;
|
|
|
+ $moline->position = $line->position;
|
|
|
+ $moline->qty_frozen = $line->qty_frozen;
|
|
|
+ $moline->disable_stock_change = $line->disable_stock_change;
|
|
|
+
|
|
|
+ $resultline = $moline->create($user, false); // Never use triggers here
|
|
|
+ if ($resultline <= 0) {
|
|
|
+ $error++;
|
|
|
+ $this->error = $moline->error;
|
|
|
+ $this->errors = $moline->errors;
|
|
|
+ dol_print_error($this->db, $moline->error, $moline->errors);
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (!$error) {
|
|
|
+ $this->db->commit();
|
|
|
+ return 1;
|
|
|
+ } else {
|
|
|
+ $this->db->rollback();
|
|
|
+ return -1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * Update quantities in lines to consume and to produce.
|
|
|
+ *
|
|
|
+ * @param User $user User that modifies
|
|
|
+ * @param bool $notrigger false=launch triggers after, true=disable triggers
|
|
|
+ * @return int <0 if KO, >0 if OK
|
|
|
+ */
|
|
|
public function updateProduction(User $user, $notrigger = true)
|
|
|
{
|
|
|
$error = 0;
|