MongoDb c# driver find item in array by field value
There is ElemMatch
var filter = Builders<Post>.Filter.ElemMatch(x => x.Tags, x => x.Name == "test");var res = await collection.Find(filter).ToListAsync()
Here's an example that returns a single complex item from an array (using MongoDB.Driver v2.5.0):
Simple Data Model
public class Zoo{ public List<Animal> Animals { get; set; }}public class Animal{ public string Name { get; set; }}
Option 1 (Aggregation)
public Animal FindAnimalInZoo(string animalName){ var zooWithAnimalFilter = Builders<Zoo>.Filter .ElemMatch(z => z.Animals, a => a.Name == animalName); return _db.GetCollection<Zoo>("zoos").Aggregate() .Match(zooWithAnimalFilter) .Project<Animal>( Builders<Zoo>.Projection.Expression<Animal>(z => z.Animals.FirstOrDefault(a => a.Name == animalName))) .FirstOrDefault(); // or .ToList() to return multiple}
Option 2 (Filter & Linq) This was about 5x slower for me
public Animal FindAnimalInZoo(string animalName){ // Same as above var zooWithAnimalFilter = Builders<Zoo>.Filter .ElemMatch(z => z.Animals, a => a.Name == animalName); var zooWithAnimal = _db.GetCollection<Zoo>("zoos") .Find(zooWithAnimalFilter) .FirstOrDefault(); return zooWithAnimal.Animals.FirstOrDefault(a => a.Name == animalName);}
You need the $elemMatch
operator. You could use Builders<T>.Filter.ElemMatch
or an Any
expression:
Find(x => x.Tags.Any(t => t.Name == "test")).ToListAsync()
http://mongodb.github.io/mongo-csharp-driver/2.0/reference/driver/expressions/#elemmatch