Bonjour,
Voici quelque temps que je suis confronté à un petit problème que je n'arrive pas à résoudre:
Voilà, durant le développement d'un petit site perso j'ai pris le parti pris d'effectuer les actions sur ma DB MySQL uniquement via des stored procedures. Conséquence j'ai remarqué que la plupart de mes requêtes avaient la même structure et j'ai donc essayé de les encapsuler dans une fonction PHP que j'appelle call_stored_procedure.
Plus précisément, je vais prendre l'exemple de la création d'une "compagnie". Mon formulaire fait appel à la classe 'creation' via l'action suivante (je retire volontairement les includes, le problème ne réside pas là):
Définie comme ci-dessous (remarquez que la classe est encore loin d'être achevée):
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13 $creation = new Creation(); if($creation->valid()){ if($creation->submit()){ header("Location: index.php?request=creation&message=success"); exit; } else{ header("Location: index.php?request=creation&message=error_raised"); exit; } }
La fonction call_stored_procedure est elle définie ainsi:
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32 class Creation{ private $parameters_in; private $parameters_out; public function __construct(){ $this->parameters_in = array(); $this->parameters_out= array(); $this->parameters_in['company_code_name']= $_POST['company_code_name']; $this->parameters_in['company_name'] = $_POST['company_name']; $this->parameters_in['password_company'] = $_POST['password_company']; $this->parameters_in['iban'] = $_POST['iban']; $this->parameters_in['enterprise_type'] = $_POST['enterprise_type']; $this->parameters_in['enterprise_number']= $_POST['enterprise_number']; $this->parameters_in['username'] = $_POST['username']; $this->parameters_in['password_user'] = $_POST['password_user']; $this->parameters_in['last_name'] = $_POST['last_name']; $this->parameters_in['first_name'] = $_POST['first_name']; $this->parameters_in['date_birth'] = $_POST['date_birth']; $this->parameters_in['activation_canal'] = $_POST['activation_canal']; $this->parameters_in['contact_value'] = $_POST['contact_value']; } public function valid(){ return true; } public function submit() { $result = call_stored_procedure('create_company',$this->parameters_in,$this->parameters_out); } }
J'attire l'attention que la partie "log" est juste là à titre de débogage
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69 function call_stored_procedure($stored_procedure,$arguments_in,$arguments_out){ $connection = new Connection(); /** STEP 1: Prepare the call to the stored procedure **/ $arguments_list = ''; $values_list = ''; foreach($arguments_in AS $arg => $value){ if(empty($arguments_list)){ $arguments_list .= ":" . $arg; $values_list .= "'" . $value . "'"; } else{ $arguments_list .= ",:" . $arg; $values_list .= ",'" . $value . "'"; } } foreach($arguments_out AS $arg){ $arguments_list .= ",@" . $arg; $values_list .= ",@" . $arg; } $stmt= $connection->prepare("CALL " . $stored_procedure . " (" . $arguments_list . ");"); $date = new DateTime(); $file = fopen("logs/Log" . $date->format("Y-m-d") . ".txt","a"); foreach($arguments_in AS $arg => $value){ fwrite($file,"\$stmt->bindParam(\":" . $arg . "\",\"" . $value . "\");\n"); $stmt->bindParam(":" . $arg,$value); } fclose($file); /** STEP 2: Log the request **/ $date = new DateTime(); $file = fopen("logs/Log" . $date->format("Y-m-d") . ".txt","a"); fwrite($file,"[" . $date->format("H:i:s.u") . "] CALL " . $stored_procedure . " (" . $arguments_list . ");\n"); fwrite($file,"[" . $date->format("H:i:s.u") . "] CALL " . $stored_procedure . " (" . $values_list . ");\n"); fclose($file); /** STEP 3: Perform the call to the stored procedure **/ try{ $stmt->execute(); } catch (PDOException $e) { print $e->getMessage(); exit; } /** STEP 4: Retrieve the content of the MySQL variables **/ $results = array(); foreach($arguments_out AS $arg){ $stmt = $connection->prepare("SELECT @" . $arg . " AS " . $arg); try{ $stmt->execute(); $results[$arg] = $stmt->fetchAll(PDO::FETCH_ASSOC)['0'][$arg]; } catch(PDOException $e) { print $e->getMessage(); exit; } } /** END **/ return $results; }
Quand je teste localement de créer une compagnie, je me retrouve avec une exception levée:
La logique voudrait que quelque chose ne fonctionne pas lors de l'appel à la stored procedure. Mais dans le fichier de log, je vois que le résultat de la ligne ci-dessous de call_stored_procedure:
est l'enregistrement suivant:
Code : Sélectionner tout - Visualiser dans une fenêtre à part $stmt= $connection->prepare("CALL " . $stored_procedure . " (" . $arguments_list . ");");
[13:28:06.000000] CALL create_company ('panos2','panos2','panos2','BE121234123414','TVA','0123456782','bambi','bambi','Bambinos','Bambi','1986-06-05','email','bambi@foret.be');
Et, ce qui est frustrant, c'est que si je vais directement exécuter cette commande en ligne de commande dans MySQL, voici le résultat:
Autrement dit, la requête est bien formée (Je retrouve bien de nouveaux records en DB après vérification).
Est-ce que quelqu'un à déjà rencontrer ce problème ou voit où se trouve le problème?
Merci d'avance!
Partager