Introduction
Les administrateurs et développeurs MongoDB doivent souvent inspecter les bases de données, diagnostiquer des problèmes et vérifier des changements sans perturber le trafic de production. Ce guide fournit une référence pratique des commandes pour les opérations quotidiennes sur MongoDB, couvrant l'identification de version, l'inventaire de l'environnement, la configuration sécurisée, les diagnostics, la récupération après incident et une liste de contrôle opérationnelle.
Chaque commande inclut les prérequis, la sortie attendue, les signaux d'échec potentiels et des conseils de récupération. L'accent est mis sur la sécurité opérationnelle : toujours observer avant de modifier, limiter le rayon d'impact, utiliser des espaces réservés au lieu d'identifiants réels et vérifier les résultats avant de continuer.
Ce guide est écrit pour MongoDB 6.0 et versions ultérieures, en utilisant le shell mongosh. Les commandes sont testées sur des instances autonomes et des jeux de réplicas. Les considérations relatives aux clusters partitionnés sont notées lorsque cela est pertinent.
1. Inventaire de version et d'environnement
Avant d'exécuter une commande, identifiez la version de MongoDB installée, l'édition et la topologie de déploiement. Cela évite d'utiliser une syntaxe non prise en charge ou d'appliquer des modifications destinées à une architecture différente.
1.1 Vérifier la version du serveur et les informations de build
Exécutez la commande suivante dans mongosh pour obtenir des informations détaillées sur le serveur :
// Connexion à l'instance cible
mongosh "mongodb://localhost:27017" --username admin --password 'VOTRE_MOT_DE_PASSE' --authenticationDatabase admin
// Obtenir les informations de build du serveur
db.version()
// Exemple de sortie attendue : '6.0.5'
db.runCommand({ buildInfo: 1 })
La commande buildInfo renvoie un document avec des champs comme version, gitVersion, modules, allocator et maxBsonObjectSize. Exemple de sortie :
{
"version": "6.0.5",
"gitVersion": "abc123...",
"modules": [],
"allocator": "tcmalloc",
"maxBsonObjectSize": 16777216,
"ok": 1
}
Pourquoi c'est important : Les différentes versions de MongoDB prennent en charge différentes fonctionnalités et options de commande. Par exemple, l'étape d'agrégation $merge a été introduite dans la version 4.2, et updateOne avec des mises à jour de pipeline nécessite la version 4.2 ou ultérieure. Connaître la version exacte évite les erreurs de syntaxe.
Signal d'échec : Si db.version() renvoie une erreur ou une chaîne de version qui n'est pas une version MongoDB valide, vérifiez la chaîne de connexion et l'authentification. Assurez-vous que le binaire mongosh correspond à une version compatible.
1.2 Déterminer la topologie de déploiement
Utilisez rs.status() pour vérifier si l'instance fait partie d'un jeu de réplicas :
rs.status().set // Renvoie le nom du jeu de réplicas s'il est configuré
Si la commande génère une erreur du type not running with --replSet, l'instance est autonome. Pour un cluster partitionné, connectez-vous à un routeur mongos et exécutez :
sh.status()
Cela affiche les partitions, la distribution des chunks et l'état de l'équilibreur.
Cas d'utilisation : Sur un jeu de réplicas, vous pouvez effectuer en toute sécurité la maintenance d'un secondaire en exécutant d'abord rs.stepDown() sur le primaire. Sur une instance autonome, vous devez planifier une interruption de service pour certaines opérations.
1.3 Observation en lecture seule de l'état actuel
Capturez les bases de données, les collections et les indicateurs clés actuels sans effectuer de modifications :
show dbs // Liste les bases de données et leurs tailles
use baseCible // Change de contexte
show collections // Liste les collections de la base actuelle
db.stats() // Statistiques au niveau de la collection (taille, nombre, index)
Exemple de sortie pour show dbs :
admin 0.000GB
config 0.000GB
local 0.000GB
mydb 0.001GB
Enregistrez toujours la sortie et l'horodatage avant d'effectuer des modifications. Cela fournit une référence pour le retour en arrière.
2. Chemin de configuration sécurisé
Les modifications de configuration dans MongoDB sont généralement effectuées via setParameter ou en modifiant le fichier de configuration. Suivez un processus strict : observez les paramètres actuels, effectuez une modification limitée, vérifiez et sachez comment revenir en arrière.
2.1 Afficher les paramètres de configuration actuels
db.adminCommand({ getParameter: '*' })
Cela renvoie un document volumineux avec tous les paramètres d'exécution. Pour filtrer un paramètre spécifique, par exemple logLevel :
db.adminCommand({ getParameter: 1, logLevel: 1 })
2.2 Modifier un paramètre en toute sécurité
Exemple : Augmenter la verbosité des journaux pour diagnostiquer une requête lente, mais seulement temporairement.
// Avant : logLevel est à 0 (par défaut)
// Définir logLevel à 1 (plus verbeux)
db.adminCommand({ setParameter: 1, logLevel: 1 })
// Attendu : { "was": 0, "ok": 1 }
// Après le diagnostic, revenir à 0
db.adminCommand({ setParameter: 1, logLevel: 0 })
Rayon d'impact : La commande setParameter affecte l'instance entière et ne persiste que jusqu'au redémarrage, sauf si elle est définie dans le fichier de configuration. Pour la production, testez toujours d'abord dans un environnement de staging.
Vérification : Réexécutez la commande getParameter pour confirmer que la nouvelle valeur est appliquée.
Récupération : Si le changement entraîne des problèmes de performances, remettez le paramètre à sa valeur d'origine. Si l'instance ne répond plus, redémarrez le processus mongod et le paramètre d'exécution reviendra à la valeur du fichier de configuration (ou à la valeur par défaut).
2.3 Modifications du fichier de configuration
Pour des modifications permanentes, éditez le fichier mongod.conf (généralement /etc/mongod.conf sous Linux). Après l'édition, redémarrez le service mongod :
sudo systemctl restart mongod
Sauvegardez toujours le fichier de configuration d'origine avant de le modifier :
cp /etc/mongod.conf /etc/mongod.conf.bak
Après le redémarrage, vérifiez que le nouveau paramètre est actif :
db.adminCommand({ getParameter: 1, <nomDuParametre>: 1 })
3. Commandes CRUD de base avec exemples
Les opérations CRUD constituent l'épine dorsale de l'administration et du développement quotidiens. Voici des exemples pratiques avec les sorties attendues.
3.1 Créer une base de données et une collection
MongoDB crée implicitement les bases de données et les collections lors de la première insertion.
use ventes // Bascule vers la base 'ventes' (pas encore créée)
db.commandes.insertOne({
_id: ObjectId(),
client: "Acme Corp",
articles: [
{ sku: "ABC123", qte: 2, prix: 10.99 },
{ sku: "XYZ789", qte: 1, prix: 24.50 }
],
statut: "en attente",
creeLe: new Date()
})
// Attendu : { acknowledged: true, insertedId: ObjectId("...") }
Maintenant, ventes et commandes existent.
3.2 Lire des documents
db.commandes.find({ statut: "en attente" }).pretty()
Compter les documents :
db.commandes.countDocuments({ statut: "en attente" })
Trouver un document par _id :
db.commandes.findOne({ _id: ObjectId("60f7b1c2e4b0a1c2e4b0a1c2") })
3.3 Mettre à jour des documents
Mettre à jour un champ :
db.commandes.updateOne(
{ _id: ObjectId("60f7b1c2e4b0a1c2e4b0a1c2") },
{ $set: { statut: "expédiée" } }
)
// Attendu : { acknowledged: true, matchedCount: 1, modifiedCount: 1 }
Mettre à jour avec un pipeline d'agrégation (version 4.2+) :
db.commandes.updateOne(
{ _id: ObjectId("60f7b1c2e4b0a1c2e4b0a1c2") },
[ { $set: { nombreArticles: { $size: "$articles" } } } ]
)
3.4 Supprimer des documents
Supprimer un document :
db.commandes.deleteOne({ _id: ObjectId("60f7b1c2e4b0a1c2e4b0a1c2") })
// Attendu : { acknowledged: true, deletedCount: 1 }
Supprimer plusieurs documents selon une condition :
db.commandes.deleteMany({ statut: "annulée" })
// Attendu : { acknowledged: true, deletedCount: 3 } // nombre d'exemple
Piège : Omettre accidentellement le filtre dans deleteMany({}) supprime tous les documents. Utilisez toujours des filtres ou envisagez d'utiliser deleteOne pour des suppressions ciblées. Pour vous protéger contre les suppressions massives accidentelles, activez l'option --setParameter protectAuditedDeletes=true (disponible à partir de MongoDB 5.0 pour les jeux de réplicas).
4. Indexation et performance
Une indexation appropriée est essentielle pour les performances des requêtes. Voici des commandes pour gérer les index en toute sécurité.
4.1 Afficher les index existants
db.commandes.getIndexes()
Sortie attendue :
[
{ "v": 2, "key": { "_id": 1 }, "name": "_id_" },
{ "v": 2, "key": { "statut": 1 }, "name": "statut_1" }
]
4.2 Créer un index
Créer un index sur un seul champ :
db.commandes.createIndex({ client: 1 })
// Attendu : { numIndexesBefore: 2, numIndexesAfter: 3, createdCollectionAutomatically: false, ok: 1 }
Créer un index composé :
db.commandes.createIndex({ statut: 1, creeLe: -1 })
Créer un index unique :
db.commandes.createIndex({ numeroCommande: 1 }, { unique: true })
Rayon d'impact : La création d'un index sur une grande collection peut verrouiller la base de données dans les anciennes versions, mais utilise une construction hybride dans MongoDB 4.2+ qui minimise l'impact. Surveillez avec currentOp() pendant la création.
Vérification : Utilisez db.commandes.getIndexes() pour confirmer que l'index apparaît. Utilisez explain() pour vérifier que l'index est utilisé :
db.commandes.find({ client: "Acme Corp" }).explain("executionStats")
Vérifiez winningPlan.inputStage.indexName pour voir si l'index est choisi.
4.3 Supprimer un index
Supprimez uniquement les index qui ne sont pas utilisés. Pour identifier les index inutilisés, interrogez l'agrégation $indexStats (disponible à partir de MongoDB 4.2) :
db.commandes.aggregate([ { $indexStats: {} } ])
Recherchez les index avec zéro accès. Supprimez avec :
db.commandes.dropIndex("client_1")
Récupération : Si les performances se dégradent après la suppression, recréez l'index. Il est recommandé de conserver un script avec les définitions d'index.
5. Vérification et diagnostics
Les commandes de diagnostic aident à identifier les opérations lentes, la contention des ressources et le retard de réplication.
5.1 Vérifier les opérations en cours
db.currentOp()
Filtrer les opérations actives de plus de 10 secondes :
db.currentOp({ "active": true, "secs_running": { $gt: 10 } })
Sortie attendue : Un tableau de documents avec opid, op, ns, secs_running, query et client. Identifiez les opérations de longue durée et arrêtez-les si nécessaire.
Arrêter une opération par opid :
db.killOp(123456)
Attention : L'arrêt d'une opération peut provoquer un retour en arrière ; utilisez-le uniquement sur des opérations clairement bloquées.
5.2 Retard de réplication et état
Sur un jeu de réplicas, vérifiez l'état :
rs.status()
Examinez le tableau members pour stateStr (PRIMARY, SECONDARY, etc.) et pingMs. Calculez le retard de réplication :
rs.printSecondaryReplicationInfo()
Exemple de sortie :
source: mongo1:27017
syncedTo: Sun Jan 07 2024 10:15:30 GMT+0000 (UTC)
0 secs (0 hrs) behind the primary
Signal d'échec : Si le retard dépasse un seuil (par exemple, 10 secondes pour les systèmes à forte écriture), examinez les problèmes de réseau, le matériel du secondaire ou les transactions de longue durée sur le primaire.
5.3 Métriques d'état du serveur
db.serverStatus()
Métriques clés à surveiller :
connections.currentetconnections.availableopcounterspour les taux de lecture/écrituremem.residentpour l'utilisation de la mémoirelockspour la contentionwiredTiger.cachepour la pression d'éviction du cache
Utilisez un outil de surveillance ou un script pour collecter ces données au fil du temps.
6. Sauvegarde et restauration essentielles
Les sauvegardes sont non négociables. Utilisez mongodump et mongorestore pour les sauvegardes logiques.
6.1 Créer une sauvegarde logique
mongodump --uri="mongodb://admin:VOTRE_MOT_DE_PASSE@localhost:27017" --out=/sauvegarde/$(date +%Y%m%d)
Cela crée des fichiers BSON pour chaque collection dans le répertoire de sortie spécifié. Pour une seule base de données :
mongodump --db ventes --out=/sauvegarde/ventes_$(date +%Y%m%d)
Vérification : Après la sauvegarde, vérifiez le répertoire de sortie et la taille des fichiers. Éventuellement, restaurez sur une instance de staging pour tester l'intégrité de la sauvegarde.
6.2 Restaurer à partir d'une sauvegarde
mongorestore --uri="mongodb://admin:VOTRE_MOT_DE_PASSE@localhost:27017" /sauvegarde/20240107/ventes
Important : mongorestore ne supprime pas les données existantes par défaut ; il fusionne. Pour remplacer une base de données, utilisez --drop :
mongorestore --drop --db ventes /sauvegarde/20240107/ventes
Échec et récupération : Si la restauration échoue en raison de problèmes de construction d'index, utilisez --noIndexRestore et reconstruisez les index après. Testez régulièrement les restaurations.
6.3 Instantanés de système de fichiers
Pour les grandes bases de données, les instantanés de système de fichiers (par exemple, LVM, instantanés AWS EBS) sont plus efficaces. Assurez-vous que l'instantané inclut tous les fichiers de données et le journal. Si vous utilisez WiredTiger, prenez un instantané pendant que l'instance est en cours d'exécution ou après un arrêt propre ; consultez la documentation MongoDB pour les exigences de point dans le temps.
7. Gestion des utilisateurs et des rôles
La gestion sécurisée des utilisateurs est une tâche quotidienne. Voici des commandes courantes.
7.1 Créer un utilisateur
use admin
db.createUser({
user: "utilisateurApp",
pwd: "MOT_DE_PASSE_FORT", // Utilisez un gestionnaire de mots de passe
roles: [
{ role: "readWrite", db: "ventes" },
{ role: "read", db: "rapports" }
]
})
7.2 Afficher les utilisateurs et les rôles
db.getUsers()
Afficher tous les rôles :
db.getRoles({ showPrivileges: true })
7.3 Accorder ou révoquer des rôles
Accorder un rôle :
db.grantRolesToUser("utilisateurApp", [ { role: "readWrite", db: "inventaire" } ])
Révoquer un rôle :
db.revokeRolesFromUser("utilisateurApp", [ { role: "readWrite", db: "inventaire" } ])
7.4 Changer le mot de passe
db.changeUserPassword("utilisateurApp", "NOUVEAU_MOT_DE_PASSE_FORT")
Note de sécurité : Ne stockez jamais de mots de passe dans des scripts. Utilisez des variables d'environnement ou un gestionnaire de secrets.
8. Pièges courants et comment les éviter
Même les opérateurs expérimentés commettent ces erreurs. Voici comment les prévenir et s'en remettre.
Piège 1 : Exécuter des commandes destructrices sans filtre
- Pourquoi cela arrive : Se précipiter ou supposer que le filtre est présent.
- Impact : Perte de données, surtout avec
deleteMany({})ouupdateMany({}). - Évitement : Écrivez toujours le filtre explicitement, utilisez
deleteOne/updateOnepour les modifications de document unique et activezprotectAuditedDeletesen production. - Récupération : Restaurez à partir d'une sauvegarde ou utilisez l'oplog pour rejouer les opérations jusqu'à juste avant l'erreur (si possible).
Piège 2 : Créer des index sans considérer l'impact
- Pourquoi cela arrive : En développement, la création d'index peut sembler instantanée ; en production, elle peut bloquer les écritures.
- Impact : Latence accrue ou temps d'arrêt.
- Évitement : Construisez les index en arrière-plan (par défaut dans 4.2+) ou utilisez des constructions d'index roulantes sur les jeux de réplicas. Surveillez avec
currentOp. - Récupération : Arrêtez la construction d'index si nécessaire :
db.killOp(<opid>), puis envisagez de construire pendant les périodes de faible trafic.
Piège 3 : Ignorer le retard de réplication
- Pourquoi cela arrive : Ne pas surveiller la santé des secondaires ou surcharger le primaire avec des opérations à forte écriture.
- Impact : Le secondaire ne peut pas basculer, la mise à l'échelle en lecture souffre, perte de données potentielle en cas de sinistre.
- Évitement : Configurez des alertes pour le retard, optimisez les écritures avec le traitement par lots et ajoutez de la capacité lorsque nécessaire.
- Récupération : Identifiez et arrêtez les opérations de longue durée, vérifiez le réseau ou resynchronisez le secondaire à partir d'une sauvegarde fraîche.
Piège 4 : Coder en dur les identifiants dans les scripts
- Pourquoi cela arrive : Commodité.
- Impact : Fuites d'identifiants, failles de sécurité.
- Évitement : Utilisez des variables d'environnement ou l'invite
--passwordde MongoDB. Dans le code, utilisez un gestionnaire de secrets comme HashiCorp Vault ou AWS Secrets Manager. - Récupération : Faites pivoter immédiatement le mot de passe exposé et auditez les journaux d'accès.
Piège 5 : Mauvaise configuration de l'authentification ou de l'autorisation
- Pourquoi cela arrive : Confusion entre la base de données d'authentification et la base de données cible.
- Impact : Les utilisateurs ne peuvent pas se connecter ou ont des privilèges excessifs.
- Évitement : Spécifiez toujours
--authenticationDatabaselors de la connexion. Accordez des rôles sur les bases de données spécifiques nécessaires, pas un rôlerootgénéral en production. - Récupération : Connectez-vous en tant qu'administrateur et corrigez les rôles avec
grantRolesToUserourevokeRolesFromUser.
9. Liste de contrôle des opérations pour l'administration quotidienne
Utilisez cette liste de contrôle lors des opérations de routine pour garantir la sécurité et la responsabilité. Attribuez un responsable à chaque décision majeure.
| Tâche | Commande/Procédure | Vérification | Responsable | Fréquence |
|---|---|---|---|---|
| Vérifier la version du serveur | db.version() | Confirmer la version attendue | Administrateur de base de données | Hebdomadaire |
| Examiner l'état du serveur | db.serverStatus() | Métriques dans les plages de référence | SRE | Quotidien |
| Vérifier le retard de réplication | rs.printSecondaryReplicationInfo() | Retard < 10 secondes | Administrateur de base de données | Horaire (automatisé) |
| Valider l'intégrité de la sauvegarde | mongorestore --dryRun sur la sauvegarde | Aucune erreur | Ingénieur de sauvegarde | Mensuel |
| Examiner l'utilisation des index | Agrégation $indexStats | Supprimer les index inutilisés | Administrateur de base de données | Trimestriel |
| Auditer les privilèges des utilisateurs | db.getUsers() et getRoles | Principe du moindre privilège appliqué | Responsable sécurité | Mensuel |
| Tester la procédure de restauration | Restaurer la sauvegarde vers le staging | Intégrité des données confirmée | Ingénieur de sauvegarde | Trimestriel |
Responsabilité : L'administrateur de base de données est responsable des vérifications de version, du retard de réplication et de l'examen des index. L'ingénieur de sauvegarde est responsable des tests de sauvegarde et de restauration. Le responsable sécurité est responsable des audits de privilèges. Chaque élément doit avoir un runbook et une personne de secours désignée.
10. Conclusion
Les commandes MongoDB de base avec exemples pratiques sont plus utiles lorsqu'elles font partie d'un flux de travail opérationnel discipliné. Ce guide a couvert les vérifications de version, les modifications de configuration sécurisées, le CRUD, l'indexation, les diagnostics, la gestion des utilisateurs, la sauvegarde/restauration et les pièges courants. Chaque commande doit être testée dans un environnement de staging avant la production, avec un plan de retour en arrière clair.
Commencez par des vérifications à faible risque : exécutez db.version(), db.serverStatus() et rs.status() sur vos instances. Enregistrez les sorties, comparez-les aux références attendues, puis intégrez progressivement les commandes plus complexes. En suivant les principes d'observation, de modification limitée, de vérification et de récupération, vous pouvez gérer MongoDB en toute confiance et éviter des erreurs coûteuses.
Pour continuer à apprendre, explorez la documentation officielle de MongoDB sur la référence des commandes, les meilleures pratiques de sécurité et l'optimisation des performances. Entraînez-vous dans un environnement sûr et gardez toujours vos sauvegardes à jour.