La pièce est nue. Une table métallique. Une chaise. Un écran qui braille du code en vert. Ils parlent tous, maintenant. Les données. Elles n'ont plus le choix.
Introduction à la DML - Le Langage de l'Extraction
Data Manipulation Language.
Trois mots pour dire : je vais te faire cracher la vérité.
Tout commence avec SELECT. Une balle de .38 chargée à blanc.
Simple. Mortel.
🌱 Sélection des Données
SELECT, FROM, WHERE – Le Petit Catechisme
La sainte trinité. Le Père, le Fils, et le Saint-Esprit du filtre.
SELECT ce_que_je_veux_voir
FROM la_table_des_suspects
WHERE la_condition_pour_qu_ils_parlent;
SELECT – Ce qui va rester sur le procès-verbal.
Les colonnes. Les preuves. Pas *. Jamais *. C'est paresseux.
On est précis, ou on rentre chez soi.
FROM – La scène du crime.
La table. Celle où les données dorment, ou font semblant.
WHERE – Le filtre.
La question qui sépare les innocents des coupables.
La condition qui fait tomber le masque.
-- Les noms. Rien que les noms.
SELECT nom, prenom
FROM client;
-- Ceux de Paris. Toujours Paris.
SELECT *
FROM client
WHERE ville = 'Paris';
Opérateurs – La Boîte à Outils de l'Inquisiteur
=– Égal. Un seul signe. En SQL, on n'a pas le luxe du double.<>– Différent. Pas pareil. L'autre.BETWEEN– Entre deux valeurs. Inclusif. Comme un étau.WHERE age BETWEEN 18 AND 25 -- Les jeunes. Toujours les jeunes.LIKE– Le motif. Le pattern.%– N'importe quoi, de n'importe quelle longueur. Un trou dans le témoignage._– Un seul caractère. Une lettre qui manque.
WHERE nom LIKE 'Dup%' -- Dupont, Duprès, Dup... WHERE email LIKE '%@gmail.com' -- Les gratuits. Les pressés.IN– La liste. "Parmi ces noms, lequel est le tien ?"WHERE ville IN ('Paris', 'Lyon', 'Marseille') -- Les grandes. Les sales.IS NULL– L'absence. Le trou. Ce qui manque.
Jamais= NULL.NULL, c'est l'inconnu. On ne compare pas à l'inconnu. On le constate.
Les logiques : AND, OR, NOT.
Les connecteurs. Les "et", les "ou", les "sauf".
AND serre la vis. OR donne une porte de sortie. NOT est un retournement de veste.
-- Majeurs. Et de Paris ou Lyon. Pas d'exception.
SELECT nom, prenom, ville
FROM client
WHERE age >= 18 AND ville IN ('Paris', 'Lyon');
-- Les ordinateurs. Entre 500 et 1500. Pas un sou de moins, pas un de plus.
SELECT *
FROM produit
WHERE nom LIKE '%ordinateur%' AND prix BETWEEN 500 AND 1500;
-- Janvier 2024. Commandes non expédiées. Des promesses non tenues.
SELECT *
FROM commande
WHERE date_commande BETWEEN '2024-01-01' AND '2024-01-31'
AND statut_expedition IS NULL; -- L'absence. Le vide.
DISTINCT – Enlever les Doublons. Les Sosies.
Un type se présente deux fois avec des noms différents.
DISTINCT fait le tri. Garde un seul exemplaire.
C'est lourd. Ça coûte. Mais parfois, nécessaire.
-- Les villes. Sans se répéter.
SELECT DISTINCT ville
FROM client;
🧱 Tri, Pagination, Regroupement
ORDER BY – Mettre de l'Ordre dans le Chaos
Sans ordre, les résultats reviennent comme ils veulent.
Comme des témoins qui parlent en même temps.
ORDER BY les fait aligner.
SELECT nom, prenom, date_inscription
FROM client
ORDER BY nom ASC, prenom ASC; -- Alphabétique. Propre.
ASC – Ascendant. Par défaut.
DESC – Descendant. Pour voir la fin de la liste en premier.
On peut trier par une colonne qu'on ne montre pas. Parce qu'on sait.
LIMIT et OFFSET – La Pagination. La Fouille au Corps.
Tu ne peux pas tout voir d'un coup.
LIMIT te donne les N premiers.
OFFSET saute les M premiers. Comme tourner les pages d'un dossier trop épais.
-- Page 3. 10 résultats par page.
SELECT *
FROM produit
ORDER BY prix DESC
LIMIT 10 OFFSET 20; -- Les 20 premiers sont déjà passés. On prend les 10 suivants.
Attention : OFFSET est lent. Très lent.
Pour sauter 100 000 lignes, il faut les lire, les trier, puis les ignorer.
La pagination sur des millions de lignes, c'est une autre histoire. Une histoire de clés.
GROUP BY et HAVING – Les Regroupements. Les Syndicats du Crime.
GROUP BY rassemble ceux qui partagent un point commun.
Une ville. Un client. Une date.
Puis on applique une fonction d'agrégation. On résume.
Les fonctions :
COUNT() – Combien ?
SUM() – Le total. L'argent.
AVG() – La moyenne. Le milieu.
MIN(), MAX() – Le plus petit, le plus grand. Les extrêmes.
HAVING – Le filtre après regroupement.
WHERE filtre les lignes.
HAVING filtre les groupes. C'est subtil. C'est crucial.
-- 1. Compter les clients par ville. La démographie du crime.
SELECT ville, COUNT(*) AS nombre_clients
FROM client
GROUP BY ville
ORDER BY nombre_clients DESC;
-- 2. Le chiffre d'affaires par client. Qui paie, qui ne paie pas.
SELECT client_id, SUM(montant) AS ca_total
FROM commande
GROUP BY client_id;
-- 3. Les villes avec plus de 100 clients. Les nids.
SELECT ville, COUNT(*) AS nb_clients
FROM client
GROUP BY ville
HAVING COUNT(*) > 100; -- Filtrer les GROUPES.
-- 4. Le combo : WHERE avant, HAVING après.
SELECT c.client_id, c.nom, SUM(co.montant) AS ca_total_2024
FROM client c
JOIN commande co ON c.client_id = co.client_id
WHERE EXTRACT(YEAR FROM co.date_commande) = 2024 -- Filtre LIGNES
GROUP BY c.client_id, c.nom
HAVING SUM(co.montant) > 1000; -- Filtre GROUPES
Règle : Si c'est dans le SELECT et que ce n'est pas une fonction d'agrégation, ça doit être dans le GROUP BY.
🔗 Jointures (JOIN) – Les Liens. Les Complicités.
La puissance. La vraie.
Relier les tables. Suivre l'argent. Suivre les liens.
Une clé étrangère est une corde. On tire dessus.
INNER JOIN – Seulement S'il y a Correspondance
Le lien prouvé. La main dans le sac.
Si un client n'a pas de commande, il disparaît.
C'est le monde des connexions avérées.
-- Les commandes, avec le nom du client. Pas d'anonymat.
SELECT c.nom, c.prenom, co.date_commande, co.montant
FROM commande co
INNER JOIN client c ON co.client_id = c.client_id;
-- 'co', 'c' : des alias. Des surnoms. Pour aller plus vite.
LEFT JOIN – Garder Tout le Monde à Gauche
Tous les clients. Même ceux sans commande.
Les colonnes de la commande seront NULL.
Le vide. L'absence de preuve.
-- Tous les clients. Et leurs commandes, s'ils en ont.
SELECT c.nom, c.prenom, co.date_commande
FROM client c
LEFT JOIN commande co ON c.client_id = co.client_id;
-- Les innocents ? Ou les plus discrets.
SELF JOIN – Une Table qui se Regarde dans le Miroir
Un employé a un manager. Le manager est aussi un employé.
La table se joint à elle-même. C'est un jeu de reflets.
-- Chaque employé, et son chef.
SELECT e.prenom AS employe, m.prenom AS manager
FROM employe e
LEFT JOIN employe m ON e.manager_id = m.employe_id;
-- LEFT JOIN : le grand patron n'a personne au-dessus. Le sommet est solitaire.
La Traversée – Plusieurs Tables, un Seul Fil
De la ligne de commande, au produit, à la commande, au client.
Suivre la trace.
SELECT cl.nom, co.date_commande, pr.nom AS produit, lc.quantite
FROM ligne_de_commande lc
INNER JOIN commande co ON lc.commande_id = co.commande_id
INNER JOIN client cl ON co.client_id = cl.client_id
INNER JOIN produit pr ON lc.produit_id = pr.produit_id;
-- Une balle peut traverser plusieurs corps.
📊 Fonctions SQL – Les Outils de l'Expertise
Les Agrégats – Le Résumé
COUNT(*) – Combien de morts ?
SUM(montant) – Combien d'argent ?
AVG(age) – L'âge moyen des suspects.
MIN(date), MAX(date) – Le début, la fin.
SELECT
COUNT(*) AS nb_commandes,
SUM(montant) AS ca_total,
AVG(montant) AS panier_moyen,
MIN(date_commande) AS premiere_cde,
MAX(date_commande) AS derniere_cde
FROM commande;
-- Le portrait robot.
Les Chaînes – Travailler le Témoignage
UPPER() – Crier.
LOWER() – Chuchoter.
TRIM() – Enlever les bavures.
CONCAT() – Assembler les morceaux.
SUBSTRING() – Extraire un bout.
REPLACE() – Changer une histoire.
-- Normaliser. Tout mettre en majuscule. Effacer les différences.
SELECT UPPER(nom) AS nom_famille, CONCAT(prenom, ' ', nom) AS nom_complet
FROM client;
-- Extraire l'année d'un code. "PROD-2023-045" → "2023".
SELECT SUBSTRING(code_produit FROM 6 FOR 4) AS annee_fabrication
FROM produit;
Les Dates – Le Temps, Notre Seul Allié
PostgreSQL :
CURRENT_DATE– Aujourd'hui.EXTRACT(YEAR FROM date_commande)– L'année seule.DATE_TRUNC('month', date_commande)– Tronquer au premier du mois. Pour grouper.
MySQL :
NOW()– Maintenant.YEAR(date_naissance)– L'année de naissance.DATEDIFF(date1, date2)– Les jours entre deux dates. L'intervalle.
-- Les commandes du mois dernier (PostgreSQL)
SELECT *
FROM commande
WHERE date_commande >= DATE_TRUNC('month', CURRENT_DATE - INTERVAL '1 month')
AND date_commande < DATE_TRUNC('month', CURRENT_DATE);
-- Un mois. Pas un jour de plus.
-- L'âge des clients (MySQL)
SELECT nom, prenom, TIMESTAMPDIFF(YEAR, date_naissance, CURDATE()) AS age
FROM client;
-- Les années qui passent. Les années qui accusent.
Fin de l'Interrogatoire
Maintenant, tu sais poser des questions.
Pas n'importe comment. Avec précision.
SELECT est ton arme. JOIN est ton fil d'Ariane.
WHERE est ta question. GROUP BY est ta synthèse.
La pratique est la seule maîtrise.
Pose des questions de plus en plus tordues.
"Qui n'a pas acheté depuis six mois ?"
"Quel produit se vend le mieux le lundi ?"
"Quelle ville a le panier moyen le plus élevé ?"
Les données ont réponse à tout.
À condition de savoir les faire parler.
La suite ? La modification. INSERT, UPDATE, DELETE.
Quand on ne se contente plus de regarder.
Quand on commence à agir.