Vous êtes sur la page 1sur 53

Chapitre 2 :

ADMINISTRATION DES BASES DE DONNEES MYSQL

I. Versions, types de licences et installation coté serveur


(Pour ceux qui n’ont pas encore MySql dans leur machine)

Très répandu, MySQL est un système de gestion de base de données


relationnelle (SGBDR) open source destinée aux applications Web. Les développeurs,
administrateurs de base de données et équipes DevOps s’en servent pour élaborer et gérer des
applications Web et cloud.

1. Les éditions de MySQL


Comme pour la plupart des solutions SGBDR open source, MySQL se décline en plusieurs éditions
pour Windows, OS X, Solaris, FreeBSD et d’autres variantes de Linux et Unix :

• MySQL Classic Edition, destinée uniquement aux fournisseurs de logiciels indépendants,


aux partenaires OEM et aux revendeurs, est conçue comme une base de données
intégrable pour les applications présentant de forts taux d’opérations de lecture.
• MySQL Community Edition est la version téléchargeable gratuite de MySQL, disponible
sous licence GPL (General Public License) GNU.
• MySQL Standard Edition est l’offre de SGBDR d’entrée de gamme pour les applications
de traitement de transactions.
• MySQL Enterprise Edition propose en plus des fonctionnalités avancées, des outils de
gestion (dont OEM pour MySQL) et une assistance technique.
• MySQL Cluster Carrier Grade Edition est conçue pour le développement Web et
Cloud.
• MySQL Database Services est la dernière catégorie en date pour mettre en
avant MySQL Heatwave, une version entièrement managée du SGBD et calibrée pour
la machine learning.

MySQL Cluster est un SGBD open source adaptable, conçu pour fournir des performances
et une disponibilité élevée à de nombreux types d’applications métier. Par exemple, MySQL Cluster
pilote les bases d’abonnés des principaux fournisseurs de services de télécommunication et est
utilisé au niveau mondial pour la détection des fraudes dans les transactions financières.

La version 7.4 de MySQL Cluster a ajouté de nouvelles fonctionnalités permettant de faire


évoluer automatiquement les services de base de données tout en assurant une disponibilité quasi
totale. Cette édition permet la mise en cluster sans partage des bases de données In-
Memory. Il peut s’agir d’une solution viable lorsque vous avez besoin de transactions ACID
(atomiques, cohérentes, isolées et durables) assorties d’une haute disponibilité ou de taux très
rapides de modification ou d’insertion des données sur du matériel bon marché.
MySQL Cluster 8.0 s’est aligné sur le développement de MySQL 8. Allocation automatisée de
la mémoire, jusqu’à quatre réplicas, possibilité de stocker plus de 100 To par cluster, synchronisation
des privilèges, auto-partitionnements… voilà quelques fonctionnalités clés de cette édition
qu’Oracle continue de peaufiner en 2022.

En outre, l’architecture modulaire de MySQL lui permet de charger et de décharger des


moteurs de stockage sur un serveur MySQL en cours d’exécution. Le moteur de stockage gère les
opérations SQL pour différents types de tables MySQL. En permutant les moteurs de stockage
MySQL, il est possible d’influer sur le comportement du SGBD. MySQL Cluster dispose donc de son
propre moteur de stockage : NDB.

InnoDB, qui assure la sécurité des transactions et est conforme au concept ACID, est le
moteur de stockage par défaut de MySQL depuis la version 5.6. Les autres moteurs sont MyISAM
(pour le Web et les entrepôts de données), Memory (pour les traitements In-Memory), CSV (pour le
texte) et Archive.

Types de données pris en charge par le SGBDR open source MySQL


MySQL inclut les types de données suivants : numérique, date et heure, chaîne (dont binaire,
caractère et BLOB – Binary Large OBject) et spatial. En outre, MySQL mappe certains types de
données issus d’autres SGBD à des types MySQL pour faciliter la portabilité.

2. Installation de MySQL

➢ Après avoir téléchargé vous cliquez sur Custom pour personnaliser l’installation,
ensuite on choisit le type de version (8.0.31). Choisir une configuration de
développement cad la base de données ne sera pas accessible à distance et par
défaut il faut laisser les informations de base concernant les ports(3306 et 33060).
➢ Pour éviter les problèmes de compatibilité il faut choisir les authentifications
classiques (use legacy authentification method).

Ensuite choisir le nom et le mot de passe (root est préférable et plus facile)
➢ Pour que la commande MySQL fonctionne en invite de commande ou sur power
Shell, nous devons modifier les variables d’environnement dans les paramètres de
votre ordinateur, plus précisément le PATH et y ajouter le chemin vers la commande
mysql.exe qui se trouve dans le dossier bin dans le dossier d’installation MySQL.
(Même chose pour maria DB)
II. Les outils d’administration MySQL
Les bases de données agissent comme un référentiel d’informations central auquel les
programmes ou services Web autorisés peuvent accéder, compléter ou modifier. Des
professionnels appelés administrateurs de bases de données sont en charge de la mise en
place et de la maintenance de ces serveurs logiciels spécialisés.
Les outils d’administration de base de données sont des programmes spécialisés qui leur
permettent d’accéder, de modifier et de mettre à jour le logiciel et les configurations de
base de données.
Dans le monde de la programmation informatique, un serveur est un programme dont le
but est de fournir des informations à d’autres logiciels appelés clients. Un serveur peut
fonctionner sur sa propre machine, à laquelle les clients accèdent via Internet ou un réseau
local. Un serveur peut également s’exécuter en tant que programme d’arrière-plan sur la
même machine que ses programmes clients. Le logiciel de base de données fonctionne
comme un serveur qui écoute sur un port spécifique les connexions entrantes des
programmes clients qui souhaitent accéder aux informations qu’il détient.

❖ Les outils d’administration de base de données que les professionnels utilisent pour
maintenir les bases de données en cours d’exécution sont des programmes distincts
et ne font pas partie du logiciel de base de données lui-même. Les administrateurs
de base de données utilisent ces outils pour émettre des commandes auxquelles un
logiciel de base de données particulier est programmé, pour reconnaître et
répondre par une action correspondante. Bien que la syntaxe exacte de ces
commandes varie d’un logiciel de base de données à l’autre, les actions qui
peuvent être effectuées à l’aide de celles-ci incluent :

• Ajouter et supprimer les informations d’identification que les programmes peuvent


utiliser pour se connecter à une base de données particulière

• Ajouter ou supprimer des bases de données sur le serveur

• Ajouter ou supprimer des tables individuelles dans une base de données

• Modifier la disposition d’un tableau

• Modifier les entrées de données individuelles

Ces programmes utilitaires peuvent avoir des interfaces utilisateur graphiques


complètes (ex : MySQL WORKBENCH pour MySQL) ou être des programmes de terminal
textuels. Les outils d’administration de base de données qui utilisent une interface textuelle
nécessitent que l’utilisateur tape la syntaxe complète pour chaque commande de
maintenance.
Les programmes dotés d’une interface graphique complète permettent aux
utilisateurs de configurer des commandes en cliquant sur des boutons et en sélectionnant
différentes options, puis ils traduisent l’action dans la syntaxe nécessaire pour une
commande dans la base de données.
❖ Les outils d’administration de base de données incluent également un logiciel qui
permet de se connecter à distance à un ordinateur et d’exécuter des commandes
système. Ceux-ci sont nécessaires lorsque l’administrateur doit mettre à jour un
logiciel de base de données qui s’exécute sur une machine sans écran d’ordinateur
ni interface graphique. Pour qu’un administrateur puisse appliquer une mise à jour, il
doit arrêter le serveur de base de données, ce qui revient à quitter une application
en cours d’exécution. Le logiciel de connexion à distance permet à un
administrateur de base de données d’accéder à l’ordinateur sur lequel la base de
données s’exécute pour arrêter le serveur de base de données, mettre à jour le
logiciel, puis redémarrer le logiciel de base de données.

Les administrateurs système les plus efficaces utilisent les bons outils de gestion de
base de données.

Nous vivons à l'ère des données et chaque entreprise a besoin d'une équipe
d'administrateurs système capables de gérer et d'organiser des bases de données très
complexes.

En tant qu'Administrateur de base de données ou Administrateur système, vous


devez toujours utiliser les meilleurs outils disponibles sur le marché. Tout est question
d'efficacité et d'un environnement irréprochable.

Il existe des tonnes d'outils obsolètes qui sont encore utilisés dans l'industrie. Donc,
pour aider les débutants et les experts, les outils suivants vous aideront à faire un travail
remarquable dans la gestion des bases de données.

a) MySQLWrapper - Bibliothèque pour MySQL


Bibliothèque qui permet d'utiliser plus facilement MySQL en C#. Elle permet les choses
suivante :

• Créer / supprimer / ... des bases de données.


• Effectuer un back-up d'une base de données.
• Ajout / Création / Update / ... des tables.
• Gérer pas mal d'erreur.
• Facilite certaines conversion C# => SQL (Blob, DateTime, etc.…)
Elle est fournie avec un exemple qui montre comment faire diverses actions. C'était
à la base une DLL personnelle que j'ai voulu mettre à profit pour ceux qui veulent effectuer
des requêtes MySQL très simplement. Elle est donc susceptible d'être mise à jour. Nécessite
que le MySQL Connector soit installé.

b) DBSync for Access & MySQL


DBSync for Access & MySQL est un utilitaire qui permet la conversion et la
synchronisation des données entre la base de données Mysql ET Access.
Il garantit l'intégrité des données que vous pourriez essayer de convertir et élimine les
risques et les échecs possibles de synchronisation.

c) DBDesigner
DBDesigner est un système de conception de base de données visuel qui intègre la
conception de base de données, la modélisation, la création et la maintenance dans un
environnement unique, homogène. Il combine des fonctionnalités professionnelles et une
interface utilisateur simple et claire et permet d'offrir le moyen le plus efficace pour gérer
vos bases de données.

DBDesigner est développé et optimisé pour la base de données open source MySQL
pour aider les utilisateurs de MySQL avec un outil de conception disponible puissant et
gratuit.

d) MySQL Workbench
MySQL Workbench est un outil visuel unifié pour architectes, développeurs et
administrateurs de base de données. MySQL Workbench permet la modélisation des
données, le développement SQL et des outils d'administration complets pour la configuration
des serveurs, l'administration des utilisateurs et davantage. MySQL Workbench est disponible
sous Windows, Linux et Mac OS. MySQL Workbench remplace MySQL Query Browser et MySQL
Administrator.

e) Navicat for MySQL - Lite Edition


Navicat est un logiciel qui permet de gérer les différents objets mis à disposition
par le SGBD MySQL (bases, tables, champs, procédures, déclencheurs, ...) et ce sous
Windows, Linux et Mac, avec toutefois des différences d'un OS à l'autre. Il supporte
plusieurs modes de connexion et fournit plusieurs outils de monitoring de code SQL
ainsi que des outils d'assistance à la conception de bases de données et un
planificateur de requêtes.

f) MySQL Front
MySQL-Front est un logiciel graphique de gestion de bases MySQL. On peut
directement manipuler les bases, tables, champs et données par le biais de l'interface
graphique mais également transmettre des scripts SQL au SGBD MySQL. MySQL Front
n'est toutefois disponible que sous Windows et il n'y a qu'une version de démonstration
de 30 jours disponible en téléchargement.

g) Spotlight on MySQL
Spotlight on MySQL est un outil de monitoring et de diagnistic en temps réel pour
les serveurs MySQL sur plateforme Windows. Il n'est valable qu'à partir de la version 5.0
de MySQL, et uniquement sur le moteur InnoDB. Néantmoins, il fournit d'importantes
sources d'informations sur les flux de données d'une base, et de puissants outils visuels
de diagnostic.
h) dbForge Studio
dbForge Studio est un outil d'administration et un environnement de
développement pour MySQL. Ses fonctionnalités permettent une exploration rapide
des bases de données, la gestion des objets dans les bases, la gestion des comptes
et privilèges, le développement de routines et la synchronisation entre bases.
Disponible uniquement sous Windows, il nécessite l'installation préalable du .NET
Framework 2.0, 3.0 ou 3.5.

i) HeidiSQL
HeidiSQL est le successeur libre de MySQL-Front. Son interface graphique permet
de gérer des serveurs MySQL : manipulation des variables serveurs, des bases, tables,
vues, champs et données, import et export de données par le biais de l'interface
graphique, ainsi que la création, l'édition et l'exécution de scripts SQL. HeidiSQL est
disponible sous Windows ainsi que sous Linux (par l'intermédiaire de Wine).

a) Quest

Quest Software, fondée en 1987, reste l'un des fournisseurs de solutions informatiques les
plus fiables à l'ère actuelle du développement logiciel.

Leurs principaux produits sont outils de gestion de base de données. La meilleure chose à
propos de Quest est le ciblage de chacun de leurs produits. Cela signifie que chaque
plate-forme ou base de données mérite son propre ensemble de boîtes à outils spécifiques.
Par exemple, si votre entreprise est fortement basée sur la base de données Cassandra,
vous pouvez opter pour le produit spécialisé Projecteur antibrouillard pour Cassandra.

En conclusion, si vous recherchez un ensemble d'outils spécialisés pour maintenir et faire


évoluer votre base de données en pleine croissance, les produits Quest sont parfaits.

Fonctionnalités

• Un outil spécifique pour chaque plateforme


• Un grand choix d'outils
• Demande de tarification personnalisée
• Services éducatifs virtuels, basés sur le Web et sur site
• Assistance 24/7

Vous pouvez voir une grande liste de solutions de gestion de base de données sur le Page
des produits Quest.
b) ManageEngine

ManageEngine offre des outils de surveillance de base de données solides orientés pour
optimiser les performances des bases de données. Ces outils de surveillance vous
informent non seulement en cas de problème, mais vous aident à résoudre rapidement
les problèmes.

Ils offrent une solution spécifique pour chaque type de base de données. Alors, si vous
recherchez un outil de surveillance optimisé pour votre base de données, n'hésitez pas à
passer en revue les solutions ManageEngine.

De plus, ces systèmes de surveillance découvrent les appels de base de données


effectués par les applications backend Java, Node, Ruby on Rails, DotNET et PHP.

Fonctionnalités

• 20+ bases de données prises en charge


• Tableau de bord visuel
• Surveillance des instructions SQL
• Analyse avancée

c) Sequel Pro

Êtes-vous un utilisateur Mac OS?

De plus, travaillez-vous avec MySQL ou MariaDB?

Si tel est bien le cas, Sequel Pro est le bon système de gestion de base de données pour
vous. C'est un projet open source qui vous donne un accès direct aux bases de données
MySQL locales et distantes.
La meilleure partie de cet outil est sa simplicité et le fait qu'il est vraiment léger. En
conséquence, vous pouvez rapidement configurer cet outil sur n'importe quelle machine
Mac.

d) PHPMyAdmin

PhpMyAdmin est un outil d'administration gratuit construit avec PHP, · Il peut effectuer un
grand nombre d'opérations avec MySQL et Bases de données MariaDB.

Vous pouvez utiliser l'interface graphique ou utiliser des séquences SQL pour effectuer la
bonne gestion de la base de données.

Cet outil a gagné plusieurs prix de 2002 à aujourd'hui. En outre, il a une documentation
approfondie et un livre traduit en anglais et en espagnol.

Remarque : Attention à confondre PhpMyAdmin avec PhpMinAdmin (ancien nom de


l'administrateur) car ce sont des projets totalement différents.

Fonctionnalités

• Gratuit et open-source
• Prise en charge des bases de données MySQL et MariaDB
• Interface Web intuitive
• Importer des données et exporter des données (CSV et SQL)
• Traduit dans les langues 72
• Effectuer des tâches administratives
• Administration de plusieurs serveurs.
La gestion de bases de données est devenue l'une des compétences les plus exigeantes
de la dernière décennie. Ceci, en raison de la quantité croissante de données, chaque
entreprise doit se développer et réussir.

Lors de la recherche des meilleurs outils pour gérer efficacement bases de données, nous
proposons des plates-formes gratuites et payantes. Vous pouvez choisir celle qui vous
convient le mieux en fonction de vos besoins en tant qu'administrateur système ou des
besoins de l'entreprise pour laquelle vous travaillez.

1. Architecture de MySQL
MySQL est un système de gestion de base de données relationnelle qui est un logiciel
libre Open Source sous licence GNU. Il est également pris en charge par Oracle
Company. Il est rapide, évolutif, facile à utiliser système de gestion de base de données.
MYSQL prend en charge de nombreux systèmes d’exploitation comme Windows, Linux,
MacOS, etc. MySQL est un langage de requête structuré qui est utilisé pour manipuler,
gérer et récupérer des données à l’aide de diverses requêtes. MySQL est développé et
supporté par MySQL AB qui est une société suédoise et écrit en C et C ++. Il a été
développé par Michael Widenius et David Hughes. Il est souvent utilisé pour dire que
MYSQL est nommé d’après le nom de la fille du co-fondateur MIchael Widenius dont le
nom est ‘My’.
L’architecture de MYSQL décrit la relation entre les différents composants du système
MYSQL. MYSQL suit l’architecture client-serveur. Il est conçu de manière à ce que
l’utilisateur final qui est Clients puisse accéder aux ressources de l’ordinateur qui est
serveur à l’aide de divers services de mise en réseau. L’architecture de MYSQL contient
les couches principales suivantes. :
•Client
•Serveur
• Couche de stockage
Couche client :
Cette couche est la couche supérieure du diagramme ci-dessus. Le client donne des
instructions de demande au service à l’aide de la couche client. Le client effectue une
demande via l’invite de commandes ou via l’écran GUI en utilisant des commandes et
des expressions MYSQL valides. Si les expressions et les commandes sont valides, la sortie
est obtenue à l’écran. Certains services importants de la couche client sont :
• Gestion de connexion (Lorsqu’un client envoie une demande au serveur et que le
serveur accepte la demande et que le client est connecté. Lorsque le client est
connecté au serveur à ce moment-là, un client obtient son propre thread pour sa
connexion. Avec l’aide de ce thread, toutes les requêtes côté client sont
exécutées)
• Authentification (L’authentification est effectuée côté serveur lorsque le client est
connecté au serveur MYSQL. L’authentification se fait à l’aide du nom d’utilisateur
et du mot de passe.)
• Sécurité (Après l’authentification, lorsque le client se connecte avec succès au
serveur MySQL, le serveur vérifie qu’un client particulier dispose des privilèges
nécessaires pour émettre certaines requêtes sur le serveur MySQL.)
Couche serveur :
La deuxième couche de l’architecture MYSQL est responsable de toutes les
fonctionnalités logiques du système de gestion de base de données relationnelle de
MYSQL. Cette couche du système MYSQL est également connue sous le nom de
« Cerveau de l’architecture MYSQL ». Lorsque le client donne des instructions de
demande au serveur et que le serveur donne la sortie dès que l’instruction est mise en
correspondance. Les différents sous-composants du serveur MYSQL sont:
- Gestion des threads : Lorsqu’un client envoie une requête au serveur et que le serveur
accepte la demande et que le client est connecté. Lorsque le client est connecté au
serveur à ce moment-là, un client obtient son propre thread pour sa connexion. Ce
thread est fourni par la gestion des threads de la couche serveur. De plus, les requêtes
côté client qui sont exécutées par le thread sont également gérées par le module
Thread Handling.
-Parser : Un Parser est un type de composant logiciel qui construit une structure de
données (arbre d’analyse) d’entrée donnée. Avant d’analyser l’analyse lexicale, c’est-
à-dire que l’entrée est divisée en nombre de jetons. Une fois que les données sont
disponibles dans les éléments plus petits, analyseur effectuer l’analyse syntaxique,
l’analyse sémantique après que l’arbre d’analyse est généré en sortie
- Optimiseur:
Dès que l’analyse est terminée, différents types de techniques d’optimisation sont
appliqués au bloc d’optimiseur. Ces techniques peuvent inclure la réécriture de la
requête, l’ordre de balayage des tables et le choix des bons index à utiliser, etc.
-Buffer et Cache :
Cache et stockage tampon de la requête précédente ou du problème demandé par
l’utilisateur. Lorsque l’utilisateur écrit une requête, elle va d’abord dans le cache de
requêtes, puis le cache de requête vérifiera que la même requête ou le même
problème est disponible dans le cache. Si la même requête est disponible, elle fournira
une sortie sans interférer avec l’analyseur, l’optimiseur.
-Table Metadata Cache
Le cache de métadonnées est une zone de mémoire réservée utilisée pour le suivi des
informations sur les bases de données, les index ou les objets. Plus le nombre de bases
de données, d’index ou d’objets ouverts est élevé, plus la taille du cache de
métadonnées n’est importante.
- Cache de clés : Un cache de clé est une entrée d’index qui identifie de manière
unique un objet dans un cache. Par défaut, les serveurs Edge mettent en cache le
contenu en fonction du chemin d’accès complet des ressources et d’une chaîne de
requête

Couche de stockage :
Cette couche de moteur de stockage de l’architecture MYSQL la rend unique et
préférable pour les développeurs. En raison de cette couche, MYSQL est compté
comme le SGBDR le plus utilisé. Dans le serveur MYSQL, pour différentes situations et
exigences, différents types de moteurs de stockage sont utilisés, à savoir InnoDB,
MYiSAM, NDB, mémoire, etc. Ces moteurs de stockage sont utilisés comme ingénierie de
stockage où les tables créées par l’utilisateur sont connectées entre elles.

4. Caractéristiques de MYSQL

Le langage MYSQL est facile à utiliser par rapport à d’autres langages de


programmation comme C, C ++, Java, etc. En apprenant avec une commande de
base, nous pouvons travailler, créer et interagir avec la base de données.
MYSQL se compose d’une couche de sécurité des données qui protège les données
contre les contrevenants. De plus, les mots de passe sont cryptés dans MYSQL
MYSQL suit l’architecture client-serveur où les commandes et instructions de la
demande du client et le serveur produira une sortie dès que l’instruction est
correspondante.
MYSQL est libre d’utilisation sous la version communautaire de celui-ci. Nous pouvons
donc le télécharger depuis le site Web de MYSQL et travailler dessus librement.
MYSQL utilise le multithreading qui le rend évolutif. Il peut gérer n’importe quelle
quantité de données. La limite de taille de fichier par défaut est de 4 Go, mais nous
pouvons l’augmenter en fonction de nos besoins
MYSQL est considéré comme l’une des bases de données rapides. Sa rapidité est
déterminée sur la base d’un grand nombre de tests de référence.
MYSQL est très flexible car il supporte un grand nombre de systèmes embarqués
MYSQL est compatible pour fonctionner sur différents systèmes d’exploitation tels que
Windows, MacOs, Linux, etc.
MYSQL permet de restaurer les transactions, de les valider et de récupérer des espaces.
Il a un faible problème de fuite de mémoire qui augmente son efficacité de la mémoire.
MYSQL version 8.0 fournit un support de double mot de passe, l’un est un mot de passe
actuel et l’autre est un mot de passe secondaire. Avec l’aide de cela, nous pouvons
créer un nouveau mot de passe
MYSQL fournit une fonctionnalité de partitionnement qui améliore les performances des
grandes bases de données

6. Changement de versions, migration

Il n’est jamais bon d’avoir des logiciels obsolètes sur votre serveur. Même la plus
petite faille dans votre sécurité pourrait être un vecteur permettant aux attaquants de se
faufiler et de prendre le contrôle.
L’assistant de migration MySQL Workbench est conçu pour faire gagner du temps aux
administrateurs de bases de données et aux développeurs en offrant une facilité
d’utilisation visuelle et par pointer-cliquer à toutes les phases de configuration et de
gestion d’un processus de migration complexe :
• Migrations de bases de données : permet les migrations à partir de Microsoft SQL Server,
Microsoft Access, PostgreSQL, Sybase ASE, Sybase SQL Anywhere, SQLite, etc.
• Gérer les projets de migration - permet de configurer, copier, éditer, exécuter et
planifier les migrations.
• Sélection de la source et de la cible - permet aux utilisateurs de définir des sources de
données spécifiques et d’analyser les données sources avant la migration.
• Migration d’objets - permet aux utilisateurs de sélectionner les objets à migrer,
d’affecter la source aux mappages cibles si nécessaire, de modifier les scripts de
migration et de créer le schéma cible.
• Mises à niveau de version - à l’aide de la migration, les utilisateurs peuvent facilement
déplacer les bases de données des anciennes versions de MySQL vers la dernière.
Avec l’assistant de migration MySQL Workbench, les utilisateurs peuvent convertir une
base de données existante en MySQL en quelques minutes plutôt qu’en quelques heures
ou jours que la même migration nécessiterait à l’aide de méthodes manuelles
traditionnelles.
La migration de données est une opération de chargement en bloc qui déplace
des lignes de données de tables MySQL dans SQL Server ou SQL Azure tables dans les
transactions. Le nombre de lignes chargées dans SQL Server dans chaque transaction est
configuré dans les paramètres du projet. Concernant les migrations nous allons les faires
en interface graphique Utilisant MySQL WORKBENCH qui est un outil graphique intégré
dans MySQL dédié aux développeurs et aux administrateurs installés avec le package
MySQL.
Aller dans le homepage et cliquer sur l’onglet DATABASE --- assistant de migration. Ensuite
on commence la migration.
Très souvent les migrations de base de données se font d’un SGBD à un autre.

7. Les objets d’une base de données MySQL

• Les tables
• Les verrous
• Les index
• Les vues
• les triggers

8. Les moteurs de stockage : MyIsam et Innodb

Dans plusieurs débats il a été reproché à MySql, de ne pas être un véritable serveur de
base de données. Par défaut MySql, il est vrai ne supporte ni les transactions ni les
contraintes sur les clés étrangères. Tout ce qui fait qu'un serveur puisse éviter la corruption
des données lors de sessions multiples simultanées.
C'est le format de table, Myisam, utilisé par défaut dans MySQL, qui est en cause. Ce type
de table, même s'il permet de très bonnes performances, ne supporte ni les transactions ni
les contraintes sur les clés étrangères ni les verrous au niveau utilisateur…

Cette limitation peut être facilement contournée dans certains cas. Mais des
environnements plus critiques demandent une exigence accrue de sécurité pour les
données.

Introduit avec la version 3.23.5 de MySQL, InnoDB répond à cette exigence en offrant le
support des transactions, des clés étrangères et les verrous dans les enregistrements. Les
versions futures annoncent le support des requêtes imbriquées et des procédures stockées.
MySQL enregistre par défaut les informations avec le moteur de stockage MyISAM, mais il
en existe d’autres incluant InnoDB (le plus connu), ISAM, Heap, NBD, Berkeley DB ou
encore Merge. Le choix d’un moteur de stockage est important et les différents parfois
méconnue. Les principales différences entre MyISAM et InnoDB pour comprendre
comment faire ce choix sont :

➢ MyISAM
Avan tages
Voici une liste non-exhaustive d’arguments en faveurs de MyISAM:

▪ Système de stockage par défaut de MySQL. Ce type de stockage est le plus ancien
disponible avec MySQL
▪ Très rapide pour effectuer des requêtes SELECT ou INSERT
▪ Supporte l’indexation plein texte (cf. index full text). Offre de bien meilleure
performance lors d’une recherche sur des champs de textes
▪ Administration plus simple
▪ Possibilité de verrouiller au niveau d’une table (cf. table lock)
▪ Plus souple au niveau de l’intégrité des données (mais ça peut avoir son revers de la
médaille …)
I nc onvénien ts
La souplesse de MyISAM entraîne quelques points négatifs lorsqu’il s’agit de garder une
bonne intégrité des données, comme le montre les points ci-dessous:

▪ Pas de transactions
▪ Pas de clés étrangères
▪ Plus difficile de récupérer après un crash. L’intégrité des données peut facilement
être compromise
Pas s er à M yI S A M
Si vous souhaitez passer une table à MyISAM il suffit simplement d’exécuter cette requête
SQL:

ALTER TABLE `table` ENGINE=MYISAM;

➢ InnoDB

Avan tages
Les principaux avantages d’utiliser InnoDB concernent la possibilité de bien gérer
l’intégrité des données, même lors d’un crash du serveur.
▪ Gère les transactions (ensemble de requêtes regroupées) tel que BEGIN ou START
TRANSACTION, COMMIT, ROLLBACK …
▪ Gère les clés étrangères et les contraintes d’intégrité
▪ Support d’ACID pour s’assurer que tous les enregistrements sont réussis ou échoué,
Risque d’erreur impossible, même lors d’une panne
▪ Système de récupération lors d’un crash grâce à un système de relecture des logs

I nc onvénien ts
Toutefois, l’intégrité des données complique l’administration d’une base de données.
▪ Plus strict concernant l’intégrité des données
▪ Ne supporte pas l’indexation plein texte (cf. index full text)
▪ Administration un peu plus complexe
▪ Moteur de stockage plus imposant. Il demande plus de ressources et est plus lent
▪ Possibilité de verrouiller au niveau d’une ligne (cf. row lock) pour insérer ou mettre à
jour un enregistrement
▪ Intéressant de noter que c’est plus récent, même si ce n’est pas forcément un
inconvénient
Pas s er à I nnoDB
Pour passer une table à InnoDB il suffit de lancer la requête suivante:

ALTER TABLE `table` ENGINE=InnoDB;

Il est important de savoir qu’il est possible dans une même base de données d’avoir des
tables en MyISAM et d’autres en InnoDB. Cela permet même d’améliorer les
performances dans certains cas.
Pour résumer sur le choix entre InnoDB et MyISAM :

▪ MyISAM : à privilégier lorsqu’il est surtout nécessaire d’effectuer des requêtes pour
lire ou insérer des données. Pour des sites web, c’est souvent la solution
recommandée.
▪ InnoDB : à privilégier pour les systèmes qui ne doivent pas comporter d’erreurs et qui
nécessite des clés étrangères. Pour une application gérant des données
importantes, tel une application bancaire, cela peut se révéler le moteur de
stockage recommandé.

9. Paramétrage d’Innodb

Les paramètres évoqués dans cette section ne sont pas nécessairement à modifier par
rapport à la configuration par défaut, mais il est important que vous ayez réfléchi à leur
bonne valeur pour votre application.
• Taille du cache mémoire (innodb_buffer_pool_size) : il s’agit du cache principal
d’InnoDB (buffer pool), où données et index fréquemment accédés sont stockés.
Pour un serveur dédié à MySQL, il est courant de lui allouer la majeure partie de la
mémoire du serveur (par exemple, environ 25 Go pour un serveur ayant 32 Go de
mémoire physique). L’idée principale est que ce cache permet d’éviter les accès
au disque : la taille du cache est d’autant plus importante que le disque est lent.
Si votre base de données est petite (quelques dizaines de Go, par exemple), il est
assez simple d’utiliser un serveur ayant suffisamment de mémoire pour que
l’ensemble des données et index InnoDB tiennent dans le cache. Sinon, il faut
essayer de faire tenir en cache la partie utile des données et index, c’est-à-dire la
partie des données et index qui est fréquemment utilisée par l’application. Il est
assez fréquent en effet d’avoir par exemple une base de 500 Go contenant
l’historique...

a. Réplication
En informatique, la réplication est un processus de partage d'informations pour assurer la
cohérence de données entre plusieurs sources de données redondantes, pour améliorer
la fiabilité, la tolérance aux pannes, ou la disponibilité. On parle de réplication de
données si les mêmes données sont dupliquées sur plusieurs périphériques.
La réplication n'est pas à confondre avec une sauvegarde : les données sauvegardées
ne changent pas dans le temps, reflétant un état fixe des données, tandis que les
données répliquées évoluent sans cesse à mesure que les données sources changent.
Dans une base de données, la réplication est fréquemment utilisée pour des systèmes qui
ont à soutenir une forte charge : le serveur maître journalise les opérations effectuées, et
les esclaves, à partir de ce journal, dupliquent les opérations effectuées. Ainsi, moyennant
un petit temps de retard (replication lag), les mêmes données sont disponibles sur
plusieurs serveurs en même temps, ce qui permet un processus de répartition de charge.
La plupart des systèmes de gestion de base de données modernes permettent un
schéma multi-maître : cependant, celui-ci introduit de nombreux coûts supplémentaires.
La résolution, ou la prévention de conflits entre plusieurs transactions simultanées est par
exemple très complexe.
Le terme de réplication SQL décrit un groupe de technologies permettant la distribution et
la mise en miroir d’informations entre différentes bases de données. La réplication SQL
permet non seulement de copier des données entre des bases de données, mais
également de copier des objets de base de données. Essentiellement, la réplication
effectue la synchronisation entre les bases de données.

La création d'un serveur de réplication s'effectue par la copie des tablespaces, des fichiers
de logs sur le serveur esclave, des fichiers.frm et l'édition de son fichier de configuration.

La réplication avec les tables InnoDB inclut la lecture des logs. Si une transaction a échoué,
celle-ci ne sera pas répliquée.

La gestion des tables n'est pas la même qu'avec MyIsam. Il n'est pas possible d'utiliser
« optmize table » pour vérifier et gérer les tables InnoDB. Il est préférable d'effectuer alors
un dump de la table et de supprimer celle-ci avant de la recréer et de réimporter les
données.

b. L'utilisation

L'utilisation d'InnoDB diffère aussi de l'utilisation classique de MySQL. Les tables et les index
de type InnoDB utilisent des méthodes différentes d'accès. Chaque table possède un
« clustered index ». Les données sont sur la même page que cet index.

Avec InnoDB, toute l'activité se produit dans un contexte transactionnel. À savoir que
même si par défaut MySQL valide automatiquement les transactions, celles-ci restent des
transactions et MySQL effectue en réalité un commit à chaque fin de requête.

Pour éviter que MySQL utilise ce comportement, on peut commencer le script par BEGIN(sur
sql server) ou START TRANSACTION(en invite de commande ou dans Workbench) et le finir
par COMMIT ou ROLLBACK. Une autre méthode consiste à fixer la variable autocommit à
0 à chaque début de session. Il est possible de fixer cette valeur dans le fichier de config
du client MySQL.

SET AUTOCOMMIT = 0;

La création de table d'InnoDB se fait en ajoutant type = INNODB à la fin de l'instruction de


création de la table :

1.CREATE TABLE nom_table


2.(. . .)
3.Engine = INNODB;

Il est aussi possible de modifier une table existante d'un autre type vers InnoDB :

1.ALTER TABLE nom table type = innodb.

Si une erreur survient lors de la modification d'une table, vérifiez si celle-ci ne contient pas
d'index full text. Il convient aussi non pas d'utiliser ALTER TABLE, mais de supprimer la table
en prenant soin d'avoir effectué un DUMP de la table, puis d'importer les données dans la
table en utilisant set autocommit = 0 avant l'insertion et un commit à la fin.

Il est à noter que la compression de tables MYISAM n'est pas supportée sous InnoDB.
Le support InnoDB permet l'utilisation des transactions, des contraintes sur les clés
étrangères et de gérer des verrous au niveau des enregistrements et des tables.

Pour illustrer notre propos, nous allons créer deux tables que nous utiliserons en exemple.

Cet exemple est une gestion, simplifiée à l'extrême, de salles de classe. Les instituteurs
(table users) sont liés à une et une seule salle.
1.set auto_commit = 1;
2.Create database innodbtest;
3.CREATE TABLE users (
4. id int(11) NOT NULL auto_increment,
5. nom varchar(25) default NULL,
6. prenom varchar(25) default NULL,
7. age int(11) default NULL,
8. PRIMARY KEY (id)
9.) Engine=InnoDB;
10.
11.CREATE TABLE salles (
12.idsalle int(11) NOT NULL auto_increment,
13.num char(3) default NULL,
14.refuser int(11) default NULL,
15.PRIMARY KEY (idsalle),
16.index user_ref (refuser),
17.foreign key theuser (refuser) references users(id) on delete set null 18.)
Engine=InnoDB;
19.
20.grant select, insert, update, delete on innodbtest.* touser1@localhost;
21.grant select, insert, update, delete on innodbtest.* to user2@localhost;
22.flush privileges;
23.flush tables;

c. Les transactions

Ici, nous allons parler du langage de transaction de données. Ce sont des commandes
SQL utilisées pour gérer les modifications qui affectent les données de la base de données.
Fondamentalement, nous utilisons ces commandes dans la transaction ou pour créer un
point stable lors des changements de base de données auquel nous pouvons annuler l’état
de la base de données si nécessaire.

Commandes TCL :
START TRANSACTION – Pour commencer la transaction
COMMIT – Rend les changements de la base de donnée permanents
ROLLBACK – annule une transaction en cas d’erreur et repars au statut précédent de la
base de données. (Si vous avez déjà Commit vous ne pouvez plus Rollback)
SAVEPOINT – définit un point de sauvegarde dans une transaction.
SET TRANSACTION – spécifiez les caractéristiques de la transaction.

Une chose à savoir est que MySQL est auto-commit donc toutes les transactions ou
changements sont enregistrés de manière automatique.
Pour annuler le auto-commit on doit Utiliser la commande START TRANSACTION
Si on sort de MySQL, on se rend compte que les changements sur la table n’ont pas été
effectués ou enregistrés. Il faudra donc utiliser la commande commit pour sauvegarder
les changements. Tant que ce n’est pas fait, les changements dans le serveur sont
temporaires.
Il faut utiliser à nouveau la commande START TRANSACTION pour désactiver l’auto-
commit car les commandes rollback et commit sont à usage unique.
On peut aussi faire des sauvegardes à plusieurs niveaux avec savepoint et revenir à
chaque changement de la modification de la base de données.

L'un des buts d'InnoDB est de pouvoir, à tout moment, revenir à l'état antérieur d'une table
après une transaction. En d'autres termes, seules les transactions validées sont considérées
comme durables et leurs données enregistrées dans les tables.

Par défaut et jusqu'à la version 4.0.4 le niveau d'isolation des transactions et REPEATABLE
READ. Les versions supérieures permettent de changer ce niveau d'isolation vers READ
UNCOMMITED, READ COMMITED, SERIALISABLE.

1. SET [SESSION | GLOBAL]


2. TRANSACTION ISOLATION LEVEL

d. Niveau d'isolation

REPEATABLE READ lit et bloque les index en laissant la possibilité d'effectuer des inserts.

READ UNCOMMITED lit les enregistrements sans possibilité de regarder à la dernière version.

READ COMMITED : une instruction peut seulement voir les lignes validées avant qu'elle ne
débute.

SERIALISABLE : la transaction en cours peut seulement voir les lignes validées avant qu'une
première requête ou une instruction de modification de données soit exécutée dans la
transaction.

10. Les types de tables


Les types de table ont été introduits à partir de MySQL 3.23!
Lors de la création d'une table, vous pouvez préciser à MySQL quel type de table utiliser.
MySQL va, dans tous les cas, créer un fichier .frm pour y noter la structure de la table, et
les définitions des colonnes. Suivant le type de table, l'index et les données seront
enregistrées dans d'autres fichiers.
Vous pouvez convertir des tables d'un type à l'autre avec la commande ALTER TABLE.
ISAM Ce type est le type original de pour les tables MySQL. Il utilise un index B-tree. L'index
est enregistré dans un fichier avec l'extension.ISM et les données sont enregistrées dans un
fichier avec l'extension .ISD.
Vous pouvez vérifier et réparer les tables ISAM avec l'utilitaire isamchk. Les tables ISAM ne
are sont pas portables d'une plateforme à l'autre

11. Les index


En informatique, dans les bases de données, un index est une structure de
données utilisée et entretenue par le système de gestion de base de données (SGBD)
pour lui permettre de retrouver rapidement les données. L'utilisation d'un index simplifie et
accélère les opérations de recherche, de tri, de jointure ou d'agrégation effectuées par
le SGBD.
L’index placé sur une table va permettre au SGBD d'accéder très rapidement aux
enregistrements, selon la valeur d'un ou plusieurs champs
Un index est une structure entretenue automatiquement, qui permet de localiser
facilement des enregistrements dans un fichier. L'utilisation des index est basée sur
l'observation suivante: pour trouver un livre dans une bibliothèque, au lieu d'examiner un
par un chaque livre (ce qui correspond à une recherche séquentielle), il est plus rapide
de consulter le catalogue où ils sont classés par thème, auteur et titre. Chaque entrée
d'un index comporte une valeur extraite des données et un pointeur sur son
emplacement d'origine. Un enregistrement peut être ainsi facilement retrouvé en
recherchant sa localisation dans l'index.
Un index peut être ordonné, haché, dense ou épars:

• Un index ordonné contient une liste de valeurs extraites d'une table et triés.
• Dans un index haché les valeurs sont transformées par une fonction de hachage.
• Dans un index dense, la totalité des enregistrements d'une table est référencée.
• Dans un index épars seule une partie des enregistrements est référencée.
L'index primaire d'une table est le premier qui est utilisé pour localiser les enregistrements.
Une table peut également contenir des index secondaires en complément de l'index
primaire2. Chaque table peut comporter un ou plusieurs index. Un index peut être issu
d'un seul champ ou peut combiner plusieurs champs
Les index sont utilisés par les SGBD pour de nombreuses opérations. Les index facilitent les
opérations de tri, de recherche, de regroupement et de jointure1. La structure la plus
courante des index est l'arbre B3. D'autres structures existent mais sont rarement utilisées
- ISAM, les tables de hachage ou les bitmaps.

• structure en arbre: un tronc auquel sont attachées des branches avec des
ramifications et des feuilles au bout. Toutes les recherches sont effectuées en partant
du tronc. En recherchant parmi les branches celle qui contient la valeur à trouver,
jusqu'à avoir atteint une feuille.
Pour accélérer les opérations, les arbres d'index sont enregistrés en un bloc comportant
un très grand nombre de ramifications: Les disques durs, sur lesquels sont enregistrés les
index, lisent les données par bloc de plusieurs kilooctets et le temps nécessaire pour lire un
bloc est généralement très inférieur au temps nécessaire pour le localiser. Avec cette
construction, la recherche d'un enregistrement dans un lot de plusieurs millions nécessite
alors seulement 2 ou 3 opérations.
Les index peuvent être ajoutés par une commande SQL. L'existence d'index est cruciale
pour accélérer les opérations de manipulation de données. L'utilisation inadéquate des
index est la principale cause de déception. Le système de gestion de base de données
(abr. SGBD) ne trouvera pas les index qui sont nécessaires pour effectuer efficacement les
opérations qui lui sont demandées. Les raisons de l'utilisation inadéquate sont que la
documentation des SGBD concernant l'utilisation des index est souvent vague et
succincte, et met en avant leurs inconvénients plus que leurs avantages.
Les index sont en particulier exploités par l´optimiseur de requêtes:

• L'optimiseur est le composant des SGBD qui recherche la manière la plus économique
d'exécuter une requête. L'optimiseur examine les différents scénarios possibles et
estime le nombre d'opérations nécessaires pour chaque scénario, puis opte pour le
scénario qui en demande le moins. Le nombre d'opérations nécessaires dépend de la
présence d'index, ainsi que du nombre de lignes de la table et de la répartition des
valeurs5.

Types d'index

• La structure la plus courante pour les index est l'arbre B (B-tree). En stockant les
différentes valeurs du champ dans un arbre équilibré, le SGBD pourra hiérarchiser les
enregistrements d'après un champ dont la plage de valeurs est infinie (ou presque).
• Un autre type d'index est l'index bitmap. Il consiste en une simple table indiquant, pour
chaque valeur possible du champ, la liste des enregistrements ayant cette valeur pour
ce champ.
Cependant, pour être efficace, il nécessite que le SGBD puisse accéder
directement à une valeur donnée. Il n'est donc applicable que sur les colonnes
pour lesquelles le nombre de valeurs est limité et ordonné.

• On trouve également des index par table de hachage. L'inconvénient majeur d'un
tel index est de ne permettre que les sélections par égalité, puisqu'il ne conserve
pas la notion d'ordre. Si n est le nombre d'enregistrements d'une table, l'utilisation
d'une table de hachage équilibrée peut permettre de réduire le nombre
d'enregistrements à parcourir à la racine carrée de n (la table étant alors
composée de valeurs de hachage accédant chacune à N enregistrements). La
même remarque sur l'efficacité existe pour l'index bitmap : le SGBD doit pouvoir
accéder directement à une valeur de hachage donnée, sans avoir à parcourir la
liste des valeurs de hachage possibles.

Impacts sur les performances en modification


Lors de l'insertion ou de la mise à jour d'un enregistrement de la base, il y a une légère
dégradation des performances : le SGBD doit en effet mettre à jour les index pour
qu'ils continuent à refléter l'état des enregistrements. Pour cette raison, on s'attachera,
lors de la conception d'une base de données, à définir uniquement les index qui
seront utilisés par le système. Ceux-ci ne seront d'ailleurs bien repérés que par une
analyse du système (et notamment des mécanismes d'interrogation de la base) en
vue de son optimisation.
Pour créer un indexe il faut taper la commande CREATE INDEX nom_de_l’index ON
nom_de _la_table (champ_selectionné) ;
Pour voir la liste des index d’une table on tape la requête SHOW INDEX FROM
nom_de_la_table ;

12. Les vues

Les vues sont des tables virtuelles issues de l'assemblage d'autres tables en fonction de
critères. Techniquement les vues sont créées à l'aide d'une requête SELECT. Elles ne
stockent pas les données qu'elles contiennent mais conservent juste la requête
permettant de les créer.

La requête SELECT qui génère la vue référence une ou plusieurs tables. La vue peut donc
être, par exemple, une jointure entre différentes tables, l'aggrégation ou l'extraction de
certaines colonnes d'une table. Elle peut également être créée à partir d'une autre vue.

Les vues sont souvent en lecture seule et ne permettent donc que de lire des données.
Cependant MySQL permet la création de vues modifiables sous certaines conditions :
• La requête qui génère la vue doit permettre à MySQL de retrouver la trace de
l'enregistrement à modifier dans la ou les tables sous-jacentes ainsi que celle de
toutes les valeurs de chaque colonne. La requête SELECT créant la vue ne doit
donc pas contenir de clause DISTINCT, GROUP BY, HAVING... et autres fonctions
d'aggrégation. La liste complète est disponible dans la documentation de MySQL.
Les vues peuvent être utilisées pour différentes raisons. Elles permettent de :
• Contrôler l'intégrité en restreignant l'accès aux données pour améliorer la
confidentialité.
o Partitionnement vertical et/ou horizontal pour cacher des champs aux
utilisateurs, ce qui permet de personnaliser l'affichage des informations suivant
le type d'utilisateur.
• Masquer la complexité du schéma.
o Indépendance logique des données, utile pour donner aux utilisateurs l’accès
à un ensemble de relations représentées sous la forme d'une table. Les
données de la vue sont alors des champs de différentes tables regroupées, ou
des résultats d’opérations sur ces champs.
• Modifier automatiquement des données sélectionnées (sum(), avg(), max(),...).
o Manipuler des valeurs calculées à partir d'autres valeurs du schéma.
• Conserver la structure d'une table si elle doit être modifiée.
o Le schéma peut ainsi être modifié sans qu'il ne soit nécessaire de changer les
requêtes du côté applicatif.

Les droits nécessaires

Pour créer une vue l'utilisateur doit avoir le droit CREATE VIEW. Il faut également avoir la
permission de sélectionner toutes les colonnes qui apparaissent dans la commande
SELECT spécifiant ce qu'est la vue.
De plus si la clause REPLACE est utilisée, le droit DROP est également nécessaire.
Le droit SHOW VIEW donne la possibilité d'exécuter la commande SHOW CREATE VIEW.
Cette commande permet d'obtenir les informations de création d'une vue. Une autre
façon d'obtenir ces informations est d'interroger la table view du
schéma information_schema. Cette information sera exhaustive seulement pour les vues
que vous avez créé.

Syntaxe d'une vue

CREATE VIEW

La commande MySQL pour créer une vue est assez proche de la syntaxe du standard
SQL.

Syntaxe de création d'une vue sous MySQL

CREATE VIEW nom_de_la_vue AS requête_select

Création d'une vue pour la relation "etudiant"

CREATE TABLE etudiant


(
id_etudiant INT UNSIGNED PRIMARY KEY,
nom CHAR(30),
prenom CHAR(30),
age TINYINT UNSIGNED,
cursus ENUM('Licence', 'Master', 'Doctorat')
);

CREATE VIEW v_etudiant_liste AS SELECT nom, prenom FROM etudiant;


Après avoir créé la table etudiant, on crée la vue v_etudiant_liste qui contient le nom et
le prénom des étudiants.
Il est possible d'ajouter d'autres informations lors de la création de la vue :

Syntaxe d'une vue MySQL

CREATE

[OR REPLACE]
[ALGORITHM = {UNDEFINED | MERGE | TEMPTABLE}]
[DEFINER = { user | CURRENT_USER }]
[SQL SECURITY { DEFINER | INVOKER }]
VIEW nom_de_la_vue [(colonne(s))]
AS requête_select
[WITH [CASCADED | LOCAL] CHECK OPTION]
Voici dans le détail les différentes clauses.
OR REPLACE : si une vue du même nom existe, elle est alors supprimée et remplacée par
la nouvelle.
ALGORITHM = {UNDEFINED | MERGE | TEMPTABLE} : clause non standard, qui prend les
valeurs suivantes :
• UNDEFINED : C'est la valeur par défaut. MySQL décide lui-même quel algorithme
choisir entre MERGE et TEMPTABLE.
• MERGE utilise la requête SQL ayant servi à la création de la vue comme base
d'opération. En d'autres termes, faire une requête sur la vue revient à faire la même
requête sur la ou les tables sous-jacentes.
• TEMPTABLE utilise une table temporaire créée pour stocker (temporairement) les
résultats. Un intérêt de cet algorithme est de libérer plus rapidement les verrous sur
les tables sous-jacentes. Les autres requêtes sont alors moins pénalisées.
Il faut noter également qu'une vue avec pour valeur MERGE sera modifiable alors
qu'avec la valeur TEMPTABLE elle ne le sera pas.
DEFINER = { user | CURRENT_USER } : clause non standard qui permet d'assigner un
créateur à la vue. Par défaut, le créateur de la vue est DEFINER = current_user, c'est-à-
dire, l'utilisateur qui exécute la commande CREATE VIEW. Il est cependant possible
d'assigner la vue à un autre compte utilisateur, à condition d'avoir le droit SUPER.
SQL SECURITY { DEFINER | INVOKER } : clause non standard encore qui permet de définir
quels seront les droits de l'utilisateur lors de l'exécution de la vue. Deux valeurs sont
possibles :
• DEFINER qui permet d'exécuter la vue avec les droits du créateur. C'est la valeur par
défaut.
• INVOKER qui permet d'exécuter la vue avec ses propres droits.
WITH [CASCADED | LOCAL] CHECK OPTION : permet de vérifier les contraintes spécifiées
dans la clause WHERE d'une vue modifiable lorsque l'on y modifie ses données. Deux
valeurs sont possibles :
• CASCADED, la valeur par défaut. Elle permet de vérifier la contrainte pour la vue
ainsi que pour les vues sous-jacentes dont elle dérive.
• LOCAL qui permet de vérifier seulement la contrainte de la vue.

ALTER VIEW

Une fois la vue créée, il est bien évidement possible de la modifier avec la
commande ALTER VIEW.

Editer une vue à l'ordre ALTER

ALTER definer='secretaire'@'localhost'
VIEW v_etudiant_liste AS SELECT nom, prenom, cursus FROM etudiant;
Cette commande modifie la clause DEFINER en lui assignant le
compte secretaire@localhost et modifie la définition de la vue en rajoutant le champ
cursus.

DROP VIEW

L'ordre DROP VIEW permet d'effacer une vue.

Supprimer des vues à partir de l'ordre DROP VIEW

DROP VIEW v_etudiant_liste, v_prof_liste;


Supprime les vues v_etudiant_liste et v_prof_liste. Il est possible d'ajouter la clause IF
EXISTS qui retourne un avertissement au lieu d'une erreur si la vue à effacer n'existe pas.
Restrictions

Lors de la création d'une vue, certaines contraintes doivent être prises en compte :
• Il n'est pas possible de créer un index sur une vue.
• La vue ne peut pas contenir de sous-requêtes dans la clause FROM du SELECT.
• Il n'est pas possible d'utiliser de variables dans une vue.
• Les objets (tables et vues) nécessaires à la création de la vue doivent exister avant
de la créer.
• Si un objet référencé par la vue est effacé, la vue n'est alors plus accessible.
• Une vue ne peut référencer une table temporaire (TEMPORARY TABLE).
• Il n'est pas possible de créer des vues temporaires.
• Il n'est pas possible d'associer un trigger à une vue.
• La définition d'une vue est "gelée" dans une requête préparée.
Par exemple :

mysql> CREATE VIEW ma_vue AS SELECT 'première valeur';


Query OK, 0 rows affected (0.24 sec)

mysql> desc ma_vue;


+-----------------+-------------+------+-----+---------+-------+
| FIELD | Type | NULL | Key | DEFAULT | Extra |
+-----------------+-------------+------+-----+---------+-------+
| première valeur | VARCHAR(15) | NO | | | |
+-----------------+-------------+------+-----+---------+-------+
1 row IN SET (0.50 sec)

mysql> PREPARE req_prepare FROM 'SELECT * FROM ma_vue';


Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> EXECUTE req_prepare;


+-----------------+
| première valeur |
+-----------------+
| première valeur |
+-----------------+
1 row IN SET (0.01 sec)

ALTER VIEW ma_vue AS SELECT 'deuxième valeur';


Query OK, 0 rows affected (0.05 sec)

mysql> desc ma_vue;


+-----------------+-------------+------+-----+---------+-------+
| FIELD | Type | NULL | Key | DEFAULT | Extra |
+-----------------+-------------+------+-----+---------+-------+
| deuxième valeur | VARCHAR(15) | NO | | | |
+-----------------+-------------+------+-----+---------+-------+
1 row IN SET (0.00 sec)

mysql> EXECUTE req_prepare;


+-----------------+
| première valeur |
+-----------------+
| première valeur |
+-----------------+
1 row IN SET (0.00 sec)
Il faut en fait recréer la requête préparée :

Utiliser une vue dans une requête préparée

mysql> DEALLOCATE PREPARE req_prepare;

Query OK, 0 rows affected (0.00 sec)

mysql> PREPARE req_prepare FROM 'SELECT * FROM ma_vue';


Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> EXECUTE req_prepare;


+-----------------+
| deuxième valeur |
+-----------------+
| deuxième valeur |
+-----------------+
1 row IN SET (0.00 sec)

Utiliser les vues

Voici quelques exemples pratiques très simples pour illustrer les différents besoins que
peuvent combler les vues. On aura ici, une vue administrateur de base de données. Les
objets créés ne seront pas utilisés directement par les utilisateurs mais aux travers d'une
application.

Contrôler l'intégrité en restreignant l'accès aux données pour améliorer la


confidentialité

La table employe de mon application, contient toutes les informations sur les employées.

Structure de la table " employe "

CREATE TABLE `employe`


(
`id_employe` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
`nom` CHAR(45) NOT NULL,
`prenom` CHAR(45) NOT NULL,
`tel_perso` CHAR(10) NOT NULL,
`tel_bureau` CHAR(10) NOT NULL,
`statut` CHAR(45) NOT NULL,
`ville` CHAR(45) NOT NULL,
`salaire` DECIMAL(7,2) NOT NULL,
PRIMARY KEY (`id_employe`)
);
Toutes les informations présentes dans cette table ne sont pas pertinentes pour les trois
types d'utilisateurs suivant : le comptable, la secrétaire pour Paris et la secrétaire pour le
reste de la France.
Une solution est donc de créer une vue par type.

Pour le comptable, il faut avoir accès aux champs nom, prénom, téléphone du bureau,
statut et salaire de chaque employé. On fait donc un partitionnement vertical de la
table employe. La vue correspondante est la suivante :

Création de la vue pour le comptable

CREATE ALGORITHM=MERGE SQL SECURITY DEFINER VIEW `v_comptable` AS


SELECT nom, prenom, tel_bureau, statut, salaire FROM employe;
Le profil "secrétaire pour Paris", n'a pas besoin de l'identifiant et il ne doit surtout pas avoir
accès aux salaires, cette information étant confidentielle. Autre restriction, ce profil ne
gère que les employés de la filiale de Paris. Le partitionnement est vertical et horizontal.

Création de la vue pour la secrétaire de Paris

CREATE ALGORITHM= MERGE SQL SECURITY DEFINER VIEW `v_secretaire_paris` AS


SELECT nom, prenom, tel_perso, tel_bureau, statut FROM employe
WHERE ville = 'Paris';
Notre troisième vue est très proche de la deuxième. La seule différence vient du fait que
là, on veut les employés qui ne travaillent pas à Paris.

Création de la vue pour les employés de Province

CREATE ALGORITHM= MERGE SQL SECURITY DEFINER VIEW `v_secretaire_autre` AS


SELECT nom, prenom, tel_perso, tel_bureau, statut FROM employe
WHERE ville <> 'Paris';

Masquer la complexité du schéma

L'équipe de développement doit écrire un moteur de recherches pour une application


de commerce électronique. Voici un extrait des tables de la base de données impliquées
dans la recherche des produits du site.

13. Les verrous

Complément indispensable des transactions, les verrous permettent de sécuriser les


requêtes en bloquant ponctuellement et partiellement l'accès aux données.

Il s'agit d'un gros chapitre, avec beaucoup d'informations. Il y a par conséquent un


maximum d'exemples pour vous aider à comprendre le comportement des verrous selon
les situations.

• Qu'est-ce qu'un verrou ?


• Quel est le comportement par défaut de MySQL par rapport aux verrous ?
• Quand et comment poser un verrou de table ?
• Quand et comment poser un verrou de ligne ?
• Comment modifier le comportement par défaut de MySQL ?

• Principe
• Syntaxe et utilisation : verrous de table
• Syntaxe et utilisation : verrous de ligne
• Niveaux d'isolation

Principe

Lorsqu'une session MySQL pose un verrou sur un élément de la base de données, cela
veut dire qu'il restreint, voire interdit, l'accès à cet élément aux autres sessions MySQL qui
voudraient y accéder.

Verrous de table et verrous de ligne

Il est possible de poser un verrou sur une table entière, ou seulement sur une ou plusieurs
0lignes d'une table. Étant donné qu'un verrou empêche l'accès d'autres sessions, il est en
général plus intéressant de poser un verrou sur la plus petite partie de la base possible.

Par exemple, si l'on travaille avec les chiens de la table Animal.

• On peut poser un verrou sur toute la table Animal. Dans ce cas, les autres sessions
n'auront pas accès à cette table, tant que le verrou sera posé. Qu'elles veuillent en
utiliser les chiens, les chats, ou autre, tout leur sera refusé.
• On peut aussi poser un verrou uniquement sur les lignes de la table qui contiennent
des chiens. De cette manière, les autres sessions pourront accéder aux chats, aux
perroquets, etc. Elles pourront toujours travailler, tant qu'elles n'utilisent pas les
chiens.

Cette notion d'accès simultané aux données par plusieurs sessions différentes s'appelle
la concurrence. Plus la concurrence est possible, donc plus le nombre de sessions
pouvant accéder aux données simultanément est grand, mieux c'est. En effet, prenons
l'exemple d'un site web. En général, on préfère permettre à plusieurs utilisateurs de surfer
en même temps, sans devoir attendre entre chaque action de pouvoir accéder aux
informations chacun à son tour. Or, chaque utilisateur crée une session chaque fois qu'il
se connecte à la base de données (pour lire les informations ou les modifier). Préférez
donc (autant que possible) les verrous de ligne aux verrous de table !

Avertissements

Les informations données dans ce chapitre concernent exclusivement MySQL, et en


particulier les tables utilisant les moteurs MyISAM ou InnoDB (selon le type de verrou
utilisé). En effet, les verrous sont implémentés différemment selon les SGDB, et même selon
le moteur de table en ce qui concerne MySQL. Si le principe général reste toujours le
même, certains comportements et certaines options peuvent différer d'une
implémentation à l'autre. N'hésitez pas à vous renseigner plus avant.

Par ailleurs, je vous présente ici les principes généraux et les principales options, mais il
faut savoir qu'il y a énormément à dire sur les verrous, et que j'ai donc dû faire un sérieux
tri des informations avant de rédiger ce chapitre. À nouveau, en cas de doute, ou si vous
avez besoin d'informations précises, je vous conseille vraiment de consulter la
documentation officielle (si possible en anglais, car elle est infiniment plus complète qu'en
français).

Enfin, dernier avertissement : de nombreux changements dans l'implémentation des


verrous sont advenus lors du développement des dernières versions de MySQL. Aussi, la
différence entre les verrous dans la version 5.0 et la version 5.5 est assez importante. Tout
ce que je présente dans ce chapitre concerne la version 5.5. Vérifiez bien votre version,
et si vous consultez la documentation officielle, prenez bien celle qui concerne votre
propre version.

Modification de notre base de données

Nous allons ajouter deux tables à notre base de données, afin d'illustrer au mieux l'intérêt
et l'utilisation des verrous : une table Client, qui contiendra les coordonnées des clients de
notre élevage, et une table Adoption, qui contiendra les renseignements concernant les
adoptions faites par nos clients. Dorénavant, certains animaux présents dans notre
table Animal ne seront plus disponibles, car ils auront été adoptés. Nous les garderons
cependant dans notre base de données. Avant toute adoption, il nous faudra donc
vérifier la disponibilité de l'animal.

Voici les requêtes à effectuer pour faire ces changements.

Afficher/Masquer le contenu masqué

La table Adoption ne contient pas de colonne id auto-incrémentée. Par contre, on a


bien défini une clé primaire, mais une clé primaire composite (sur plusieurs colonnes). En
effet, une adoption est définie par un client adoptant un animal. Il n'est pas nécessaire
d'ajouter une colonne supplémentaire pour définir individuellement chaque ligne ; le
couple (client_id, animal_id) fait très bien l'affaire (il est composé de deux SMALLINT, donc
les recherches sur cette clé seront rapides). Notez que nous définissons également un
index UNIQUE sur la colonne animal_id. Par conséquent, on aurait même pu définir
directement animal_id comme étant la clé primaire. Je trouvais cependant plus logique
d'inclure le client dans la définition d'une adoption. C'est un choix plutôt arbitraire, qui a
surtout comme avantage de vous montrer un exemple de clé composite.

Syntaxe et utilisation : verrous de table

Les verrous de table sont les seuls supportés par MyISAM. Ils sont d'ailleurs principalement
utilisés pour pallier en partie l'absence de transactions dans MyISAM. Les tables InnoDB
peuvent également utiliser ce type de verrou.

Pour verrouiller une table, il faut utiliser la commande LOCK TABLES :

1LOCK TABLES nom_table [AS alias_table] [READ | WRITE] [, ...];

• En utilisant READ, un verrou de lecture sera posé ; c'est-à-dire que les autres sessions
pourront toujours lire les données des tables verrouillées, mais ne pourront plus les
modifier.
• En utilisant WRITE, un verrou d'écriture sera posé. Les autres sessions ne pourront plus
ni lire ni modifier les données des tables verrouillées.
Pour déverrouiller les tables, on utilise UNLOCK TABLES. Cela déverrouille toutes les tables
verrouillées. Il n'est pas possible de préciser les tables à déverrouiller. Tous les verrous de
table d'une session sont relâchés en même temps.

Session ayant obtenu le verrou

Lorsqu'une session acquiert un ou plusieurs verrous de table, cela a plusieurs


conséquences pour cette session :

• Elle ne peut plus accéder qu'aux tables sur lesquelles elle a posé un verrou ;
• Elle ne peut accéder à ces tables qu'en utilisant les noms qu'elle a donnés lors du
verrouillage (soit le nom de la table, soit le/les alias donné(s)) ;
• S’il s'agit d'un verrou de lecture (READ), elle peut uniquement lire les données, pas
les modifier.

Exemples : on pose deux verrous, l'un READ, l'autre WRITE, l'un en donnant un alias au nom
de la table, l'autre sans.

1LOCK TABLES Espece READ, -- On pose un verrou de lecture sur Espece


2 Adoption AS adopt WRITE; -- et un verrou d'écriture sur Adoption avec l'alias adopt

Voyons maintenant le résultat de ces différentes requêtes.

1. Sélection dans Espece, sans alias.

1SELECT id, nom_courant FROM Espece;

id nom_courant
1 Chien
2 Chat
3 Tortue d'Hermann
4 Perroquet amazone
5 Rat brun

Pas de problème, on a bien un verrou sur Espece, sans alias.

2. Sélection dans Espece, avec alias.

1SELECT id, nom_courant


2FROM Espece AS table_espece;

1ERROR 1100 (HY000): Table 'table_espece' was not locked with LOCK TABLES

Par contre, si l'on essaye d'utiliser un alias, cela ne fonctionne pas. Le verrou est posé
sur Espece, pas sur Espece AS table_espece.

3. Modification dans Espece, sans alias.


1UPDATE Espece
2SET description = 'Petit piaf bruyant'
3WHERE id = 4;

1ERROR 1099 (HY000): Table 'Espece' was locked with a READ lock and can't be updated

Avec ou sans alias, impossible de modifier la table Espece, puisque le verrou que l'on
possède dessus est un verrou de lecture.

4. Sélection dans Adoption, sans alias.

1SELECT client_id, animal_id


2FROM Adoption;

1ERROR 1100 (HY000): Table 'Adoption' was not locked with LOCK TABLES

Cette fois, c'est le contraire, sans alias, ça ne passe pas.

5. Sélection dans Adoption, avec alias.

1SELECT client_id, animal_id


2FROM Adoption AS adopt
3WHERE client_id = 4;

client_id animal_id
4 26
4 41

6. Modification dans Adoption, sans alias.

1UPDATE Adoption
2SET paye = 0
3WHERE client_id = 10 AND animal_id = 49;

1ERROR 1100 (HY000): Table 'Adoption' was not locked with LOCK TABLES

Idem pour la modification, l'alias est indispensable.

7. Modification dans Adoption, avec alias.

1UPDATE Adoption AS adopt


2SET paye = 0
3WHERE client_id = 10 AND animal_id = 49;
1Query OK, 1 row affected (0.03 sec)

Il faut donc penser à acquérir tous les verrous nécessaires aux requêtes à exécuter. De
plus, il faut les obtenir en une seule requête LOCK TABLES. En effet, LOCK
TABLES commence par enlever tous les verrous de table de la session avant d'en acquérir
de nouveaux. Il est bien entendu possible de poser plusieurs verrous sur la même table en
une seule requête afin de verrouiller son nom ainsi qu'un ou plusieurs alias.

Exemples : on pose un verrou de lecture sur Adoption, puis avec une seconde requête,
on pose deux verrous de lecture sur la table Espece, l'un avec alias, l'autre sans.

1UNLOCK TABLES; -- On relâche d'abord les deux verrous précédents


2
3LOCK TABLES Adoption READ;
4LOCK TABLES Espece READ, Espece AS table_espece READ;

Une fois ces deux requêtes effectuées, nous aurons donc bien deux verrous de lecture sur
la table Espece : un avec son nom, l'autre avec un alias. Par contre, le verrou
sur Adoption n'existera plus puisqu'il aura été relâché par l'exécution de la seconde
requête LOCK TABLES.

1. Sélection dans Espece, sans alias.

1SELECT id, nom_courant FROM Espece;

id nom_courant
1 Chien
2 Chat
3 Tortue d'Hermann
4 Perroquet amazone
5 Rat brun

2. Sélection dans Espece, avec alias.

1SELECT id, nom_courant FROM Espece AS table_espece;

id nom_courant
1 Chien
2 Chat
3 Tortue d'Hermann
4 Perroquet amazone
5 Rat brun

Avec ou sans alias, on peut sélectionner les données de la table Espece, puisque l'on a
un verrou sur Espece et sur Espece AS table_espece.
3. Sélection dans Espece, avec mauvais alias.

1SELECT id, nom_courant FROM Espece AS table_esp;

1ERROR 1100 (HY000): Table 'table_esp' was not locked with LOCK TABLES

Bien entendu, cela ne fonctionne que pour l'alias que l'on a donné lors du verrouillage.

4. Sélection dans Adoption, sans alias.

1SELECT * FROM Adoption;

1ERROR 1100 (HY000): Table 'Adoption' was not locked with LOCK TABLES

Le verrou sur Adoption a été relâché lorsque l'on a posé les verrous sur Espece. On ne
peut donc pas lire les données d'Adoption (avec ou sans alias).

Conséquences pour les autres sessions

Si une session a obtenu un verrou de lecture sur une table, les autres sessions :

• Peuvent lire les données de la table ;


• Peuvent également acquérir un verrou de lecture sur cette table ;
• Ne peuvent pas modifier les données, ni acquérir un verrou d'écriture sur cette
table.

Si par contre une session a obtenu un verrou d'écriture, les autres sessions ne peuvent
absolument pas accéder à cette table tant que ce verrou existe.

Exemples : ouvrez un deuxième client MySQL et connectez-vous à votre base de


données, afin d'avoir deux sessions ouvertes.

1. Sélection sur des tables verrouillées à partir d'une autre session.

Session 1 :

1LOCK TABLES Client READ, -- Verrou de lecture sur Client


2 Adoption WRITE; -- Verrou d'écriture sur Adoption

Session 2 :

1SELECT id, nom, prenom, ville, email


2FROM Client
3WHERE ville = 'Houtsiplou';
id nom prenom ville email
1 Dupont Jean Houtsiplou jean.dupont@email.com
12 Broussaille Virginie Houtsiplou vibrousaille@email.com

La sélection sur Client se fait sans problème.

Session 2 :

1SELECT *
2FROM Adoption
3WHERE client_id = 4;

Par contre, la sélection sur Adoption ne passe pas. La session se bloque, jusqu'à ce que la
session 1 déverrouille les tables avec UNLOCK TABLES.

2. Modification sur des tables verrouillées à partir d'une autre session.

Reverrouillez les tables avec la session 1 :

1LOCK TABLES Client READ, -- Verrou de lecture sur Client


2 Adoption WRITE; -- Verrou d'écriture sur Adoption

Session 2 :

1UPDATE Client
2SET pays = 'Suisse'
3WHERE id = 5;

La modification sur Client, contrairement à la sélection, est bloquée jusqu'au


déverrouillage. Déverrouillez puis verrouillez à nouveau avec la session 1.

Session 2:

1UPDATE Adoption
2SET paye = 1
3WHERE client_id = 3;

Bien entendu, la modification sur la table Adoption attend également que les verrous
soient relâchés par la session 1.

En ce qui concerne la pose de verrous de table par les autres sessions, faites vos propres
tests, mais simplement : si une session peut lire les données d'une table, elle peut
également poser un verrou de lecture. Si une session peut modifier les données d'une
table, elle peut également poser un verrou d'écriture.
Interaction avec les transactions

Si l'on utilise des tables MyISAM, il n'y a évidemment aucune précaution particulière à
prendre par rapport aux transactions lorsqu'on utilise des verrous de table (les tables
MyISAM étant non-transactionnelles). Par contre, si on utilise des tables InnoDB, il convient
d'être prudent. En effet :

• START TRANSACTION ôte les verrous de table ;


• les commandes LOCK TABLES et UNLOCK TABLES provoquent une validation
implicite si elles sont exécutées à l'intérieur d'une transaction.

Pour utiliser à la fois les transactions et les verrous de table, il faut renoncer à démarrer
explicitement les transactions, et donc utiliser le mode non-autocommit. Lorsque l'on est
dans ce mode, il est facile de contourner la validation implicite provoquée par LOCK
TABLES et UNLOCK TABLES : il suffit d'appeler LOCK TABLES avant toute modification de
données, et de commiter/annuler les modifications avant d'exécuter UNLOCK TABLES.

Exemple :

1SET autocommit = 0;
2LOCK TABLES Adoption WRITE; -- La validation implicite ne commite rien puisque aucun cha
3
4UPDATE Adoption SET date_adoption = NOW() WHERE client_id = 9 AND animal_id = 54;
5SELECT client_id, animal_id, date_adoption FROM Adoption WHERE client_id = 9;
6
7ROLLBACK;
8UNLOCK TABLES; -- On a annulé les changements juste avant donc la validation implicite n
9SELECT client_id, animal_id, date_adoption FROM Adoption WHERE client_id = 9;
10 SET autocommit = 1;

Syntaxe et utilisation : verrous de ligne

Ces verrous ne peuvent pas être posés sur une table utilisant le moteur MyISAM ! Tout ce
qui est dit ici concerne les tables InnoDB uniquement.

Comme les verrous de table, les verrous de ligne peuvent être de deux types :

• Les verrous partagés : permettent aux autres sessions de lire les données, mais pas
de les modifier (équivalents aux verrous de table de lecture) ;
• Les verrous exclusifs : ne permettent ni la lecture ni la modification des données
(équivalents aux verrous d'écriture).

Requêtes de modification, insertion et suppression

• Les requêtes de modification et suppression des données posent automatiquement


un verrou exclusif sur les lignes concernées, à savoir les lignes sélectionnées par la
clause WHERE, ou toutes les lignes s'il n'y a pas de clause WHERE (ou s'il n'y a pas
d'index, sur les colonnes utilisées comme nous verrons plus loin).
• Les requêtes d'insertion quant à elles posent un verrou exclusif sur la ligne insérée.

Requêtes de sélection

Les requêtes de sélection, par défaut, ne posent pas de verrous. Il faut donc en poser
explicitement au besoin.

Verrou partagé

Pour poser un verrou partagé, on utilise LOCK IN SHARE MODE à la fin de la


requête SELECT.

1SELECT * FROM Animal WHERE espece_id = 5 LOCK IN SHARE MODE;

Cette requête pose donc un verrou partagé sur les lignes de la table Animal pour
lesquelles espece_id vaut 5.

Ce verrou signifie en fait, pour les autres sessions : "Je suis en train de lire ces données.
Vous pouvez venir les lire aussi, mais pas les modifier tant que je n'ai pas terminé.".

Verrou exclusif

Pour poser un verrou exclusif, on utilise FOR UPDATE à la fin de la requête SELECT.

1SELECT * FROM Animal WHERE espece_id = 5 FOR UPDATE;

Ce verrou signifie aux autres sessions : "Je suis en train de lire ces données dans le but
probable de faire une modification. Ne les lisez pas avant que j'aie fini (et bien sûr, ne les
modifiez pas).".

Transactions et fin d'un verrou de ligne

Les verrous de ligne ne sont donc pas posés par des commandes spécifiques, mais par
des requêtes de sélection, insertion ou modification. Ces verrous existent donc
uniquement tant que la requête qui les a posés interagit avec les données.

Par conséquent, ce type de verrou s'utilise en conjonction avec les transactions. En effet,
hors transaction, dès qu'une requête est lancée, elle est effectuée et les éventuelles
modifications des données sont immédiatement validées. Par contre, dans le cas d'une
requête faite dans une transaction, les changements ne sont pas validés tant que la
transaction n'a pas été commitée. Donc, à partir du moment où une requête a été
exécutée dans une transaction, et jusqu'à la fin de la transaction
(COMMIT ou ROLLBACK), la requête a potentiellement un effet sur les données. C'est à ce
moment-là (quand une requête a été exécutée mais pas validée ou annulée) qu'il est
intéressant de verrouiller les données qui vont potentiellement être modifiées (ou
supprimées) par la transaction.
Un verrou de ligne est donc lié à la transaction dans laquelle il est posé. Dès que l'on fait
un COMMIT ou un ROLLBACK de la transaction, le verrou est levé.

Exemples
Verrou posé par une requête de modification

Session 1 :

1START TRANSACTION;
2
3UPDATE Client SET pays = 'Suisse'
4WHERE id = 8; -- un verrou exclusif sera posé sur la ligne avec id = 8

Session 2:

1START TRANSACTION;
2
3SELECT * FROM Client
4WHERE id = 8; -- pas de verrou
5
6SELECT * FROM Client
7WHERE id = 8
8LOCK IN SHARE MODE; -- on essaye de poser un verrou partagé

La première session a donc posé un verrou exclusif automatiquement en faisant


un UPDATE.

La seconde session fait d'abord une simple sélection, sans poser de verrou. Pas de
problème, la requête passe.

Ah ? La requête passe ? Et c'est normal ? Et le verrou exclusif alors ?

Oui, c'est normal et c'est important de comprendre pourquoi. En fait, lorsqu'une


session démarre une transaction, elle prend en quelque sorte une photo des tables dans
leur état actuel (les modifications non commitées n'étant pas visibles). La transaction va
alors travailler sur la base de cette photo, tant qu'on ne lui demande pas d'aller vérifier
que les données n'ont pas changé. Donc le SELECT ne voit pas les changements, et ne se
heurte pas au verrou, puisque celui-ci est posé sur les lignes de la table, et non pas sur la
photo de cette table que détient la session.

Et comment fait-on pour demander à la session d'actualiser sa photo ?

On lui demande de poser un verrou ! Lorsqu'une session pose un verrou sur une table, elle
est obligée de travailler vraiment avec la table, et pas sur sa photo. Elle va donc aller
chercher les dernières infos disponibles, et actualiser sa photo par la même occasion. On
le voit bien avec la seconde requête, qui tente de poser un verrou partagé (qui vise
donc uniquement la lecture). Elle va d'abord chercher les lignes les plus à jour et tombe
sur le verrou posé par la première session ; elle se retrouve alors bloquée jusqu'à ce que la
première session ôte le verrou exclusif.

Session 1 :

1COMMIT;

En committant les changements de la session 1, le verrou exclusif posé par la requête de


modification est relâché. La session 2 est donc libre de poser à son tour un verrou
partagé.

On peut également essayer la même manœuvre, avec cette fois-ci un UPDATE plutôt
qu'un SELECT ... LOCK IN SHARE MODE (donc une requête qui va tenter de poser un
verrou exclusif plutôt qu'un verrou partagé).

Session 1 :

1START TRANSACTION;
2
3UPDATE Adoption SET paye = 0
4WHERE client_id = 11;

Session 2 :

1START TRANSACTION;
2
3UPDATE Adoption SET paye = 1
4WHERE animal_id = 32; -- l'animal 32 a été adopté par le client 11

Comme prévu, la seconde session est bloquée, jusqu'à ce que la première session
termine sa transaction. Validez la transaction de la première session, puis de la seconde.
Le comportement sera le même si la deuxième session fait un DELETE sur les lignes
verrouillées, ou un SELECT ... FOR UPDATE.

Verrou posé par une requête d'insertion


Session 1 :

1START TRANSACTION;
2
3INSERT INTO Adoption (client_id, animal_id, date_reservation, prix)
4VALUES (12, 75, NOW(), 10.00);

Session 2 :

1SELECT * FROM Adoption


2WHERE client_id > 13
3LOCK IN SHARE MODE;
4
5SELECT * FROM Adoption
6WHERE client_id < 13
7LOCK IN SHARE MODE;

La première session insère une adoption pour le client 12 et pose un verrou exclusif sur
cette ligne. La seconde session fait deux requêtes SELECT en posant un verrou partagé :
l'une qui sélectionne les adoptions des clients avec un id supérieur à 13 ; l'autre qui
sélectionne les adoptions des clients avec un id inférieur à 13. Seule la seconde
requête SELECT se heurte au verrou posé par la première session, puisqu'elle tente de
récupérer notamment les adoptions du client 12, dont une est verrouillée.

Dès que la session 1 commite l'insertion, la sélection se fait dans la session 2.

Session 1 :

1COMMIT;

Verrou posé par une requête de sélection

Voyons d'abord le comportement d'un verrou partagé, posé par SELECT ... LOCK IN
SHARE MODE.

Session 1 :

1START TRANSACTION;
2
3SELECT * FROM Client
4WHERE id < 5
5LOCK IN SHARE MODE;

Session 2 :
1START TRANSACTION;
2
3SELECT * FROM Client
4WHERE id BETWEEN 3 AND 8;
5
6SELECT * FROM Client
7WHERE id BETWEEN 3 AND 8
8LOCK IN SHARE MODE;
9
10 SELECT * FROM Client
11 WHERE id BETWEEN 3 AND 8
12 FOR UPDATE;

La première session pose un verrou partagé sur les clients 1, 2, 3 et 4. La seconde session
fait trois requêtes de sélection. Toutes les trois concernent les clients 3 à 8 (dont les deux
premiers sont verrouillés).

• Requête 1 : ne pose aucun verrou (travaille sur une "photo" de la table et pas sur les
vraies données) donc s'effectue sans souci.
• Requête 2 : pose un verrou partagé, ce qui est faisable sur une ligne verrouillée par
un verrou partagé. Elle s'effectue également.
• Requête 3 : tente de poser un verrou exclusif, ce qui lui est refusé.

Bien entendu, des requêtes UPDATE ou DELETE (posant des verrous exclusifs) faites par la
deuxième session se verraient, elles aussi, bloquées.

Terminez les transactions des deux sessions (par un rollback ou un commit).

Quant aux requêtes SELECT ... FOR UPDATE posant un verrou exclusif, elles provoqueront
exactement les mêmes effets qu'une requête UPDATE ou DELETE (après tout, un verrou
exclusif, c'est un verrou exclusif).

Session 1 :

1START TRANSACTION;
2
3SELECT * FROM Client
4WHERE id < 5
5FOR UPDATE;

Session 2 :

1START TRANSACTION;
2
3SELECT * FROM Client
4WHERE id BETWEEN 3 AND 8;
5
6SELECT * FROM Client
7WHERE id BETWEEN 3 AND 8
8LOCK IN SHARE MODE;

Cette fois-ci, même la requête SELECT ... LOCK IN SHARE MODE de la seconde session est
bloquée (comme le serait une requête SELECT ... FOR UPDATE, ou une requête UPDATE,
ou une requête DELETE).

En résumé

• On pose un verrou partagé lorsqu'on fait une requête dans le but de lire des
données.
• On pose un verrou exclusif lorsqu'on fait une requête dans le but (immédiat ou non)
de modifier des données.
• Un verrou partagé sur les lignes x va permettre aux autres sessions d'obtenir
également un verrou partagé sur les lignes x, mais pas d'obtenir un verrou exclusif.
• Un verrou exclusif sur les lignes x va empêcher les autres sessions d'obtenir un verrou
sur les lignes x, qu'il soit partagé ou exclusif.

En fait, ils portent plutôt bien leurs noms ces verrous !

Rôle des index

Tentons une nouvelle expérience.

Session 1 :

1START TRANSACTION;
2UPDATE Animal
3SET commentaires = CONCAT_WS(' ', 'Animal fondateur.', commentaires) -On
4ajoute une phrase de commentaire
WHERE date_naissance < '2007-01-01'; -- à tous les animaux nés
avant 2007

Session 2 :

1START TRANSACTION;
2UPDATE Animal
3SET commentaires = 'Aveugle' -- On modifie les commentaires
4WHERE date_naissance = '2008-03-10 13:40:00'; -- De l'animal né le 10 mars 2008 à 13h40

Dans la session 1, on fait un UPDATE sur les animaux nés avant 2007. On s'attend donc à
pouvoir utiliser les animaux nés après dans une autre session, puisque InnoDB pose des
verrous sur les lignes et pas sur toute la table. Pourtant, la session 2 semble bloquée
lorsque l'on fait un UPDATE sur un animal né en 2008. Faites un rollback sur la session 1 ;
ceci débloque la session 2. Annulez également la requête de cette session.

Ce comportement est donc en contradiction avec ce qu'on obtenait précédemment.


Quelle est la différence ?

Le sous-titre vous a évidemment soufflé la réponse : la différence se trouve au niveau des


index. Voyons donc ça ! Voici une commande qui va vous afficher les index présents sur
la table Animal :

1SHOW INDEX FROM Animal;

Table Non_unique Key_name Column_name Null


Animal 0 PRIMARY id
Animal 0 ind_uni_nom_espece_id nom YES
Animal 0 ind_uni_nom_espece_id espece_id
Animal 1 fk_race_id race_id YES
Animal 1 fk_espece_id espece_id
Animal 1 fk_mere_id mere_id YES
Animal 1 fk_pere_id pere_id YES

Une partie des colonnes du résultat montré ici a été retirée pour des raisons de clarté.

Nous avons donc des index sur les colonnes suivantes


: id, nom, mere_id, pere_id, espece_id et race_id. Mais aucun index sur la
colonne date_naissance.

Il semblerait donc que lorsque l'on pose un verrou, avec dans la clause WHERE de la
requête une colonne indexée (espece_id), le verrou est bien posé uniquement sur les
lignes pour lesquelles espece_id vaut la valeur recherchée. Par contre, si dans la
clause WHERE on utilise une colonne non-indexée (date_naissance), MySQL n'est pas
capable de déterminer quelles lignes doivent être bloquées, donc on se retrouve avec
toutes les lignes bloquées.

Pourquoi faut-il un index pour pouvoir poser un verrou efficacement ?

C'est très simple ! Vous savez que lorsqu'une colonne est indexée (que ce soit un index
simple, unique, ou une clé primaire ou étrangère), MySQL stocke les valeurs de cette
colonne en les triant. Du coup, lors d'une recherche sur l'index, pas besoin de parcourir
toutes les lignes, il peut utiliser des algorithmes de recherche performants et trouver
facilement les lignes concernées. S'il n'y a pas d'index par contre, toutes les lignes doivent
être parcourues chaque fois que la recherche est faite, et il n'y a donc pas moyen de
verrouiller simplement une partie de l'index (donc une partie des lignes). Dans ce cas,
MySQL verrouille toutes les lignes.

Cela fait une bonne raison de plus de mettre des index sur les colonnes qui servent
fréquemment dans vos clauses WHERE !

Encore une petite expérience pour illustrer le rôle des index dans le verrouillage de lignes :
Session 1 :

1START TRANSACTION;
2UPDATE Animal -- Modification de tous les rats
3SET commentaires = CONCAT_WS(' ', 'Très intelligent.', commentaires)
4WHERE espece_id = 5;

Session 2 :

1START TRANSACTION;
2UPDATE Animal
3SET commentaires = 'Aveugle'
4WHERE id = 34; -- Modification de l'animal 34 (un chat)
5UPDATE Animal
6SET commentaires = 'Aveugle'
7WHERE id = 72; -- Modification de l'animal 72 (un rat)

La session 1 se sert de l'index sur espece_id pour verrouiller les lignes contenant des rats
bruns. Pendant ce temps, la session 2 veut modifier deux animaux : un chat et un rat, en
se basant sur leur id. La modification du chat se fait sans problème, par contre, la
modification du rat est bloquée, tant que la transaction de la session 1 est ouverte. Faites
un rollback des deux transactions.

On peut conclure de cette expérience que, bien que MySQL utilise les index pour
verrouiller les lignes, il n'est pas nécessaire d'utiliser le même index pour avoir des accès
concurrents.

Lignes fantômes et index de clé suivante

Qu'est-ce qu'une ligne fantôme ?

Dans une session, démarrons une transaction et sélectionnons toutes les adoptions faites
par les clients dont l'id dépasse 13, avec un verrou exclusif.

Session 1 :

1START TRANSACTION;
2
3SELECT * FROM Adoption WHERE client_id > 13 FOR UPDATE; -- ne pas oublier le FOR UPDATE

La requête va poser un verrou exclusif sur toutes les lignes dont client_id vaut 14 ou plus.

client_id animal_id date_reservation date_adoption prix paye


14 58 2012-02-25 2012-02-25 700.00 1
15 30 2008-08-17 2008-08-17 735.00 1
Imaginons maintenant qu'une seconde session démarre une transaction à ce moment-là,
insère et commite une ligne dans Adoption pour le client 15. Si, par la suite, la première
session refait la même requête de sélection avec verrou exclusif, elle va faire apparaître
une troisième ligne de résultat : l'adoption nouvellement insérée (étant donné que pour
poser le verrou, la session va aller chercher les données les plus à jour, prenant en compte
le commit de la seconde session).

Cette ligne nouvellement apparue malgré les verrous est une "ligne fantôme".

Pour pallier ce problème, qui est contraire au principe d'isolation, les verrous posés par
des requêtes de lecture, de modification et de suppression sont des verrous dits "de clé
suivante" ; ils empêchent l'insertion d'une ligne dans les espaces entre les lignes
verrouillées, ainsi que dans l'espace juste après les lignes verrouillées.

L'espace entre ? L'espace juste après ?

Nous avons vu que les verrous se basent sur les index pour verrouiller uniquement les lignes
nécessaires. Voici un petit schéma qui vous expliquera ce qu'est cet "index de clé
suivante".

On peut représenter l'index sur client_id de la table Adoption de la manière suivante (je
ne mets que les client_id < 10)

Si l'on insère une adoption avec 4 pour client_id, l'index va être réorganisé de la manière

suivante :

Mais, si l'on pose un verrou de clé suivante sur l'index, sur les lignes dont client_id vaut 4,
on va alors verrouiller les lignes, les espaces entre les lignes et les espaces juste après.
Ceci va bloquer l'insertion de la nouvelle ligne

Démonstration

On a toujours un verrou exclusif (grâce à notre SELECT ... FOR UPDATE) sur
les client_id supérieurs à 14 dans la session 1 (sinon, reposez-le).

Session 2 :
1START TRANSACTION;
2
3INSERT INTO Adoption (client_id, animal_id, date_reservation, prix)
4VALUES (15, 61, NOW(), 735.00);

L'insertion est bloquée ! Pas de risque de voir apparaître une ligne fantôme. Annulez les
deux transactions.

Exception

Si la clause WHERE concerne un index UNIQUE (cela inclut bien sûr les clés primaires) et
recherche une seule valeur (exemple : WHERE id = 4), alors seule la ligne concernée (si
elle existe) est verrouillée, et pas l'espace juste après dans l'index. Forcément, s'il s'agit
d'un index UNIQUE, l'insertion d'une nouvelle valeur ne changera rien : WHERE id = 4 ne
renverra jamais qu'une seule ligne.

Pourquoi poser un verrou exclusif avec une requête SELECT ?

Après tout, une requête SELECT ne fait jamais que lire des données. Que personne ne
puisse les modifier pendant qu'on est en train de les lire, c'est tout à fait compréhensible.
Mais pourquoi carrément interdire aux autres de les lire aussi ?

Tout simplement parce que certaines données sont lues dans le but prévisible et avoué
de les modifier immédiatement après.

L'exemple typique est la vérification de stock dans un magasin (ou dans un élevage
d'animaux). Un client arrive et veut adopter un chat, on vérifie donc les chats disponibles
pour l'adoption, en posant un verrou partagé :

Session 1 :

1START TRANSACTION;
2
3SELECT Animal.id, Animal.nom, Animal.date_naissance, Race.nom as race, COALESCE(Rac
4FROM Animal
5INNER JOIN Espece ON Animal.espece_id = Espece.id
6LEFT JOIN Race ON Animal.race_id = Race.id -- Jointure externe, on ne veut pas que
7WHERE Espece.nom_courant = 'Chat' -- Uniquement les chats...
8AND Animal.id NOT IN (SELECT animal_id FROM Adoption) -- ... qui n'ont pas encore été ad
9LOCK IN SHARE MODE;

id nom date_naissance race prix


2 Roucky 2010-03-24 02:23:00 NULL 150.00
8 Bagherra 2008-09-11 15:38:00 Maine coon 735.00
29 Fiero 2009-05-14 06:30:00 Singapura 985.00
31 Filou 2008-02-20 15:45:00 Bleu russe 835.00
34 Capou 2008-04-20 03:22:00 Maine coon 735.00
35 Raccou 2006-05-19 16:56:00 Bleu russe 835.00
36 Boucan 2009-05-14 06:42:00 Singapura 985.00
id nom date_naissance race prix
37 Callune 2006-05-19 16:06:00 Nebelung 985.00
38 Boule 2009-05-14 06:45:00 Singapura 985.00
43 Cracotte 2007-03-12 11:54:00 Maine coon 735.00
44 Cawette 2006-05-19 16:16:00 Nebelung 985.00
61 Yoda 2010-11-09 00:00:00 Maine coon 735.00

Je rappelle que la fonction COALESCE() prend un nombre illimité de paramètres, et


renvoie le premier paramètre non NULL qu'elle rencontre. Donc ici, s'il s'agit d'un chat de
race, Race.prix ne sera pas NULL et sera donc renvoyé. Par contre, s'il n'y a pas de
race, Race.prix sera NULL, mais pas Espece.prix, qui sera alors sélectionné.

Si, pendant que le premier client fait son choix, un second client arrive, qui veut adopter
un chat Maine Coon, il va également chercher la liste des chats disponibles. Et vu qu'on
travaille pour l'instant en verrous partagés, il va pouvoir l'obtenir.

Session 2 :

1START TRANSACTION;
2
3SELECT Animal.id, Animal.nom, Animal.date_naissance, Race.nom as race, COALESCE(Rac
4FROM Animal
5INNER JOIN Espece ON Animal.espece_id = Espece.id
6INNER JOIN Race ON Animal.race_id = Race.id -- Jointure interne cette fois
7WHERE Race.nom = 'Maine Coon' -- Uniquement les Maine Coon...
8AND Animal.id NOT IN (SELECT animal_id FROM Adoption) -- ... qui n'ont pas encore été ad
9LOCK IN SHARE MODE;

id nom date_naissance race prix


8 Bagherra 2008-09-11 15:38:00 Maine coon 735.00
34 Capou 2008-04-20 03:22:00 Maine coon 735.00
43 Cracotte 2007-03-12 11:54:00 Maine coon 735.00
61 Yoda 2010-11-09 00:00:00 Maine coon 735.00

C'est alors que le premier client, M. Dupont, décide de craquer pour Bagherra.

1INSERT INTO Adoption (client_id, animal_id, date_reservation, prix, paye)


2SELECT id, 8, NOW(), 735.00, 1
3FROM Client
4WHERE email = 'jean.dupont@email.com';
5
6COMMIT;

Et M. Durant jette également son dévolu sur Bagherra (qui est décidément très très
mignon) !

1INSERT INTO Client (nom, prenom, email)


2VALUES ('Durant', 'Philippe', 'phidu@email.com');
3
4INSERT INTO Adoption (client_id, animal_id, date_reservation, prix, paye)
5VALUES (LAST_INSERT_ID(), 8, NOW(), 735.00, 0);

L'insertion dans Client fonctionne mais l'insertion dans Adoption pose problème :

1ERROR 1062 (23000): Duplicate entry '8' for key 'ind_uni_animal_id'

Et pour cause : Bagherra vient d'être adopté, à l'instant. Furieux, M. Durant s'en va, et
l'élevage a perdu un client. Il ne reste plus qu'à annuler sa transaction.

C'est pour éviter ce genre de situation qu'il vaut parfois mieux mettre un verrou exclusif sur
une sélection. Si l'on sait que cette sélection sert à déterminer quels changements vont
être faits, ce n'est pas la peine de laisser quelqu'un d'autre lire des informations qui
cesseront d'être justes incessamment sous peu.

Niveaux d'isolation

Nous avons vu que par défaut :

• lorsque l'on démarre une transaction, la session prend une photo des tables, et
travaille uniquement sur cette photo (donc sur des données potentiellement
périmées) tant qu'elle ne pose pas un verrou ;
• les requêtes SELECT ne posent pas de verrous si l'on ne le demande pas
explicitement ;
• les requêtes SELECT ... LOCK IN SHARE MODE, SELECT ... FOR
UPDATE, DELETE et UPDATE posent un verrou de clé suivante (sauf dans le cas d'une
recherche sur index unique, avec une valeur unique).

Ce comportement est défini par le niveau d'isolation des transactions.

Syntaxe

Pour définir le niveau d'isolation des transactions, on utilise la requête suivante :

1SET [GLOBAL | SESSION] TRANSACTION ISOLATION LEVEL { READ UNCOMMITTED | READ COM
READ | SERIALIZABLE }

• Le mot-clé GLOBAL définit le niveau d'isolation pour toutes les sessions MySQL qui
seront créées dans le futur. Les sessions existantes ne sont pas affectées.
• SESSION définit le niveau d'isolation pour la session courante.
• Si l'on ne précise ni GLOBAL, ni SESSION, le niveau d'isolation défini ne concernera
que la prochaine transaction que l'on ouvrira dans la session courante.
Les différents niveaux
REPEATABLE READ

Il s'agit du niveau par défaut, celui avec lequel vous travaillez depuis le
début. Repeatable read signifie "lecture répétable", c'est-à-dire que si l'on fait plusieurs
requêtes de sélection (non-verrouillantes) de suite, elles donneront toujours le même
résultat, quels que soient les changements effectués par d'autres sessions. Si l'on pense à
bien utiliser les verrous là où c'est nécessaire, c'est un niveau d'isolation tout à fait suffisant.

READ COMMITTED

Avec ce niveau d'isolation, chaque requête SELECT (non-verrouillante) va reprendre une


"photo" à jour de la base de données, même si plusieurs SELECT se font dans la même
transaction. Ainsi, un SELECT verra toujours les derniers changements commités, même s'ils
ont été faits dans une autre session, après le début de la transaction.

READ UNCOMMITTED

Le niveau READ UNCOMMITTED fonctionne comme READ COMMITTED, si ce n'est qu'il


autorise la "lecture sale". C'est-à-dire qu'une session sera capable de lire des
changements encore non commités par d'autres sessions.

Exemple

Session 1 :

1START TRANSACTION;
2
3UPDATE Race
4SET prix = 0
5WHERE id = 7;

Session 2 :

1SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;


2START TRANSACTION;
3
4SELECT id, nom, espece_id, prix FROM Race;

id nom espece_id prix


1 Berger allemand 1 485.00
2 Berger blanc suisse 1 935.00
3 Singapura 2 985.00
4 Bleu russe 2 835.00
5 Maine coon 2 735.00
7 Sphynx 2 0.00
8 Nebelung 2 985.00
9 Rottweiller 1 600.00
La modification faite par la session 1 n'a pas été commitée. Elle ne sera donc
potentiellement jamais validée, auquel cas, elle n'affectera jamais les données. Pourtant,
la session 2 voit ce changement de données non-commitées. "Lecture sale" n'a pas une
connotation négative par hasard, bien entendu ! Aussi, évitez de travailler avec ce
niveau d'isolation. Annulez la modification de données réalisée par la session 1 et
terminez la transaction de la seconde session.

SERIALIZABLE

Ce niveau d'isolation se comporte comme REPEATABLE READ, sauf que lorsque le mode
autocommit est désactivé, tous les SELECT simples sont implicitement convertis en SELECT
... LOCK IN SHARE MODE.

En résumé

• Les verrous permettent de restreindre, voire interdire l'accès, à une partie des
données.
• Les verrous de table peuvent s'utiliser sur des tables transactionnelles et non-
transactionnelles, contrairement aux verrous de ligne qui ne sont disponibles que
pour des tables transactionnelles.
• Les verrous de lecture (tables) et partagés (lignes) permettent aux autres sessions
de lire les données verrouillées, mais pas de les modifier. Les verrous d'écriture
(tables) et exclusif (lignes) par contre, ne permettent aux autres sessions ni de lire,
ni de modifier les données verrouillées.
• Les verrous de ligne s'utilisent avec les transactions, et dépendent des index.
• Les requêtes de suppression, modification et insertion posent automatiquement un
verrou de ligne exclusif de clé suivante sur les lignes concernées par la requête. Les
requêtes de sélection par contre, ne posent pas de verrou par défaut, il faut en
poser un explicitement.
• Le comportement par défaut des verrous de ligne est défini par le niveau
d'isolation des transactions, qui est modifiable.

InnoDB permet la gestion des verrous au niveau des enregistrements et non plus au niveau
des tables.

Ces verrous sont associés à une requête de sélection. Il en existe de deux sortes.

1 .SELECT … LOCK IN SHARE MODE

Permet d'éviter aux autres utilisateurs de modifier ou d'effacer les enregistrements


sélectionnés. Cela permet d'avoir la dernière version des enregistrements.

1 .SELECT … FOR UPDATE

Même chose que pour LOCK IN SHARE MODE, sauf que les autres utilisateurs ne peuvent
lire les enregistrements verrouillés.

Cela peut être utile lorsque l'on doit modifier des enregistrements à partir de données dans
ces mêmes enregistrements.
La validation de la transaction implicite ou explicite permet de déverrouiller les tables et les
enregistrements.

Si vous projetez d'utiliser régulièrement les verrous sur les enregistrements, il est judicieux de
donner une valeur en secondes à innodb_lock_wait_timeout pour éviter des effets de
verrous permanents. Vous pouvez d'ailleurs vérifier vos tables et l'état des derniers verrous
bloqués avec innodb monitor.

Les Verrous dans MySql


Les verrous sont automatiquement levés dès que la connexion à la base MySQL est
fermée, ou dès que des verrous sont posés sur une autre table de la base par la même
connexion. Lorsqu'une connexion veut accéder à une donnée verrouillée par une autre
connexion, MySQL met la requête en attente.
Lorsqu'une session MySQL pose un verrou sur un élément de la base de données, cela
veut dire qu'il restreint, voire interdit, l'accès à cet élément aux autres sessions MySQL qui
voudraient y accéder.

Verrous de table et verrous de ligne

Il est possible de poser un verrou sur une table entière, ou seulement sur une ou plusieurs
lignes d'une table. Étant donné qu'un verrou empêche l'accès d'autres sessions, il est en
général plus intéressant de poser un verrou sur la plus petite partie de la base possible.

Par exemple, si l'on travaille avec les chiens de la table Animal.

On peut poser un verrou sur toute la table Animal. Dans ce cas, les autres sessions
n'auront pas accès à cette table, tant que le verrou sera posé. Qu'elles veuillent en utiliser
les chiens, les chats, ou autre, tout leur sera refusé.
On peut aussi poser un verrou uniquement sur les lignes de la table qui contiennent des
chiens. De cette manière, les autres sessions pourront accéder aux chats, aux perroquets,
etc. Elles pourront toujours travailler, tant qu'elles n'utilisent pas les chiens.
Cette notion d'accès simultané aux données par plusieurs sessions différentes s'appelle la
concurrence. Plus la concurrence est possible, donc plus le nombre de sessions pouvant
accéder aux données simultanément est grand, mieux c'est. En effet, prenons l'exemple
d'un site web. En général, on préfère permettre à plusieurs utilisateurs de surfer en même
temps, sans devoir attendre entre chaque action de pouvoir accéder aux informations
chacun à son tour. Or, chaque utilisateur crée une session chaque fois qu'il se connecte à
la base de données (pour lire les informations ou les modifier). Préférez donc (autant que
possible) les verrous de ligne aux verrous de table !

Syntax et utilisation des verrou


Les verrous de table sont les seuls supportés par MyISAM. Ils sont d'ailleurs principalement
utilisés pour pallier en partie l'absence de transactions dans MyISAM. Les tables InnoDB
peuvent également utiliser ce type de verrou.

Pour verrouiller une table, il faut utiliser la commande LOCK TABLES :

1
LOCK TABLES nom_table [AS alias_table] [READ | WRITE] [, ...];
En utilisant READ, un verrou de lecture sera posé ; c'est-à-dire que les autres sessions
pourront toujours lire les données des tables verrouillées, mais ne pourront plus les modifier.
En utilisant WRITE, un verrou d'écriture sera posé. Les autres sessions ne pourront plus ni lire
ni modifier les données des tables verrouillées.
Pour déverrouiller les tables, on utilise UNLOCK TABLES. Cela déverrouille toutes les tables
verrouillées. Il n'est pas possible de préciser les tables à déverrouiller. Tous les verrous de
table d'une session sont relâchés en même temps.

Session ayant obtenu le verrou

Lorsqu'une session acquiert un ou plusieurs verrous de table, cela a plusieurs


conséquences pour cette session :

elle ne peut plus accéder qu'aux tables sur lesquelles elle a posé un verrou ;
elle ne peut accéder à ces tables qu'en utilisant les noms qu'elle a donnés lors du
verrouillage (soit le nom de la table, soit le/les alias donné(s)) ;
s'il s'agit d'un verrou de lecture (READ), elle peut uniquement lire les données, pas les
modifier.

14-Surveillance d’une activité SQL

S’applique à : SQL Server (toutes les versions prises en charge)


Le but de la surveillance des bases de données est d'évaluer le fonctionnement d'un
serveur. Une surveillance efficace implique la prise d'instantanés périodiques des
performances actuelles afin d'isoler les processus à l’origine des problèmes, ainsi que la
collecte de données en continu pour suivre de près les tendances des performances.
(a faire en exposé)
15. Gestion des utilisateurs et privilèges
(a faire en exposé en invite de commande et en interface graphique)

16. Sauvegarde et Restauration

Les sauvegardes des tables InnoDB ne peuvent s'envisager comme la sauvegarde de


tables MyIsam. En effet un simple DUMP des tables ne permet que d'extraire les données.
Les transactions en cours ne sont donc pas conservées. Cette méthode ne doit être utilisée
que dans les cas de corruption totale des fichiers de données.

MySql n'inclut pas d'outils de backup pour les tables InnoDB. Pour effectuer un backup des
tables et des transactions, il existe deux méthodes : la copie de fichiers ou la réplication de
tables.

La copie des fichiers s'effectue après l'arrêt du serveur, vous devez alors copier les fichiers
de données et les fichiers de logs dans un endroit sûr.

Les fichiers à copier sont :

• les fichiers de données ;


• les fichiers journaux ;
• les fichiers.FRM correspondant à la structure des tables ;
• les fichiers de configuration de MySQL.

La réplication utilise un serveur secondaire où les données sont copiées. Le support des
tables InnoDB permet une copie propre des données et journaux.

La restauration dépend de la méthode utilisée. Il faut cependant savoir que MySQL vérifie
les logs à chaque redémarrage du serveur. Les transactions non abouties seront donc
totalement annulées.

Après avoir récupéré les fichiers venant soit d'une simple copie soit d'une réplication,
remplacez et redémarrez le serveur si possible à partir de la ligne de commande, pour
vérifier que les opérations se déroulent bien.

Si l'opération échoue pour cause de fichiers corrompus, tentez de trouver un jeu de fichiers
non corrompus. SI cela échoue, vous pouvez toujours tenter de recréer les tables et
d'insérer les enregistrements que vous avez conservés.

- Types de sauvegardes
(a faire en exposé)

- Stratégies de sauvegarde
(a faire en exposé)

- Types de restauration
(a faire en exposé)

Vous aimerez peut-être aussi