Introdução ao MongoDB: um banco de dados NoSQL

Já faz algum tempo que venho estudando o MongoDB.  Dentro da turma dos SGBDs NoSQL este foi aquele com o qual acabei criando maior simpatia pela sua simplicidade e documentação (apesar de muita gente falar do Apache Cassandra, sua documentação ainda é horrível).

O MongoDB é um banco de dados orientados a documentos. Sendo assim, se você, assim como eu (e 99% dos desenvolvedores) vêm de um ambiente dominado pelo modelo relacional, em um primeiro momento verá este SGBD como um alienígena – o que é incrívelmente empolgante e assustador. Meu objetivo neste post não é ensinar a usar o MongoDB (será assunto do próximo), mas sim expor as principais diferenças entre este e o confortável modelo relacional.

Este assustador (e maravilhoso) “mundo novo”

Para os acostumados com o modelo relacional, o MongoDB se mostrará assustador no primeiro contato porque a maior parte dos conceitos que nos forneciam uma certa sensação de segurança basicamente “desaparecem”. Aqui é obrigatório saber lidar com o medo: conforme mostrarei neste post, há riscos, mas os ganhos os compensam.

Não acho que o modelo não relacional possa ser aplicado a todos os casos, porém é sempre importante conhecer mais de um paradigma para que possamos no mínimo ampliar nossos horizontes quando nos deparamos com situações que fogem da nossa zona de conforto (e o MongoDB pode ser bastante desconfortável neste primeiro momento).

Não há registros, mas documentos

Algo sempre me incomodou no modelo relacional: com ele tentamos representar o mundo real (que é n-dimensional) usando uma abordagem bidimensional. Tudo o que eu for representar em minhas tabelas possui apenas duas dimensões: linhas e colunas. É verdade que podemos representar quantas dimensões quisermos no modelo relacional a partir de relacionamentos, porém sempre fica aquela sensação de se estar “forçando a barra”.

Além disto, por mais bem feita que seja o processo de análise, sempre há a possibilidade de posteriormente mais um atributo ser encontardo. O mundo é um ambiente complexo: acredito que para representá-lo, precisamos também de uma terminologia complexa.

No MongoDB, o equivalente aos registros são os documentos, que utilizam a sintaxe JSON. A melhor maneira de se ter um feeling do que quero dizer é ver o bicho. Sendo assim, observe o código abaixo:


Kico = {
nome: "Henrique Lobo Weissmann",
apelido: "Kico (ou seria este o nome?)",
cidade: "Belo Horizonte"
}

Eu criei um documento chamado kico que possui 3 atributos: nome, apelido e cidade. Repare que em momento algum defini o tamanho máximo de cada atributo, regras de validação ou qualquer tipo de restrição. Em seguida, se quiser armazená-lo em um banco de dados, bastaria executar o código abaixo:


db.kicodb.save(Kico)

Neste caso, eu estaria armazenando o documento Kico no banco de dados kicodb. Agora, observe o código abaixo:


Nanna = {nome:"Maria Angélica Alvares da Silva e Silva",
apelido:"Nãnna",
esposaDo:"Kico",
cidade:{nome:"Belo Horizonte", estado:{nome:"Minas Gerais", pais:"Brasil"}},
caes:[{nome:"Fraude", raça:"Pinscher?"}, {nome:"Zé", raça:"Schnauzer"}]}

db.kicodb.save(Nanna)

Repare que um registro com estrutura completamente diferente foi incluida no banco de dados. Até o atributo cidade é diferente. Enquanto no registro “Kico” eu tenho apenas uma string, no objeto Nanna eu tenho um outro documento. Outro ponto interessante: repare que eu tenho inclusive uma coleção associada ao objeto Nanna.

E tudo é mesmo assim salvo no mesmo banco de dados sem problema algum. Na realidade, eu poderia armazenar até o registro abaixo sem problemas:


esquisitao = {quantidade:34, poemaFavorito:"Batatinha"}

Como pode ser visto, não há regras de validação rígidas: qualquer tipo de documento pode ser armazenado no banco de dados. Claro: na prática somente objetos semelhantes são armazenados na base de dados, porém é bacana saber que se um dia aparecer algum novo atributo, poderemos inclui-lo apenas nos documentos aonde o mesmo é necessário, ao contrário do modelo relacional, aonde uma coluna se aplica a todos os registros.

Desvantagem: o desenvolvedor precisa ficar esperto para que suas bases de dados não virem um “samba do criolo doido”

Vantagens:

  • Finalmente você se livrou de uma abordagem bidimensional e pode representar objetos do mundo real como realmente são: complexos e únicos.
  • Caso no futuro surja algum caso no qual novos atributos apareçam, você pode aplicá-los somente aonde é necessário, e não em todos os casos, como no modelo relacional, aonde normalmente cria-se uma nova “coluna” na tabela relacionada

Redundância de dados máxima

No modelo relacional somos o tempo inteiro incentivados a reduzir ao máximo possível a redundância de dados. Aliás, os relacionamentos existem justamente para isto. E é um modelo que inegávelmente funciona muito bem. Já no MongoDB a situação é inversa: não há relacionamentos, e a duplicação de dados, pelo que pude observar é até incentivada.

Dê uma olhada no código abaixo:


pessoa1 = {nome:"Peçonhento", cidade:{nome:"Belo Horizonte", estado:"MG"}}

pessoa2 = {nome:"Zequinha", cidade:{nome:"Belo Horizonte", estado: "MG"}}

pessoa3 = {nome:"Joca", cidade:"Lagoa Santa"}

pessoa4 = {nome:"Complexado", cidade:{nome:"Rio de Janeiro", estado:{nome:"Rio de Janeiro", pais:{nome:"Brasil"}}}

Lembre-se de que aqui não há tabelas: há coleções de documentos. Em cada documento armazeno os dados da forma que eu quiser. Eu poderia criar uma coleção contendo apenas cidades e em seguida criar um relacionamento entre duas ou mais coleções distintas, é verdade (foge do assunto deste post), mas isto iria contra a idéia básica por trás do modelo orientado a documentos.

A idéia básica aqui é a de que um documento deve ser auto-contido, ou seja, isolado já deve conter todas as informações de que necessita. Por que isto? Simples: porque assim você ao invés de fazer uma consulta com vários joins como é o caso do modelo relacional executa uma única consulta, que já te retorna o documento inteiro. Resultado: mais performance.

Desvantagem: se você quiser alterar todos os registros relacionados a uma unidade semântica, precisa tratá-los um a um

Vantagem: maior performance. Uma única consulta já te retorna tudo o que você precisa saber a respeito do documento. Esta é uma das razões pelas quais vêm sendo adotado em projetos que exigem alta performance.

Concluindo

Estas são as duas principais diferenças (que só são vantagens de acordo com o caso) que vi no MongoDB (do modelo baseado em documenots na realidade) com relação ao modelo relacional. É aplicado a todos os casos? Óbvio que não.

O importante a meu ver é sair da área de conforto do modelo relacional: isto, como mencionei, amplia os nossos horizontes, faz com que vejamos outras possibilidades além de tabelas para armazenar nossos dados. Fico assustado quando topo com desenvolvedores que só conseguem desenvolver algo que envolva tabelas, colunas e registros. Aliás, a grande vantagem que vejo nesta “moda” de modelos noSQL é justamente esta: a exposição de “novos” paradigmas a um mundo dominado pelo modelo relacional, que só considero ruim quando tomado como a única alternativa viável pela maior parte das pessoas.

Este post é fundamental para que eu possa partir para os próximos, nos quais exporei como usar o MongoDB e, ainda mais importante, como aplicá-lo com Groovy e Java. Grande abraço!

Ah, quer baixar o MongoDB? Este é o site oficial: http://www.mongodb.org

68 thoughts on “Introdução ao MongoDB: um banco de dados NoSQL

  1. Parabéns pelo post!! Assunto interessante e bem escrito. Não conhecia o MongoDB e vou ler mais a respeito. Abração .

    Responda

    admin Reply:

    Opa. Valeu pelo apoio!

    Responda

    Andressa Reply:

    hahahahahahahahahahhahhaha, “A melhor maneira de se ter um feeling do que quero dizer é ver o bicho.”

    “o desenvolvedor precisa ficar esperto para que suas bases de dados não virem um “samba do criolo doido””
    ri muito .. ahahaha.. q isso gente.
    Bom summary.

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    E?

    Responda

    Andressa Reply:

    e nada. So elogiei seu post cara.

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Oi Andressa, me desculpe pelo mal jeito. É que realmente na hora (estava exausto) não havia entendido o seu comentário.
    Mil desculpas: realmente não queria soar grosseiro de forma alguma.

    Responda

  2. Excelente post!
    É bom ver que podemos ampliar nossos horizontes e experimentar algo novo sem medo de sermos mais eficiente!
    Parabéns!

    Responda

    admin Reply:

    Que bom que gostoy Geyzon! Valeu!

    Responda

  3. Olá, essas características não se apresente somente ao MondoDB, mas a qualquer um dos NoSQL que são armazenados como documentos (CouchDB e Apache Cassandra).

    :)

    Responda

    admin Reply:

    Oi Cairo,

    mas isto está claro no texto, não? A diferença é que estou aplicando estes conhecimentos a um SGBD específico. :)

    Responda

  4. Incrível como isso me faz lembrar XML e suas marcações. Mas o melhor de tudo é que é “palpável” aos olhos cada linha que você lê. Sem abstração para conseguir entender e enxergar o que há numa base de dados.

    Responda

    admin Reply:

    Eu também tenho o mesmo sentimento Daniel. E não é a toa, porque o que estamos vendo é um formato de intercambio de informações assim como o XML né?

    Eu sinceramente acho o XML uma das maiores invenções de todos os tempos. É uma pena que o mal uso do mesmo tenha queimado tanto o seu filme entre os desenvolvedores, porque na minha opinião, é uma tecnologia simplesmente fantástica

    Responda

  5. Pessoal, o único ponto que realmente me deixa desconfortável é a questão da redundância, mas vendo no dia-a-dia como os projetos de TI se desenrolam (ou melhor se enrolam) no ambiente corporativo uma solução como essa nos daria a flexibilidade exigida pela instabilidade dos requisitos com que temos que lidar.

    Responda

  6. Fazer um sistema de log usando um NoSQL faria bastante sentido, inclusão e apenas consulta.

    Vou fazer alguns testes para ver suas vantagens e desvantagens em uma aplicação do tipo.

    Responda

    admin Reply:

    Mas ai só se for um log ultra complexo né? Porque arquivo texto pra coisas simples ainda é imbatível não? Qual a vantagem em usar um banco de dados ao invés de arquivos simples para log?

    Da uma olhada nisto: http://www.splunk.com – desconfio que é exatamente o que você está procurando. :)

    Responda

  7. Muito bom artigo. Ele expõe de maneira prática o que é esse “alienígena” que chega derrubando algumas “leis fundamentais” sobre bancos de dados. O legal disso é que inova em uma área na qual a ortodoxia estava ganhando rumos assustadores. Se o mundo real não pudesse adaptar-se ao “schema” e aos “roles” certos, o mundo real estaria errado.
    Parabéns pelo artigo com sua linguagem clara e objetiva.

    Responda

    admin Reply:

    Oi Roberto, valeu!

    Responda

  8. Mas o que seria o kicodb?
    Um documento que devo criar manualmente ou existe um comando para isso?
    Estou iniciando o estudo.
    Obrigado.

    Responda

    admin Reply:

    Oi Jr,

    kicodb é o nome do banco de dados. No MongoDB, quando você executa um comando como por exemplo db.[nome do banco].save(), caso o banco de dados ainda não exista, ele é criado automáticamente.

    No caso, eu estava salvando/mandando criar um banco de dados chamado kicodb.

    Responda

  9. Parabéns! Gostei do Post, bem explicado, quem já viu XML tem mais facilidade de entender. Gostei das vantagens e não gostei das desvantagens, hehe! Ter que mudar um-a-um os valores de campos “atributos” que são iguais deve dar um trabalhinho, no mais, gostei muito.

    Responda

  10. Muito bom o post, realmente não conhecia este DB. Mas só refletindo sobre o que você disse sobre performance, isso funciona para cadastramento, mas quando se pensa em relatórios, onde ao invés de extrair apenas as colunas que interessam de cada join, e de forma indexada, nós teríamos que extrair todo o documento antes, e tratar caso a caso, teríamos uma relação inversa de performance. Sem falar que para manter índices, acredito que seja necessário voltar ao conceito do DBase… até fico pensando se a abordagem deste DB não seria idêntica à do Tamino, que é baseado em XML.
    Abraço!

    Responda

    admin Reply:

    Oi Rodrigo,

    fico feliz que você tenha gostado. Sabe, você tem razão: eu também não sei como seria o uso do MongoDB para a geração de relatórios tradicionais como os que fazemos com SGBDs relacionais.

    É aquele negócio né? Cada macaco no seu galho. A gente deve usar estes bancos NoSQL para alguns casos (tabelas MUITO esparsas é um bom indício de que você deve usar) e relacionais para outros.

    Na prática, eu acredito inclusive na sinergia entre os dois modelos, usando um quando o outro não atende e vice-versa.

    Responda

  11. Muito bom! Por vezes o modelo relacional me sufoca, literalmente falando, com toda essa preocupação com normalização, redundância e tudo. Se bobear, a menor das preocupações é em representar o mundo real… Mas enfim, isso não é uma crítica ao paradigma relacional (ele ainda é meu ganha pão!), é mais um desabafo – um desabafo alegre ao ler essa novidade do post. Minha cabeça já ferve com as possibilidades!

    E falando em relatórios, vamos deixar um pensamento no ar. Quando dizemos que esse modelo não é prático para relatórios, talvez estejamos pensando em relação a eles tão tradicionalmente quanto o próprio modelo relacional… ;)

    Responda

    admin Reply:

    Oi Daniel, fico feliz que tenha gostado.

    E cara… seu último comentário vai DIRETO ao ponto! MUITO bem observado. Não havia pensado nisto ainda. Acho alta (99%) a probabilidade de você ter razão. :)

    Responda

  12. Gostei muito, mais didático impossível. Parabéns!

    Responda

    admin Reply:

    Valeu Cássio!
    Pretendo em breve publicar mais algumas coisas sobre o assunto por aqui.

    Responda

  13. Parabens pelo ótimo post. Estou começando a estudar banco NoSQL e minha duvida é sobre: Se usar um banco convencional (sql) onde foi definido que as tabelas não possuem relacionamento, ou seja, a tabela possui campos: cidade, estado, etc. em uma consulta não terá a mesma performance do banco NoSql já que não é necessário unir várias tabelas?

    Responda

    admin Reply:

    Oi Ed, valeu!

    Cada caso é um caso, mas eu costumo observar o seguinte fato ao fazer minhas escolhas: minhas tabelas estão ficando muito esparsas, isto é, há muitas colunas que raramente estão sendo preenchidas? Se a resposta for sim, ai é sinal de que algo NoSQL pode ser uma alternativa interessante.

    No caso que você falou, de uma tabela sem relacionamentos, de fato: você tá certo. A performance seria a mesma ou, no máximo, muito próxima. Além do quê, é uma situação ideal para SGBDs relacionais né? E neste caso, os bichinhos são 100% otimizados pra isto.

    Aliás, neste caso, nem teria muito porquê usar um banco NoSQL se trata-se de algo que fácilmente pode ser representado no modelo tabular né?

    Outro fator que uso como indicador: meu objeto de domínio consegue ser 100% representado em uma metáfora bidimensional como uma tabela? Se sim, banco relacional é uma excelente opção. Se não, e eu tiver tabelas esparsas ou relacionamentos MUITO complexos, NoSQL começa a se mostrar viável.

    Responda

    Ed Reply:

    Obrigado pela resposta.

    Responda

    admin Reply:

    Precisando é só chamar! :)

    Responda

  14. Parabéns pelo post, estou iniciando meus estudos com NoSql e gostei muito da introdução aqui apresentada. abraços.

    Responda

    admin Reply:

    Oi Karen, valeu!

    Responda

  15. Otimo Post, porém gostaria de saber com identificar um documento neste tipo de banco, tentando uma semelhança a PK do banco relacional.

    Responda

  16. Olá Kico,

    Fino no grão teu post, excelente cara meus parabéns!
    Achei muito interessante a abordagem do MongoDB me parece bem simples utilizar vou realizar alguns testes.

    Responda

    admin Reply:

    Oi Bruno. Que bom que gostou. Valeu!

    Responda

  17. Poxa Kiko, você fez tudo parecer fácil. :) Obrigado mesmo pelo post. Para um desenvolvedor front-ender como eu, fica bem mais fácil quando está tudo bem escrito e explicado de forma simples.
    Continue o bom trabalho!

    um abraço

    Responda

  18. Adorei o tópico gostaria de saber se para games? se esse banco seria mais adequado e como ele se comporta na nuvem ?

    Responda

  19. Parabéns pelo post. Mas olha….Ufaaa!!! Realmente da um nó, mas é excelente poder ver novas formas de desenvolver. Já estou fazendo alguns testes em C#.NET e Java, estou gostando dos resultados, apesar de ter que pensar diferente, é muito empolgante! É uma grande quebra de paradigma, perspectiva nova. Vale muito a pena entender esse modelo de BD.

    Responda

  20. Muito bom o post, talvez eu tenha pego o bonde andando, mas acho que vale ainda um comentário.

    Veja bem, eu gostei muito quando em um dos comentários acima você falou que em usar um SGBD relacional juntamente com um orientado a documentos. Isso sim sería realmente “revolucionário” no meu ponto de vista.

    Entendo que resumir o mundo em tabelas relacionadas seja uma forma pobre para esse processo, porém há de se observar que ainda que você trabalhe com nosql vc irá necessitar de exatidão, precisão, consistência, certeza! O sistema não pode errar.

    JSON, na prática é um array. Então para que eu quero uma coleção de arrays completamente distintos? Vamos supor que vc queira criar uma collection em um db relacional. Faremos assim:

    table: test_collections
    field: json_code

    Pra ficar mais claro…

    INSERT INTO test_collections( json_code) VALUES (‘{nome: “anderson”, cidade: “recife”}’);

    Então dentro de um relacional e com poucos algorítimos sería possível eliminar a necessidade real de um db orientado a documento. Claro, óbvio, que existe a questão do desempenho, onde o Mongo é MUITO melhor que o MySQL, por exemplo, em quase todos os quesitos.

    Então, realmente, se não for por questões de desempenho, eu não vejo muita ultilidade no NoSQL. Me fala que eu to errado, por favor! hehehehe

    Abraço e parabéns pelo artigo!

    Realmente, não acho que os nosql da vida irão “derrubar” os relacionais de forma nenhuma. Talvez eu esteja sendo alienado, não sei. Você não acha que o mongo e outros nosql são inferiores aos relacionais?

    Responda

  21. Realmente é uma nova proposta, mas tenho grande dificuldade de ver a vantagem sobre o modelo relacional quanto estou trabalhando por exemplo com diferentes tabelas, a exemplo saber o saldo de compras dos clientes por estado. Pelo que soube não hã “join” nos NoSQL e a questão do banco validar dados, a exemplo um cadastro que não aceita menor de idade, no Firebird que uso posso por exemplo criar uma regra onde ele confronta o valor do dado já considerando a data no servidor… em outras palavras o SGBD por ter as tantas regras e formalidade me permite passar à ele as validações, reduzindo assim a demanda de processamento nos terminais.

    Bom enfim, entendo que o NoSQL é para ser usando em situações tipicas como blogs, mas dificil, pelo menos agora, ver ele em um ERP onde padrões e formalidade são necessidades que evitam redundância de dados e inconsistência nos relacionamentos.

    Abraços aos amigos

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Oi Carlos, eu concordo com você. Na realidade, até hoje, encontrei poucas situações que justificassem o uso do MongoDB: basicamente apenas em situações nas quais eu topava com tabelas muito esparsas ou casos em que os atributos variassem demais de registro para registro.

    Tirando isto, o modelo relacional resolve bem os nossos problemas: de fato, se eu quero fazer um relatório gerencial, o formato tabular vêm bem mais a calhar do que o documental.

    Acho que a melhor alternativa é mesclar os dois mesmo: relacional para uma parte, documental ou gráfico para outra.

    Responda

  22. Excelente Post, extremamente claro e objetivo. Obrigado, me ajudou muito! :)

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Que bom que foi util. Obrigado

    Responda

  23. Parabéns pelo artigo, você me ajudou bastante agora que estou começando com o MongoDB.

    Como você mesmo disse: É assustador e MARAVILHOSO ao mesmo tempo. Simplesmente estou adorando.

    Valeu!

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Opa, bacana que tenha gostado.
    Mas uma dica: opte por um modelo de persistência misto.
    Coloque a parte que requeira relacionamentos fora do mongodb.

    Responda

    Marcio Vinicius Reply:

    Opa valeu pela dica, muito interessante.

    Abraços estou acompanhando seu site.

    Responda

  24. Velho! muito bom artigo, parabens! simples e objetivo.

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Opa, obrigado Tomaz!

    Responda

  25. Estou começando com Banco de dados NoSql e gostaria de saber onde encontrar uma base de dados para testes no MongoDB sendo que esta base como ja sabemos deve ter um grande volume e variabilidade….obrigado pessoal.

    Responda

    Kico (Henrique Lobo Weissmann) Reply:

    Oi Fernando,

    sinceramente não sei viu. Talvez o melhor a fazer seja você mesmo criar esta base de dados usando algum script ou algo similar. Nunca vi alguém fornecendo uma base assim para download.

    Responda

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>