- 1 1. Le SQL le plus court pour obtenir la date/heure actuelle en MySQL
- 1.1 1.1 Obtenir la date/heure actuelle (basique)
- 1.2 1.2 Obtenir uniquement la date d’aujourd’hui
- 1.3 1.3 Obtenir uniquement l’heure actuelle
- 1.4 1.4 Obtenir l’heure actuelle en UTC (important)
- 1.5 1.5 Obtenir les millisecondes / microsecondes
- 1.6 1.6 Meilleure fonction par cas d’utilisation (commencez ici si vous n’êtes pas sûr)
- 1.7 Points clés souvent manqués
- 2 2. Différences entre NOW() / CURRENT_TIMESTAMP / SYSDATE()
- 3 3. Modifier le format d’affichage de la date/heure actuelle
- 4 4. Calculs de datetime en utilisant le temps actuel
- 4.1 4.1 Ajouter/soustraire avec INTERVAL
- 4.2 4.2 Obtenir les données des dernières 24 heures (modèle le plus courant)
- 4.3 4.3 Obtenir les différences de jours avec DATEDIFF()
- 4.4 4.4 Utiliser TIMESTAMPDIFF() pour les heures/minutes/secondes
- 4.5 4.5 Obtenir le début du mois / la fin du mois (piège réel courant)
- 4.6 Résumé des erreurs courantes
- 4.7 Points clés de cette section
- 5 5. Pour les requêtes de plage, c’est plus sûr que BETWEEN
- 5.1 5.1 Bases de BETWEEN et le piège
- 5.2 5.2 Modèle plus sûr (recommandé)
- 5.3 5.3 La bonne façon d’obtenir les données d’aujourd’hui
- 5.4 5.4 Modèles sûrs pour les 7 derniers / 30 derniers jours
- 5.5 5.5 Règle clé pour garder les index efficaces
- 5.6 Résumé des erreurs courantes
- 5.7 Points clés de cette section
- 6 6. DEFAULT CURRENT_TIMESTAMP et ON UPDATE (bases de conception de table)
- 6.1 6.1 Auto-définir created_at (DEFAULT CURRENT_TIMESTAMP)
- 6.2 6.2 Auto-mettre à jour updated_at (ON UPDATE)
- 6.3 6.3 DATETIME vs TIMESTAMP (important)
- 6.4 6.4 CURRENT_TIMESTAMP peut aussi être utilisé avec DATETIME
- 6.5 6.5 Si vous voulez utiliser NOW() : une alternative (déclencheur)
- 6.6 Erreurs de conception courantes
- 6.7 Points clés de cette section
- 7 7. Conception des fuseaux horaires (stockage en UTC, affichage en heure locale)
- 7.1 7.1 Vérifier le fuseau horaire actuel
- 7.2 7.2 Modifier le fuseau horaire par session
- 7.3 7.3 Pourquoi stocker en UTC (principe du monde réel)
- 7.4 7.4 Convertir les fuseaux horaires avec CONVERT_TZ()
- 7.5 7.5 Pourquoi CONVERT_TZ() renvoie NULL
- 7.6 7.6 Modifier le fuseau horaire global du serveur
- 7.7 Erreurs courantes
- 7.8 Points clés de cette section
- 8 8. Exemples pratiques prêts à l’emploi
- 8.1 8.1 Insérer automatiquement l’heure actuelle dans les journaux
- 8.2 8.2 Mettre à jour l’heure de la dernière connexion
- 8.3 8.3 Fixer une heure de référence dans les jobs batch
- 8.4 8.4 Agrégation pour aujourd’hui / hier / les 7 derniers jours
- 8.5 8.5 Vérifications d’expiration (sessions/jetons)
- 8.6 8.6 Obtenir les lignes expirant dans N heures
- 8.7 Ce que vous devez toujours garder à l’esprit
- 8.8 Points clés de cette section
- 9 9. Questions fréquemment posées (FAQ)
- 9.1 9.1 Quelle est la différence entre NOW() et CURRENT_TIMESTAMP ?
- 9.2 9.2 Devriez-vous utiliser SYSDATE() ?
- 9.3 9.3 Pourquoi l’heure est-elle décalée ?
- 9.4 9.4 CONVERT_TZ() retourne NULL
- 9.5 9.5 Décalages de plage avec BETWEEN
- 9.6 9.6 Comment choisir entre DATETIME et TIMESTAMP ?
- 9.7 9.7 Les microsecondes ne sont pas stockées
- 9.8 Points clés de cette section
- 10 10. Résumé
- 10.1 10.1 Obtenir l’heure actuelle (basics)
- 10.2 10.2 Requêtes de plage : « >= AND < » est la règle d’or
- 10.3 10.3 Bases de l’arithmétique datetime
- 10.4 10.4 Principes de conception des fuseaux horaires
- 10.5 10.5 Meilleures pratiques pour la conception de table
- 10.6 Les 4 points les plus importants du monde réel
1. Le SQL le plus court pour obtenir la date/heure actuelle en MySQL
Si vous voulez obtenir la date/heure actuelle en MySQL, les premières fonctions à retenir sont NOW() et CURRENT_TIMESTAMP. Voici ci-dessous les exemples SQL les plus courts par cas d’utilisation.
1.1 Obtenir la date/heure actuelle (basique)
SELECT NOW();
ou
SELECT CURRENT_TIMESTAMP;
- Les deux retournent la date/heure actuelle (YYYY-MM-DD HH:MM:SS) .
- Au sein de la même requête, l’heure est fixée au « moment de début de la requête ».
Cas d’utilisation
- Journalisation
- Obtention d’un horodatage de création d’enregistrement
- Obtention d’une heure de référence
Erreur courante
- La zone horaire de l’application et celle de la base de données diffèrent et « les heures se décalent ». → Vérifiez avec
SELECT @@session.time_zone;
1.2 Obtenir uniquement la date d’aujourd’hui
SELECT CURDATE();
- Format de retour :
YYYY-MM-DD - Le type est DATE (date uniquement, pas datetime)
Cas d’utilisation
- Recherche de « données d’aujourd’hui »
- Agrégation quotidienne
Notes
- Contrairement à
NOW(), cela n’inclut pas l’heure. - Si vous avez besoin de l’heure pour des requêtes de plage, utilisez
NOW().
1.3 Obtenir uniquement l’heure actuelle
SELECT CURTIME();
- Format de retour :
HH:MM:SS - Le type est TIME (heure uniquement)
Cas d’utilisation
- Affichage du temps d’exécution par lots
- Impression de la partie heure uniquement dans les journaux
Piège courant
- Comme cela n’inclut pas de date, vous ne pouvez pas l’utiliser pour des comparaisons datetime.
1.4 Obtenir l’heure actuelle en UTC (important)
SELECT UTC_TIMESTAMP();
- Retourne UTC indépendamment de la zone horaire du serveur.
- Recommandé pour les services globaux.
Politique de base dans les projets réels
- Stocker en UTC
- Convertir en heure locale lors de l’affichage
Notes
- Si l’application convertit déjà en UTC, méfiez-vous d’une double conversion.
1.5 Obtenir les millisecondes / microsecondes
SELECT NOW(3); -- milliseconds (3 digits after the decimal point)
SELECT NOW(6); -- microseconds (6 digits after the decimal point)
- Disponible dans MySQL 5.6.4 et versions ultérieures.
- Utilisé pour les journaux haute précision et l’audit des transactions.
Idée fausse courante
NOW()seul ne peut pas retourner de secondes fractionnaires.- Votre colonne doit également spécifier la précision, par ex.
DATETIME(6).
1.6 Meilleure fonction par cas d’utilisation (commencez ici si vous n’êtes pas sûr)
| Use case | Recommended function |
|---|---|
| General current datetime | NOW() |
| Table default value | CURRENT_TIMESTAMP |
| Date only | CURDATE() |
| Time only | CURTIME() |
| Unified UTC management | UTC_TIMESTAMP() |
| High-precision logs | NOW(6) |
Points clés souvent manqués
NOW()etCURRENT_TIMESTAMPsont effectivement équivalents (même valeur)- Au sein de la même requête, l’heure est fixée
- La valeur affichée change en fonction des paramètres de zone horaire
- Pour les microsecondes, la définition de votre colonne doit spécifier la précision
2. Différences entre NOW() / CURRENT_TIMESTAMP / SYSDATE()
Il existe plusieurs fonctions pour obtenir l’heure actuelle, mais la partie la plus confuse est la différence entre NOW(), CURRENT_TIMESTAMP, et SYSDATE().
Si vous ne comprenez pas cela correctement, vous pouvez obtenir un comportement inattendu dans les journaux et le traitement des transactions.
2.1 NOW() et CURRENT_TIMESTAMP sont effectivement équivalents
SELECT NOW(), CURRENT_TIMESTAMP;
- Les deux retournent la datetime actuelle (une valeur DATETIME) .
- Au sein de la même requête, l’heure est fixée au « moment de début de la requête ».
CURRENT_TIMESTAMPpeut également être utilisé avec la syntaxe d’appel de fonction :SELECT CURRENT_TIMESTAMP();
Comment choisir dans les projets réels
| Use case | Recommended |
|---|---|
| Simple retrieval | NOW() |
| Table DEFAULT / ON UPDATE | CURRENT_TIMESTAMP |
Points importants
- La signification de la valeur récupérée est la même.
- La principale différence est la syntaxe/utilisation (par ex., autorisé dans DEFAULT).
- Ce n’est pas une différence de type (facile à mal comprendre).
2.2 SYSDATE() retourne l’heure au « moment d’évaluation »
SYSDATE() ressemble à NOW(), mais le moment où la valeur est fixée est différent.
SELECT NOW(), SLEEP(2), NOW();
Résultat (exemple) :
2025-02-23 14:00:00
2025-02-23 14:00:00
SELECT SYSDATE(), SLEEP(2), SYSDATE();
Résultat (exemple) :
2025-02-23 14:00:00
2025-02-23 14:00:02
La différence essentielle
| Function | When the time is fixed |
|---|---|
NOW() | Query start time |
SYSDATE() | Evaluation time |
En d’autres termes, SYSDATE() peut changer au sein de la même requête au fur et à mesure que le temps passe.
2.3 Notes pour les transactions et la réplication
Parce que NOW() est fixé au début de la requête, il est
plus sûr lorsque vous avez besoin d’un temps de référence cohérent à l’intérieur d’une transaction.
En revanche, comme SYSDATE() dépend du moment d’exécution, il peut affecter la reproductibilité dans :
- Réplication
- Jobs par lots
- Traitement de journaux en masse
Règle générale
- Vous voulez un temps de référence fixe →
NOW() - Vous avez besoin de l’instant exact à chaque fois →
SYSDATE()(usage limité)
2.4 Note : CURRENT_DATE / CURRENT_TIME / LOCALTIME
MySQL prend également en charge :
SELECT CURRENT_DATE;
SELECT CURRENT_TIME;
SELECT LOCALTIME;
CURRENT_DATE→ identique àCURDATE()CURRENT_TIME→ identique àCURTIME()LOCALTIME→ identique àNOW()
Confusion courante
- Ce sont principalement des « différences cosmétiques » ; il y a peu de différence fonctionnelle.
- Par mesure de sécurité, privilégiez la lisibilité et standardisez au sein du projet.
Points clés de cette section
NOW()etCURRENT_TIMESTAMPsignifient essentiellement la même chose.SYSDATE()se comporte différemment car il est basé sur le temps d’évaluation.- Pour des temps de référence fixes, utilisez
NOW()par défaut. - Utilisez
CURRENT_TIMESTAMPpour DEFAULT et ON UPDATE.
3. Modifier le format d’affichage de la date/heure actuelle
Le temps actuel que vous obtenez avec NOW() est affiché par défaut sous la forme YYYY-MM-DD HH:MM:SS. Dans le travail réel, vous aurez souvent besoin de choses comme :
- Afficher uniquement la date
- Utiliser
YYYY/MM/DD - Utiliser un format localisé (p. ex., 23 févr. 2025)
- Afficher les millisecondes
Pour cela, utilisez DATE_FORMAT() (convertir un datetime en une chaîne de format arbitraire).
3.1 Syntaxe de base de DATE_FORMAT()
DATE_FORMAT(datetime, 'format_string')
Exemple : convertir le temps actuel en YYYY/MM/DD HH:MM
SELECT DATE_FORMAT(NOW(), '%Y/%m/%d %H:%i');
Exemple de sortie :
2025/02/23 14:35
Spécificateurs de format courants
| Specifier | Meaning | Example |
|---|---|---|
%Y | 4-digit year | 2025 |
%m | 2-digit month | 02 |
%d | 2-digit day | 23 |
%H | Hour (24-hour) | 14 |
%i | Minutes | 35 |
%s | Seconds | 50 |
%f | Microseconds | 123456 |
Remarques
- Certains spécificateurs diffèrent entre majuscules et minuscules.
%hcorrespond à l’heure sur 12 h,%Hà l’heure sur 24 h.
3.2 Exemples de formats courants (fréquents dans le travail réel)
1. Séparé par des barres obliques
SELECT DATE_FORMAT(NOW(), '%Y/%m/%d');
2. Localisé (anglais)
SELECT DATE_FORMAT(NOW(), '%b %d, %Y');
3. Sans secondes
SELECT DATE_FORMAT(NOW(), '%Y-%m-%d %H:%i');
Piège courant
- Comme il renvoie une chaîne, vous ne pouvez pas l’utiliser pour des calculs numériques.
- Pour les comparaisons et les recherches, vous devez utiliser le type DATETIME original.
3.3 Extraire uniquement la partie date ou heure
Vous pouvez également récupérer des parties tout en conservant le type (au lieu de formater en chaîne).
SELECT DATE(NOW()); -- date only (DATE type)
SELECT TIME(NOW()); -- time only (TIME type)
SELECT YEAR(NOW()); -- year only
SELECT MONTH(NOW()); -- month only
SELECT DAY(NOW()); -- day only
Utilisation recommandée
| Goal | Recommended |
|---|---|
| Formatting for display | DATE_FORMAT |
| Calculation / comparison | DATE() / TIME() |
3.4 Affichage avec microsecondes
Lorsque vous avez besoin de journaux haute précision :
SELECT NOW(6);
Avec formatage :
SELECT DATE_FORMAT(NOW(6), '%Y-%m-%d %H:%i:%s.%f');
Notes importantes
- Votre colonne doit être
DATETIME(6)ouTIMESTAMP(6), sinon la précision ne sera pas stockée. - Non disponible dans les versions de MySQL antérieures à 5.6.4 (selon l’environnement).
Erreurs courantes
Utiliser
DATE_FORMAT()dans une clause WHERE empêche l’utilisation des index. wp:list /wp:list- Mauvais exemple :
WHERE DATE_FORMAT(created_at, '%Y-%m-%d') = '2025-02-23' - Recommandé :
WHERE created_at >= '2025-02-23 00:00:00' AND created_at < '2025-02-24 00:00:00' - Stocker directement la chaîne formatée pour l’affichage (dégrade les performances de recherche)
- Mauvais exemple :
Points clés de cette section
- Utilisez
DATE_FORMAT()pour changer les formats d’affichage. - Pour les calculs/comparaisons, conservez le type original.
- Si vous avez besoin de microsecondes, spécifiez la précision dans la définition de la colonne.
- Utiliser des fonctions dans les clauses WHERE peut entraîner des problèmes de performance.
4. Calculs de datetime en utilisant le temps actuel
Dans MySQL, il est courant de calculer des choses comme « N heures plus tard », « N jours auparavant », ou « les N derniers jours » en fonction de l’heure actuelle.
Le cas réel le plus fréquent est « obtenir les données des dernières 24 heures ».
Le fondement de l’arithmétique des dates et heures est INTERVAL (syntaxe pour ajouter/soustraire des unités de temps).
4.1 Ajouter/soustraire avec INTERVAL
Obtenir 1 heure plus tard
SELECT NOW() + INTERVAL 1 HOUR;
Obtenir 3 jours auparavant
SELECT NOW() - INTERVAL 3 DAY;
Obtenir 1 mois plus tard
SELECT NOW() + INTERVAL 1 MONTH;
Unités courantes
| Unit | Meaning |
|---|---|
| SECOND | Seconds |
| MINUTE | Minutes |
| HOUR | Hours |
| DAY | Days |
| WEEK | Weeks |
| MONTH | Months |
| YEAR | Years |
Erreurs courantes
DAYdansINTERVAL 1 DAYfonctionne même en minuscules, mais vous devriez standardiser au sein de l’équipe.- Les calculs de fin de mois peuvent différer des attentes parce que le nombre de jours varie (par ex., 31 janv. + 1 mois).
4.2 Obtenir les données des dernières 24 heures (modèle le plus courant)
SELECT *
FROM users
WHERE created_at >= NOW() - INTERVAL 1 DAY;
Signification
- Cible « à partir de maintenant jusqu’à il y a 24 heures ».
Notes
- Si vous utilisez
CURDATE(), la référence devient « aujourd’hui à 00 h », ce qui change le sens.
Exemple (données d’aujourd’hui) :
SELECT *
FROM users
WHERE created_at >= CURDATE();
Comprendre la différence est crucial
| Expression | Meaning |
|---|---|
NOW() - INTERVAL 1 DAY | Past 24 hours |
CURDATE() | Since today 00:00 |
4.3 Obtenir les différences de jours avec DATEDIFF()
SELECT DATEDIFF('2025-03-01', '2025-02-23');
Résultat :
6
- L’unité est « jours »
- La partie temps est ignorée
Notes
- Le signe change selon l’ordre des arguments.
- Vous ne pouvez pas calculer les différences en heures/minutes/secondes.
4.4 Utiliser TIMESTAMPDIFF() pour les heures/minutes/secondes
SELECT TIMESTAMPDIFF(HOUR,
'2025-02-23 12:00:00',
'2025-02-23 18:30:00');
Résultat :
6
Minutes
SELECT TIMESTAMPDIFF(MINUTE,
'2025-02-23 12:00:00',
'2025-02-23 12:30:00');
Secondes
SELECT TIMESTAMPDIFF(SECOND,
'2025-02-23 12:00:00',
'2025-02-23 12:00:45');
Cas d’utilisation
- Calculs de durée de session
- Vérifications d’expiration
- Décisions de timeout
4.5 Obtenir le début du mois / la fin du mois (piège réel courant)
Obtenir le premier jour de ce mois :
SELECT DATE_FORMAT(NOW(), '%Y-%m-01');
Premier jour du mois suivant :
SELECT DATE_FORMAT(NOW() + INTERVAL 1 MONTH, '%Y-%m-01');
Notes
- La fin du mois n’est pas une date fixe.
- Pour les requêtes de plage, « >= début ET < premier jour du mois suivant » est sûr.
Résumé des erreurs courantes
- Utiliser
BETWEENavec des valeurs uniquement date et oublier l’heure - Désactiver les index en utilisant
DATE(created_at)dans les clauses WHERE - Tomber dans le piège du « 31e jour » dans les calculs de mois
- Mal comprendre la différence entre
NOW()etCURDATE()
Points clés de cette section
INTERVALest le fondement de l’arithmétique des dates et heures.- Les dernières 24 heures =
NOW() - INTERVAL 1 DAY. - Jours =
DATEDIFF(); unités plus petites =TIMESTAMPDIFF(). - Soyez prudent avec les conditions de fin pour les calculs basés sur les mois.
5. Pour les requêtes de plage, c’est plus sûr que BETWEEN
Lors de recherches de plages de dates dans MySQL, de nombreux débutants utilisent BETWEEN. Cependant, cela produit souvent des résultats inattendus si vous gérez mal les limites de temps, donc un modèle plus sûr est recommandé en pratique.
5.1 Bases de BETWEEN et le piège
Une requête courante
SELECT *
FROM orders
WHERE order_date BETWEEN '2025-02-01' AND '2025-02-10';
Cela semble correct, mais en interne c’est équivalent à :
WHERE order_date >= '2025-02-01 00:00:00'
AND order_date <= '2025-02-10 00:00:00'
Donc cela n’inclut pas les données après 00 h le 10 févr.
5.2 Modèle plus sûr (recommandé)
Modèle recommandé
SELECT *
FROM orders
WHERE order_date >= '2025-02-01 00:00:00'
AND order_date < '2025-02-11 00:00:00';
Points clés
- Spécifiez la limite de fin comme « inférieur au lendemain à 00:00 »
- Plus sûr que
<= 23:59:59(supporte les microsecondes)
5.3 La bonne façon d’obtenir les données d’aujourd’hui
Mauvais exemple :
WHERE DATE(created_at) = CURDATE();
Problèmes :
- Appliquer une fonction à la colonne désactive les index
- Peut causer des ralentissements sérieux sur les grandes tables
Recommandé :
WHERE created_at >= CURDATE()
AND created_at < CURDATE() + INTERVAL 1 DAY;
Cela assure :
- Les index peuvent être utilisés
- Recherches rapides
- Pas de problèmes de limites
5.4 Modèles sûrs pour les 7 derniers / 30 derniers jours
7 derniers jours
WHERE created_at >= NOW() - INTERVAL 7 DAY;
30 derniers jours
WHERE created_at >= NOW() - INTERVAL 30 DAY;
Notes
CURDATE() - INTERVAL 7 DAYest basé sur « aujourd’hui 00:00 »NOW() - INTERVAL 7 DAYest basé sur « l’heure actuelle »- Choisissez en fonction des exigences
5.5 Règle clé pour garder les index efficaces
Mauvais :
WHERE DATE(created_at) = '2025-02-23';
Bon :
WHERE created_at >= '2025-02-23 00:00:00'
AND created_at < '2025-02-24 00:00:00';
Pourquoi :
- Les index fonctionnent sur « la colonne elle-même »
- Appliquer une fonction empêche l’utilisation de l’index (scan complet)
Résumé des erreurs courantes
- Oublier d’inclure l’heure à la limite de fin dans
BETWEEN - Manquer les microsecondes lors de l’utilisation de
23:59:59 - Utiliser
DATE()dans les clauses WHERE et ralentir les requêtes - Laisser ambigu « maintenant » vs « aujourd’hui 00:00 »
Points clés de cette section
- Les requêtes de plage sont les plus sûres avec
>= début AND < fin. BETWEENnécessite une gestion minutieuse des limites.- Pour garder les index efficaces, ne mettez pas les colonnes dans des fonctions.
- Choisissez clairement entre la logique basée sur
NOW()et celle basée surCURDATE().
6. DEFAULT CURRENT_TIMESTAMP et ON UPDATE (bases de conception de table)
Dans la conception de base de données, il est courant de gérer automatiquement created_at et updated_at.
En MySQL, CURRENT_TIMESTAMP vous permet de définir l’heure actuelle automatiquement lors de l’insertion et de la mise à jour.
6.1 Auto-définir created_at (DEFAULT CURRENT_TIMESTAMP)
CREATE TABLE users (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(255),
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
Comportement :
INSERT INTO users (name) VALUES ('Alice');
→ L’heure actuelle est automatiquement insérée dans created_at.
Points clés
CURRENT_TIMESTAMPpeut être utilisé dans DEFAULT.NOW()ne peut pas être utilisé directement dans DEFAULT.
Erreur courante
created_at DATETIME DEFAULT NOW(); -- error
Raison :
- En MySQL, vous ne pouvez généralement pas définir une fonction comme DEFAULT (l’exception est CURRENT_TIMESTAMP).
6.2 Auto-mettre à jour updated_at (ON UPDATE)
CREATE TABLE users (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(255),
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
ON UPDATE CURRENT_TIMESTAMP
);
Comportement :
UPDATE users SET name = 'Bob' WHERE id = 1;
→ updated_at est automatiquement mis à jour avec l’heure actuelle.
Cas d’utilisation
- Suivi de la dernière connexion
- Historique des mises à jour
- Journaux d’audit
6.3 DATETIME vs TIMESTAMP (important)
| Type | Range | Time zone impact |
|---|---|---|
| DATETIME | Year 1000 to 9999 | No |
| TIMESTAMP | 1970 to 2038 | Yes |
La différence essentielle
TIMESTAMPest stocké en interne en UTC et converti vers le fuseau horaire de la session lors de l’affichage.DATETIMEstocke la valeur littérale (pas de conversion).
Directives
| Case | Recommended type |
|---|---|
| Log management | TIMESTAMP |
| Future dates (after 2038) | DATETIME |
| Fixed values not requiring TZ conversion | DATETIME |
6.4 CURRENT_TIMESTAMP peut aussi être utilisé avec DATETIME
En MySQL 5.6 et versions ultérieures, vous pouvez spécifier CURRENT_TIMESTAMP comme DEFAULT et ON UPDATE pour les colonnes DATETIME également.
created_at DATETIME DEFAULT CURRENT_TIMESTAMP
Notes
- Les anciennes versions de MySQL ont des restrictions (dépendantes de l’environnement).
- Si vous avez besoin de précision :
DATETIME(6) DEFAULT CURRENT_TIMESTAMP(6)
6.5 Si vous voulez utiliser NOW() : une alternative (déclencheur)
CREATE TRIGGER set_created_at
BEFORE INSERT ON logs
FOR EACH ROW
SET NEW.created_at = NOW();
Cas d’utilisation
- Logique de valeur initiale complexe
- Attribution conditionnelle de l’horodatage
Remarques
- Les déclencheurs sont difficiles à déboguer.
- Évitez-les sauf si nécessaire.
Erreurs de conception courantes
- Ajouter ON UPDATE à la fois sur
created_atetupdated_at - Confondre le comportement de DATETIME et TIMESTAMP
- Reporter les décisions de fuseau horaire
Points clés de cette section
- Utilisez
CURRENT_TIMESTAMPpour DEFAULT. - Utilisez
ON UPDATE CURRENT_TIMESTAMPpour le suivi des mises à jour. - Choisissez les types en fonction du comportement du fuseau horaire et du problème de 2038.
- Si vous avez besoin de précision, n’oubliez pas
(6).
7. Conception des fuseaux horaires (stockage en UTC, affichage en heure locale)
Lorsqu’on travaille avec l’heure actuelle, une mauvaise conception des fuseaux horaires entraîne une dérive temporelle et une double conversion.
En pratique, le paramètre par défaut le plus sûr est « stocker en UTC, convertir en heure locale pour l’affichage ».

Figure : Architecture de base pour stocker l’UTC dans MySQL et afficher l’heure locale
7.1 Vérifier le fuseau horaire actuel
Tout d’abord, vérifiez quel fuseau horaire MySQL utilise.
SELECT @@global.time_zone, @@session.time_zone;
@@global.time_zone→ paramètre global du serveur@@session.time_zone→ paramètre de la connexion/session actuelle- Si cela indique
SYSTEM, cela dépend du paramètre du système d’exploitation
Problèmes courants
- Les serveurs de production et de développement ont des fuseaux horaires OS différents
- L’application convertit en UTC, puis la base de données reconvertit (double conversion)
7.2 Modifier le fuseau horaire par session
SET time_zone = 'Asia/Tokyo';
ou uniformiser en UTC :
SET time_zone = '+00:00';
Points importants
- Il revient à l’original lorsque la connexion est fermée
- Si vous utilisez un pool de connexions, vérifiez les paramètres de votre application
7.3 Pourquoi stocker en UTC (principe du monde réel)
Politique recommandée
- Stocker les données en UTC
- Convertir dans le fuseau horaire de l’utilisateur lors de l’affichage
Raisons :
- Support international plus facile
- Éviter les problèmes liés à l’heure d’été (DST)
- Minimiser l’impact lors du déplacement des serveurs
Obtenir l’UTC :
SELECT UTC_TIMESTAMP();
7.4 Convertir les fuseaux horaires avec CONVERT_TZ()
Exemple : UTC → JST
SELECT CONVERT_TZ('2025-02-23 05:35:00', '+00:00', '+09:00');
Utilisation des noms de fuseau horaire :
SELECT CONVERT_TZ('2025-02-23 05:35:00', 'UTC', 'Asia/Tokyo');
Exemple du monde réel
SELECT CONVERT_TZ(created_at, 'UTC', 'Asia/Tokyo')
FROM users;
7.5 Pourquoi CONVERT_TZ() renvoie NULL
Si elle renvoie NULL, les causes courantes incluent :
- Les tables de fuseaux horaires de MySQL ne sont pas chargées
- Le nom de fuseau horaire spécifié n’existe pas
Exemple de chargement sous Linux :
mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root -p mysql
Remarques
- En production, confirmez les permissions et si un redémarrage est nécessaire
- Dans Docker, zoneinfo peut ne pas être inclus selon l’image
7.6 Modifier le fuseau horaire global du serveur
Fichier de configuration (my.cnf / my.ini) :
[mysqld]
default_time_zone = '+00:00'
Vérifier après redémarrage :
SELECT @@global.time_zone;
Important
- Pour les changements en production, confirmez l’étendue de l’impact
- Soyez prudent avec les données existantes (parfois seules les affichages changent)
Erreurs courantes
- Stocker l’heure locale au lieu de l’UTC, puis ajouter le support international plus tard
- Double conversion entre l’application et la base de données
- Concevoir avec DATETIME sans prendre en compte les fuseaux horaires
- Paramètres de fuseau horaire différents entre test et production
Points clés de cette section
- Stocker en UTC et convertir lors de l’affichage.
- Utilisez
UTC_TIMESTAMP(). - Lors de l’utilisation de
CONVERT_TZ(), vérifiez les tables de fuseaux horaires. - Prenez toujours en compte les différences d’environnement au niveau des fuseaux horaires.
8. Exemples pratiques prêts à l’emploi
Voici des exemples SQL concrets montrant comment utiliser l’heure actuelle de MySQL dans le développement/opérations réelles.
Ils sont rédigés pour que vous puissiez les copier‑coller directement.
8.1 Insérer automatiquement l’heure actuelle dans les journaux
Créer la table
CREATE TABLE system_logs (
id INT AUTO_INCREMENT PRIMARY KEY,
level VARCHAR(50),
message TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
Insertion du journal
INSERT INTO system_logs (level, message)
VALUES ('ERROR', 'Failed to connect to the DB');
Points clés
created_atest inséré automatiquement- Pas besoin de transmettre un horodatage depuis l’application
- Conception essentielle pour l’audit et l’investigation d’incidents
Erreurs courantes
- Gérer le temps à la fois dans l’application et la base de données
- Incohérences temporelles dues à des fuseaux horaires non unifiés
8.2 Mettre à jour l’heure de la dernière connexion
Conception de la table
CREATE TABLE users (
id INT AUTO_INCREMENT PRIMARY KEY,
username VARCHAR(255),
last_login TIMESTAMP DEFAULT CURRENT_TIMESTAMP
ON UPDATE CURRENT_TIMESTAMP
);
Mise à jour lors de la connexion
UPDATE users
SET last_login = NOW()
WHERE id = 1;
Remarques
ON UPDATEne s’active que lorsque la colonne change- Certaines instructions UPDATE peuvent ne pas modifier la valeur et donc ne pas mettre à jour
8.3 Fixer une heure de référence dans les jobs batch
Pour les processus de longue durée, il est plus sûr de fixer une heure de référence.
SET @base_time = NOW();
SELECT *
FROM orders
WHERE created_at >= @base_time - INTERVAL 1 DAY;
Pourquoi
- Le temps ne change pas en cours de processus
- La cohérence est maintenue
8.4 Agrégation pour aujourd’hui / hier / les 7 derniers jours
Ventes d’aujourd’hui
SELECT SUM(amount)
FROM orders
WHERE created_at >= CURDATE()
AND created_at < CURDATE() + INTERVAL 1 DAY;
Ventes d’hier
SELECT SUM(amount)
FROM orders
WHERE created_at >= CURDATE() - INTERVAL 1 DAY
AND created_at < CURDATE();
7 derniers jours
SELECT COUNT(*)
FROM users
WHERE created_at >= NOW() - INTERVAL 7 DAY;
Important
- Ne pas appliquer de fonctions aux colonnes dans les clauses WHERE
- Écrire des conditions qui conservent l’utilisabilité des index
8.5 Vérifications d’expiration (sessions/jetons)
SELECT *
FROM sessions
WHERE expires_at > NOW();
Supprimer les lignes expirées
DELETE FROM sessions
WHERE expires_at <= NOW();
Erreurs courantes
- Utiliser
CURDATE()en ignorant l’heure - Stocker en UTC mais comparer avec le
NOW()local
8.6 Obtenir les lignes expirant dans N heures
SELECT *
FROM coupons
WHERE expires_at <= NOW() + INTERVAL 1 HOUR;
Cas d’utilisation :
- Alertes d’expiration
- Notifications d’expiration
Ce que vous devez toujours garder à l’esprit
- Soyez explicite quant à savoir si votre référence est « maintenant » ou « aujourd’hui 00:00 »
- Écrivez des prédicats qui maintiennent l’efficacité des index
- Décidez dès le départ de la conception du fuseau horaire
- Ne mélangez pas
NOW()etUTC_TIMESTAMP()sans une politique claire
Points clés de cette section
- Pour les journaux/audits/suivi des mises à jour, utilisez
CURRENT_TIMESTAMP - Pour l’agrégation, utilisez le modèle sûr
>= ET < - Pour la gestion des sessions, comparez avec
NOW() - Fixez une heure de référence pour garder le traitement cohérent
9. Questions fréquemment posées (FAQ)
Voici des questions courantes sur l’heure actuelle de MySQL, notamment les pièges qui apparaissent dans le travail réel.
9.1 Quelle est la différence entre NOW() et CURRENT_TIMESTAMP ?
Conclusion : la signification de la valeur retournée est la même.
SELECT NOW(), CURRENT_TIMESTAMP;
Les deux renvoient la date et l’heure actuelles.
La principale différence réside dans l’utilisation syntaxique
CURRENT_TIMESTAMPpeut être utilisé dansDEFAULTetON UPDATENOW()ne peut pas être utilisé directement dans DEFAULT
Remarques
- Ce n’est pas une différence de type
- Vous pouvez spécifier la précision avec des arguments comme
(6)
9.2 Devriez-vous utiliser SYSDATE() ?
SYSDATE() renvoie l’heure au moment de « l’évaluation ».
SELECT SYSDATE(), SLEEP(2), SYSDATE();
La valeur peut changer même au sein de la même requête.
Quand l’utiliser
- Lorsque vous devez enregistrer l’instant réel exact
Quand l’éviter
- Réplication
- Traitement de transaction où la cohérence est importante
Dans la plupart des cas, l’utilisation de NOW() suffit.
9.3 Pourquoi l’heure est-elle décalée ?
Causes principales :
- Paramètres de fuseau horaire du serveur
- Paramètres de fuseau horaire de la session
- Conversion double avec l’application
- Comportement de conversion automatique du type TIMESTAMP
Vérifiez avec :
SELECT @@global.time_zone, @@session.time_zone;
Atténuation
- Stocker en UTC par défaut
- Convertir seulement lors de l’affichage
- Unifier la politique entre l’app et la DB
9.4 CONVERT_TZ() retourne NULL
Causes :
- Les tables de fuseaux horaires ne sont pas chargées
- Nom de fuseau horaire incorrect
Correction :
mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root -p mysql
Soyez particulièrement prudent dans les environnements Docker.
9.5 Décalages de plage avec BETWEEN
Mauvais :
WHERE created_at BETWEEN '2025-02-01' AND '2025-02-10';
Sûr :
WHERE created_at >= '2025-02-01 00:00:00'
AND created_at < '2025-02-11 00:00:00';
Raisons :
- Problème de temps de limite finale
- Fuite de microsecondes
- Efficacité de l’index
9.6 Comment choisir entre DATETIME et TIMESTAMP ?
- Support international / gestion UTC → TIMESTAMP
- Après 2038 ou datetimes fixes → DATETIME
Décidez cela lors de la conception.
9.7 Les microsecondes ne sont pas stockées
Cause :
- Aucune précision spécifiée dans la définition de la colonne
Correction :
created_at DATETIME(6)
Points clés de cette section
- Commencez avec
NOW()etCURRENT_TIMESTAMP - Pour les requêtes de plage, utilisez
>= AND < - Le stockage UTC est le défaut le plus sûr
- N’oubliez pas la sélection du type et la précision
10. Résumé
Cet article organise des méthodes pratiques pour récupérer, formater, calculer et gérer l’heure actuelle en MySQL.
Enfin, voici les essentiels minimaux que vous devriez connaître pour rester en sécurité.
10.1 Obtenir l’heure actuelle (basics)
- Récupération générale →
NOW() - DEFAULT de table / suivi de mise à jour →
CURRENT_TIMESTAMP - Date seulement →
CURDATE() - Heure seulement →
CURTIME() - UTC →
UTC_TIMESTAMP() - Haute précision →
NOW(6)
Règles empiriques
- Si vous n’êtes pas sûr, utiliser
NOW()est bien dans la plupart des cas. - Pour la conception de schéma, utilisez
CURRENT_TIMESTAMP.
10.2 Requêtes de plage : « >= AND < » est la règle d’or
Modèle sûr :
WHERE created_at >= 'START'
AND created_at < 'END'
Pourquoi :
- Évite de manquer les lignes de limite finale
- Fonctionne avec les microsecondes
- Maintient les index utilisables
Mauvais exemple
WHERE DATE(created_at) = CURDATE();
Ne mettez pas la colonne dans une fonction.
10.3 Bases de l’arithmétique datetime
- Ajouter/soustraire →
INTERVAL - Différences de jours →
DATEDIFF() - Différences de temps →
TIMESTAMPDIFF()
Gardez toujours à l’esprit si votre base est « maintenant » ou « aujourd’hui 00:00 ».
10.4 Principes de conception des fuseaux horaires
- Stocker en UTC
- Convertir à l’affichage
- Unifier la politique entre l’app et la DB
Vérifiez avec :
SELECT @@global.time_zone, @@session.time_zone;
10.5 Meilleures pratiques pour la conception de table
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
ON UPDATE CURRENT_TIMESTAMP
- Équipement standard pour l’audit/journalisation/suivi de mise à jour
- Si vous avez besoin de précision, spécifiez
(6)
Les 4 points les plus importants du monde réel
- Ne méprenez pas la différence entre
NOW()etCURRENT_TIMESTAMP - Pour les requêtes de plage, utilisez
>= AND < - Stocker en UTC par défaut
- Décidez des types (DATETIME vs TIMESTAMP) lors de la conception
La gestion de l’heure actuelle en MySQL est fondamentale pour la journalisation, l’agrégation des ventes, la gestion d’authentification/sessions, les travaux par lots, et plus encore.
Si vous suivez les principes de cet article, vous pouvez éviter de nombreux problèmes courants tels que la dérive temporelle, les bugs de limite, et la dégradation des performances.


