Dans cet article, nous utiliserons les bases de test définies ci-dessous.
Première base de test
Sélectionne les éléments de la table de gauche avec éventuellement pour chaque élément (de la table de gauche), les éléments correspondants de la table de droite, s'il y a correspondance.
Nous désignerons la table de gauche par l'appellation "table de référence".
Tous les enregistrements de la table de référence seront présents au moins une fois dans la sélection.
SELECT ...
FROM table_de_référence
LEFT JOIN autre_table ON ...
- La table de référence ("A") est représentée avec la couleur rouge pâle.
- @T: Un enregistrement de la table "T".
- +@T: Un enregistrement de la table "T" est présent au moins une fois.
- *@T: Un enregistrement de la table "T" est présent zéro ou plusieurs fois.
Exemple: On sélectionne tous les citoyens, avec leurs activités correspondantes.
Exemple: On sélectionne toutes les activités, avec les citoyens qui les assurent.
Sélectionne tous les éléments de la table de droite avec éventuellement pour chaque élément (de la table de droite), les éléments correspondants de la table de gauche, s'il y a correspondance
Nous désignerons la table de droite par l'appellation "table de référence".
Tous les enregistrements de la table de référence seront présents au moins une fois dans la sélection.
SELECT ...
FROM autre_table
RIGHT JOIN table_de_référence ON ...
- La table de référence ("B") est représentée avec la couleur rouge pâle.
- @T: Un enregistrement de la table "T".
- +@T: Un enregistrement de la table "T" est présent au moins une fois.
- *@T: Un enregistrement de la table "T" est présent zéro ou plusieurs fois.
Exemple: On sélectionne tous les citoyens, avec leurs activités correspondantes.
Exemple: On sélectionne toutes les activités, avec les citoyens qui les assurent.
On suppose que l'on a une base composée de trois tables "A", "B" et "C".
- "A" est liée à "B".
- "A" est liée à "C".
SELECT ...
FROM A
LEFT JOIN B ON A... = B...
RIGHT JOIN C ON A... = C...
- La table de référence ("A") est représentée avec la couleur rouge pâle.
- @T: Un enregistrement de la table "T".
- +@T: Un enregistrement de la table "T" est présent au moins une fois.
- *@T: Un enregistrement de la table "T" est présent zéro ou plusieurs fois.
On commence par exécuter la première jointure, dans l'ordre d'écriture des jointures. C'est la jointure de type "LEFT JOIN".
On obtient une sélection intermédiaire.
Puis on exécute la seconde jointure (le RIGHT JOIN, en l'occurrence).
On obtient la sélection finale.
Tous les enregistrements de la dernière table de référence (la table "C", en l'occurrence) seront présents au moins une fois dans la sélection.
Exemple:
SELECT citoyen.name as 'citoyen', voiture.name as 'voiture', activite.name as 'activite'
FROM citoyen
LEFT JOIN activite ON citoyen.fk_activite = activite.id
RIGHT JOIN voiture ON citoyen.fk_voiture = voiture.id;
On commence par effectuer le "LEFT JOIN". La table de référence est "citoyen". Cette jointure intermédiaire est :
SELECT citoyen.name as 'citoyen', activite.name as 'activite'
FROM citoyen
LEFT JOIN activite ON citoyen.fk_activite = activite.id;
Résultat:
Puis, on effectue le "RIGHT JOIN" entre le résultat de la jointure intermédiaire et la table "voiture". La table de référence est la table "voiture".
Résultat:
On sélectionne tous les enregistrements de la "table de référence" qui n'ont pas de correspondance dans une autre table.
SELECT ...
FROM table_de_reference
LEFT JOIN autre_table ON table_de_reference.key = autre_table.key
WHERE autre_table.key IS NULL
Exemple: On sélectionne tous les citoyens qui n'ont pas d'activité.
Et pour information, on affiche les voitures des citoyens qui n'ont pas d'activité.
Et pour information, on sélectionne les citoyens qui n'ont ni activité ni voiture.
On sélectionne tous les enregistrements de la table de référence qui n'ont pas de correspondance dans une autre table.
SELECT ...
FROM autre_table
RIGHT JOIN table_de_reference ON table_de_reference.key = autre_table.key
WHERE autre_table.key IS NULL
Dans cet article, nous utiliserons les bases de test définies ci-dessous.
Première base de test
Par défaut, toutes les valeurs agrégées sont distinctes.
Dans de nombreux cas d'utilisation il faut utiliser des parenthèses!.
Exemple:
Exemple: Sélectionner tous les citoyens sans activité et toutes les activités qui ne sont assurées par aucun citoyen.
La discrimination, au niveau du code, entre les différentes erreurs susceptibles de se produire n’est pas toujours évidente. Il faut analyser des codes d’erreurs propres au SGBD...
Il peut être intéressant d’intégrer aux procédures stockées la « mécanique » permettant de discriminer certaines erreurs « particulièrement importantes », afin de faciliter le traitement ultérieur de ces erreurs (dans le code).
L’exemple qui suit illustre la technique utiliser.
La procédure stockée ci-dessous permet de mettre à jour une table qui contient des compagnies. Plusieurs erreurs peuvent de produire:
- Le code du pays spécifié n'existe pas. Plus généralement : une clé de jointure n'est pas définie.
- La nouvelle adresse email spécifiée est déjà utilisée par une autre compagnie. Plus généralement : une contrainte d'unicité n'est pas respectée.
- La mise à jour doit modifier un enregistrement. Ce n'est pas le cas.
- Une autre erreur.
L’exemple ci-dessous est plus complet.
- Il illustre l’utilisation des transactions.
- Il illustre une technique pour définir une liste de tags dans des messages d’erreur.
Les quelques fonctions présentées ci-dessous permettent de rédiger des tests unitaires.
Il peut être utile de lancer une requête de sélection via la ligne de commande. Cela permet, par exemple, de diriger le résultat de la requête vers un script qui se chargera de l’exploitation des données.
Les options N et B permettent de supprimer le formatage du résultat en tableau.
Par exemple :
mysql -u root test -e 'select name from t_car_color limit 5';
Va retourner :
mysql -u root test -NBe 'select name from t_car_color limit 5';
Va retourner :
Une fois les données extraites, vous pouvez avoir besoin de les présenter sur une seule ligne. Pour cela vous pouvez utiliser Perl de la façon suivante :
mysql -u root test -NBe 'select name from t_car_color limit 5' | perl -e '@lines = (); while (<STDIN>) { chomp; push(@lines, $_); } print join(",", @lines);'
Va retourner :
Pour extraire le schéma d'une table :
mysql -u root test -NBe 'show create table t_car_color;' | perl -e '$t=<STDIN>; $t=~s/^[^\s]+\s+//; $t=~s/\\n/\n/mg; print $t;'
Il arrive fréquemment que vous vouliez insérer une donnée uniquement si cette dernière n’a pas déjà été insérée.
Une solution simple pour parvenir à cet objectif est d’utiliser la construction « INSERT IGNORE ».
Par exemple :
La table définit un index unique sur le champ « name » (qui représentent le nom de la couleur). Vous disposez d’un grand nombre de couleurs
dont certaines sont déjà déclarées dans la table. La construction « INSERT IGNORE » vous dispense de procéder à un tri préalablement au
processus d’injection.
La commande mysql -u root test -e 'INSERT INTO t_car_color SET name="Air Force blue";'
échoue car la couleur "Air Force blue" est déjà présente dans la table.
En revanche la commande mysql -u root test -e 'INSERT IGNORE INTO t_car_color SET name="Air Force blue";'
fonctionne.