From beb12ba1a9ac5b5f3660b980c60d55c7ce7d0c5c Mon Sep 17 00:00:00 2001
From: Guillaume Heurtier <guillaume.heurtier@maarch.org>
Date: Thu, 19 Nov 2020 09:21:13 +0100
Subject: [PATCH] FEAT #14534 TIME 5:35 added min visa and max sign in visa
 circuit

---
 sql/data_fr.sql                               |  2 ++
 .../controllers/ActionMethodController.php    | 23 +++++++++++++++
 .../PreProcessActionController.php            | 22 ++++++++++++--
 .../controllers/ListInstanceController.php    | 29 +++++++++++++++++++
 .../controllers/ListTemplateController.php    | 22 ++++++++++++++
 src/lang/lang-en.json                         |  6 ++--
 src/lang/lang-fr.json                         |  4 ++-
 7 files changed, 103 insertions(+), 5 deletions(-)

diff --git a/sql/data_fr.sql b/sql/data_fr.sql
index 34a8f54ba94..20909e4870e 100755
--- a/sql/data_fr.sql
+++ b/sql/data_fr.sql
@@ -1022,6 +1022,8 @@ INSERT INTO parameters (id, param_value_string) VALUES ('registeredMailImportedS
 INSERT INTO parameters (id, description, param_value_int) VALUES ('keepDiffusionRoleInOutgoingIndexation', 'Si activé (1), prend en compte les roles du modèle de diffusion de l''entité.', 1);
 INSERT INTO parameters (id, param_value_string) VALUES ('bindingDocumentFinalAction', 'copy');
 INSERT INTO parameters (id, param_value_string) VALUES ('nonBindingDocumentFinalAction', 'delete');
+INSERT INTO parameters (id, param_value_int) VALUES ('minimumVisaRole', 0);
+INSERT INTO parameters (id, param_value_int) VALUES ('maximumSignRole', 0);
 
 ------------
 --DIFFLIST_TYPES
diff --git a/src/app/action/controllers/ActionMethodController.php b/src/app/action/controllers/ActionMethodController.php
index f251d647779..c7268842139 100644
--- a/src/app/action/controllers/ActionMethodController.php
+++ b/src/app/action/controllers/ActionMethodController.php
@@ -34,6 +34,7 @@ use History\controllers\HistoryController;
 use MessageExchange\controllers\MessageExchangeReviewController;
 use Note\models\NoteEntityModel;
 use Note\models\NoteModel;
+use Parameter\models\ParameterModel;
 use RegisteredMail\controllers\RegisteredMailTrait;
 use ExportSeda\controllers\ExportSEDATrait;
 use Resource\controllers\ResController;
@@ -341,6 +342,28 @@ class ActionMethodController
             return ['errors' => ['No available circuit']];
         }
 
+        $minimumVisaRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'minimumVisaRole']);
+        $maximumSignRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'maximumSignRole']);
+
+        $minimumVisaRole = !empty($minimumVisaRole['param_value_int']) ? $minimumVisaRole['param_value_int'] : 0;
+        $maximumSignRole = !empty($maximumSignRole['param_value_int']) ? $maximumSignRole['param_value_int'] : 0;
+
+        $nbVisaRole = 0;
+        $nbSignRole = 0;
+        foreach ($circuit as $listInstance) {
+            if ($listInstance['item_mode'] == 'visa') {
+                $nbVisaRole++;
+            } elseif ($listInstance['item_mode'] == 'sign') {
+                $nbSignRole++;
+            }
+        }
+        if ($minimumVisaRole != 0 && $nbVisaRole < $minimumVisaRole) {
+            return ['errors' => ['Circuit does not have enough visa users']];
+        }
+        if ($maximumSignRole != 0 && $nbSignRole > $maximumSignRole) {
+            return ['errors' => ['Circuit have too many sign users']];
+        }
+
         $resource       = ResModel::getById(['select' => ['integrations'], 'resId' => $args['resId']]);
         $integrations   = json_decode($resource['integrations'], true);
         $resourceIn     = !empty($integrations['inSignatureBook']);
diff --git a/src/app/action/controllers/PreProcessActionController.php b/src/app/action/controllers/PreProcessActionController.php
index 21d849bba81..cb5cf93c997 100755
--- a/src/app/action/controllers/PreProcessActionController.php
+++ b/src/app/action/controllers/PreProcessActionController.php
@@ -568,7 +568,19 @@ class PreProcessActionController
             }
         }
 
-        return $response->withJson(['signatureBookEnabled' => $signatureBookEnabled, 'additionalsInfos' => $additionalsInfos, 'errors' => $errors]);
+        $minimumVisaRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'minimumVisaRole']);
+        $maximumSignRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'maximumSignRole']);
+
+        $minimumVisaRole = !empty($minimumVisaRole['param_value_int']) ? $minimumVisaRole['param_value_int'] : 0;
+        $maximumSignRole = !empty($maximumSignRole['param_value_int']) ? $maximumSignRole['param_value_int'] : 0;
+
+        return $response->withJson([
+            'signatureBookEnabled' => $signatureBookEnabled,
+            'additionalsInfos'     => $additionalsInfos,
+            'errors'               => $errors,
+            'minimumVisaRole'      => $minimumVisaRole,
+            'maximumSignRole'      => $maximumSignRole
+        ]);
     }
 
     public function checkExternalNoteBook(Request $request, Response $response, array $aArgs)
@@ -1011,7 +1023,13 @@ class PreProcessActionController
             }
         }
 
-        return $response->withJson(['resourcesInformations' => $resourcesInformations]);
+        $minimumVisaRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'minimumVisaRole']);
+        $maximumSignRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'maximumSignRole']);
+
+        $minimumVisaRole = !empty($minimumVisaRole['param_value_int']) ? $minimumVisaRole['param_value_int'] : 0;
+        $maximumSignRole = !empty($maximumSignRole['param_value_int']) ? $maximumSignRole['param_value_int'] : 0;
+
+        return $response->withJson(['resourcesInformations' => $resourcesInformations, 'minimumVisaRole' => $minimumVisaRole, 'maximumSignRole' => $maximumSignRole]);
     }
 
     public function checkContinueVisaCircuit(Request $request, Response $response, array $args)
diff --git a/src/app/entity/controllers/ListInstanceController.php b/src/app/entity/controllers/ListInstanceController.php
index 24f889cb86b..5a702433166 100755
--- a/src/app/entity/controllers/ListInstanceController.php
+++ b/src/app/entity/controllers/ListInstanceController.php
@@ -20,6 +20,7 @@ use Entity\models\ListInstanceHistoryModel;
 use Entity\models\ListInstanceModel;
 use Group\controllers\PrivilegeController;
 use History\controllers\HistoryController;
+use Parameter\models\ParameterModel;
 use Resource\controllers\ResController;
 use Resource\models\ResModel;
 use Respect\Validation\Validator;
@@ -357,6 +358,14 @@ class ListInstanceController
             return $response->withStatus(400)->withJson(['errors' => 'Route params type is empty or not valid']);
         }
 
+        if ($args['type'] == 'visaCircuit') {
+            $minimumVisaRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'minimumVisaRole']);
+            $maximumSignRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'maximumSignRole']);
+
+            $minimumVisaRole = !empty($minimumVisaRole['param_value_int']) ? $minimumVisaRole['param_value_int'] : 0;
+            $maximumSignRole = !empty($maximumSignRole['param_value_int']) ? $maximumSignRole['param_value_int'] : 0;
+        }
+
         DatabaseModel::beginTransaction();
 
         foreach ($body['resources'] as $resourceKey => $resource) {
@@ -448,6 +457,26 @@ class ListInstanceController
                 ];
             }
 
+            if ($args['type'] == 'visaCircuit' && (!empty($minimumVisaRole) || !empty($maximumSignRole))) {
+                $nbVisaRole = 0;
+                $nbSignRole = 0;
+                foreach ($listInstances as $listInstance) {
+                    if ($listInstance['item_mode'] == 'visa') {
+                        $nbVisaRole++;
+                    } elseif ($listInstance['item_mode'] == 'sign') {
+                        $nbSignRole++;
+                    }
+                }
+                if ($minimumVisaRole != 0 && $nbVisaRole < $minimumVisaRole) {
+                    DatabaseModel::rollbackTransaction();
+                    return $response->withStatus(400)->withJson(['errors' => "Body resources[{$resourceKey}] listInstances does not have enough visa users", 'lang' => 'notEnoughVisaUser']);
+                }
+                if ($maximumSignRole != 0 && $nbSignRole > $maximumSignRole) {
+                    DatabaseModel::rollbackTransaction();
+                    return $response->withStatus(400)->withJson(['errors' => "Body resources[{$resourceKey}] listInstances have too many sign users", 'lang' => 'tooManySignUser']);
+                }
+            }
+
             foreach ($listInstances as $key => $listInstance) {
                 ListInstanceModel::create([
                     'res_id'                => $resource['resId'],
diff --git a/src/app/entity/controllers/ListTemplateController.php b/src/app/entity/controllers/ListTemplateController.php
index f4ec8e0e3dc..e068e23d484 100755
--- a/src/app/entity/controllers/ListTemplateController.php
+++ b/src/app/entity/controllers/ListTemplateController.php
@@ -643,6 +643,14 @@ class ListTemplateController
         ValidatorModel::stringType($args, ['type']);
         ValidatorModel::intVal($args, ['entityId']);
 
+        $minimumVisaRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'minimumVisaRole']);
+        $maximumSignRole = ParameterModel::getById(['select' => ['param_value_int'], 'id' => 'maximumSignRole']);
+
+        $minimumVisaRole = !empty($minimumVisaRole['param_value_int']) ? $minimumVisaRole['param_value_int'] : 0;
+        $maximumSignRole = !empty($maximumSignRole['param_value_int']) ? $maximumSignRole['param_value_int'] : 0;
+
+        $nbVisaRole = 0;
+        $nbSignRole = 0;
         $destFound = false;
         foreach ($args['items'] as $item) {
             if ($destFound && $item['mode'] == 'dest') {
@@ -674,6 +682,20 @@ class ListTemplateController
             } elseif ($args['type'] == 'opinionCircuit' && !PrivilegeController::hasPrivilege(['privilegeId' => 'avis_documents', 'userId' => $item['id']])) {
                 return ['errors' => 'item has not enough privileges'];
             }
+            if ($item['mode'] == 'visa') {
+                $nbVisaRole++;
+            } elseif ($item['mode'] == 'sign') {
+                $nbSignRole++;
+            }
+        }
+
+        if ($args['type'] == 'visaCircuit') {
+            if ($minimumVisaRole != 0 && $nbVisaRole < $minimumVisaRole) {
+                return ['errors' => 'Template does not have enough visa users'];
+            }
+            if ($maximumSignRole != 0 && $nbSignRole > $maximumSignRole) {
+                return ['errors' => 'Template have too many sign users'];
+            }
         }
 
         return true;
diff --git a/src/lang/lang-en.json b/src/lang/lang-en.json
index 836ba246470..406b6ef14a9 100644
--- a/src/lang/lang-en.json
+++ b/src/lang/lang-en.json
@@ -2168,5 +2168,7 @@
     "chooseNewVisaUser": "is in <b>visa / signature</b> of some mails, please choose a <b>user replacement</b>",
     "hideModal": "Hide this modal",
     "noPreviousValid": "No valid previous user",
-    "youCannotUnsign": "You do not have the right to <b>unsign</b> this document. You must be the person who signed this document."
-}
\ No newline at end of file
+    "youCannotUnsign": "You do not have the right to <b>unsign</b> this document. You must be the person who signed this document.",
+    "notEnoughVisaUser": "Not enough approvers",
+    "tooManySignUser": "Too many signatories"
+}
diff --git a/src/lang/lang-fr.json b/src/lang/lang-fr.json
index b85be2b2df2..050c95e7df1 100644
--- a/src/lang/lang-fr.json
+++ b/src/lang/lang-fr.json
@@ -2160,5 +2160,7 @@
     "chooseNewVisaUser": "est en <b>visa / signature</b> de certains courriers, veuillez choisir un utilisateur de <b>remplacement</b>",
     "hideModal": "Ne plus afficher cette fenêtre",
     "noPreviousValid": "Aucun utilisateur précédent valide",
-    "youCannotUnsign" : "Vous n'avez pas le droit de <b>dé-signer</b> ce document. Vous devez ếtre la personne qui a signé ce document."
+    "youCannotUnsign" : "Vous n'avez pas le droit de <b>dé-signer</b> ce document. Vous devez ếtre la personne qui a signé ce document.",
+    "notEnoughVisaUser": "Nombre de viseur insuffisant",
+    "tooManySignUser": "Nombre de signataire maximum dépassé"
 }
-- 
GitLab