La documentation russe est disponible pour tout le monde
Vous pouvez le télécharger sous forme d'archive, le cloner à partir de ce site ou le télécharger via composer (lien vers packagist.org) :
composer require krugozor/database
krugozor/database
? krugozor/database
est une bibliothèque de classes PHP >= 8.0 pour un travail simple, pratique, rapide et sécurisé avec la base de données MySql, en utilisant l'extension PHP mysqli.
Les principaux inconvénients de toutes les bibliothèques pour travailler avec la base de données mysql en PHP sont :
int
et float
.krugozor/database
est une classe pour travailler avec MySqlmysqli
et mysqli_result
pour créer les méthodes avec lesquelles vous devez travailler.krugozor/database
?La plupart des wrappers de divers pilotes de base de données sont un tas de code inutile avec une architecture dégoûtante. Leurs auteurs, ne comprenant pas eux-mêmes le but pratique de leurs wrappers, les transforment en une sorte de générateurs de requêtes (sql builder), de bibliothèques ActiveRecord et d'autres solutions ORM.
La bibliothèque krugozor/database
n'est rien de ce qui précède. Il s'agit simplement d'un outil pratique pour travailler avec du SQL standard dans le cadre du SGBD MySQL - et rien de plus !
Espaces réservés : marqueurs typés spéciaux qui sont écrits dans la chaîne de requête SQL au lieu de valeurs explicites (paramètres de requête) . Et les valeurs elles-mêmes sont transmises "plus tard", comme arguments ultérieurs à la méthode principale qui exécute une requête SQL :
$ result = $ db -> query (
" SELECT * FROM `users` WHERE `name` = '?s' AND `age` = ?i " ,
" d'Artagnan " , 41
);
Les paramètres de requête SQL transmis via le système d'espaces réservés sont traités par des mécanismes d'échappement spéciaux, en fonction du type d'espaces réservés. Ceux. vous n'avez plus besoin d'envelopper les variables dans les fonctions d'échappement, tapez mysqli_real_escape_string()
ou de les convertir en un type numérique comme avant :
<?php
// Previously, before each request to the DBMS, we did
// something like this (and many people still don't do it):
$ id = ( int ) $ _POST [ ' id ' ];
$ value = mysqli_real_escape_string ( $ mysql , $ _POST [ ' value ' ]);
$ result = mysqli_query ( $ mysql , " SELECT * FROM `t` WHERE `f1` = ' $ value ' AND `f2` = $ id " );
Il est désormais devenu facile d'écrire des requêtes, rapidement, et surtout, la bibliothèque krugozor/database
empêche complètement toute éventuelle injection SQL.
Les types de charges et leurs objectifs sont décrits ci-dessous. Avant de vous familiariser avec les types de charges, il est nécessaire de comprendre comment fonctionne le mécanisme de la bibliothèque.
PHP est un langage faiblement typé et un dilemme idéologique s'est posé lors du développement de cette bibliothèque. Imaginons que nous ayons un tableau avec la structure suivante :
` name ` varchar not null
` flag ` tinyint not null
et la bibliothèque DOIT (pour une raison quelconque, éventuellement indépendante de la volonté du développeur) exécuter la requête suivante :
$ db -> query (
" INSERT INTO `t` SET `name` = '?s', `flag` = ?i " ,
null , false
);
Dans cet exemple, une tentative est effectuée pour écrire une valeur null
dans le champ de texte not null
name
et un type booléen false
dans le champ numérique flag
. Que devons-nous faire dans cette situation ?
false
de la colonne tinyint
comme la valeur 0
et null
comme une chaîne vide pour la colonne name
?Au vu des questions soulevées, il a été décidé d'implémenter deux modes de fonctionnement dans cette bibliothèque.
Mysql::MODE_STRICT
, le type d'argument doit correspondre au type d'espace réservé . Par exemple, une tentative de transmission de la valeur 55.5
ou '55.5'
comme argument pour un espace réservé entier ?i
entraînera la levée d'une exception : // set strict mode
$ db -> setTypeMode (Mysql:: MODE_STRICT );
// this expression will not be executed, an exception will be thrown:
// attempt to specify a value of type "integer" for placeholder of type "double" in query template "SELECT ?i"
$ db -> query ( ' SELECT ?i ' , 55.5 );
Mysql::MODE_TRANSFORM
est défini par défaut et est un mode "tolérant" - si le type d'espace réservé et le type d'argument ne correspondent pas, il ne lève pas d'exception, mais essaie de convertir l'argument en type d'espace réservé souhaité en utilisant le Langage PHP lui-même . À propos, en tant qu'auteur de la bibliothèque, j'utilise toujours ce mode particulier, je n'ai jamais utilisé le mode strict ( Mysql::MODE_STRICT
) dans un travail réel, mais peut-être en aurez-vous spécifiquement besoin. Les transformations suivantes sont autorisées dans Mysql::MODE_TRANSFORM
:
int
(espace réservé ?i
)string
et en type double
bool
TRUE est converti en int(1)
, FALSE est converti en int(0)
null
est converti en int(0)
double
(espace réservé ?d
)string
et int
bool
TRUE devient float(1)
, FALSE devient float(0)
null
est converti en float(0)
string
de type (espace réservé ?s
)bool
TRUE est converti en string(1) "1"
, FALSE est converti en string(1) "0"
. Ce comportement est différent de la conversion bool
en int
en PHP, car souvent, en pratique, le type booléen est écrit dans MySql sous forme de nombre.numeric
est convertie en chaîne selon les règles de conversion de PHPnull
est converti en string(0) ""
null
(espace réservé ?n
)krugozor/database
? ?i
— espace réservé entier $ db -> query (
' SELECT * FROM `users` WHERE `id` = ?i ' , 123
);
Requête SQL après conversion du modèle :
SELECT * FROM ` users ` WHERE ` id ` = 123
ATTENTION! Si vous opérez sur des nombres qui sont en dehors des limites de PHP_INT_MAX
, alors :
?s
(voir ci-dessous). Le fait est que les nombres au-delà des limites PHP_INT_MAX
, PHP les interprète comme des nombres à virgule flottante. L'analyseur de la bibliothèque essaiera de convertir le paramètre en type int
, par conséquent " le résultat sera indéfini, car le float n'a pas une précision suffisante pour renvoyer le résultat correct. Dans ce cas, ni un avertissement ni même une remarque ne seront affichés ! »-php.net. ?d
— espace réservé à virgule flottante $ db -> query (
' SELECT * FROM `prices` WHERE `cost` IN (?d, ?d) ' ,
12.56 , ' 12.33 '
);
Requête SQL après conversion du modèle :
SELECT * FROM ` prices ` WHERE ` cost ` IN ( 12 . 56 , 12 . 33 )
ATTENTION! Si vous utilisez une bibliothèque pour travailler avec le type de données double
, définissez les paramètres régionaux appropriés de sorte que si le séparateur des parties entières et fractionnaires était le même au niveau PHP et au niveau du SGBD.
?s
— espace réservé de type chaîne Les valeurs des arguments sont échappées à l'aide de la méthode mysqli::real_escape_string()
:
$ db -> query (
' SELECT "?s" ' ,
" You are all fools, and I am d'Artagnan! "
);
Requête SQL après conversion du modèle :
SELECT " You are all fools, and I am d'Artagnan! "
?S
— espace réservé de type chaîne pour la substitution dans l'opérateur SQL LIKE Les valeurs des arguments sont échappées à l'aide de la mysqli::real_escape_string()
+ caractères spéciaux d'échappement utilisés dans l'opérateur LIKE ( %
et _
) :
$ db -> query ( ' SELECT "?S" ' , ' % _ ' );
Requête SQL après conversion du modèle :
SELECT " % _ "
?n
— espace réservé de type NULL
La valeur de tous les arguments est ignorée, les espaces réservés sont remplacés par la chaîne NULL
dans la requête SQL :
$ db -> query ( ' SELECT ?n ' , 123 );
Requête SQL après conversion du modèle :
SELECT NULL
?A*
— espace réservé d'ensemble associatif à partir d'un tableau associatif, générant une séquence de paires de la forme key = value
où le caractère *
est l'un des espaces réservés :
i
(espace réservé entier)d
(espace réservé flottant)s
(espace réservé de type chaîne)les règles de conversion et d'échappement sont les mêmes que pour les types scalaires uniques décrits ci-dessus. Exemple:
$ db -> query (
' INSERT INTO `test` SET ?Ai ' ,
[ ' first ' => ' 123 ' , ' second ' => 456 ]
);
Requête SQL après conversion du modèle :
INSERT INTO ` test ` SET ` first ` = " 123 " , ` second ` = " 456 "
?a*
- définit un espace réservé à partir d'un tableau simple (ou également associatif), générant une séquence de valeurs où *
est l'un des types :
i
(espace réservé entier)d
(espace réservé flottant)s
(espace réservé de type chaîne)les règles de conversion et d'échappement sont les mêmes que pour les types scalaires uniques décrits ci-dessus. Exemple:
$ db -> query (
' SELECT * FROM `test` WHERE `id` IN (?ai) ' ,
[ 123 , 456 ]
);
Requête SQL après conversion du modèle :
SELECT * FROM ` test ` WHERE ` id ` IN ( " 123 " , " 456 " )
?A[?n, ?s, ?i, ...]
— espace réservé d'ensemble associatif avec une indication explicite du type et du nombre d'arguments, générant une séquence de paires key = value
Exemple:
$ db -> query (
' INSERT INTO `users` SET ?A[?i, "?s"] ' ,
[ ' age ' => 41 , ' name ' => " d'Artagnan " ]
);
Requête SQL après conversion du modèle :
INSERT INTO ` users ` SET ` age ` = 41 , ` name ` = " d'Artagnan "
?a[?n, ?s, ?i, ...]
— définit un espace réservé avec une indication explicite du type et du nombre d'arguments, générant une séquence de valeursExemple:
$ db -> query (
' SELECT * FROM `users` WHERE `name` IN (?a["?s", "?s"]) ' ,
[ ' Daniel O"Neill ' , " d'Artagnan " ]
);
Requête SQL après conversion du modèle :
SELECT * FROM ` users ` WHERE ` name ` IN ( " Daniel O " Neill " , " d ' Artagnan")
?f
— espace réservé pour le nom de la table ou du champCet espace réservé est destiné aux cas où le nom d'une table ou d'un champ est passé dans la requête en paramètre. Les noms de champs et de tables sont encadrés d'une apostrophe :
$ db -> query (
' SELECT ?f FROM ?f ' ,
' name ' ,
' database.table_name '
);
Requête SQL après conversion du modèle :
SELECT ` name ` FROM ` database ` . ` table_name `
La bibliothèque oblige le programmeur à suivre la syntaxe SQL. Cela signifie que la requête suivante ne fonctionnera pas :
$ db -> query (
' SELECT CONCAT("Hello, ", ?s, "!") ' ,
' world '
);
— les espaces réservés ?s
doivent être placés entre guillemets simples ou doubles :
$ db -> query (
' SELECT concat("Hello, ", "?s", "!") ' ,
' world '
);
Requête SQL après conversion du modèle :
SELECT concat( " Hello, " , " world " , " ! " )
Pour ceux qui sont habitués à travailler avec PDO, cela semblera étrange, mais implémenter un mécanisme qui détermine s'il est nécessaire ou non de mettre la valeur de l'espace réservé entre guillemets dans un cas est une tâche très non triviale qui nécessite d'écrire un analyseur complet. .
Voir dans le fichier ./console/tests.php