From 3215e066e49b74e71a51ab2f4b1ecd2477396f09 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Mon, 11 Mar 2019 10:00:44 +0100 Subject: [PATCH 01/11] copy linked categories when cloning a product --- htdocs/langs/en_US/products.lang | 1 + htdocs/langs/fr_FR/products.lang | 1 + htdocs/product/card.php | 14 ++++++++++++++ htdocs/product/class/product.class.php | 26 ++++++++++++++++++++++++++ 4 files changed, 42 insertions(+) diff --git a/htdocs/langs/en_US/products.lang b/htdocs/langs/en_US/products.lang index 401ccc5462e..9c96f12c589 100644 --- a/htdocs/langs/en_US/products.lang +++ b/htdocs/langs/en_US/products.lang @@ -147,6 +147,7 @@ RowMaterial=Raw Material CloneProduct=Clone product or service ConfirmCloneProduct=Are you sure you want to clone product or service %s? CloneContentProduct=Clone all main information of product/service +CloneCategoriesProduct=Clone tags/categories linked ClonePricesProduct=Clone prices CloneCompositionProduct=Clone virtual product/service CloneCombinationsProduct=Clone product variants diff --git a/htdocs/langs/fr_FR/products.lang b/htdocs/langs/fr_FR/products.lang index 77ad53a3eff..2339a0c921f 100644 --- a/htdocs/langs/fr_FR/products.lang +++ b/htdocs/langs/fr_FR/products.lang @@ -146,6 +146,7 @@ RowMaterial=Matière première CloneProduct=Cloner produit/service ConfirmCloneProduct=Êtes-vous sûr de vouloir cloner le produit ou service %s ? CloneContentProduct=Cloner les informations générales du produit/service +CloneCategoriesProduct=Cloner les catégories associées ClonePricesProduct=Cloner les prix CloneCompositionProduct=Cloner le produits packagés CloneCombinationsProduct=Cloner les variantes diff --git a/htdocs/product/card.php b/htdocs/product/card.php index 18ea87cb03a..e433b9a6558 100644 --- a/htdocs/product/card.php +++ b/htdocs/product/card.php @@ -520,6 +520,19 @@ if (empty($reshook)) } } + if (GETPOST('clone_categories')) + { + $result = $object->clone_categories($originalId, $id); + + if ($result < 1) + { + $db->rollback(); + setEventMessage($langs->trans('ErrorProductClone'), null, 'errors'); + header("Location: ".$_SERVER["PHP_SELF"]."?id=".$originalId); + exit; + } + } + // $object->clone_fournisseurs($originalId, $id); $db->commit(); @@ -1982,6 +1995,7 @@ $formquestionclone=array( 'text' => $langs->trans("ConfirmClone"), array('type' => 'text', 'name' => 'clone_ref','label' => $langs->trans("NewRefForClone"), 'value' => empty($tmpcode) ? $langs->trans("CopyOf").' '.$object->ref : $tmpcode, 'size'=>24), array('type' => 'checkbox', 'name' => 'clone_content','label' => $langs->trans("CloneContentProduct"), 'value' => 1), + array('type' => 'checkbox', 'name' => 'clone_categories', 'label' => $langs->trans("CloneCategoriesProduct"), 'value' => 1), array('type' => 'checkbox', 'name' => 'clone_prices', 'label' => $langs->trans("ClonePricesProduct").' ('.$langs->trans("FeatureNotYetAvailable").')', 'value' => 0, 'disabled' => true), ); if (! empty($conf->global->PRODUIT_SOUSPRODUITS)) diff --git a/htdocs/product/class/product.class.php b/htdocs/product/class/product.class.php index 51a5d7c72d0..3466625dfe5 100644 --- a/htdocs/product/class/product.class.php +++ b/htdocs/product/class/product.class.php @@ -3611,6 +3611,32 @@ class Product extends CommonObject return 1; } + + // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps + /** + * copy related categories to another product + * + * @param int $fromId Id produit source + * @param int $toId Id produit cible + * @return int < 0 si erreur, > 0 si ok + */ + function clone_categories($fromId, $toId) + { + $this->db->begin(); + + $sql = 'INSERT INTO '.MAIN_DB_PREFIX.'categorie_product (fk_categorie, fk_product)'; + $sql.= " SELECT fk_categorie, $toId FROM ".MAIN_DB_PREFIX."categorie_product"; + $sql.= " WHERE fk_product = '".$fromId."'"; + + if (! $this->db->query($sql)) + { + $this->db->rollback(); + return -1; + } + + $this->db->commit(); + return 1; + } // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps /** * Recopie les fournisseurs et prix fournisseurs d'un produit/service sur un autre From 08d517c053ebb4f8bd87d6edd3301505ce745c17 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Mon, 11 Mar 2019 10:35:27 +0100 Subject: [PATCH 02/11] custom content was deleted --- htdocs/custom/.gitignore | 4 ++++ htdocs/custom/README.md | 22 ++++++++++++++++++++++ htdocs/custom/index.html | 0 3 files changed, 26 insertions(+) create mode 100644 htdocs/custom/.gitignore create mode 100644 htdocs/custom/README.md create mode 100644 htdocs/custom/index.html diff --git a/htdocs/custom/.gitignore b/htdocs/custom/.gitignore new file mode 100644 index 00000000000..9420e8c61eb --- /dev/null +++ b/htdocs/custom/.gitignore @@ -0,0 +1,4 @@ +/* +!.gitignore +!README.md +!index.html diff --git a/htdocs/custom/README.md b/htdocs/custom/README.md new file mode 100644 index 00000000000..3a486e5a4a8 --- /dev/null +++ b/htdocs/custom/README.md @@ -0,0 +1,22 @@ +# DOLIBARR ERP & CRM custom directory for external modules. + +This directory is dedicated to store external modules. +To use it, just copy here the directory of the module into this directory. + +Note: On linux or MAC systems, it is better to unzip/store the external module directory into +a different place than this directory and just adding a symbolic link here to the htdocs directory +of the module. + +For example on Linux OS: Get the module from the command +mkdir ~/git; cd ~/git +git clone https://git.framasoft.org/p/newmodule/newmodule.git +Then create the symbolic link +ln -fs ~/git/newmodule/htdocs /path_to_dolibarr/htdocs/custom/newmodule + +WARNING !!! +Check also that the /custom directory is active by adding into dolibarr conf/conf.php file the following +two lines, so dolibarr will also scan /custom directory to find external external modules: + +$dolibarr_main_url_root_alt='/custom'; +$dolibarr_main_document_root_alt='/path_to_dolibarr/htdocs/custom/'; + diff --git a/htdocs/custom/index.html b/htdocs/custom/index.html new file mode 100644 index 00000000000..e69de29bb2d From 7bc0260661a138193afa4a442a22dfdef51dc029 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Mon, 18 Mar 2019 14:15:55 +0100 Subject: [PATCH 03/11] begin factorization of categories cloning --- htdocs/langs/en_US/categories.lang | 1 + htdocs/langs/fr_FR/categories.lang | 1 + htdocs/product/card.php | 2 +- 3 files changed, 3 insertions(+), 1 deletion(-) diff --git a/htdocs/langs/en_US/categories.lang b/htdocs/langs/en_US/categories.lang index eb34e302cad..dd446249ebe 100644 --- a/htdocs/langs/en_US/categories.lang +++ b/htdocs/langs/en_US/categories.lang @@ -88,3 +88,4 @@ AddProductServiceIntoCategory=Add the following product/service ShowCategory=Show tag/category ByDefaultInList=By default in list ChooseCategory=Choose category +CloneCategoriesProduct=Clone tags/categories linked diff --git a/htdocs/langs/fr_FR/categories.lang b/htdocs/langs/fr_FR/categories.lang index b65024a5217..9d58f0ff40d 100644 --- a/htdocs/langs/fr_FR/categories.lang +++ b/htdocs/langs/fr_FR/categories.lang @@ -88,3 +88,4 @@ AddProductServiceIntoCategory=Ajouter le produit/service suivant ShowCategory=Afficher tag/catégorie ByDefaultInList=Par défaut dans la liste ChooseCategory=Choisissez une catégorie +CloneCategories=Cloner les catégories associées diff --git a/htdocs/product/card.php b/htdocs/product/card.php index e433b9a6558..9becc71bbb8 100644 --- a/htdocs/product/card.php +++ b/htdocs/product/card.php @@ -1995,7 +1995,7 @@ $formquestionclone=array( 'text' => $langs->trans("ConfirmClone"), array('type' => 'text', 'name' => 'clone_ref','label' => $langs->trans("NewRefForClone"), 'value' => empty($tmpcode) ? $langs->trans("CopyOf").' '.$object->ref : $tmpcode, 'size'=>24), array('type' => 'checkbox', 'name' => 'clone_content','label' => $langs->trans("CloneContentProduct"), 'value' => 1), - array('type' => 'checkbox', 'name' => 'clone_categories', 'label' => $langs->trans("CloneCategoriesProduct"), 'value' => 1), + array('type' => 'checkbox', 'name' => 'clone_categories', 'label' => $langs->trans("CloneCategories"), 'value' => 1), array('type' => 'checkbox', 'name' => 'clone_prices', 'label' => $langs->trans("ClonePricesProduct").' ('.$langs->trans("FeatureNotYetAvailable").')', 'value' => 0, 'disabled' => true), ); if (! empty($conf->global->PRODUIT_SOUSPRODUITS)) From 61f9aac887f9755531884043abe5a11e091e51d3 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Mon, 18 Mar 2019 14:16:41 +0100 Subject: [PATCH 04/11] begin factorization of categories cloning --- htdocs/langs/en_US/products.lang | 1 - htdocs/langs/fr_FR/products.lang | 1 - 2 files changed, 2 deletions(-) diff --git a/htdocs/langs/en_US/products.lang b/htdocs/langs/en_US/products.lang index 9c96f12c589..401ccc5462e 100644 --- a/htdocs/langs/en_US/products.lang +++ b/htdocs/langs/en_US/products.lang @@ -147,7 +147,6 @@ RowMaterial=Raw Material CloneProduct=Clone product or service ConfirmCloneProduct=Are you sure you want to clone product or service %s? CloneContentProduct=Clone all main information of product/service -CloneCategoriesProduct=Clone tags/categories linked ClonePricesProduct=Clone prices CloneCompositionProduct=Clone virtual product/service CloneCombinationsProduct=Clone product variants diff --git a/htdocs/langs/fr_FR/products.lang b/htdocs/langs/fr_FR/products.lang index 2339a0c921f..77ad53a3eff 100644 --- a/htdocs/langs/fr_FR/products.lang +++ b/htdocs/langs/fr_FR/products.lang @@ -146,7 +146,6 @@ RowMaterial=Matière première CloneProduct=Cloner produit/service ConfirmCloneProduct=Êtes-vous sûr de vouloir cloner le produit ou service %s ? CloneContentProduct=Cloner les informations générales du produit/service -CloneCategoriesProduct=Cloner les catégories associées ClonePricesProduct=Cloner les prix CloneCompositionProduct=Cloner le produits packagés CloneCombinationsProduct=Cloner les variantes From f167ad910e280172e2384b771593f999424d02db Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Fri, 5 Apr 2019 11:30:51 +0200 Subject: [PATCH 05/11] camelCase and generic cloneCategories function --- htdocs/core/class/commonobject.class.php | 31 ++++++++++++++++++++++++ htdocs/langs/en_US/products.lang | 1 + htdocs/langs/fr_FR/products.lang | 1 + htdocs/product/card.php | 4 +-- 4 files changed, 35 insertions(+), 2 deletions(-) diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index e962e59264c..ccf255af4d7 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -7517,4 +7517,35 @@ abstract class CommonObject } } } + + /** + * copy related categories to another object + * + * @param int $fromId Id object source + * @param int $toId Id object cible + * @param string $type Type of category ('product', ...) + * @return int < 0 si erreur, > 0 si ok + */ + function cloneCategories($fromId, $toId, $type='') + { + $this->db->begin(); + + if (empty($type)) $type = $this->table_element; + + require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php'; + $categorystatic = new Categorie($this->db); + + $sql = "INSERT INTO ".MAIN_DB_PREFIX."categorie_" . $categorystatic->MAP_CAT_TABLE[$type] . " (fk_categorie, fk_product)"; + $sql.= " SELECT fk_categorie, $toId FROM ".MAIN_DB_PREFIX."categorie_" . $categorystatic->MAP_CAT_TABLE[$type]; + $sql.= " WHERE fk_product = '".$fromId."'"; + + if (! $this->db->query($sql)) + { + $this->db->rollback();die($sql); + return -1; + } + + $this->db->commit(); + return 1; + } } diff --git a/htdocs/langs/en_US/products.lang b/htdocs/langs/en_US/products.lang index 401ccc5462e..62c22548f36 100644 --- a/htdocs/langs/en_US/products.lang +++ b/htdocs/langs/en_US/products.lang @@ -148,6 +148,7 @@ CloneProduct=Clone product or service ConfirmCloneProduct=Are you sure you want to clone product or service %s? CloneContentProduct=Clone all main information of product/service ClonePricesProduct=Clone prices +CloneCategoriesProduct=Clone tags/categories linked CloneCompositionProduct=Clone virtual product/service CloneCombinationsProduct=Clone product variants ProductIsUsed=This product is used diff --git a/htdocs/langs/fr_FR/products.lang b/htdocs/langs/fr_FR/products.lang index 77ad53a3eff..be288c604af 100644 --- a/htdocs/langs/fr_FR/products.lang +++ b/htdocs/langs/fr_FR/products.lang @@ -147,6 +147,7 @@ CloneProduct=Cloner produit/service ConfirmCloneProduct=Êtes-vous sûr de vouloir cloner le produit ou service %s ? CloneContentProduct=Cloner les informations générales du produit/service ClonePricesProduct=Cloner les prix +CloneCategoriesProduct=Cloner les catégories associées CloneCompositionProduct=Cloner le produits packagés CloneCombinationsProduct=Cloner les variantes ProductIsUsed=Ce produit est utilisé diff --git a/htdocs/product/card.php b/htdocs/product/card.php index 9becc71bbb8..5354fcde70f 100644 --- a/htdocs/product/card.php +++ b/htdocs/product/card.php @@ -522,7 +522,7 @@ if (empty($reshook)) if (GETPOST('clone_categories')) { - $result = $object->clone_categories($originalId, $id); + $result = $object->cloneCategories($originalId, $id); if ($result < 1) { @@ -1995,7 +1995,7 @@ $formquestionclone=array( 'text' => $langs->trans("ConfirmClone"), array('type' => 'text', 'name' => 'clone_ref','label' => $langs->trans("NewRefForClone"), 'value' => empty($tmpcode) ? $langs->trans("CopyOf").' '.$object->ref : $tmpcode, 'size'=>24), array('type' => 'checkbox', 'name' => 'clone_content','label' => $langs->trans("CloneContentProduct"), 'value' => 1), - array('type' => 'checkbox', 'name' => 'clone_categories', 'label' => $langs->trans("CloneCategories"), 'value' => 1), + array('type' => 'checkbox', 'name' => 'clone_categories', 'label' => $langs->trans("CloneCategoriesProduct"), 'value' => 1), array('type' => 'checkbox', 'name' => 'clone_prices', 'label' => $langs->trans("ClonePricesProduct").' ('.$langs->trans("FeatureNotYetAvailable").')', 'value' => 0, 'disabled' => true), ); if (! empty($conf->global->PRODUIT_SOUSPRODUITS)) From d0fcece6130dcfb99504a5a824c8414879d23055 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Fri, 5 Apr 2019 11:34:23 +0200 Subject: [PATCH 06/11] dont make generic translations --- htdocs/langs/en_US/categories.lang | 1 - htdocs/langs/fr_FR/categories.lang | 1 - 2 files changed, 2 deletions(-) diff --git a/htdocs/langs/en_US/categories.lang b/htdocs/langs/en_US/categories.lang index dd446249ebe..eb34e302cad 100644 --- a/htdocs/langs/en_US/categories.lang +++ b/htdocs/langs/en_US/categories.lang @@ -88,4 +88,3 @@ AddProductServiceIntoCategory=Add the following product/service ShowCategory=Show tag/category ByDefaultInList=By default in list ChooseCategory=Choose category -CloneCategoriesProduct=Clone tags/categories linked diff --git a/htdocs/langs/fr_FR/categories.lang b/htdocs/langs/fr_FR/categories.lang index 9d58f0ff40d..b65024a5217 100644 --- a/htdocs/langs/fr_FR/categories.lang +++ b/htdocs/langs/fr_FR/categories.lang @@ -88,4 +88,3 @@ AddProductServiceIntoCategory=Ajouter le produit/service suivant ShowCategory=Afficher tag/catégorie ByDefaultInList=Par défaut dans la liste ChooseCategory=Choisissez une catégorie -CloneCategories=Cloner les catégories associées From 45b3a0588f6b02b6bffdfcc2cdc5856d243a3281 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Fri, 5 Apr 2019 11:40:57 +0200 Subject: [PATCH 07/11] remove old dev --- htdocs/product/class/product.class.php | 25 ------------------------- 1 file changed, 25 deletions(-) diff --git a/htdocs/product/class/product.class.php b/htdocs/product/class/product.class.php index 3466625dfe5..0087be5eab5 100644 --- a/htdocs/product/class/product.class.php +++ b/htdocs/product/class/product.class.php @@ -3612,31 +3612,6 @@ class Product extends CommonObject } - // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps - /** - * copy related categories to another product - * - * @param int $fromId Id produit source - * @param int $toId Id produit cible - * @return int < 0 si erreur, > 0 si ok - */ - function clone_categories($fromId, $toId) - { - $this->db->begin(); - - $sql = 'INSERT INTO '.MAIN_DB_PREFIX.'categorie_product (fk_categorie, fk_product)'; - $sql.= " SELECT fk_categorie, $toId FROM ".MAIN_DB_PREFIX."categorie_product"; - $sql.= " WHERE fk_product = '".$fromId."'"; - - if (! $this->db->query($sql)) - { - $this->db->rollback(); - return -1; - } - - $this->db->commit(); - return 1; - } // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps /** * Recopie les fournisseurs et prix fournisseurs d'un produit/service sur un autre From 8e2ef8e56cf807e56e3ef949142dfd7c95e25af5 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Fri, 5 Apr 2019 11:42:12 +0200 Subject: [PATCH 08/11] remove old dev --- htdocs/product/class/product.class.php | 1 - 1 file changed, 1 deletion(-) diff --git a/htdocs/product/class/product.class.php b/htdocs/product/class/product.class.php index 0087be5eab5..51a5d7c72d0 100644 --- a/htdocs/product/class/product.class.php +++ b/htdocs/product/class/product.class.php @@ -3611,7 +3611,6 @@ class Product extends CommonObject return 1; } - // phpcs:disable PEAR.NamingConventions.ValidFunctionName.ScopeNotCamelCaps /** * Recopie les fournisseurs et prix fournisseurs d'un produit/service sur un autre From 6bb5860f62463dc8fe28c5621cc829529746287a Mon Sep 17 00:00:00 2001 From: stickler-ci Date: Thu, 5 Sep 2019 14:12:52 +0000 Subject: [PATCH 09/11] Fixing style errors. --- htdocs/core/class/commonobject.class.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index 55fef7d0185..b668ae0465f 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -7801,7 +7801,7 @@ abstract class CommonObject * @param string $type Type of category ('product', ...) * @return int < 0 si erreur, > 0 si ok */ - function cloneCategories($fromId, $toId, $type='') + function cloneCategories($fromId, $toId, $type = '') { $this->db->begin(); From 6902b2cbf22969c58202404c15521fa3bfa3f916 Mon Sep 17 00:00:00 2001 From: Christophe Battarel Date: Thu, 5 Sep 2019 16:14:15 +0200 Subject: [PATCH 10/11] fix function visibility thanks to stckler --- htdocs/core/class/commonobject.class.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index 55fef7d0185..0f8dd4f0c00 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -7801,7 +7801,7 @@ abstract class CommonObject * @param string $type Type of category ('product', ...) * @return int < 0 si erreur, > 0 si ok */ - function cloneCategories($fromId, $toId, $type='') + public function cloneCategories($fromId, $toId, $type='') { $this->db->begin(); From cd96238adc0407213ce276e60f6d788933e9f0be Mon Sep 17 00:00:00 2001 From: stickler-ci Date: Thu, 5 Sep 2019 14:19:35 +0000 Subject: [PATCH 11/11] Fixing style errors. --- htdocs/core/class/commonobject.class.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/htdocs/core/class/commonobject.class.php b/htdocs/core/class/commonobject.class.php index 0f8dd4f0c00..e395f3d4455 100644 --- a/htdocs/core/class/commonobject.class.php +++ b/htdocs/core/class/commonobject.class.php @@ -7801,7 +7801,7 @@ abstract class CommonObject * @param string $type Type of category ('product', ...) * @return int < 0 si erreur, > 0 si ok */ - public function cloneCategories($fromId, $toId, $type='') + public function cloneCategories($fromId, $toId, $type = '') { $this->db->begin();