var thename = 'Andrew';
db.collection.find({'name':thename});
Como faço uma consulta sem distinção entre maiúsculas e minúsculas? Quero encontrar o resultado mesmo que "andrew";
var thename = 'Andrew';
db.collection.find({'name':thename});
Como faço uma consulta sem distinção entre maiúsculas e minúsculas? Quero encontrar o resultado mesmo que "andrew";
Respostas:
A solução de Chris Fulstow funcionará (+1), entretanto, pode não ser eficiente, especialmente se sua coleção for muito grande. Expressões regulares não enraizadas (aquelas que não começam com ^
, que ancoram a expressão regular no início da string) e aquelas que usam o i
sinalizador para insensibilidade a maiúsculas e minúsculas não usarão índices, mesmo se eles existirem.
Uma opção alternativa que você pode considerar é desnormalizar seus dados para armazenar uma versão em minúsculas do name
campo, por exemplo como name_lower
. Você pode então consultar isso de forma eficiente (especialmente se for indexado) para correspondências exatas que não diferenciam maiúsculas de minúsculas como:
db.collection.find({"name_lower": thename.toLowerCase()})
Ou com uma correspondência de prefixo (uma expressão regular enraizada) como:
db.collection.find( {"name_lower":
{ $regex: new RegExp("^" + thename.toLowerCase(), "i") } }
);
Ambas as consultas usarão um índice em name_lower
.
new RegExp('^'+ username + '$', "i")
para ser uma correspondência exata.
".*"
.
Você precisaria usar uma expressão regular que não diferencia maiúsculas de minúsculas para este, por exemplo
db.collection.find( { "name" : { $regex : /Andrew/i } } );
Para usar o padrão regex de sua thename
variável, construa um novo objeto RegExp :
var thename = "Andrew";
db.collection.find( { "name" : { $regex : new RegExp(thename, "i") } } );
Atualização: para correspondência exata, você deve usar o regex "name": /^Andrew$/i
. Graças a Yannick L.
name
, não apenas igualando.
{ "name": /^Andrew$/i }
Eu resolvi assim.
var thename = 'Andrew';
db.collection.find({'name': {'$regex': thename,$options:'i'}});
Se você quiser fazer uma consulta sobre 'correspondência exata que não diferencia maiúsculas de minúsculas', pode fazer o seguinte.
var thename = '^Andrew$';
db.collection.find({'name': {'$regex': thename,$options:'i'}});
Com o Mongoose (e Node), isso funcionou:
User.find({ email: /^name@company.com$/i })
User.find({ email: new RegExp(
`^ $ {emailVariable} $`, 'i')})
No MongoDB, isso funcionou:
db.users.find({ email: { $regex: /^name@company.com$/i }})
Ambas as linhas não diferenciam maiúsculas de minúsculas. O email no DB pode ser NaMe@CompanY.Com
e ambas as linhas ainda encontrarão o objeto no DB.
Da mesma forma, poderíamos usar /^NaMe@CompanY.Com$/i
e ainda encontraria email: name@company.com
no DB.
O MongoDB 3.4 agora inclui a capacidade de criar um índice que não diferencia maiúsculas de minúsculas, o que aumentará drasticamente a velocidade das pesquisas que não diferenciam maiúsculas de minúsculas em grandes conjuntos de dados. É feito especificando um agrupamento com uma intensidade de 2.
Provavelmente, a maneira mais fácil de fazer isso é definir um agrupamento no banco de dados. Então, todas as consultas herdam esse agrupamento e o usarão:
db.createCollection("cities", { collation: { locale: 'en_US', strength: 2 } } )
db.names.createIndex( { city: 1 } ) // inherits the default collation
Você também pode fazer assim:
db.myCollection.createIndex({city: 1}, {collation: {locale: "en", strength: 2}});
E use-o assim:
db.myCollection.find({city: "new york"}).collation({locale: "en", strength: 2});
Isso retornará cidades chamadas "nova york", "Nova York", "Nova york" etc.
Para mais informações: https://jira.mongodb.org/browse/SERVER-90
Para encontrar strings que não diferenciam maiúsculas de minúsculas, use isso,
var thename = "Andrew";
db.collection.find({"name":/^thename$/i})
Acabei de resolver esse problema há algumas horas.
var thename = 'Andrew'
db.collection.find({ $text: { $search: thename } });
Você pode até mesmo expandir isso selecionando os campos necessários do objeto de usuário de Andrew, fazendo isso desta maneira:
db.collection.find({ $text: { $search: thename } }).select('age height weight');
Referência: https://docs.mongodb.org/manual/reference/operator/query/text/#text
... com mangusto em NodeJS que consulta:
const countryName = req.params.country;
{ 'country': new RegExp(`^${countryName}$`, 'i') };
ou
const countryName = req.params.country;
{ 'country': { $regex: new RegExp(`^${countryName}$`), $options: 'i' } };
// ^australia$
ou
const countryName = req.params.country;
{ 'country': { $regex: new RegExp(`^${countryName}$`, 'i') } };
// ^turkey$
Um exemplo de código completo em Javascript, NodeJS com Mongoose ORM no MongoDB
// get all customers that given country name
app.get('/customers/country/:countryName', (req, res) => {
//res.send(`Got a GET request at /customer/country/${req.params.countryName}`);
const countryName = req.params.countryName;
// using Regular Expression (case intensitive and equal): ^australia$
// const query = { 'country': new RegExp(`^${countryName}$`, 'i') };
// const query = { 'country': { $regex: new RegExp(`^${countryName}$`, 'i') } };
const query = { 'country': { $regex: new RegExp(`^${countryName}$`), $options: 'i' } };
Customer.find(query).sort({ name: 'asc' })
.then(customers => {
res.json(customers);
})
.catch(error => {
// error..
res.send(error.message);
});
});
Você pode usar índices que não diferenciam maiúsculas de minúsculas :
O exemplo a seguir cria uma coleção sem agrupamento padrão e, em seguida, adiciona um índice no campo de nome com um agrupamento que não diferencia maiúsculas de minúsculas. Componentes Internacionais para Unicode
/*
* strength: CollationStrength.Secondary
* Secondary level of comparison. Collation performs comparisons up to secondary * differences, such as diacritics. That is, collation performs comparisons of
* base characters (primary differences) and diacritics (secondary differences). * Differences between base characters takes precedence over secondary
* differences.
*/
db.users.createIndex( { name: 1 }, collation: { locale: 'tr', strength: 2 } } )
Para usar o índice, as consultas devem especificar o mesmo agrupamento.
db.users.insert( [ { name: "Oğuz" },
{ name: "oğuz" },
{ name: "OĞUZ" } ] )
// does not use index, finds one result
db.users.find( { name: "oğuz" } )
// uses the index, finds three results
db.users.find( { name: "oğuz" } ).collation( { locale: 'tr', strength: 2 } )
// does not use the index, finds three results (different strength)
db.users.find( { name: "oğuz" } ).collation( { locale: 'tr', strength: 1 } )
ou você pode criar uma coleção com agrupamento padrão:
db.createCollection("users", { collation: { locale: 'tr', strength: 2 } } )
db.users.createIndex( { name : 1 } ) // inherits the default collation
A consulta a seguir encontrará os documentos com a string necessária de forma insensível e com ocorrência global também
db.collection.find({name:{
$regex: new RegExp(thename, "ig")
}
},function(err, doc) {
//Your code here...
});
Para encontrar strings de literais que não diferenciam maiúsculas de minúsculas:
db.collection.find({
name: {
$regex: new RegExp('^' + name.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&') + '$', 'i')
}
});
db.collection.find({
name_lower: name.toLowerCase()
});
As expressões regulares são mais lentas do que a correspondência de string literal. No entanto, um campo adicional em minúsculas aumentará a complexidade do código. Em caso de dúvida, use expressões regulares. Eu sugeriria usar apenas um campo explicitamente em minúsculas se ele puder substituir o seu campo, ou seja, você não se importa com o caso em primeiro lugar.
Observe que você precisará escapar do nome antes do regex. Se você quiser caracteres curinga de entrada do usuário, prefira acrescentar .replace(/%/g, '.*')
depois de escapar para que possa corresponder a "a%" para encontrar todos os nomes que começam com 'a'.
Uma maneira fácil seria usar $ toLower conforme abaixo.
db.users.aggregate([
{
$project: {
name: { $toLower: "$name" }
}
},
{
$match: {
name: the_name_to_search
}
}
])