FreeSql: one IFreeSql instance, a dozen database engines
.NET AOT ORM for VB.NET/C#. Supports MySQL, PostgreSQL, SqlServer, Oracle, SQLite, Firebird, ClickHouse, DuckDB, TDengine, QuestDB and MsAccess, plus the Chinese databases Dameng, Kingbase, Xugu, Hangao, GaussDB, Shentong and GBase.
At a glance
- What is it?
- FreeSql is a MIT licensed ORM for .NET that ships separate provider packages per database and offers a raw FreeSql usage mode alongside DbContext and repository layers. It suits .NET teams that talk to more than one engine, including domestic Chinese databases, and teams prepared to own the generated SQL.
- Who is it for?
- Adopt FreeSql if your application already runs on .NET and touches more than one database engine, or if you want expression tree queries without taking on a change tracker. Do not enable UseAutoSyncStructure(true) if your team expects the application never to issue DDL, because it synchronizes the entity structure to the database at startup.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 5 days ago.
- What is it written in?
- Mainly C#, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on November 14, 2026, and from our analysis. They are not legal advice.
Star history
- dotnetcore/FreeSql4,410 ★ · +6
| Repository | 2026-09-23 | 2026-11-14 |
|---|---|---|
| dotnetcore/FreeSql | 4.4k | 4.4k |
6 Stars in the last 52 days, measured from the daily GitHub snapshot. Compare with other projects
Editorial analysis
The IFreeSql singleton is the whole entry surface
FreeSql is not built around a DbContext class you subclass. It is built around one interface, IFreeSql, produced by a builder and, in the README's own words, meant to be defined as singleton mode. Every feature the project advertises hangs off that object: Select for queries, navigation properties for relations, UnitOfWork for transactions, ADO for raw access.
The audience is .NET developers who need to reach several engines from the same query code. The provider list in the README runs from MySql, SqlServer, PostgreSQL and Oracle through Sqlite and Firebird to ClickHouse, DuckDB, TDengine, QuestDB and MsAccess, plus a group of Chinese domestic engines named in Chinese in the README itself. That breadth is the reason to look here rather than at a single engine ORM. The trade-off is that you assemble capabilities yourself by picking provider packages.
Query methods are expression trees, and WhereIf builds SQL you can read
Select is a fluent chain over a lambda. Relationships load through IncludeMany, which takes both the navigation property and a nested filter, so one round of filtering applies to the included rows rather than to the parent set alone.
fsql.Select<Song>()
.IncludeMany(a => a.Tags, then => then.Where(sub => sub.Name == "foo"))
.Where(s => s.Tags.Any(t => t.Name == "Chinese"))
.ToList();The WhereIf overload is the part worth copying. It takes the condition as its first argument, so a filter is added only when a keyword is present or a role id is positive, and the emitted SQL changes to match. Several WhereIf calls stack on one query without a preceding if block in your own code. The README also shows expression functions the query engine translates for you, such as comparing a.CreateTime.Date against DateTime.Today and an OrderBy over Guid.NewGuid for a random ten rows.
Provider packages come one per database, and the Sqlite one is the shortest path in
The quick start installs a provider, not the core package. For a file based database the whole first step is one command:
dotnet add package FreeSql.Provider.SqliteThe builder then names the DataType enum and the connection string, and turns on schema sync so the entity shape is pushed into the database at startup:
static IFreeSql fsql = new FreeSql.FreeSqlBuilder()
.UseConnectionString(FreeSql.DataType.Sqlite, @"Data Source=document.db")
.UseAutoSyncStructure(true) //automatically synchronize the entity structure to the database
.Build(); //be sure to define as singleton modeSwitching engine means swapping the package and the DataType value, not rewriting queries. What you get with UseAutoSyncStructure(true) is startup time structure alteration, which matters if your deployment forbids DDL from the application.
Three usage modes sit side by side, so the DbContext choice is a real fork
The README does not hide that FreeSql offers three distinct development modes. One is plain FreeSql with the original usage style. The second is FreeSql.DbContext with a Repository plus UnitOfWork, which pulls in a separate package:
dotnet add package FreeSql.RepositoryIn that mode a method is marked Transactional, resolved through ioc as a BaseRepository of the entity type, and given EnableCascadeSave so a parent insert writes its children in one unit of work. The third is FreeSql.BaseEntity, a simple mode shown under Examples/base_entity. Choosing between them at the start is harder than switching between providers later, because the repository mode changes how transactions and cascade saves are expressed in application code.
The performance block compares FreeSql against Dapper, including its own losses
The README prints elapsed times for FreeSql and Dapper over 131072 rows across entity, tuple and dynamic materialisation. Reading it closely matters more than the headline. In the first block, entity and tuple queries land around 0.68s and 0.61s for FreeSql against 0.67s and 0.46s for Dapper, so the ORM is slower on both of those rows. The dynamic row widens the gap, 1.02s for FreeSql against 0.68s for Dapper. Only the tuple materialisation row favours FreeSql at 0.42s, and the second comparison block shows FreeSql ToList at 0.67s against a Query Entity time of 0.65s.
The point is not that either library wins. The point is that the project's own table shows the gap is per query shape, and that a team deciding between FreeSql and a mapper needs to measure its own projection rather than assume.
Where DbFirst and CodeFirst pull in opposite directions
FreeSql supports CodeFirst data migration and DbFirst import of entity classes from an existing database, either in code or through the separate generation tool in the project wiki. Having both is convenient during a schema transition but it invites drift. An accidental UseAutoSyncStructure(true) against a live database synchronizes the entity structure to it at startup.
The read and write separation feature, table or database splitting, global filters and both optimistic and pessimistic locking all sit at the same layer as this sync behaviour. None of them is opt out of the data model itself, which is the part to test before a schema change goes anywhere near production.
SqlSugar, not EF Core, is the comparison this README invites
The README names no ORM competitor other than the Dapper it benchmarks against, so the comparison has to be made on approach. FreeSql keeps a single IFreeSql entry point and lets you call ADO when a query gets awkward, with the query surface expressed as expression trees translated per provider. Entity Framework Core centres on a DbContext with a change tracker and migrations applied by name.
For a team that would rather write every statement explicitly and keep query shape under control in code, FreeSql and EF Core solve different halves of the same problem. Maintenance here is not in doubt: the last push was on 2026-11-01 and the repository is not archived.
Editorial conclusion
Adopt FreeSql if your application already runs on .NET and touches more than one database engine, or if you want expression tree queries without taking on a change tracker. Do not enable UseAutoSyncStructure(true) if your team expects the application never to issue DDL, because it synchronizes the entity structure to the database at startup. Verify first that a provider package exists for the exact engine and version you run, including the Chinese engines, and that its sync behaviour matches your deployment model.
Frequently asked questions
What is FreeSql?
FreeSql is an ORM component for .NET Core 2.1+, .NET Framework 4.0+, Xamarin and AOT, released under the MIT license. Its entry point is a single IFreeSql instance created through FreeSqlBuilder.
How do I use FreeSql?
Install the package for your database, for example FreeSql.Provider.Sqlite, then build a singleton with FreeSqlBuilder using UseConnectionString and UseAutoSyncStructure(true). Queries start from fsql.Select and chain Where, IncludeMany and ToList.
FreeSql vs SqlSugar
The FreeSql README does not compare itself with SqlSugar; the only library it benchmarks against is Dapper. It presents three usage modes of its own, plain FreeSql, DbContext with Repository plus UnitOfWork, and the simple BaseEntity mode.
What is a FreeSql alternative?
Entity Framework Core is the practical alternative for .NET teams, and the two differ in approach: EF Core centres on a DbContext with change tracking and named migrations, while FreeSql exposes one IFreeSql object with expression tree queries and raw ADO access when needed.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/dotnetcore-freesql)Star history chart for your README
[](https://hysenlabs.com/projects/dotnetcore-freesql)Was this useful?