Pergunta

Eu agrupados aplicações que requerem um dos nós de ser designado como o mestre. Os nós do cluster são monitorados em uma tabela com nodeID , isMaster , LastTimestamp colunas.

Cada nó no cluster vai tentar se tornar um mestre a cada X segundos. Nó só pode se tornar um mestre se qualquer

  • não existe nenhum outro nó mestre
  • LastTimestamp no nó mestre atual é mais velho por 2 * X

Quando uma das condições acima é satisfeita

  • do nó mestre atual isMaster devem ser apuradas
  • do novo nó mestre isMaster deve ser definido
  • do novo nó mestre LastTimestamp deve ser definido como 'empresa' timestamp.

O que é o única declaração (portátil) SQL para alcançar o acima, sem a possibilidade de dois ou mais nós se tornando o mestre?

Foi útil?

Solução

Não é este tipo de coordenação normalmente tratada pelo próprio DBMS, em vez de aplicativos em execução no DBMS? Eu também posso imaginar maneiras de fazê-lo no DBMS estou familiarizado, mas sem saber mais sobre o seu sistema (que presumivelmente é usando discos compartilhados, para que todos os nós de ver os mesmos dados, existem protocolos que impedem o acesso simultâneo presumivelmente bloqueio aos dados; é um processo de usuário no nó mestre que atualiza periodicamente o LastTimestamp), ele vai ser duro para ajudar muito. E, como Jamie Amor apontou, o DBMS deve permitir que vários processos para coordenar o acesso aos registros relevantes -. A principal registro relevante sendo o registro mestre de corrente

[ Editado :. Talvez eu estava lendo muito para isso

A instrução UPDATE única tem a ver atualizações diferenciais em duas linhas da tabela, e deve falhar se apenas uma das duas atualizações é possível. Ou seja, ele deve tanto a mudança do atual mestre de ser não-master e também alterar o seu próprio recorde por isso é o mestre. Uma questão é como é que o DBMS impor a 'apenas uma linha pode ser o mestre' restrição. Vamos supor que obras e a declaração como um todo irá falhar se houver um problema - como deveria. Por que as pessoas muitas vezes omitir o nome da tabela, mesmo quando eles fornecem os nomes das colunas? Oh bem, o nome da tabela é daqui em diante ClusterControl . Cada nó deve conhecer o seu próprio NodeID de alguma forma; Eu usei {MyNodeID} para indicar onde que aparece no SQL.

Você precisa de uma atualização batimentos cardíacos separada:

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

A actualização "aproveitar status de mestre" poderia ser:

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'
          );

A teoria por trás do update 'aproveitar status de mestre' é (cláusula SET):

  • campo LastTimestamp para o novo mestre é definido para o timestamp atual, mas o velho mestre é inalterada.
  • o campo isMaster é alterado para 'Y' para o novo mestre e a 'N' para a idade mestre.

A teoria por trás da cláusula WHERE é:

  • Apenas alterar o registro para o nó atual se não é o mestre atual ou o registro para o nó mestre atual quando este nó não é o nó atual e a hora é mais de 120 segundos ( "2 * X" na questão) de idade.

Uma vez que existe um (possivelmente mítica) restrição no local para garantir que apenas uma linha tem o sinalizador 'Y', isso deve falhar como necessária quando o mestre é até à data.

SQL Untested!

]

Outras dicas

Eu posso imaginar uma solução para um banco de dados Oracle, mas eu não tenho certeza que seria portátil. Por que essa necessidade de ser uma única instrução SQL portátil? A maioria de banco de dados permitem bloqueio mesa e transações, que permitem que você faça esse tipo de coisa em múltiplas declarações.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top