segunda-feira, 21 de dezembro de 2015

MongoDB - Find/FindOne


Nesse post será abordado a pesquisa no banco de dados.

Para brincarmos com as pesquisas seria bom que você tivesse um database com vários dados. Nesse post usaremos um banco com pokemons para as pesquisas.

Esse é o link da database. Copiei e salve em um arquivo com o nome pokemons.json e importe os dados.

Fiz minha importação
mongoimport --db pokedex --collection pokemons --drop --file pokemons.json

Vamos lá!

Nesse post iremos falar sobre o find e o findOne. Mas antes uma curiosidade sobre o _id (UUID – Universally Unique Identifier) esse atributo é automaticamente colocado em cada registro que você insere no seu banco. Eles é formado por:

4-bytes: valor que representa os segundo desde a época Unix;
3-bytes: identificador de máquina;
2-bytes: ID do processo;
3-bytes: contador, começando com um valor aleatório.

Voltando…

Primeiro o find. A sintaxe dele é a seguinte:
db.collection.find({clausulas}, {campos})
Onde as clausulas são as condições da pesquisa e os campos são os atributos que você quer que ele retorne na pesquisa. Clausulas e campos, são opcionais, se você não colocá-los a pesquisa irá retornar todos os dados da collection.

Vamos fazer uma consulta. Primeiramente iremos criar uma variável para colocar nossa query e em seguida executaremos a pesquisa. Na execução da pesquisa podemos guardar ou não o resultado, para guardar para usar uma variável recebendo a pesquisa, caso não queria guardar, basta apenas executar o find. Veja…

var query = {name = 'Pikachu'}
db.pokemons.find(query)
ou
var poke = db.pokemons.find(query)
poke

Execute e veja o que acontece.

Agora vamos adicionar os campos que queremos que a pesquisa retorne. Ao usarmos campos, iremos especificar o campo com 1 (TRUE) caso queira que ele retorne ou 0 (FALSE) caso não queira o campo. Veja a prática…
var fields = {name: 1, types: 1}

Ou seja, queremos que retorne apenas o nome e o tipo do pokemon, os outros atributos não serão retornados. Mas se não quisermos que ele retorne por exemplo o atributo created, variamos…
var fields2 = {created: 0}
Agora execute dois find, pois temos duas fields. E use nossa query criada no inicio e veja a diferença…

db.pokemons.find(query, fields)
db.pokemons.find(query, fields2)

Você pode ter percebido que nos dois casos o _id sempre apareceu. Por padrão ele sempre irá aparecer, se por algum motivo você não deseja receber, basta negar nos campos.

findOne
Bom… O findOne basicamente faz o mesmo que o find, ele pesquisa. A diferença é que ele retorna apenas um elemento, o primeiro elemento que ele encontra. Sua sintaxe é a praticamente a mesma do find, a diferença é que é acrescentado o One.

Então, todos os comandos feitos anteriormente podem ser feito com o findOne, basta substituir find por findOne.

Operadores Aritméticos
É comum usarmos operadores aritméticos em atributos que sejam do tipo numérico, mas no Mongo esses operadores são um pouco diferente. Veja como é no Mongo:

< é $lt (less than)
<= é $lte (less than or equal)
> é $gt (greater than)
>= é $gte (greater than or equal)

Veja na prática. Vamos ver quais pokemons tem um attack maior ou igual ao Pikachu
var query = {attack: {$gte: 55}}
db.pokemons.find(query)

Como você pode ver… o Pikachu não é o mais forte :O

Operadores Lógicos
Os operadores lógicos no Mongo também são um pouco diferentes, mas é fácil, veja…

OR é $or
Not OR é $nor
AND é $and

A sintaxe é a seguinte:
$or: [{cláusula}, {cláusula}]
$nor: [{cláusula}, {cláusula}]
$and: [{cláusula}, {cláusula}]

Para usarmos os operadores lógicos, precisaremos de no mínimo duas cláusulas que passaremos como objetos ({}).

Na prática…
var query = {$or: [{name: 'Pikachu'}, {name: 'Charmander'}]}
db.pokemons.find(query)


Operador Existencial
Você nunca tinha ouvido falar nisso né!? Psé… Como você já deve saber o Mongo é Schemaless, você não tem uma estrutura pré definida, o que permite que você insira dados com campos que outros objetos não tem. É ainda que entra o operador existencial, você usa ele na busca para retornar apenas os objetos que possuam aquele campo.

A sintaxe é simples:
db.collection.find({ nome_do_campo: {$exists: true} })


Para fazermos buscas em array precisamos usar outros operadores. Mas não se preocupe, é fácil.

Veja!

Caso deseja fazer uma busca em algum campo do tipo array e quer que retorne os documentos que possuam algum dos valores que você passou, basta usar o $in.
var query = {campo: {$in: [array_de_valores]}}
db.pokemons.find(query)

O $in é o OU na nossa busca em array.

No Mongo também temos o $nin, que retorna os documentos que não possuem os valores que você passou na pesquisa.
{campo: {$nin: [array_de_valores]}}
db.pokemons.find(query)

E se temos um “OU” também temos um “AND”, que é o $all. Ele apenas retorna os documentos que possuem todos os valores que você passar.
{campo: {$all: [array_de_valores]}}
db.pokemons.find(query)

Agora, por fim, um operador de negação, que no caso seria o diferente, o $not.
var query = {name: {$not: /pikachu/i}}
db.pokemons.find(query)
Nessa busca que fizemos, será retornado todos os pokemons que não possuam o nome Pikachu.

Por hoje, é isso. Até o próximo post!

0 comentários:

Postar um comentário