From a0d2ca65f943f9143e6383617cbeaf42f8fd357c Mon Sep 17 00:00:00 2001 From: xdrm-brackets Date: Sun, 11 Mar 2018 19:34:11 +0100 Subject: [PATCH] [webpack.ue.view] [repo.ue] [module.ue] implemented CREATE|DELETE|UPDATE (but BUGGGS EVERYWHERE !!!) --- build/api/core/Checker.php | 5 ++ build/api/module/ueController.php | 104 ++++++++++++++++++++++++++++++ build/database/repo/ue.php | 40 ++++++------ config/modules.json | 24 ++++++- webpack/component/ue/view.vue | 5 +- webpack/data/ue.js | 59 ++++++++--------- 6 files changed, 181 insertions(+), 56 deletions(-) diff --git a/build/api/core/Checker.php b/build/api/core/Checker.php index f2657ee..14eaf46 100755 --- a/build/api/core/Checker.php +++ b/build/api/core/Checker.php @@ -91,6 +91,11 @@ return $checker && is_numeric($value) && $value <= 2147483647 && $value >= 0; break; + // Entier relatif (neg ou pos) + case 'int': + return $checker && is_int($value); + break; + // String quelconque (peut etre vide) case 'text': return $checker && is_string($value); diff --git a/build/api/module/ueController.php b/build/api/module/ueController.php index 7b1917d..a1e891b 100644 --- a/build/api/module/ueController.php +++ b/build/api/module/ueController.php @@ -42,6 +42,66 @@ class ueController{ } + /* (2) Creates a new UE + * + * @code The code of the UE + * @label The UE label (name) + * @required If the UE is required + * @volumeCours The UE required volume of COURSES + * @volumeTD The UE required volume of TD + * @volumeTP The UE required volume of TP + * @disabled [OPT] If it is disabled + * @defaultFormation [OPT] If there is a foreign key for a default formation (if only one formation) + * + * @return created_code The created UE code (if no error) + * + ---------------------------------------------------------*/ + public static function post($args){ + $code = ""; + $label = ""; + $required = false; + $volumeCours = 0; + $volumeTD = 0; + $volumeTP = 0; + $disabled = true; + $defaultFormation = null; + extract($args); + + /* Get the ue repo */ + /** @var ue $ue_repo */ + $ue_repo = Repo::getRepo('ue'); + + /* (1) Check if ue code already exists */ + $exists = $ue_repo->get($code); + + /* (2) If found -> already exists */ + if( count($exists) > 0 ) + return ['error' => new Error(Err::AlreadyExists)]; + + /* (3) Else try to create */ + $repo_rtn = $ue_repo->create( + $code, + $label, + $required, + $volumeCours, + $volumeTD, + $volumeTP, + $disabled, + $defaultFormation + ); + + + /* (4) If repo error -> return it */ + if( is_null($repo_rtn) ) + return ['error' => new Error(Err::RepoError)]; + + + /* (5) Else return UID */ + return ['created_code' => $repo_rtn]; + + } + + /* (3) Deletes an existing UE * * @code The UE code @@ -63,4 +123,48 @@ class ueController{ } + /* (4) Edits an existing UE + * + * @code The code of the UE + * @label [OPT] The UE label (name) + * @required [OPT] If the UE is required + * @volumeCours [OPT] The UE required volume of COURSES + * @volumeTD [OPT] The UE required volume of TD + * @volumeTP [OPT] The UE required volume of TP + * @disabled [OPT] If it is disabled + * @defaultFormation [OPT] If there is a foreign key for a default formation (if only one formation) + * + * @return updated Whether it has been updated + * + ---------------------------------------------------------*/ + public static function put($args){ + $code = ""; + $label = ""; + $required = false; + $volumeCours = 0; + $volumeTD = 0; + $volumeTP = 0; + $disabled = true; + $defaultFormation = null; + extract($args); + + /* Get the ue repo */ + /** @var ue $ue_repo */ + $ue_repo = Repo::getRepo('ue'); + + /* (1) Try to update */ + return ['updated' => $ue_repo->update( + $code, + $label, + $required, + $volumeCours, + $volumeTD, + $volumeTP, + $disabled, + $defaultFormation < 0 ? null : $defaultFormation + )]; + + } + + } \ No newline at end of file diff --git a/build/database/repo/ue.php b/build/database/repo/ue.php index 31037bd..49d04d4 100644 --- a/build/database/repo/ue.php +++ b/build/database/repo/ue.php @@ -18,16 +18,17 @@ class ue extends Repo_i { * * @code The code of the UE * @label The UE label (name) + * @required If the UE is required * @volumeCours The UE required volume of COURSES * @volumeTD The UE required volume of TD * @volumeTP The UE required volume of TP - * @disabled If it is disabled - * @defaultFormation If there is a foreign key for a default formation (if only one formation) + * @disabled [OPT] If it is disabled + * @defaultFormation [OPT] If there is a foreign key for a default formation (if only one formation) * * @return created_code Code of the created UE (NULL on error) * ---------------------------------------------------------*/ - public function create(string $code, string $label, bool $required, float $volumeCours, float $volumeTD, float $volumeTP, bool $disabled = false, ?int $defaultFormation = null) : ?int { + public function create(string $code, string $label, bool $required, float $volumeCours, float $volumeTD, float $volumeTP, bool $disabled = false, ?int $defaultFormation = null) : ?string { /* (1) Prepare request */ $st = $this->pdo->prepare("INSERT INTO UE(`code`, `label`, `required`, `volumeCours`, `volumeTD`, `volumeTP`, `disabled`, `Formation_idFormation`) @@ -39,14 +40,14 @@ class ue extends Repo_i { /* (3) Bind params and execute request */ $success = $st->execute([ - "code" => $code, - "label" => $label, - "required" => $required ? 1 : 0, - "volCours" => $volumeCours, - "volTD" => $volumeTD, - "volTP" => $volumeTP, - "disabled" => $disabled ? 1 : 0, - "idFormation" => $defaultFormation + ':code' => $code, + ':label' => $label, + ':required' => $required ? 1 : 0, + ':volCours' => $volumeCours, + ':volTD' => $volumeTD, + ':volTP' => $volumeTP, + ':disabled' => $disabled ? 1 : 0, + ':idFormation' => $defaultFormation ]); /* (4) Manage execution error */ @@ -54,7 +55,7 @@ class ue extends Repo_i { return null; /* (5) Return insert id */ - return $this->pdo->lastInsertId(); + return $code; } @@ -80,11 +81,11 @@ class ue extends Repo_i { $bind_param = [ ':code' => $code ]; if( !is_null($label) ){ $build_rq[] = '`label` = :label'; $bind_param[':label'] = $label; } - if( !is_null($required) ){ $build_rq[] = '`required` = :required'; $bind_param[':required'] = $required; } + if( !is_null($required) ){ $build_rq[] = '`required` = :required'; $bind_param[':required'] = $required?1:0; } if( !is_null($volumeCours) ){ $build_rq[] = '`volumeCours` = :volumeCours'; $bind_param[':volumeCours'] = $volumeCours; } if( !is_null($volumeTD) ){ $build_rq[] = '`volumeTD` = :volumeTD'; $bind_param[':volumeTD'] = $volumeTD; } if( !is_null($volumeTP) ){ $build_rq[] = '`volumeTP` = :volumeTP'; $bind_param[':volumeTP'] = $volumeTP; } - if( !is_null($disabled) ){ $build_rq[] = '`disabled` = :disabled'; $bind_param[':disabled'] = $disabled; } + if( !is_null($disabled) ){ $build_rq[] = '`disabled` = :disabled'; $bind_param[':disabled'] = $disabled?1:0; } if( !is_null($defaultFormation) ){ $build_rq[] = '`Formation_idFormation` = :defaultFormation'; $bind_param[':defaultFormation'] = $defaultFormation; } /* (2) ERROR if no updated field */ @@ -160,16 +161,17 @@ class ue extends Repo_i { * @return ues The UEs matching code (NULL on error) * ---------------------------------------------------------*/ - public function get(?String $code=null) : ?array{ + public function get(?String $code=null) : array{ /* (1) Manage if no id given */ - $cond = is_null($code) ? '' : 'AND `code` = :code'; + $cond = is_null($code) ? '' : 'WHERE `code` = :code'; $parm = is_null($code) ? [] : [':code' => $code]; /* (2) Prepare Statement */ - $st = $this->pdo->prepare("SELECT ue.code, ue.label, ue.disabled, ue.required, ue.volumeCours, ue.volumeTD, ue.volumeTP, ue.Formation_idFormation idForm, f.labelFormation labelForm - FROM `UE` ue, `Formation` f - WHERE f.idFormation = ue.Formation_idFormation + $this->pdo->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION); + $st = $this->pdo->prepare("SELECT ue.code, ue.label, ue.disabled, ue.required, ue.volumeCours, ue.volumeTD, ue.volumeTP, IFNULL(ue.Formation_idFormation, -1) idForm, f.labelFormation labelForm + FROM `UE` ue + LEFT JOIN Formation f ON ue.Formation_idFormation = f.idFormation $cond ORDER BY `ue`.`label` ASC"); diff --git a/config/modules.json b/config/modules.json index e519d6b..cbb732b 100644 --- a/config/modules.json +++ b/config/modules.json @@ -186,7 +186,7 @@ "per": [], "par": { "code": { "des": "UE code.", "typ": "varchar(4,20,alphanumeric)" }, - "label": { "des": "UE label", "typ": "varchar(2,30,alphanumeric)" }, + "label": { "des": "UE label", "typ": "varchar(4,30,alphanumeric)" }, "required": { "des": "If UE is required", "typ": "bool" }, "volumeCours": { "des": "Number of course hours for UE", "typ": "float" }, "volumeTD": { "des": "Number of TD hours for UE", "typ": "float" }, @@ -195,7 +195,7 @@ "defaultFormation": { "des": "UID for optional default formation", "typ": "id", "opt": true } }, "out": { - "created_code": { "des": "Created UE code", "typ": "varchar(2,30,alphanumeric)" } + "created_code": { "des": "Created UE code", "typ": "varchar(4,20,alphanumeric)" } } }, @@ -203,7 +203,7 @@ "des": "Get one or all UE", "per": [], "par": { - "URL0": { "des": "Optional UE code.", "typ": "varchar(2,30,alphanumeric)", "ren": "code", "opt": true } + "URL0": { "des": "Optional UE code.", "typ": "varchar(4,20,alphanumeric)", "ren": "code", "opt": true } }, "out": { "ues": { "des": "UE list", "typ": "array" } @@ -220,6 +220,24 @@ "out": { "deleted": { "des": "Whether it has been deleted", "typ": "boolean" } } + }, + + "PUT": { + "des": "Edits an existing UE", + "per": [], + "par": { + "URL0": { "des": "UE code.", "typ": "varchar(4,20,alphanumeric)", "ren": "code" }, + "label": { "des": "UE label", "typ": "varchar(4,30,alphanumeric)", "opt": true }, + "required": { "des": "If UE is required", "typ": "bool", "opt": true }, + "volumeCours": { "des": "Number of course hours for UE", "typ": "float", "opt": true }, + "volumeTD": { "des": "Number of TD hours for UE", "typ": "float", "opt": true }, + "volumeTP": { "des": "Number of TP hours for UE", "typ": "float", "opt": true }, + "disabled": { "des": "Whether UE is disabled", "typ": "boolean", "opt": true }, + "defaultFormation": { "des": "UID for optional default formation (-1 for none)", "typ": "int", "opt": true } + }, + "out": { + "updated": { "des": "Whether the UE has been updated", "typ": "boolean" } + } } diff --git a/webpack/component/ue/view.vue b/webpack/component/ue/view.vue index 48e79d9..a51c9e3 100644 --- a/webpack/component/ue/view.vue +++ b/webpack/component/ue/view.vue @@ -51,7 +51,7 @@ - {{ ue.labelForm }} + {{ ue.labelForm || 'Pas de formation par défaut' }} - () + ({{ ue.code }}) + diff --git a/webpack/data/ue.js b/webpack/data/ue.js index 01c4b0a..64ab2dc 100644 --- a/webpack/data/ue.js +++ b/webpack/data/ue.js @@ -37,7 +37,6 @@ api.call('GET formation', {}, function(rs){ - /* (2) Manage Instant Search (IS) ---------------------------------------------------------*/ /* (1) Define global timeout index */ @@ -135,11 +134,11 @@ gstore.add('ic_handler', function(){ if( isNaN(form) ) errors.push('La formation de l\'UE est manquante'); /* (5.5.2) Check label */ - if( !/^.{4,}$/.test(label) ) + if( typeof label !== 'string' || label.length < 4 ) errors.push('Le label doit comprendre faire au moins 4 caractères'); /* (5.5.3) Check code */ - if( !/^[A-Z0-9 -]{4,20}$/.test(code) ) + if( !/^[A-Z0-9]{4,20}$/.test(code) ) errors.push('Le code doit comprendre de 4 à 20 lettres/chiffres'); /* (5.5.4) Check volumes */ @@ -173,11 +172,11 @@ gstore.add('ic_handler', function(){ volumeTD: parseInt(vtd), /*TODO*/ volumeTP: parseInt(vtp), /*TODO*/ required: false, /*TODO*/ - disabled: false, /*TODO*/ + disabled: false /*TODO*/ }; // optional param - if( form == -1 ) + if( form != -1 ) rq.defaultFormation = form; /* (4.5.2) Send request */ @@ -305,7 +304,7 @@ gstore.add('edit_i', -1); /* (2) Initialize inputs */ gstore.add('edit_form', '-'); gstore.add('edit_label', ''); -gstore.add('edit_code', ''); +// gstore.add('edit_code', ''); gstore.add('edit_vol', { c: '', td: '', tp: ''}); /* (3) Initialize error message */ @@ -348,7 +347,7 @@ gstore.add('ie_handler', function(ue_i){ /* (5.3) Trim text input */ gstore.get.edit_label = gstore.get.edit_label.trim(); - gstore.get.edit_code = gstore.get.edit_code.toString().trim().toUpperCase(); + // gstore.get.edit_code = gstore.get.edit_code.toString().trim().toUpperCase(); gstore.get.edit_vol.c = gstore.get.edit_vol.c.toString().trim(); gstore.get.edit_vol.td = gstore.get.edit_vol.td.toString().trim(); gstore.get.edit_vol.tp = gstore.get.edit_vol.tp.toString().trim(); @@ -356,7 +355,7 @@ gstore.add('ie_handler', function(ue_i){ /* (5.4) Store values locally */ var form = gstore.get.edit_form; var label = gstore.get.edit_label; - var code = gstore.get.edit_code; + // var code = gstore.get.edit_code; var vco = gstore.get.edit_vol.c; var vtd = gstore.get.edit_vol.td; var vtp = gstore.get.edit_vol.tp; @@ -368,12 +367,12 @@ gstore.add('ie_handler', function(ue_i){ if( isNaN(form) ) errors.push('La formation de l\'UE est manquante'); /* (5.5.2) Check label */ - if( !/^.{4,}$/.test(label) ) + if( typeof label !== 'string' || label.length < 4 ) errors.push('Le label doit comprendre faire au moins 4 caractères'); /* (5.5.3) Check code */ - if( !/^[A-Z0-9 -]{4,20}$/.test(code) ) - errors.push('Le code doit comprendre de 4 à 20 lettres/chiffres'); + // if( !/^[A-Z0-9]{4,20}$/.test(code) ) + // errors.push('Le code doit comprendre de 4 à 20 lettres/chiffres'); /* (5.5.4) Check volumes */ if( vco === '' || isNaN(vco) || vco < 0 ) @@ -399,22 +398,18 @@ gstore.add('ie_handler', function(ue_i){ /* (5.7) Création de la requête */ var rq = {}; - ( label != ue.label ) && ( rq.label = label ); - ( code != ue.code ) && ( rq.code = code ); - ( vco != ue.volumeCours ) && ( rq.volumeCours = parseInt(vco) ); - ( vtd != ue.volumeTD ) && ( rq.volumeTD = parseInt(vtd) ); - ( vtp != ue.volumeTP ) && ( rq.volumeTP = parseInt(vtp) ); - ( form != ue.defaultFormation ) && ( rq.defaultFormation = form ); - - // optional form arg - if( rq.hasOwnProperty('form') && rq.form == -1 ) - rq.form = null; + ( label != ue.label ) && ( rq.label = label ); + // ( code != ue.code ) && ( rq.code = code ); + ( vco != ue.volumeCours ) && ( rq.volumeCours = parseInt(vco) ); + ( vtd != ue.volumeTD ) && ( rq.volumeTD = parseInt(vtd) ); + ( vtp != ue.volumeTP ) && ( rq.volumeTP = parseInt(vtp) ); + ( form != ue.defaultFormation ) && ( rq.defaultFormation = parseInt(form) ); (new Promise( (resolve, reject) => { popup.ask({ title: 'Confirmation de modification', - content: "La modification de l'UE "+ue.label+" ("+ue.code+") est irréversible.

Voulez-vous la modifier ?", + content: `La modification de l'UE ${ue.label} (${ue.code}) est irréversible.

Voulez-vous la modifier ?`, action: 'Modifier', type: 'search' }, (popup_rs) => { popup_rs && resolve() }); @@ -425,10 +420,10 @@ gstore.add('ie_handler', function(ue_i){ return new Promise( (resolve, reject) => { /* (5.8.1) Update UE */ - api.call('PUT ue/'+ue.code, rq, function(rs){ + api.call(`PUT ue/${ue.code}`, rq, function(rs){ /* (5.8.1.1) Abort on error */ - if( rs.error !== 0 || rs.updated !== true ) + if( rs.error != 0 || rs.updated != true ) return reject(rs.error); /* (5.8.1.2) Success */ @@ -442,21 +437,21 @@ gstore.add('ie_handler', function(ue_i){ }).then(function(){ /* (5.9.1) update VueJS element */ - gstore.get.ues[ue_i].label = label; - gstore.get.ues[ue_i].code = code; - gstore.get.ues[ue_i].idForm = form; - gstore.get.ues[ue_i].volumeCours = vco; - gstore.get.ues[ue_i].volumeTD = vtd; - gstore.get.ues[ue_i].volumeTP = vtp; + gstore.get.ues[ue_i].label = label; + gstore.get.ues[ue_i].code = code; + gstore.get.ues[ue_i].idForm = parseInt(form); + gstore.get.ues[ue_i].volumeCours = parseInt(vco); + gstore.get.ues[ue_i].volumeTD = parseInt(vtd); + gstore.get.ues[ue_i].volumeTP = parseInt(vtp); /* (5.9.2) Try to set the formation label */ - var fi = gstore.get.categories.map( (data, i) => { return ( data.idForm && data.idForm == form ) ? i : ''; }).join(''); + var fi = gstore.get.formations.map( (data, i) => { return ( data.idForm && data.idForm == form ) ? i : ''; }).join(''); /* (5.9.3) Exit if not found */ if( isNaN(fi) ) return gstore.add('edit_i', -1); /* (5.9.4) If found -> set formation label */ - gstore.get.ues[ue_i].labelForm = gstore.get.categories[fi].labelForm; + gstore.get.ues[ue_i].labelForm = gstore.get.formations[fi].labelForm; /* (5.9.5) Remove edit mode */ gstore.add('edit_i', -1);