Les 3 premiers exercices se basent sur le schéma relationnel de la Boutique :
1Clients (numero, nom, prenom, rue, codePostal, ville, telephone, categorie, compte)2Commandes (numero, numeroClient*, dateCommande, statut)3Produits (numero, nom, prix, stock)4Details (numeroCommande*, numeroProduit*, quantite)
Vous pouvez télécharger une nouvelle copie de la base de données Boutique si vous souhaitez faire des vérifications sur votre machine.
Vous pouvez aussi travailler directement sur la version en ligne de la base, mais attention, les données ne sont pas persistantes et vous perdrez vos modifications si vous rafraichissez la page.
Exercice 1
Rédiger le code SQL DDL pour effectuer les action suivantes :
-
Création d’une nouvelle table
Details_Commandes
avec les spécifications suivantes :- La table
Details_Commandes
doit contenir les colonnes suivantes :numeroCommande
,numeroProduit
,dateCommande
,quantite
,prixUnitaire
,total
- Les colonnes doivent avoir le même type de données que dans les tables
Commandes
etDetails
, et la colonnetotal
doit être de type réel - La clé primaire de la table est la paire des colonnes :
numeroCommande
etnumeroProduit
- Les colonnes
numeroCommande
etnumeroProduit
doivent être des clés étrangères vers leur table respective
- La table
Solution :
1CREATE TABLE Details_Commandes (2 numeroCommande INTEGER,3 numeroProduit INTEGER,4 dateCommande TEXT,5 quantite INTEGER,6 prixUnitaire REAL,7 total REAL,8 PRIMARY KEY (numeroCommande, numeroProduit),9 FOREIGN KEY (numeroCommande) REFERENCES Commandes(numeroCommande),10 FOREIGN KEY (numeroProduit) REFERENCES Details(numeroProduit)11);
- Importation des données : Rédiger une requête d’insertion de données utilisant une requête de sélection avec jointure pour remplir la table depuis les tables
Commandes
etDetails
Solution :
1INSERT INTO Details_Commandes (numeroCommande, numeroProduit, dateCommande, quantite, prixUnitaire, total)2SELECT c.numeroCommande, d.numeroProduit, c.dateCommande, d.quantite, d.prixUnitaire, d.quantite * d.prixUnitaire3FROM Commandes c4JOIN Details d ON c.numeroCommande = d.numeroCommande;
- Ajout d’une contrainte de type
CHECK
sur la colonne quantité pour vérifier que la quantité est toujours supérieure à0
Solution :
Pour MySQL, PostgreSQL :
1ALTER TABLE Details_Commandes2ADD CONSTRAINT check_quantite CHECK (quantite > 0);
Pour SQLite, on ne peut pas altérer une table pour ajouter une contrainte (CHECK
ou autre), il faut nécessairement recréer la table :
1PRAGMA foreign_keys=off; -- On désactive les contraintes de clés étrangères2BEGIN TRANSACTION; -- On commence une transaction3
4ALTER TABLE Details RENAME TO Details_old; -- On renomme la table Details en Details_old5
6-- On recrée la table Details avec la contrainte CHECK7CREATE TABLE Details (8 numeroCommande INT,9 numeroProduit INT,10 quantite INT CHECK (quantite > 0),11 PRIMARY KEY (numeroCommande,numeroProduit),12 FOREIGN KEY(numeroCommande) REFERENCES Commandes(numero),13 FOREIGN KEY(numeroProduit) REFERENCES Produits(numero)14);15
16INSERT INTO Details SELECT * FROM Details_old; -- On copie les données de l'ancienne table17
18DROP TABLE Details_old; -- On supprime l'ancienne table19
20COMMIT; -- On valide la transaction21PRAGMA foreign_keys=on; -- On réactive les contraintes de clés étrangères
- Il est possible de créer la table
Details_Commandes
directement depuis unSELECT
à l’aide deAS
. Produire une telle requête. Attention: Les tables créées depuis unSELECT
ne conserveront pas les contraintes référentielles, il faudra donc ajouter les contraintes par la suite avecALTER
.
Solution :
1CREATE TABLE Details_Commandes AS2SELECT c.numeroCommande, d.numeroProduit, c.dateCommande, d.quantite, d.prixUnitaire, d.quantite * d.prixUnitaire AS total3FROM Commandes c4JOIN Details d ON c.numeroCommande = d.numeroCommande;
Exercice 2
Rédiger les requêtes SQL pour effectuer les actions suivantes sur la base de données de la Boutique
:
- Ajouter une nouvelle colonne
poids
à la tableProduits
de type réel
Solution :
1ALTER TABLE Produits2ADD COLUMN poids REAL;
-
Ajouter une nouvelle table
Composition
avec les colonnes suivantes :numeroCompose
de type entiernumeroComposant
de type entierquantite
de type entier- La clé primaire de la table est la paire des colonnes
numeroCompose
etnumeroComposant
- Les colonnes
numeroCompose
etnumeroComposant
doivent être des clés étrangères vers leur table respectiveProduits
Solution :
1CREATE TABLE Composition (2 numeroCompose INTEGER,3 numeroComposant INTEGER,4 quantite INTEGER,5 PRIMARY KEY (numeroCompose, numeroComposant),6 FOREIGN KEY (numeroCompose) REFERENCES Produits(numeroProduit),7 FOREIGN KEY (numeroComposant) REFERENCES Produits(numeroProduit)8);
- Proposer une requête pour insérer une ligne dans la table
Composition
Solution :
1INSERT INTO Composition (numeroCompose, numeroComposant, quantite)2VALUES (1, 2, 3);
- Essayer de supprimer un produit référencé dans la table
Composition
. Modifier le comportement de laCascade
des tables de la base de données pour que les références d’unProduit
supprimé soit automatiquement supprimées.
Solution :
1ALTER TABLE Composition2ADD FOREIGN KEY (numeroCompose) REFERENCES Produits(numeroProduit) ON DELETE CASCADE,3ADD FOREIGN KEY (numeroComposant) REFERENCES Produits(numeroProduit) ON DELETE CASCADE;
Exercice 3
- Annuler les comptes négatifs de clients de catégorie
C1
(c.à.d mettre ces comptes clients à0
)
Solution :
1UPDATE Clients2SET compte = 03WHERE categorie = 'C1' AND compte < 0;
- Supprimer les commandes de plus de 3 mois
Solution :
1DELETE FROM Commandes2WHERE dateCommande < DATE('now', '-3 months');
- Ajouter une colonne
dateLivraison
à la tableCommandes
de type datetime
Solution :
1ALTER TABLE Commandes2ADD COLUMN dateLivraison TEXT;
- Ajouter une contrainte de type
CHECK
sur la colonnedateLivraison
pour vérifier que la date de livraison est toujours postérieure à la date de commande
Solution :
1ALTER TABLE Commandes2ADD CONSTRAINT check_dateLivraison CHECK (dateLivraison > dateCommande);
- Mettre à jour les comptes des clients en déduisant le montant des commandes en cours. Optionnellement, mettre à jour des quantités en stock des produits ; attention aux clients qui n’ont pas commandé.
Solution :
1UPDATE Clients2SET compte = compte - (3 SELECT SUM(d.quantite * d.prixUnitaire)4 FROM Details d5 JOIN Commandes c ON d.numeroCommande = c.numeroCommande6 WHERE c.numeroClient = Clients.numeroClient7)8WHERE EXISTS (9 SELECT 110 FROM Commandes c11 WHERE c.numeroClient = Clients.numeroClient12);13
14UPDATE Produits15SET stock = stock - (16 SELECT SUM(d.quantite)17 FROM Details d18 JOIN Commandes c ON d.numeroCommande = c.numeroCommande19 WHERE d.numeroProduit = Produits.numeroProduit20)21WHERE EXISTS (22 SELECT 123 FROM Details d24 JOIN Commandes c ON d.numeroCommande = c.numeroCommande25 WHERE d.numeroProduit = Produits.numeroProduit26);
Exercice 4 - DCL et MySQL
En vous documentant sur internet si nécessaire, rédiger les requêtes SQL pour effectuer les actions suivantes :
- Créer un nouveau schéma (une nouvelle base de données) dans le SGBD MySQL
Solution :
1CREATE DATABASE maBase;2USE maBase;
- Créer une table avec 3 colonnes dans MySQL
Solution :
1CREATE TABLE maTable (2 id INT PRIMARY KEY,3 nom VARCHAR(50),4 age INT5);
- Création d’un nouvel utilisateur dans MySQL
- Ajout des droits en
lecture
sur la table précédemment créée - Ajout des droits en
écriture
sur une colonne
Solution :
1CREATE USER 'monUtilisateur'@'localhost' IDENTIFIED BY 'monMotDePasse';2GRANT SELECT ON maBase.maTable TO 'monUtilisateur'@'localhost';3GRANT UPDATE(nom) ON maBase.maTable TO 'monUtilisateur'@'localhost';