A maioria de nós poderia fazer uma primeira tentativa de criar um modelo de banco de dados relacional enquanto dormia.

No entanto, depois de optar por trabalhar com um banco de dados de documentos, você precisará pensar um pouco diferente.

Não é mais difícil, é só que você está otimizando para coisas diferentes.

Então, quais são os princípios básicos para fazer isso corretamente?

Bem, há três princípios que podem ajudar a orientar seu pensamento:

  • Responda às perguntas que você sabe que fará.
  • Incorporar dados por conveniência, consultar por integridade.
  • Nomeie suas chaves de forma previsível e semântica.

Hoje, vamos examinar a primeira delas em detalhes.

Perguntas, não respostas

Quando dividimos nossos dados em tabelas, colunas e linhas do modelo relacional, estamos otimizando a capacidade de consulta. Estamos criando uma fonte de respostas quase ilimitadas e adiando nossas decisões sobre quais perguntas fazer.

Vejamos um exemplo simples: um sistema de gerenciamento de estoque que nos permite rastrear brindes com a marca Couchbase. 

Nesse sistema, temos camisetas, pen drives, canetas e esse tipo de coisa. De tempos em tempos, recebemos pedidos para enviá-los a grupos de encontro, conferências e indivíduos.

Muito provavelmente, isso nos daria as seguintes tabelas relacionais:

  • produtos
  • clientes
  • pedidos
  • detalhes do pedido

À primeira vista, Detalhes do pedido pode não parecer óbvio. No entanto, isso nos permite armazenar referências a todos os itens em cada pedido sem quebrar a primeira forma normal. Caso contrário, teríamos que serializar os itens de linha de cada pedido em uma cadeia de caracteres e armazená-la em uma coluna TEXT.

A menos que cometamos um erro, cada produto, cliente e pedido aparecerá apenas uma vez em nosso banco de dados. Isso nos dá a garantia de que as atualizações dos registros são universais e torna extremamente fácil consultar os dados da maneira que quisermos. 

Há sempre compensações, sempre há compensações

Dessa forma, podemos armazenar os dados do nosso sistema de gerenciamento de brindes em sua forma mais pura e consultá-los posteriormente da maneira que nos for mais conveniente.

Então, qual é o problema?

Bem, há algumas vantagens e desvantagens:

  • As consultas SQL são caras: para cada junção, há uma busca em disco, há uma sobrecarga de CPU, há um usuário aguardando a renderização da página.
  • Os bancos de dados relacionais são difíceis de escalonar em um cluster.

Vamos nos concentrar no primeiro trade-off por enquanto: se você estiver sendo indelicado, poderá dizer que a modelagem de dados relacionais é um exercício de roubo de ciclos de CPU do seu futuro eu. 

Conhecemos a maioria dos nossos padrões de consulta desde o início e, ainda assim, muitas vezes gastamos tempo retirando cuidadosamente esse contexto dos nossos dados. Dividimos os dados uma vez e, depois, passamos o resto da vida útil de nossos aplicativos solicitando ao servidor de banco de dados que junte tudo novamente.

É claro que isso tem seu lugar, mas é quase o oposto do caminho mais eficiente com um banco de dados de documentos.

Não faça com que as pessoas esperem por respostas

A primeira coisa que fazemos ao modelar um banco de dados de documentos é perguntar: "Que perguntas quero fazer aos meus dados?"

Então, quando o estado do nosso sistema muda, calculamos as respostas a essas perguntas e as armazenamos de forma pré-planejada no banco de dados.

Em vez de refazer as respostas cada vez que fazemos uma consulta, extraímos a resposta totalmente formada do banco de dados em uma única pesquisa.

O que isso significa na prática?

Vamos voltar ao nosso exemplo de gerenciamento de brindes. Uma de nossas perguntas seria:

O que preciso fazer para atender a um pedido específico?

Com um banco de dados relacional, escreveríamos uma consulta SQL que encontraria o pedido, usaria uma união para encontrar os itens no pedido, depois outra união para encontrar os detalhes de cada item e outra união para encontrar os detalhes do cliente.

Com o Couchbase, seria mais ou menos assim:

  1. O usuário seleciona seus itens e faz seu pedido.
  2. Nosso sistema grava o pedido no banco de dados como um único documento.
  3. Quando precisamos obter detalhes do pedido, é só ler para pegar o lote.

O documento de pedido resultante pode ter a seguinte aparência:

{
"orderID": 200,
"cliente":
{
"nome": "Matthew Revell",
"endereço": "11-21 Paul Street",
"city": "London"
},
"produtos":
[
{
"itemCode": "RedTShirt",
"itemName": "Camiseta vermelha do Couchbase",
"quantityOrdered": 3
},
{
"itemCode": "USB",
"itemName": "Pendrive USB preto de 8 GB com o logotipo vermelho do Couchbase",
"quantityOrder": 51
}
],
"status": "paid"
}

Este exemplo é bastante desnormalizado. Nosso sistema de gerenciamento de brindes já teria detalhes de cada cliente e produto em documentos separados, mas estamos repetindo o que sabemos sobre eles ao incorporar seus detalhes aqui.

Analisaremos as vantagens e desvantagens envolvidas na incorporação de dados em comparação com a referência a dados em uma publicação futura. 

A produção é mais complexa

Em um sistema de produção, provavelmente geraríamos várias dessas respostas prontas. Sem pensar muito sobre isso, provavelmente podemos pensar em algumas delas para o nosso sistema de gerenciamento de brindes:

  • Histórico de pedidos do cliente: os clientes querem ver tudo o que pediram, portanto, registraríamos esse pedido em relação a essa pessoa.
  • Status do pedido em tempo real: da mesma forma, nossos clientes desejarão ver o status de seus pedidos, portanto, podemos gerar essas informações agora e atualizá-las sempre que houver alguma alteração.
  • Instruções de envio: precisaremos informar às pessoas em nosso depósito o que elas precisam enviar para onde.

O importante é que não precisamos gerar tudo isso enquanto um ser humano está esperando uma resposta. 

Embora possamos querer atualizar o status do pedido em tempo real do cliente imediatamente, para que ele possa verificar se o pedido foi registrado, não há problema em processar a instrução de envio de forma assíncrona.

Dessa forma, quando um humano visualiza algo em nosso sistema, os dados já estão lá esperando. 

Em resumo: calcule previamente suas respostas

A primeira etapa para a modelagem eficiente do banco de dados de documentos é pensar em termos de pré-computação de suas respostas.

Sabemos de antemão quais perguntas queremos fazer e, portanto, podemos atender a essas perguntas na forma como escrevemos nossos dados.

Embora haja muito apelo intelectual na ideia de uma representação pura, normalizada e matematicamente sólida de nossos dados, na prática isso pode dificultar o atendimento a vários usuários simultâneos e o dimensionamento de nossa operação à medida que a demanda muda.

Ao computar nossas várias respostas no momento da gravação, nós:

  • remover o atraso de nossa experiência de usuário
  • pode distribuir mais facilmente os dados em um cluster
  • obtém o bônus adicional de menos incompatibilidade entre o estado do objeto e o que está no banco de dados.

Na próxima vez, examinarei quando incorporar dados e quando fazer referência a dados.

Autor

Postado por Matthew Revell, líder de suporte ao desenvolvedor, EMEA, Couchbase

Matthew Revell é um dos principais defensores do desenvolvimento do Couchbase na região EMEA. Ele desenvolveu uma estratégia global para colocar o Couchbase na mente dos desenvolvedores do produto.

5 Comentários

  1. Richard Stanford outubro 20, 2014 em 2:02 pm

    Espero que você explore pelo menos um caso simbólico não trivial nesta série, como, por exemplo, perceber depois do fato que você precisa ver a quantidade de cada item a ser encomendado (talvez map-reduce incremental).

  2. Como a atualização das informações de um cliente funcionaria bem se você as armazenasse em 8 milhões de lugares diferentes?

    1. Matthew Revell junho 16, 2015 em 2:33 pm

      Se você fizer referência aos mesmos dados em oito milhões de lugares diferentes, e eles nunca devem sair de sincronia, então é quase certo que será melhor manter um registro canônico desses dados e fazer referência a eles em cada um dos oito milhões de lugares em que precisar deles.

      Se você tivesse um grande número de cópias desses dados que precisassem permanecer em documentos separados e que também precisassem permanecer consistentes, o caminho mais fácil seria uma consulta N1QL, eu acho.

  3. Roberto Gamarra agosto 23, 2016 em 1:35 pm

    Então, existe uma Parte II?

Deixar uma resposta