MongoDB
 sql >> Base de données >  >> NoSQL >> MongoDB

État de récupération sans fin du secondaire

Le problème (le plus probable)

La dernière opération sur le primaire est de "2015-05-15T02:10:56Z", alors que la dernière opération du secondaire est de "2015-05-14T11:23:51Z", soit une différence d'environ 15 heures. Cette fenêtre peut bien dépasser votre fenêtre d'oplog de réplication (la différence entre l'heure de la première et de la dernière entrée d'opération dans votre oplog). En termes simples, il y a trop d'opérations sur le primaire pour que le secondaire rattrape.

Un peu plus élaboré (bien que simplifié) :lors d'une synchronisation initiale, les données à partir desquelles le secondaire se synchronise sont les données d'un point donné dans le temps. Lorsque les données de ce point dans le temps sont synchronisées, le secondaire se connecte à l'oplog et applique les modifications qui ont été apportées entre ledit point dans le temps et maintenant en fonction des entrées de l'oplog. Cela fonctionne bien tant que l'oplog conserve toutes les opérations entre le moment mentionné. Mais l'oplog a une taille limitée (il s'agit d'une collection dite capped collection ). Donc, s'il y a plus d'opérations en cours sur le primaire que l'oplog ne peut en contenir pendant la synchronisation initiale, les opérations les plus anciennes "disparaissent". Le secondaire reconnaît que toutes les opérations nécessaires pour "construire" les mêmes données que le primaire ne sont pas disponibles et refuse de terminer la synchronisation, en restant dans RECOVERY mode.

La ou les solutions

Le problème est connu et non un bogue, mais le résultat du fonctionnement interne de MongoDB et de plusieurs hypothèses de sécurité formulées par l'équipe de développement. Par conséquent, il existe plusieurs façons de gérer la situation. Malheureusement, puisque vous n'avez que deux nœuds porteurs de données, tous impliquent des temps d'arrêt.

Option 1 :Augmenter la taille de l'oplog

C'est ma méthode préférée, car elle traite le problème une fois (en quelque sorte) pour toutes. C'est un peu plus compliqué que d'autres solutions, cependant. D'un point de vue général, voici les étapes à suivre.

  1. Arrêter le primaire
  2. Créer une sauvegarde de l'oplog en utilisant un accès direct aux fichiers de données
  3. Redémarrer le mongod en mode autonome
  4. Copier l'oplog actuel dans une collection temporaire
  5. Supprimer l'oplog actuel
  6. Recréer l'oplog avec la taille souhaitée
  7. Recopiez les entrées oplog de la collection temporaire vers le nouvel oplog brillant
  8. Redémarrer mongod dans le cadre du jeu de répliques

N'oubliez pas d'augmenter l'oplog du secondaire avant de faire la synchronisation initiale, car il peut devenir principal à un moment donné !

Pour plus de détails, veuillez lire "Modifier la taille de l'oplog" dans les didacticiels concernant la maintenance des jeux de répliques .

Option 2 :Arrêtez l'application pendant la synchronisation

Si l'option 1 n'est pas viable, la seule véritable autre solution consiste à arrêter l'application provoquant une charge sur le jeu de répliques, à redémarrer la synchronisation et à attendre qu'elle soit trop complète. En fonction de la quantité de données à transférer, calculez avec plusieurs heures.

Une note personnelle

Le problème de la fenêtre oplog est bien connu. Bien que les jeux de réplicas et les clusters fragmentés soient faciles à configurer avec MongoDB, certaines connaissances et un peu d'expérience sont nécessaires pour les maintenir correctement. N'exécutez pas quelque chose d'aussi important qu'une base de données avec une configuration complexe sans connaître les bases - au cas où Something Bad (tm) se produirait, cela pourrait bien conduire à une situation FUBAR.