Question

J'ai des applications en cluster qui nécessitent que l'un des nœuds soit désigné comme maître. Les nœuds de cluster sont suivis dans une table avec les colonnes nodeID , isMaster , lastTimestamp .

Chaque nœud du cluster tente de devenir un maître toutes les X secondes. Le nœud ne peut devenir un maître que si

  • il n'y a pas d'autres nœuds maîtres
  • le lastTimestamp du noeud principal actuel est plus ancien de 2 * X

Lorsque l'une des conditions ci-dessus est remplie

  • le isMaster du nœud maître actuel doit être effacé
  • le isMaster du nouveau nœud maître doit être défini
  • le lastTimestamp du nouveau nœud maître doit être défini sur l'horodatage "maintenant".

Qu'est-ce que l'instruction unique (portable) SQL permettant d'atteindre les objectifs ci-dessus sans possibilité que deux ou plusieurs nœuds deviennent le maître?

Était-ce utile?

La solution

Cette sorte de coordination n'est-elle pas gérée normalement par le SGBD lui-même plutôt que par les applications qui y sont exécutées? Moi aussi, je peux envisager des solutions dans le SGBD avec lequel je suis familier, mais sans en savoir plus sur votre système (il utilise probablement des disques partagés, de sorte que tous les nœuds voient les mêmes données; il existe probablement des protocoles de verrouillage empêchant les accès simultanés. (c’est un processus utilisateur sur le nœud maître qui met à jour périodiquement le dernier horodatage), il sera difficile d’aider beaucoup. Et, comme Jamie Love l'a fait remarquer, le SGBD devrait permettre à plusieurs processus de coordonner l'accès aux enregistrements pertinents - l'enregistrement principal pertinent étant l'enregistrement principal actuel.

[ Édité : Peut-être que je lisais trop dedans.

La seule instruction UPDATE doit effectuer des mises à jour différentielles sur deux lignes de la table et doit échouer si une seule des deux mises à jour est possible. En d'autres termes, il doit à la fois changer le maître actuel pour qu'il ne soit pas maître et modifier également son propre enregistrement pour qu'il s'agisse du maître. L’un des problèmes est de savoir comment le SGBD applique la contrainte «une seule ligne peut être maîtresse». Supposons que cela fonctionne et que la déclaration dans son ensemble échouera s'il y a un problème - comme il se doit. Pourquoi les gens omettent-ils si souvent le nom de la table, même lorsqu'ils fournissent les noms des colonnes? Le nom de la table est désigné ci-après par ClusterControl . Chaque nœud doit connaître son propre identifiant de nœud; J'ai utilisé {MyNodeID} pour indiquer où cela apparaît dans le code SQL.

Vous avez besoin d'une mise à jour de pulsation séparée:

 UPDATE ClusterControl
     SET lastTimestamp = CURRENT_TIMESTAMP
     WHERE NodeID = {MyNodeID};

Le " seize master status " la mise à jour peut être:

UPDATE ClusterControl
    SET lastTimestamp = (CASE
                         WHEN NodeID = {MyNodeID} THEN CURRENT_TIMESTAMP
                         ELSE lastTimestamp END),
        isMaster      = (CASE
                         WHEN NodeID = {MyNodeId} THEN 'Y'
                         ELSE 'N' END)
    WHERE (NodeID  = {MyNodeID} AND isMaster = 'N') OR
          (NodeID != {MyNodeID} AND
           lastTimestamp < CURRENT_TIMESTAMP - INTERVAL '120' SECOND AND
           isMaster = 'Y'
          );

La théorie à la base de la mise à jour 'seize master status' est (clause SET):

  • le champ lastTimestamp du nouveau maître est défini sur l'horodatage actuel, mais l'ancien maître reste inchangé.
  • le champ isMaster est remplacé par "Y" pour le nouveau maître et par "N" pour l'ancien maître.

La théorie derrière la clause WHERE est la suivante:

  • Ne modifiez l'enregistrement du noeud actuel que s'il ne s'agit pas du maître actuel ou de l'enregistrement du noeud principal actuel lorsque ce noeud n'est pas le noeud actuel et que l'horodatage est supérieur à 120 secondes (" 2 * X " in la question) vieux.

Dans la mesure où une contrainte (peut-être mythique) est en place pour garantir qu'une seule ligne possède l'indicateur "Y", cette opération devrait échouer si le maître est à jour.

SQL non testé!

]

Autres conseils

Je peux imaginer une solution pour une base de données Oracle mais je ne suis pas sûr que ce serait portable. Pourquoi faut-il une seule instruction SQL portable? La plupart des bases de données permettent le verrouillage de table et les transactions, ce qui vous permet de faire ce genre de chose dans plusieurs instructions.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top