Implement Mongo DB Filters in .NET Using MongoDB.Driver

Learn how to use MongoDB.Driver filters in .NET with practical examples for equality, ranges, arrays, regex, and compound queries.

Implement Mongo DB Filters in .NET Using MongoDB.Driver cover

Introduction

In this article, we will understand how to use the different filters available in MongoDB.Driver with .NET and C#. The article uses a .NET 8 Web API project and performs the operations directly in the controller instead of introducing a separate service or repository layer.

If you want to see how MongoDB is configured in a .NET project, refer to the previous article, Implementing MongoDB with .NET.

Create the Collection Instance

The controller uses an IMongoCollection<Employee> instance that is created from configuration values.

private readonly IMongoCollection<Employee> _employeeCollection; public MongoFiltersController(IMongoClient mongoClient, IConfiguration configuration) { var databaseName = configuration.GetValue<string>("MongoDbSettings:DatabaseName"); var employeeCollection = configuration.GetValue<string>("MongoDbSettings:Collections:EmployeeCollection"); var database = mongoClient.GetDatabase(databaseName); _employeeCollection = database.GetCollection<Employee>(employeeCollection); }

The sample employee document uses this model:

public class Employee { [BsonId] [BsonRepresentation(BsonType.ObjectId)] public string Id { get; set; } public string Name { get; set; } public int Age { get; set; } public string Designation { get; set; } public decimal Salary { get; set; } public DateTime DateOfBirth { get; set; } public string[] Skills { get; set; } }

Equality Filter

[HttpGet("eq")] public async Task<IActionResult> Equal(string name) { var filter = Builders<Employee>.Filter.Eq(emp => emp.Name, name); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Eq when you need to match an exact field value.

Not Equal Filter

[HttpGet("ne")] public async Task<IActionResult> NotEqual(string name) { var filter = Builders<Employee>.Filter.Ne(emp => emp.Name, name); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Ne to exclude documents with a matching value.

Greater Than Filter

[HttpGet("gt")] public async Task<IActionResult> GreaterThan(int age) { var filter = Builders<Employee>.Filter.Gt(emp => emp.Age, age); // var filter = Builders<Employee>.Filter.Gt(emp => emp.DateOfBirth, DateTime.Now); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Gt for numeric or date values that must be greater than the provided value.

Greater Than or Equal Filter

[HttpGet("gte")] public async Task<IActionResult> GreaterThanOrEqual(int age) { var filter = Builders<Employee>.Filter.Gte(emp => emp.Age, age); // var filter = Builders<Employee>.Filter.Gte(emp => emp.DateOfBirth, DateTime.Now); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Gte to include values equal to the target as well.

Less Than Filter

[HttpGet("lt")] public async Task<IActionResult> LessThan(int age) { var filter = Builders<Employee>.Filter.Lt(emp => emp.Age, age); // var filter = Builders<Employee>.Filter.Lt(emp => emp.DateOfBirth, DateTime.Now); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Lt for values below the given threshold.

Less Than or Equal Filter

[HttpGet("lte")] public async Task<IActionResult> LessThanOrEqual(int age) { var filter = Builders<Employee>.Filter.Lte(emp => emp.Age, age); // var filter = Builders<Employee>.Filter.Lte(emp => emp.DateOfBirth, DateTime.Now); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Lte to include values equal to the target.

In Filter

[HttpGet("in")] public async Task<IActionResult> In([FromQuery] string[] names) { var filter = Builders<Employee>.Filter.In(emp => emp.Name, names); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use In when a field can match any value from a list.

Not In Filter

[HttpGet("nin")] public async Task<IActionResult> NotIn([FromQuery] string[] names) { var filter = Builders<Employee>.Filter.Nin(emp => emp.Name, names); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Nin to exclude documents that match any value in the list.

And Filter

[HttpGet("and")] public async Task<IActionResult> And(string name, int age) { var filter = Builders<Employee>.Filter.And( Builders<Employee>.Filter.Eq(emp => emp.Name, name), Builders<Employee>.Filter.Eq(emp => emp.Age, age)); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use And when every condition must be true.

Or Filter

[HttpGet("or")] public async Task<IActionResult> Or(string name, int age) { var filter = Builders<Employee>.Filter.Or( Builders<Employee>.Filter.Eq(emp => emp.Name, name), Builders<Employee>.Filter.Eq(emp => emp.Age, age)); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Or when any one of the conditions can match.

Exists Filter

[HttpGet("exists")] public async Task<IActionResult> Exists(string fieldName) { var filter = Builders<Employee>.Filter.Exists(fieldName); // or // var filter = Builders<Employee>.Filter.Exists(x => x.Designation); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Exists to find documents where a field is present.

Type Filter

[HttpGet("type")] public async Task<IActionResult> Type(string fieldName, BsonType bsonType) { var filter = Builders<Employee>.Filter.Type(fieldName, bsonType); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Type to match the BSON type of a field.

Regular Expression Filter

[HttpGet("regex")] public async Task<IActionResult> Regex() { var pattern = "^J"; // Names starting with 'J' // var pattern = "n$"; // Names ending with 'n' // var pattern = ".[aei]."; // Names containing 'a', 'e', or 'i' var filter = Builders<Employee>.Filter.Regex(emp => emp.Name, new BsonRegularExpression(pattern)); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Regex for pattern-based string matching.

All Filter

[HttpGet("all")] public async Task<IActionResult> All([FromQuery] string[] skills) { var filter = Builders<Employee>.Filter.All(emp => emp.Skills, skills); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use All when an array field must contain every value from the provided list.

ElemMatch Filter

[HttpGet("elemMatch")] public async Task<IActionResult> ElemMatch(string skill) { var filter = Builders<Employee>.Filter.ElemMatch(emp => emp.Skills, skill); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use ElemMatch when at least one array element must satisfy a condition.

Size Filter

[HttpGet("size")] public async Task<IActionResult> Size(int size) { var filter = Builders<Employee>.Filter.Size(emp => emp.Skills, size); var results = await _employeeCollection.Find(filter).ToListAsync(); return Ok(results); }

Use Size to match the exact number of items in an array field.

Conclusion

In this article, we explored a range of MongoDB filters available in MongoDB.Driver using .NET and C#. These filters make it easy to build precise queries for different types of fields and collections.

The original article also links to the source code on GitHub.