Kvr.SqlBuilder 1.2.6

There is a newer version of this package available.
See the version list below for details.
dotnet add package Kvr.SqlBuilder --version 1.2.6
                    
NuGet\Install-Package Kvr.SqlBuilder -Version 1.2.6
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="Kvr.SqlBuilder" Version="1.2.6" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="Kvr.SqlBuilder" Version="1.2.6" />
                    
Directory.Packages.props
<PackageReference Include="Kvr.SqlBuilder" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add Kvr.SqlBuilder --version 1.2.6
                    
#r "nuget: Kvr.SqlBuilder, 1.2.6"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package Kvr.SqlBuilder@1.2.6
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=Kvr.SqlBuilder&version=1.2.6
                    
Install as a Cake Addin
#tool nuget:?package=Kvr.SqlBuilder&version=1.2.6
                    
Install as a Cake Tool

SqlBuilder

Copyright © 2024 Kvr.SqlBuilder. All rights reserved.

A lightweight, fluent SQL query builder for .NET that provides type-safe SQL query construction with support for table aliases, column selection, and complex joins. With Table and Column attributes annotations support. RawSql methods support for appending raw sql script to builder. Could be used with Dapper, NPoco, etc.

Table of Contents

Features

  • Fluent API for building SQL queries
  • Type-safe property and table selection
  • Support for table aliases and prefixes
  • Automatic handling of SQL Server and standard SQL syntax
  • Support for complex JOIN operations
  • Column selection with aliasing
  • WHERE clause construction with multiple conditions
  • ORDER BY clause support
  • Minimal boilerplate code
  • TableAttribute and ColumnAttribute annotations support

Installation

You can install the package via NuGet Package Manager:

dotnet add package Kvr.SqlBuilder

Quick Start Guide

Here's a quick example of how to use SqlBuilder to construct SQL queries:

using Kvr.SqlBuilder;

public class Customer
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string Email { get; set; }
}

public class Order
{
    public int OrderId { get; set; }
    public int CustomerId { get; set; }
    public decimal Amount { get; set; }
}

// Basic query
var query = SqlBuilder.Create()
    .SelectAll<Customer>()
    .From<Customer>()
    .Build();
// Result: SELECT [Id], [Name], [Email] FROM [Customers]

// Join query with conditions
var joinQuery = SqlBuilder.Create()
    .SelectAll<Customer>(out var customerPrefix)
    .SelectAll<Order>(out var orderPrefix)
    .From<Customer>()
    .Join<Customer, Order, int>(
        customer => customer.Id,
        order => order.CustomerId)
    .Where<Customer>(c => c.Id, 1)
    .OrderBy<Order>(o => o.Amount, false)
    .Build();
// Result: SELECT kvr0.[Id], kvr0.[Name], kvr0.[Email], kvr1.[OrderId], kvr1.[CustomerId], kvr1.[Amount] 
//        FROM [Customers] kvr0 
//        JOIN [Orders] kvr1 ON kvr0.[Id] = kvr1.[CustomerId] 
//        WHERE kvr0.[Id] = 1 
//        ORDER BY kvr1.[Amount] DESC

Usage

Table Names

SqlBuilder supports both singular and plural table names, with customization options:

// Global setting for plural table names
SqlBuilder.UseGlobalPluralTableNames();

// Instance-specific setting
var builder = SqlBuilder.Create()
    .UsePluralTableNames()
    .SelectAll<Customer>()
    .From<Customer>();

// Custom table name mapping
SqlBuilder.MapGlobalTable<Customer>("tbl_customers");
// or instance-specific
builder.MapTable<Customer>("tbl_customers");

Column Selection

Multiple ways to select columns:

// Select all columns
SqlBuilder.Create().SelectAll<Customer>();

// Return c.Id as first column, it is important for Dapper's splitOn parameter
SqlBuilder.Create().SelectAll<Customer>(c => c.Id);

// Select specific columns
SqlBuilder.Create().Select<Customer>(c => new[] { c.Id, c.Name });

// Select with alias
SqlBuilder.Create().Select<Customer>(c => c.Name, "CustomerName");

// Exclude specific columns
SqlBuilder.Create().SelectAll<Customer>(excludeColumns: new[] { c => c.Email });

// Exclude specific column Email. Return c.Id as first column, it is important for Dapper's splitOn parameter
SqlBuilder.Create().SelectAll<Customer>(excludeColumns: new[] { c => c.Email }, c => c.Id);

Joins

Support for various JOIN types:

// INNER JOIN
SqlBuilder.Create().Join<Customer, Order, int>(
    customer => customer.Id,
    order => order.CustomerId);

// LEFT JOIN
SqlBuilder.Create().LeftJoin<Customer, Order, int>(
    customer => customer.Id,
    order => order.CustomerId);

// RIGHT JOIN
SqlBuilder.Create().RightJoin<Customer, Order, int>(
    customer => customer.Id,
    order => order.CustomerId);

// FULL JOIN
SqlBuilder.Create().FullJoin<Customer, Order, int>(
    customer => customer.Id,
    order => order.CustomerId);

Where Clauses

Building WHERE conditions:

    SqlBuilder.Create()
    .Where<Customer>(c => c.Id, "1")
    .And<Customer>(c => c.Name, "'John'")
    .Or<Customer>(c => c.Email, "'john@example.com'");

NameConvention

SqlBuilder supports custom naming conventions which implements INameConvention interface:

SqlBuilder.UseGlobalNameConvention(new CustomNameConvention());

There are two built-in naming conventions: DefaultNameConvention and SnakeCaseNameConvention. Both of them have UseSqlServer property to specify whether to use SQL Server specific syntax to escape identifiers with square brackets and UsePlural property to specify whether to use plural table names.

Table Name determination priority:
  1. Custom table name mapping (Highest priority)
  • using MapGlobalTable or MapTable method to map table names which could not inherit from CustomNameConvention
// Global mapping
SqlBuilder.MapGlobalTable<Customer>("tbl_customers");
// or instance-specific mapping
this.sqlBuilder.MapTable<Customer>("tbl_customers");
  1. TableAttribute on the entity class to specify the table name
[Table("tbl_customers")]
public class Customer
  1. ToTableName method in CustomNameConvention to convert the table name
protected override string ToTableName(string typeName)
Column Name determination priority:
  1. Custom column name sepecified in Select method (Highest priority)
    this.sqlBuilder.Select<Customer>("customer_id", "Name");
    
  2. ColumnAttribute on the property to specify the column name
    [Column("customer_id")]
    public int Id { get; set; }
    
  3. ToColumnName method in CustomNameConvention to convert the column name
    protected override string ToColumnName(string propertyName)
    

RawSql

SqlBuilder supports RawSql methods to build WHERE, AND, OR, ORDER BY clauses, also RawSql methods to append raw sql script to builder:

builder.SelectAll<Customer>().RawSql(", count(*) as TotalCount") // append total count of customers to the result
    .Where<Customer>(c => c.Email, "@customerEmail") // using parameter
    .Or<Customer>("@customerEmail is null") // using raw sql string for parameter condition
    .OrderBy<Customer>("Id desc")
    .RawSql(" having count(*) > 0") // using raw sql string for having clause
    .Build();
// Result: SELECT [Id], [Name], [Email], count(*) as TotalCount FROM [Customers] WHERE [Email] = @customerEmail OR @customerEmail is null ORDER BY Dd desc having count(*) > 0

Best Practices

  • Use strongly-typed expressions when possible
  • Leverage table aliases for complex queries
  • Keep SQL Server compatibility in mind
  • Use appropriate column selection instead of SELECT *
  • Consider query performance when building complex JOINs

Limitations

  1. Limited support for complex subqueries (could use RawSql methods for this)
  2. No direct support for GROUP BY and HAVING clauses
  3. No NamingConvention support for table and column (e.g. SnakeCase, PascalCase for table and column names)

Supported Frameworks

  • .NET Standard 2.0+
  • .NET 5.0+
  • .NET 6.0+
  • .NET 7.0+

Version History

  • 1.2.6

    • Add NotMappedAttribute support for SelectAll method to exclude columns.
  • 1.2.5

    • Add SelectAll overload methods for more than 10 types.
  • 1.2.4

    • Add SelectFrom method to generate a SELECT * FROM clause.
  • 1.2.3

    • Add SelectFromWhere method to generate a SELECT * FROM WHERE clause with a WHERE clause to filter by a specific property value.
  • 1.2.2

    • Fix incorrect alias for snake case name convention.
    • Add test project and cases.
  • 1.2.1

    • Add prefix for missing Where, Join, Select, From, OrderBy methods.
  • 1.2.0

    • Add NameConvention support
  • 1.1.0

    • Add RawSql methods (Where, And, Or, OrderBy) and AppendRawSql method
    • Change parameter type from LambdaExpression to Expression<Func<T, object>> for strongly-typed expressions
  • 1.0.0

    • Initial release
    • Basic SQL query building
    • Support for JOINs, WHERE clauses, and ORDER BY
    • Table name customization
    • SQL Server compatibility

License

This project is licensed under the Apache License 2.0 - see the LICENSE file for details.

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

  1. Fork the Project
  2. Create your Feature Branch (git checkout -b feature/AmazingFeature)
  3. Commit your Changes (git commit -m 'Add some AmazingFeature')
  4. Push to the Branch (git push origin feature/AmazingFeature)
  5. Open a Pull Request

Dependencies

System.ComponentModel.Annotations for Table and Column attributes

Support

If you encounter any issues or have questions, please file an issue on the GitHub repository.

Build Status

Build and Test Publish to NuGet

Product Compatible and additional computed target framework versions.
.NET net5.0 is compatible.  net5.0-windows was computed.  net6.0 is compatible.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 is compatible.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 was computed.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 was computed.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 was computed. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages (1)

Showing the top 1 NuGet packages that depend on Kvr.SqlBuilder:

Package Downloads
Kvr.Query

An extension for Dapper to query the entity with relationships.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
1.2.7.1 233 12/16/2024
1.2.7 147 12/16/2024
1.2.6 151 12/16/2024
1.2.5 198 12/9/2024
1.2.4 157 12/9/2024
1.2.3 146 12/9/2024
1.2.2 145 12/1/2024
1.2.1 154 12/1/2024
1.2.0 141 11/30/2024
1.1.0 151 11/29/2024
1.0.0 140 11/29/2024
0.0.1 139 11/28/2024