From 718e4029a7ca5475b67e034f6b23dcfccfc1d7bb Mon Sep 17 00:00:00 2001 From: xdrm-brackets Date: Sat, 23 Jul 2016 15:23:46 +0200 Subject: [PATCH] ORM: Insertion fonctionnelle --- manager/ORM/Rows.php | 234 +++++++++++++++++++++++++++++++++++++++++- manager/repo/user.php | 147 ++++++++------------------ test/automate.php | 54 ++++++---- 3 files changed, 308 insertions(+), 127 deletions(-) diff --git a/manager/ORM/Rows.php b/manager/ORM/Rows.php index 5344be8..b7081ce 100644 --- a/manager/ORM/Rows.php +++ b/manager/ORM/Rows.php @@ -5,6 +5,10 @@ use \manager\Database; + // TODO: Suppression (avec prise en compte des jointures (sur le modèle de 'edit') + // TODO: Insertion + + class Rows{ @@ -17,6 +21,8 @@ const COND_SUPEQ = '>='; const COND_LIKE = 'LIKE'; + const DEFAULT = '__DEFAULT__'; // Valeur DEFAULT (pour insertion) + /* Attributs */ private $where; // Tableau associatif contenant les conditions private $select; // Tableau contenant la liste des champs à afficher @@ -354,7 +360,7 @@ =========================================================*/ /* (1) Si c'est pas un tableau, erreur */ if( !is_array($updates) ) - return $this; + return false; /* (2) On retire les champ inconnus / clés primaires */ $cleared = []; @@ -381,7 +387,7 @@ /* (4) Si on a plus de champ, on retourne l'object courant */ if( count($cleared) == 0 ) - return $this; + return false; /* [1] Rédaction de la clause UPDATE @@ -478,13 +484,235 @@ + /* AJOUTE UNE ENTREE DANS LA TABLE + * + * @entry Tableau associatif de la forme (colonne => valeur) + * + * @return status Retourne si TRUE ou FALSE les entrées ont bien été supprimées + * + */ + public function insert($entry){ + /* [0] On vérifie les paramètres + =========================================================*/ + /* (1) Si c'est pas un tableau, erreur */ + if( !is_array($entry) ) + return false; + + /* (2) On retire les champ inconnus */ + $cleared = []; + + // Pour chaque entrée du tableau + foreach($entry as $field=>$value) + if( isset($this->schema['columns'][$field]) ) // Champ existe + $cleared[$field] = $value; + + /* (3) On vérifie les types des champs */ + foreach($cleared as $field=>$value){ + + $type = $this->schema['columns'][$field]['type']; + + // {1} Si de type INT/FLOAT et pas numérique, on retire le champ // + if( in_array($type, ['int', 'float']) && !is_numeric($value) && $value != self::DEFAULT ) + unset($cleared[$field]); + + // {2} Si de type TEXT/VARCHAR et pas string, on retire le champ // + if( in_array($type, ['text', 'varchar']) && !is_string($value) && $value != self::DEFAULT ) + unset($cleared[$field]); + } + + /* (4) Si il manque des données, erreur */ + if( count($cleared) != count($this->schema['columns']) ) + return false; + + + /* [1] On crée la requête + =========================================================*/ + /* (1) Clause INSERT INTO table */ + $requestS = 'INSERT INTO '.$this->schema['table']."("; + + /* (2) Clause : table(col1, col2, ...) */ + $c = 0; + foreach($cleared as $field=>$value){ + if( $c > 0 ) $requestS .= ', '; + $requestS .= $field; + + $c++; + } + + // Fin de clause + $requestS .= ")\n"; + + /* (3) Clause : VALUES(val1, val2, ...) */ + $requestS .= 'VALUES('; + + $c = 0; + foreach($cleared as $field=>$value){ + if( $c > 0 ) $requestS .= ', '; + + if( $value == self::DEFAULT) $requestS .= 'DEFAULT'; // On insère directement les valeurs 'DEFAULT' + else $requestS .= ':insert_'.$field; + + $c++; + } + + // Fin de clause + $requestS .= ")"; + + + + /* [2] On bind les paramètres et exécute la requête + =========================================================*/ + /* (0) On initialise la requête et les paramètres */ + $request = Database::getPDO()->prepare($requestS.';'); + $binded = []; + + /* (1) On bind les paramètres */ + foreach($cleared as $field=>$value) + if( $value != self::DEFAULT ) + $binded[':insert_'.$field] = $value; + + + + /* [3] On exécute la requête et envoie le status + =========================================================*/ + $inserted = $request->execute($binded); + + // On retourne le status + return $inserted; + } + + + + /* SUPPRIME LES ENTREES * * @return status Retourne si TRUE ou FALSE les entrées ont bien été supprimées * */ - public function delete(){} + public function delete(){ + /* [0] Vérification des paramètres + =========================================================*/ + /* (1) Si c'est pas un tableau, erreur */ + if( !is_array($updates) ) + return false; + /* (2) On retire les champ inconnus / clés primaires */ + $cleared = []; + + // Pour chaque entrée du tableau + foreach($updates as $field=>$value) + if( isset($this->schema['columns'][$field]) && !$this->schema['columns'][$field]['primary'] ) // Champ existe et n'est pas clé primaire + $cleared[$field] = $value; + + /* (3) On vérifie les types des champs */ + foreach($cleared as $field=>$value){ + + $type = $this->schema['columns'][$field]['type']; + + // {1} Si de type INT/FLOAT et pas numérique, on retire le champ // + if( in_array($type, ['int', 'float']) && !is_numeric($value) ) + unset($cleared[$field]); + + // {2} Si de type TEXT/VARCHAR et pas string, on retire le champ // + if( in_array($type, ['text', 'varchar']) && !is_string($value) ) + unset($cleared[$field]); + + } + + /* (4) Si on a plus de champ, on retourne l'object courant */ + if( count($cleared) == 0 ) + return false; + + + /* [1] Rédaction de la clause UPDATE + =========================================================*/ + /* (1) On initialise la requête */ + $requestS = "UPDATE ".$this->schema['table']."\n"; + + + + /* [2] Rédaction de la clause SET + =========================================================*/ + /* (5) On met tout les champs à modifier */ + $c = 0; + foreach($cleared as $field=>$value){ + if( $c == 0 ) $requestS .= 'SET '.$field.' = :update_'.$field; + else $requestS .= "\n, ".$field.' = :update_'.$field; + $c++; + } + + $requestS .= "\n"; + + + + /* [3] On rédige la clause WHERE/AND + =========================================================*/ + /* (1) On met les conditions locales */ + $c = 0; + foreach($this->where as $field=>$conditions) + foreach($conditions as $cdt=>$value){ + if( $c == 0 ) $requestS .= 'WHERE '.$this->schema['table'].'.'.$field.' '.$value[1].' :'.$this->schema['table'].'_x_'.$field.'_'.$cdt."\n"; + else $requestS .= 'AND '.$this->schema['table'].'.'.$field.' '.$value[1].' :'.$this->schema['table'].'_x_'.$field.'_'.$cdt."\n"; + + $c++; + } + + /* (2) On ajoute les jointures */ + foreach($this->joined as $localField=>$rows){ + if( $c == 0 ) $requestS .= 'WHERE '; + else $requestS .= 'AND '; + + // {1} Clause SELECT interne // + $requestS .= $this->schema['table'].'.'.$localField." = (\n\tSELECT "; + + // Jointure du SELECT, champ joint lié au champ local + $requestS .= $rows->schema['table'].'.'.$this->schema['columns'][$localField]['references'][1]."\n"; + + // {2} Clause FROM interne // + $requestS .= "\tFROM ".$this->schema['columns'][$localField]['references'][0]."\n"; + + // {3} Clause WHERE/AND interne // + $c2 = 0; + foreach($rows->where as $field=>$conditions) + foreach($conditions as $cdt=>$value){ + if( $c2 == 0 ) $requestS .= "\tWHERE ".$rows->schema['table'].'.'.$field.' '.$value[1].' :'.$rows->schema['table'].'_x_'.$field.'_'.$cdt."\n"; + else $requestS .= "\tAND ".$rows->schema['table'].'.'.$field.' '.$value[1].' :'.$rows->schema['table'].'_x_'.$field.'_'.$cdt."\n"; + $c2++; + } + + $requestS .= "\tLIMIT 1)\n"; + } + + + /* [4] On exécute la requête et 'bind' les paramètres + =========================================================*/ + /* (0) On prépare la requête */ + $request = Database::getPDO()->prepare($requestS.';'); + $binded = []; + + /* (1) On bind tous les paramètres locaux */ + foreach($this->where as $field=>$conditions) + foreach($conditions as $cdt=>$value) + $binded[':'.$this->schema['table'].'_x_'.$field.'_'.$cdt] = $value[0]; + + /* (3) On bind tous les paramètres des jointures */ + foreach($this->joined as $rows) + foreach($rows->where as $field=>$conditions) + foreach($conditions as $cdt=>$value) + $binded[':'.$rows->schema['table'].'_x_'.$field.'_'.$cdt] = $value[0]; + + /* (4) On bind les nouvelles valeurs */ + foreach($cleared as $field=>$value) + $binded[':update_'.$field] = $value; + + /* [6] On exécute la requête et retourne le résultat + =========================================================*/ + /* (1) On exécute la requête */ + $updated = $request->execute($binded); + + /* (2) On retourne l'état de la requête */ + return $updated; + } diff --git a/manager/repo/user.php b/manager/repo/user.php index f8efb0e..eed1c12 100755 --- a/manager/repo/user.php +++ b/manager/repo/user.php @@ -108,22 +108,16 @@ public static function getClusters($id_warehouse, $id_user){ /* [1] On redige/execute la requete =========================================================*/ - $get_clusters = Database::getPDO()->prepare("SELECT c.* - FROM user_cluster as c, user_cluster_merge as cm, user as u - WHERE cm.id_user_cluster = c.id_user_cluster - AND cm.id_user = u.id_user - AND cm.id_user = :id_user - AND c.id_warehouse = u.id_warehouse - AND u.id_warehouse = :id_warehouse - ORDER BY c.name"); - $get_clusters->execute([ - ':id_warehouse' => $id_warehouse, - ':id_user' => $id_user - ]); + $cluster = Table::get('user_cluster') + ->whereIdWarehouse($id_warehouse) + ->select('*'); + $cluster_merge = Table::get('user_cluster_merge') + ->whereIdUser($id_user) + ->join('id_user_cluster', $cluster); /* [2] On retourne la liste des groupes =========================================================*/ - return Database::delNumeric( $get_clusters->fetchAll() ); + return $cluster_merge->fetch(); } @@ -150,12 +144,12 @@ /* [1] Verification de l'unicite de code+username (si differents) =========================================================*/ // On recupere les utilisateurs ayant le meme code ou username (si existent) - // pour éviter les collisions (car code/username doivent être uniquent) + // pour éviter les collisions (car code/username doivent être uniques) $getbycode = self::getByCode($id_warehouse, $code); $getbyusername = self::getByUsername($id_warehouse, $username); - $check_unique = is_array($getbycode) && $getbycode['id_user'] == $id_user || !is_array($getbycode); - $check_unique = $check_unique && is_array($getbyusername) && $getbyusername['id_user'] == $id_user || !is_array($getbyusername); + $check_unique = isset($getbycode['id_user']) && $getbycode['id_user'] == $id_user || !is_array($getbycode); + $check_unique = $check_unique && isset($getbyusername['id_user']) && $getbyusername['id_user'] == $id_user || !is_array($getbyusername); // Si un utilisateur a deja ce code ou cet username (sauf lui), on renvoie une erreur if( !$check_unique ) @@ -163,39 +157,22 @@ /* [2] Modification de l'utilisateur =========================================================*/ - $edit_user = Database::getPDO()->prepare("UPDATE user - SET code = :code, - username = :username, - firstname = :firstname, - lastname = :lastname, - mail = :mail - WHERE id_user = :id_user - AND id_warehouse = :id_warehouse"); - $edit_user->execute([ - ':code' => $code, - ':username' => $username, - ':firstname' => $firstname, - ':lastname' => $lastname, - ':mail' => $mail, - ':id_user' => $id_user, - ':id_warehouse' => $id_warehouse - ]); + $edited = Table::get('user') + ->whereId($id_user) + ->whereIdWarehouse($id_warehouse) + ->edit([ + 'code' => $code, + 'username' => $username, + 'firstname' => $firstname, + 'lastname' => $lastname, + 'mail' => $mail, + ]); /* [3] On retourne si tout a ete modifie, si erreur =========================================================*/ - $check_user = self::getById($id_warehouse, $id_user); - - $checker = $check_user['id_user'] == $id_user; - $checker = $checker && $check_user['code'] == $code; - $checker = $checker && $check_user['username'] == $username; - $checker = $checker && $check_user['firstname'] == $firstname; - $checker = $checker && $check_user['lastname'] == $lastname; - $checker = $checker && $check_user['mail'] == $mail; - - // On retourne l'etat de la modification - return $checker; + return $edited; } @@ -248,24 +225,13 @@ public static function getById($id_warehouse, $id_user){ /* [1] On rédige/execute la requête =========================================================*/ - $get = Database::getPDO()->prepare("SELECT u.id_user, u.code, u.username, u.firstname, u.lastname, u.mail - FROM user as u - WHERE u.id_warehouse = :id_warehouse - AND u.id_user = :id_user"); - $get->execute([ - ':id_warehouse' => $id_warehouse, - ':id_user' => $id_user - ]); + $user = Table::get('user') + ->whereIdWarehouse($id_warehouse) + ->whereIdUser($id_user) + ->select(['id_user', 'code', 'username', 'firstname', 'lastname', 'mail']) + ->unique(); - /* [2] Gestion des données - =========================================================*/ - $found = $get->fetch(); - - // Si aucun résultat - if( $found === false ) - return false; - - return Database::delNumeric( $found, true ); + return $user->fetch(); } @@ -287,24 +253,13 @@ public static function getByCode($id_warehouse, $code){ /* [1] On rédige/execute la requête =========================================================*/ - $get = Database::getPDO()->prepare("SELECT u.id_user, u.code, u.username, u.firstname, u.lastname, u.mail - FROM user as u - WHERE u.id_warehouse = :id_warehouse - AND u.code = :code"); - $get->execute([ - ':id_warehouse' => $id_warehouse, - ':code' => $code - ]); + $user = Table::get('user') + ->whereIdWarehouse($id_warehouse) + ->whereCode($code) + ->select(['id_user', 'code', 'username', 'firstname', 'lastname', 'mail']) + ->unique(); - /* [2] Gestion des données - =========================================================*/ - $found = $get->fetch(); - - // Si aucun résultat - if( $found === false ) - return false; - - return Database::delNumeric( $found, true ); + return $user->fetch(); } @@ -326,24 +281,13 @@ public static function getByUsername($id_warehouse, $username){ /* [1] On rédige/execute la requête =========================================================*/ - $get = Database::getPDO()->prepare("SELECT u.id_user, u.code, u.username, u.firstname, u.lastname, u.mail - FROM user as u - WHERE u.id_warehouse = :id_warehouse - AND u.username = :username"); - $get->execute([ - ':id_warehouse' => $id_warehouse, - ':username' => $username - ]); + $user = Table::get('user') + ->whereIdWarehouse($id_warehouse) + ->whereUsername($username) + ->select(['id_user', 'code', 'username', 'firstname', 'lastname', 'mail']) + ->unique(); - /* [2] Gestion des données - =========================================================*/ - $found = $get->fetch(); - - // Si aucun résultat - if( $found === false ) - return false; - - return Database::delNumeric( $found, true ); + return $user->fetch(); } @@ -363,16 +307,11 @@ public static function getAll($id_warehouse){ /* [1] On rédige/execute la requête =========================================================*/ - $get = Database::getPDO()->prepare("SELECT u.id_user, u.code, u.username, u.firstname, u.lastname, u.mail - FROM user as u - WHERE u.id_warehouse = :id_warehouse"); - $get->execute([ - ':id_warehouse' => $id_warehouse - ]); + $user = Table::get('user') + ->whereIdWarehouse($id_warehouse) + ->select(['id_user', 'code', 'username', 'firstname', 'lastname', 'mail']); - /* [2] Gestion des données - =========================================================*/ - return Database::delNumeric( $get->fetchAll() ); + return $user->fetch(); } diff --git a/test/automate.php b/test/automate.php index 389d344..3d4069d 100755 --- a/test/automate.php +++ b/test/automate.php @@ -366,34 +366,48 @@ // ]); - $id_user = 1; + $id_user = 10; $id_warehouse = 7; + $code = '13-34-56-67'; + $username = '13'; + $firstname = '12'; + $lastname = '12'; + $mail = '12@ds.com'; - $get_clusters = Database::getPDO()->prepare("SELECT c.* - FROM user_cluster as c, user_cluster_merge as cm, user as u - WHERE cm.id_user_cluster = c.id_user_cluster - AND cm.id_user = u.id_user - AND c.id_warehouse = u.id_warehouse - AND cm.id_user = :id_user - AND u.id_warehouse = :id_warehouse - ORDER BY c.name"); - $get_clusters->execute([ - ':id_warehouse' => $id_warehouse, - ':id_user' => $id_user - ]); - var_dump( Database::delNumeric($get_clusters->fetchAll()) ); + // $edit_user = Database::getPDO()->prepare("UPDATE user + // SET code = :code, + // username = :username, + // firstname = :firstname, + // lastname = :lastname, + // mail = :mail + // WHERE id_user = :id_user + // AND id_warehouse = :id_warehouse"); + // $edit_user->execute([ + // ':code' => $code, + // ':username' => $username, + // ':firstname' => $firstname, + // ':lastname' => $lastname, + // ':mail' => $mail, + // ':id_user' => $id_user, + // ':id_warehouse' => $id_warehouse + // ]); // With ORM - $c = Table::get('user_cluster')->whereIdWarehouse($id_warehouse)->select('*'); - $cm = Table::get('user_cluster_merge') - ->whereIdUser($id_user) - ->join('id_user_cluster', $c); - $clusters = $cm->fetch(); + $insert = Table::get('user') + ->insert([ + 'id_user' => Rows::DEFAULT, + 'id_warehouse' => $id_warehouse, + 'code' => $code, + 'username' => $username, + 'firstname' => $firstname, + 'lastname' => $lastname, + 'mail' => $mail, + ]); - var_dump($clusters); + var_dump($insert); ?>