Skip to content

FlexQuery.NETTurn your API into a secure, composable query engine

Flexible querying for .NET IQueryable — filtering, sorting, paging, projection, validation, and field-level security.

What is FlexQuery.NET?

FlexQuery.NET is a query abstraction layer for .NET APIs.

It sits between your controller and your IQueryable and translates client-provided query parameters into safe, validated, server-side expressions.

It is not just a filtering helper. It handles the full query lifecycle:

HTTP Request → Parse → Validate → Filter → Sort → Page → Project → JSON Response

A 60-Second Example

The client sends this HTTP request:

GET /api/users?filter=status:eq:active&sort=createdAt:desc&page=1&pageSize=10&select=id,name,email

Your controller handles it in 3 lines:

csharp
[HttpGet]
public async Task<IActionResult> GetUsers([FromQuery] FlexQueryParameters parameters)
{
    var result = await _context.Users.FlexQueryAsync<User>(parameters, exec =>
    {
        exec.AllowedFields = new HashSet<string> { "id", "name", "email", "status", "createdAt" };
    });

    return Ok(result);
}

The response:

json
{
  "data": [
    { "id": 1, "name": "Alice", "email": "alice@example.com" },
    { "id": 2, "name": "Bob",   "email": "bob@example.com" }
  ],
  "totalCount": 48,
  "page": 1,
  "pageSize": 10
}

One endpoint. Full query power. Zero unsafe code.


Choose Your Level of Control

FlexQuery.NET is designed to work at the level of abstraction that suits your use case.

LevelMethodUse When
High-level (recommended)FlexQueryAsyncYou want parse + validate + execute in one call
Mid-levelQueryOptionsParser.Parse + manual pipelineYou need custom steps between parse and execute
Low-levelApplyFilter, ApplySort, ApplyPaging, ApplySelectYou need full control over each pipeline stage

How the Execution Model Works

FlexQueryParameters (HTTP DTO)


  QueryOptionsParser.Parse()


     QueryOptions (AST)

         ├── ValidateOrThrow<T>()       ← Field access, operator, type checks

         ├── ApplyFilter()              ← WHERE clause (expression tree)
         ├── ApplySort()                ← ORDER BY
         ├── ApplyPaging()              ← SKIP / TAKE
         ├── ApplyFilteredIncludes()    ← Include pipeline (independent)
         └── ApplySelect()             ← Dynamic projection


            QueryResult<object>
         { data, totalCount, page, pageSize }

All expression trees are translated to SQL by EF Core. No client-side evaluation.


Supported Query Formats

FlexQuery.NET auto-detects the input format:

FormatExample
DSLfilter=status:eq:active
JQLquery=status = "active" AND age >= 18
JSONfilter={"logic":"and","filters":[{"field":"status","operator":"eq","value":"active"}]}
Indexedfilter[0].field=status&filter[0].operator=eq&filter[0].value=active

Package Overview

PackagePurpose
FlexQuery.NETCore library — filtering, sorting, paging, projection, validation
FlexQuery.NET.EFCoreEF Core async execution — FlexQueryAsync, ApplyFilteredIncludes
FlexQuery.NET.AspNetCoreASP.NET Core integration — FieldAccessFilter, [FieldAccess] attribute

Released under the MIT License.