diff --git a/.gitignore b/.gitignore deleted file mode 100644 index bdc3535..0000000 --- a/.gitignore +++ /dev/null @@ -1,108 +0,0 @@ -# Build Folders (you can keep bin if you'd like, to store dlls and pdbs) -[Bb]in/ -[Oo]bj/ - -# mstest test results -TestResults - -## Ignore Visual Studio temporary files, build results, and -## files generated by popular Visual Studio add-ons. - -# User-specific files -*.suo -*.user -*.sln.docstates - -# Build results -[Dd]ebug/ -[Rr]elease/ -x64/ -*_i.c -*_p.c -*.ilk -*.meta -*.obj -*.pch -*.pdb -*.pgc -*.pgd -*.rsp -*.sbr -*.tlb -*.tli -*.tlh -*.tmp -*.log -*.vspscc -*.vssscc -.builds - -# Visual C++ cache files -ipch/ -*.aps -*.ncb -*.opensdf -*.sdf - -# Visual Studio profiler -*.psess -*.vsp -*.vspx - -# Guidance Automation Toolkit -*.gpState - -# ReSharper is a .NET coding add-in -_ReSharper* - -# NCrunch -*.ncrunch* -.*crunch*.local.xml - -# Installshield output folder -[Ee]xpress - -# DocProject is a documentation generator add-in -DocProject/buildhelp/ -DocProject/Help/*.HxT -DocProject/Help/*.HxC -DocProject/Help/*.hhc -DocProject/Help/*.hhk -DocProject/Help/*.hhp -DocProject/Help/Html2 -DocProject/Help/html - -# Click-Once directory -publish - -# Publish Web Output -*.Publish.xml - -# NuGet Packages Directory -packages - -# Windows Azure Build Output -csx -*.build.csdef - -# Windows Store app package directory -AppPackages/ - -# Others -[Bb]in -[Oo]bj -sql -TestResults -[Tt]est[Rr]esult* -*.Cache -ClientBin -[Ss]tyle[Cc]op.* -~$* -*.dbmdl -Generated_Code #added for RIA/Silverlight projects - -# Backup & report files from converting an old project file to a newer -# Visual Studio version. Backup files are not needed, because we have git ;-) -_UpgradeReport_Files/ -Backup*/ -UpgradeLog*.XML diff --git a/LambdaSqlBuilder.Tests/Entities/Category.cs b/LambdaSqlBuilder.Tests/Entities/Category.cs deleted file mode 100644 index 61445ad..0000000 --- a/LambdaSqlBuilder.Tests/Entities/Category.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System.Collections.Generic; - -namespace LambdaSqlBuilder.Tests.Entities -{ - [SqlLamTable(Name = "Categories")] - public class Category - { - [SqlLamColumn(Name = "Category ID")] - public int CategoryId { get; set; } - - public int GetCategoryId() - { - return CategoryId; - } - - [SqlLamColumn(Name = "Category Name")] - public string CategoryName { get; set; } - - public List Products { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/Entities/Employee.cs b/LambdaSqlBuilder.Tests/Entities/Employee.cs deleted file mode 100644 index eb5053e..0000000 --- a/LambdaSqlBuilder.Tests/Entities/Employee.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Tests.Entities -{ - [SqlLamTable(Name = "Employees")] - public class Employee - { - [SqlLamColumn(Name = "Employee ID")] - public int EmployeeId { get; set; } - - [SqlLamColumn(Name = "First Name")] - public string FirstName { get; set; } - - [SqlLamColumn(Name = "Last Name")] - public string LastName { get; set; } - - [SqlLamColumn(Name = "City")] - public string City { get; set; } - - [SqlLamColumn(Name = "Title")] - public string Title { get; set; } - - [SqlLamColumn(Name = "Birth Date")] - public DateTime BirthDate { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/Entities/FakeGuid.cs b/LambdaSqlBuilder.Tests/Entities/FakeGuid.cs deleted file mode 100644 index 2c29ee9..0000000 --- a/LambdaSqlBuilder.Tests/Entities/FakeGuid.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Tests.Entities -{ - class FakeGuid - { - public FakeGuid() - { - Id = Guid.NewGuid(); - } - - public Guid? Id { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/Entities/Order.cs b/LambdaSqlBuilder.Tests/Entities/Order.cs deleted file mode 100644 index 3d229ca..0000000 --- a/LambdaSqlBuilder.Tests/Entities/Order.cs +++ /dev/null @@ -1,28 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Tests.Entities -{ - [SqlLamTable(Name = "Orders")] - public class Order - { - [SqlLamColumn(Name = "Order ID")] - public int OrderId { get; set; } - - [SqlLamColumn(Name = "Ship Name")] - public string ShipName { get; set; } - - [SqlLamColumn(Name = "Ship Region")] - public string ShipRegion { get; set; } - - [SqlLamColumn(Name = "Required Date")] - public DateTime RequiredDate { get; set; } - - [SqlLamColumn(Name = "Shipped Date")] - public DateTime ShippedDate { get; set; } - - public List Products { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/Entities/OrderDetails.cs b/LambdaSqlBuilder.Tests/Entities/OrderDetails.cs deleted file mode 100644 index 5518fc3..0000000 --- a/LambdaSqlBuilder.Tests/Entities/OrderDetails.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Tests.Entities -{ - [SqlLamTable(Name = "Order Details")] - public class OrderDetails - { - [SqlLamColumn(Name = "Order ID")] - public int OrderId { get; set; } - - [SqlLamColumn(Name = "Product ID")] - public int ProductId { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/Entities/Product.cs b/LambdaSqlBuilder.Tests/Entities/Product.cs deleted file mode 100644 index 76c607d..0000000 --- a/LambdaSqlBuilder.Tests/Entities/Product.cs +++ /dev/null @@ -1,38 +0,0 @@ - -namespace LambdaSqlBuilder.Tests.Entities -{ - [SqlLamTable(Name = "Products")] - public class Product - { - [SqlLamColumn(Name = "Product ID")] - public int ProductId { get; set; } - - public int GetProductId() - { - return ProductId; - } - - [SqlLamColumn(Name = "Product Name")] - public string ProductName { get; set; } - - [SqlLamColumn(Name = "English Name")] - public string EnglishName { get; set; } - - [SqlLamColumn(Name = "Category ID")] - public int CategoryId { get; set; } - - [SqlLamColumn(Name = "Unit Price")] - public double UnitPrice { get; set; } - - [SqlLamColumn(Name = "Reorder Level")] - public int ReorderLevel { get; set; } - - [SqlLamColumn(Name = "Reorder Level")] - public int? NullableReorderLevel { get { return ReorderLevel; } } - - [SqlLamColumn(Name = "Discontinued")] - public bool Discontinued { get; set; } - - public Category Category { get; set; } - } -} diff --git a/LambdaSqlBuilder.Tests/ExpressionTests.cs b/LambdaSqlBuilder.Tests/ExpressionTests.cs deleted file mode 100644 index 0dcd18f..0000000 --- a/LambdaSqlBuilder.Tests/ExpressionTests.cs +++ /dev/null @@ -1,438 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Tests.Entities; -using LambdaSqlBuilder.Tests.Infrastructure; -using NUnit.Framework; -using Dapper; - -namespace LambdaSqlBuilder.Tests -{ - public class ExpressionTests : TestBase - { - /// - /// Find the products which name starts with 'To' - /// - [Test] - public void FindByStringPrefix() - { - const string prefix = "To"; - - var query = new SqlLam(p => p.ProductName.StartsWith(prefix)); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(2, result.Count); - - foreach (var product in result) - { - Assert.IsTrue(product.ProductName.StartsWith(prefix)); - } - } - - /// - /// Find the products which name ends with 'ld' - /// - [Test] - public void FindByStringSuffix() - { - const string suffix = "ld"; - - var query = new SqlLam(p => p.ProductName.EndsWith(suffix)); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(2, result.Count); - - foreach (var product in result) - { - Assert.IsTrue(product.ProductName.EndsWith(suffix)); - } - } - - /// - /// Find the products which name contains substring 'ge' - /// - [Test] - public void FindByStringPart() - { - const string part = "ge"; - - var query = new SqlLam(p => p.ProductName.Contains(part)); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(9, result.Count); - - foreach (var product in result) - { - Assert.IsTrue(product.ProductName.ToLower().Contains(part)); - } - } - - /// - /// Find the products which name is equal to string 'Tofu' - /// - [Test] - public void FindByStringEquality() - { - const string name = "Tofu"; - - var query = new SqlLam(p => p.ProductName.Equals(name)); - - var result = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(name, result.ProductName); - } - - /// - /// Use an unsupported function to trigger the exception - /// - [Test] - public void FindByInvalidFunction() - { - Assert.Throws(() => new SqlLam(p => p.ProductName.IsNormalized())); - } - - /// - /// Find the orders which ship region is null - /// - [Test] - public void FindByNull() - { - var query = new SqlLam(o => o.ShipRegion == null); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(671, result.Count); - - foreach (var order in result) - { - Assert.IsTrue(order.ShipRegion == null); - } - } - - /// - /// Find the orders which ship region is not null - /// - [Test] - public void FindByNotNull() - { - var query = new SqlLam(o => o.ShipRegion != null); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(407, result.Count); - - foreach (var order in result) - { - Assert.IsTrue(order.ShipRegion != null); - } - } - - /// - /// Find products with unit price greater than 10.5 - /// - [Test] - public void FindByDouble() - { - const double minUnitPrice = 10.5d; - - var query = new SqlLam(p => p.UnitPrice >= minUnitPrice); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(63, result.Count); - - foreach (var product in result) - { - Assert.GreaterOrEqual(product.UnitPrice, minUnitPrice); - } - } - - /// - /// Find products by nullable reorder level - /// - [Test] - public void FindByNullableField() - { - var product = new Product() {ReorderLevel = 5}; - - var query = new SqlLam(p => p.NullableReorderLevel == product.NullableReorderLevel.Value); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(8, result.Count); - } - - /// - /// Find discontinued products - /// - [Test] - public void FindByBoolean() - { - const int expectedNumberOfResults = 8; - - var query = new SqlLam(p => p.Discontinued); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedNumberOfResults, result.Count); - - foreach (var product in result) - { - Assert.AreEqual(true, product.Discontinued); - } - } - - /// - /// Find employees born before 1.1.1960 - /// - [Test] - public void FindByDateTime() - { - var minBirthDate = new DateTime(1960, 1, 1); - const int expectedNumberOfResults = 5; - - var query = new SqlLam(p => p.BirthDate < minBirthDate); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedNumberOfResults, result.Count); - - foreach (var employee in result) - { - Assert.Less(employee.BirthDate, minBirthDate); - } - } - - /// - /// Test guid access and nullable guid conversion - /// - [Test] - public void FindByGuidFake() - { - var fakeGuid = new FakeGuid(); - - var query = new SqlLam(p => p.Id == fakeGuid.Id.Value); - Assert.AreEqual("[FakeGuid].[Id] = @Param1", query.SqlBuilder.WhereConditions.First()); - Assert.AreEqual(fakeGuid.Id.Value, query.QueryParameters.First().Value); - } - - /// - /// Find orders where the shipped date is after the required date - /// - [Test] - public void FindByMemberComparison() - { - const int expectedNumberOfResults = 55; - - var query = new SqlLam(o => o.RequiredDate < o.ShippedDate); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedNumberOfResults, result.Count); - - foreach (var order in result) - { - Assert.Less(order.RequiredDate, order.ShippedDate); - } - } - - /// - /// Find product by an Id retrieved using a member access - /// - [Test] - public void FindByMemberAccess() - { - var product = new Product() - { - ProductId = 17 - }; - - var query = new SqlLam(p => p.ProductId == product.ProductId); - - var result = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(product.ProductId, result.ProductId); - } - - /// - /// Find category by an Id retrieved using a member access - /// - [Test] - public void FindByDoubleMemberAccess() - { - var category = new Category() - { - CategoryId = 8 - }; - - var product = new Product() - { - Category = category - }; - - var query = new SqlLam(c => c.CategoryId == product.Category.CategoryId); - - var result = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(category.CategoryId, result.CategoryId); - } - - /// - /// Find product by an Id retrieved using a method call - /// - [Test] - public void FindByMethodCall() - { - var product = new Product() - { - ProductId = 17 - }; - - var query = new SqlLam(p => p.ProductId == product.GetProductId()); - - var result = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(product.ProductId, result.ProductId); - } - - /// - /// Find product by an Id retrieved using a method call - /// - [Test] - public void FindByMemberAccessAndMethodCall() - { - var category = new Category() - { - CategoryId = 8 - }; - - var product = new Product() - { - Category = category - }; - - var query = new SqlLam(c => c.CategoryId == product.Category.GetCategoryId()); - - var result = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(category.CategoryId, result.CategoryId); - } - - [Test] - public void FindByComplexQuery1() - { - const int expectedResultCount = 3; - var expectedNames = new [] {"Nancy", "Margaret", "Laura"}; - - var query = new SqlLam(p => p.City == "Seattle" || p.City == "Redmond" && p.Title == "Sales Representative") - .OrderByDescending(p => p.FirstName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedResultCount, results.Count); - for (int i=0; i < expectedResultCount; ++i) - { - Assert.AreEqual(expectedNames[i], results[i].FirstName); - } - } - - [Test] - public void FindByComplexQuery2() - { - const int expectedResultCount = 2; - var expectedNames = new[] { "Nancy", "Margaret" }; - - var query = new SqlLam(p => (p.City == "Seattle" || p.City == "Redmond") && p.Title == "Sales Representative") - .OrderByDescending(p => p.FirstName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedResultCount, results.Count); - for (int i = 0; i < expectedResultCount; ++i) - { - Assert.AreEqual(expectedNames[i], results[i].FirstName); - } - } - - [Test] - public void FindByComplexQuery2Flipped() - { - const int expectedResultCount = 2; - var expectedNames = new[] { "Nancy", "Margaret" }; - - var query = new SqlLam(p => "Sales Representative" == p.Title && ("Seattle" == p.City || "Redmond" == p.City) ) - .OrderByDescending(p => p.FirstName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedResultCount, results.Count); - for (int i = 0; i < expectedResultCount; ++i) - { - Assert.AreEqual(expectedNames[i], results[i].FirstName); - } - } - - [Test] - public void FindByComplexQuery2Negated() - { - const int expectedResultCount = 13; - - var query = new SqlLam(p => !(p.City == "Seattle" || p.City == "Redmond") || p.Title != "Sales Representative") - .OrderByDescending(p => p.FirstName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedResultCount, results.Count); - } - - [Test] - public void FindByComplexQuery3() - { - const int expectedNumberOfResults = 16; - const int reorderLevel = 0; - - var query = new SqlLam(p => !p.Discontinued && p.ReorderLevel == reorderLevel); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedNumberOfResults, result.Count); - - foreach (var product in result) - { - Assert.AreEqual(false, product.Discontinued); - Assert.AreEqual(reorderLevel, product.ReorderLevel); - } - } - - [Test] - public void FindByComplexQuery4() - { - var dateTime1 = new DateTime(1900, 1, 1); - var dateTime2 = new DateTime(1950, 1, 1); - var dateTime3 = new DateTime(1970, 1, 1); - var dateTime4 = new DateTime(2000, 1, 1); - - const int expectedNumberOfResults = 5; - - var query = - new SqlLam(e => - (e.BirthDate > dateTime1 && e.BirthDate < dateTime2) - || - (e.BirthDate > dateTime3 && e.BirthDate < dateTime4)); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(expectedNumberOfResults, result.Count); - - foreach (var employee in result) - { - Assert.IsTrue((employee.BirthDate > dateTime1 && employee.BirthDate < dateTime2) - || (employee.BirthDate > dateTime3 && employee.BirthDate < dateTime4)); - } - } - } -} diff --git a/LambdaSqlBuilder.Tests/ExtraTests.cs b/LambdaSqlBuilder.Tests/ExtraTests.cs deleted file mode 100644 index 4bb20ec..0000000 --- a/LambdaSqlBuilder.Tests/ExtraTests.cs +++ /dev/null @@ -1,80 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Data.SqlServerCe; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Tests.Entities; -using LambdaSqlBuilder.Tests.Infrastructure; -using LambdaSqlBuilder.ValueObjects; -using NUnit.Framework; -using Dapper; - -namespace LambdaSqlBuilder.Tests -{ - public class ExtraTests : TestBase - { - /// - /// Access the underlying SqlBuilder to directly specify the selection and the having condition - /// - [Test] - public void DirectSqlBuilderAccess() - { - var query = from product in new SqlLam() - where product.ReorderLevel > 10 - group product by product.ReorderLevel; - - query.SqlBuilder.SelectionList.Add("MAX([Unit Price]) AS MaxPrice"); - query.SqlBuilder.HavingConditions.Add("MAX([Unit Price]) < @PriceParam"); - query.SqlBuilder.Parameters.Add("PriceParam", 25M); - - var result = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, result.Count); - Assert.AreEqual(24, result.First()); - } - - /// - /// Load all product names without using the Dapper only with the standard Sql Command and the Data Reader - /// - [Test] - public void DapperLessExecution() - { - var query = from product in new SqlLam() - orderby product.ProductName - select product.ProductName; - - var selectCommand = new SqlCeCommand(query.QueryString, Connection); - foreach (var param in query.QueryParameters) - selectCommand.Parameters.AddWithValue(param.Key, param.Value); - - var result = selectCommand.ExecuteReader(); - - int count = 0; - while(result.Read()) - { - ++count; - Assert.NotNull(result.GetString(0)); - } - Assert.AreEqual(77, count); - } - - /// - /// Change the adapter to Sql Server 2008 and verify whether the pagination SQL string contains the specific keyword ROW_NUMBER - /// - [Test] - public void ChangeSqlAdapter() - { - SqlLamBase.SetAdapter(SqlAdapter.SqlServer2008); - - var query = from product in new SqlLam() - orderby product.ProductName - select product; - - var queryString = query.QueryStringPage(10, 1); - - SqlLamBase.SetAdapter(SqlAdapter.SqlServer2012); - - Assert.IsTrue(queryString.Contains("ROW_NUMBER")); - } - } -} diff --git a/LambdaSqlBuilder.Tests/Infrastructure/Bootstrap.cs b/LambdaSqlBuilder.Tests/Infrastructure/Bootstrap.cs deleted file mode 100644 index 6a18b05..0000000 --- a/LambdaSqlBuilder.Tests/Infrastructure/Bootstrap.cs +++ /dev/null @@ -1,43 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using System.Text; -using Dapper; - -namespace LambdaSqlBuilder.Tests.Infrastructure -{ - static class Bootstrap - { - public const string CONNECTION_STRING = @"Data Source=AppData\Northwind.sdf"; - - public static void Initialize() - { - InitializeDapper(); - } - - private static void InitializeDapper() - { - const string @namespace = "LambdaSqlBuilder.Tests.Entities"; - - var entityTypes = from t in Assembly.GetExecutingAssembly().GetTypes() - where t.IsClass && t.Namespace == @namespace - select t; - - foreach (var entityType in entityTypes) - { - SqlMapper.SetTypeMap( - entityType, - new CustomPropertyTypeMap( - entityType, - (type, columnName) => - type.GetProperties().FirstOrDefault(prop => - prop.GetCustomAttributes(false) - .OfType() - .Any(attr => attr.Name == columnName)) - ) - ); - } - } - } -} diff --git a/LambdaSqlBuilder.Tests/Infrastructure/TestBase.cs b/LambdaSqlBuilder.Tests/Infrastructure/TestBase.cs deleted file mode 100644 index 07c7e62..0000000 --- a/LambdaSqlBuilder.Tests/Infrastructure/TestBase.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Data.SqlServerCe; -using System.Linq; -using System.Text; -using NUnit.Framework; - -namespace LambdaSqlBuilder.Tests.Infrastructure -{ - public abstract class TestBase - { - protected SqlCeConnection Connection; - - [SetUp] - public void Init() - { - Bootstrap.Initialize(); - - Connection = new SqlCeConnection(Bootstrap.CONNECTION_STRING); - Connection.Open(); - } - - [TearDown] - public void TearDown() - { - Connection.Close(); - } - } -} diff --git a/LambdaSqlBuilder.Tests/JoinSqlQueryTests.cs b/LambdaSqlBuilder.Tests/JoinSqlQueryTests.cs deleted file mode 100644 index 9e31d5d..0000000 --- a/LambdaSqlBuilder.Tests/JoinSqlQueryTests.cs +++ /dev/null @@ -1,234 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using Dapper; -using LambdaSqlBuilder.Tests.Entities; -using LambdaSqlBuilder.Tests.Infrastructure; -using NUnit.Framework; - -namespace LambdaSqlBuilder.Tests -{ - public class JoinSqlQueryTests : TestBase - { - /// - /// Find all products for the category Beverages - /// - [Test] - public void FindByJoinedEntityValue() - { - const string categoryName = "Beverages"; - const int categoryId = 1; - - var query = new SqlLam() - .Join((p, c) => p.CategoryId == c.CategoryId) - .Where(c => c.CategoryName == categoryName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(12, results.Count); - Assert.IsTrue(results.All(p => p.CategoryId == categoryId)); - } - - /// - /// Find products with category being one of Beverages, Condiments, or Seafood - /// - [Test] - public void FindByJoinedEntityListOfValues() - { - var categoryNames = new object[] { "Beverages", "Condiments", "Seafood" }; - var categoryIds = new[] { 1, 2, 8 }; - - var query = new SqlLam() - .Join((p, c) => p.CategoryId == c.CategoryId) - .WhereIsIn(c => c.CategoryName, categoryNames); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(36, results.Count); - Assert.IsTrue(results.All(p => categoryIds.Contains(p.CategoryId))); - } - - /// - /// Find products by getting the category Ids first using a subquery - /// - [Test] - public void FindByJoinedEntityWithSubQuery() - { - var categoryNames = new object[] { "Beverages", "Condiments", "Seafood" }; - var categoryIds = new[] { 1, 2, 8 }; - - var subQuery = new SqlLam() - .WhereIsIn(c => c.CategoryName, categoryNames) - .Select(p => p.CategoryId); - - var query = new SqlLam() - .Join((p, c) => p.CategoryId == c.CategoryId) - .WhereIsIn(c => c.CategoryId, subQuery); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(36, results.Count); - Assert.IsTrue(results.All(p => categoryIds.Contains(p.CategoryId))); - } - - /// - /// Get products sorted by categories - /// - [Test] - public void OrderEntitiesByJoinedEntityField() - { - var categoryQuery = new SqlLam(); - var categories = Connection.Query(categoryQuery.QueryString).ToDictionary(k => k.CategoryId); - - var query = new SqlLam() - .Join((p, c) => p.CategoryId == c.CategoryId) - .OrderBy(c => c.CategoryName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal( - categories[results[i - 1].CategoryId].CategoryName, - categories[results[i].CategoryId].CategoryName) - <= 0); - } - } - - /// - /// Get products sorted by categories - /// - [Test] - public void OrderEntitiesByJoinedEntityFieldDescending() - { - var categoryQuery = new SqlLam(); - var categories = Connection.Query(categoryQuery.QueryString).ToDictionary(k => k.CategoryId); - - var query = new SqlLam() - .Join((p, c) => p.CategoryId == c.CategoryId) - .OrderByDescending(c => c.CategoryName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal( - categories[results[i - 1].CategoryId].CategoryName, - categories[results[i].CategoryId].CategoryName) - >= 0); - } - } - - /// - /// Load products together with their category details (many to one relationship) - /// The complex selection of the product properties is only required because of the identical column names in the Northwind database for the primary key column and the foreign key column - /// - [Test] - public void GetEntitiesWithManyToOneRelationship() - { - var query = new SqlLam() - .Select(p => p.ProductId, p => p.ProductName, p => p.EnglishName, p => p.ReorderLevel, p => p.UnitPrice) - .Join((p, c) => p.CategoryId == c.CategoryId) - .Select(c => c); - - var result = Connection.Query( - query.QueryString, - (product, category) => - { - product.Category = category; - product.CategoryId = category.CategoryId; - return product; - }, - splitOn: query.SplitColumns[0]).ToList(); - - Assert.AreEqual(77, result.Count); - foreach (var product in result) - { - Assert.IsNotNull(product.Category); - Assert.IsNotNull(product.Category.CategoryName); - } - } - - /// - /// Load categories together with all their products (one to many relationship) - /// The complex selection of the product properties is only required because of the identical column names in the Northwind database for the primary key column and the foreign key column - /// - [Test] - public void GetEntitiesWithOneToManyRelationship() - { - var query = new SqlLam() - .Select(c => c.CategoryName) - .Join((c, p) => c.CategoryId == p.CategoryId) - .Select(p => p.CategoryId, p => p.ProductId, p => p.ProductName, p => p.EnglishName, p => p.ReorderLevel, p => p.UnitPrice); - - var result = new Dictionary(); - Connection.Query( - query.QueryString, - (category, product) => - { - if(!result.ContainsKey(product.CategoryId)) - { - category.CategoryId = product.CategoryId; - category.Products = new List(); - result.Add(category.CategoryId,category); - } - product.Category = result[product.CategoryId]; - result[product.CategoryId].Products.Add(product); - return category; - }, - splitOn: query.SplitColumns[0]); - - Assert.AreEqual(8, result.Count); - foreach (var category in result.Values) - { - Assert.Greater(category.Products.Count, 0); - foreach(var product in category.Products) - { - Assert.AreEqual(category.CategoryId, product.CategoryId); - } - } - } - - /// - /// Load orders together with all their assigned products (many to many relationship via Order Details) - /// - [Test] - public void GetEntitiesWithManyToManyRelationship() - { - var query = new SqlLam() - .Select(o => o) - .Join((o, d) => o.OrderId == d.OrderId) - .Join((d, p) => d.ProductId == p.ProductId) - .Select(p => p); - - var result = new Dictionary(); - Connection.Query( - query.QueryString, - (order, product) => - { - if (!result.ContainsKey(order.OrderId)) - { - order.Products = new List(); - result.Add(order.OrderId, order); - } - result[order.OrderId].Products.Add(product); - return order; - }, - splitOn: query.SplitColumns[1]); - - var controlQuery = new SqlLam(); - var controlSet = - Connection.Query(controlQuery.QueryString).ToLookup(d => d.OrderId + "_" + d.ProductId); - Assert.AreEqual(1078, result.Count); - foreach (var order in result.Values) - { - Assert.Greater(order.Products.Count, 0); - foreach (var product in order.Products) - { - Assert.IsTrue(controlSet.Contains(order.OrderId + "_" + product.ProductId)); - } - } - } - } -} diff --git a/LambdaSqlBuilder.Tests/LambdaSqlBuilder.Tests.csproj b/LambdaSqlBuilder.Tests/LambdaSqlBuilder.Tests.csproj deleted file mode 100644 index 2b5fead..0000000 --- a/LambdaSqlBuilder.Tests/LambdaSqlBuilder.Tests.csproj +++ /dev/null @@ -1,87 +0,0 @@ - - - - Debug - AnyCPU - 8.0.30703 - 2.0 - {75D22AB3-B90A-4E91-9888-E7FAB585F393} - Library - Properties - LambdaSqlBuilder.Tests - LambdaSqlBuilder.Tests - v4.0 - 512 - - - true - full - false - bin\Debug\ - DEBUG;TRACE - prompt - 4 - - - pdbonly - true - bin\Debug\ - TRACE - prompt - 4 - - - - ..\packages\Dapper.1.13\lib\net40\Dapper.dll - - - ..\packages\NUnit.2.6.2\lib\nunit.framework.dll - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - {3DF62791-F514-40A9-A335-BED1D9CBB34B} - LambdaSqlBuilder - - - - - Always - - - - - \ No newline at end of file diff --git a/LambdaSqlBuilder.Tests/LinqSqlQueryTests.cs b/LambdaSqlBuilder.Tests/LinqSqlQueryTests.cs deleted file mode 100644 index 2904037..0000000 --- a/LambdaSqlBuilder.Tests/LinqSqlQueryTests.cs +++ /dev/null @@ -1,132 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Tests.Entities; -using LambdaSqlBuilder.Tests.Infrastructure; -using NUnit.Framework; -using Dapper; - -namespace LambdaSqlBuilder.Tests -{ - [TestFixture] - public class LinqSqlQueryTests : TestBase - { - /// - /// Find the product with name Tofu - /// - [Test] - public void FindByFieldValue() - { - const string productName = "Tofu"; - - var query = from product in new SqlLam() - where product.ProductName == productName - select product; - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, results.Count); - Assert.AreEqual(productName, results.First().ProductName); - } - - /// - /// Get product Tofu by its Id and select the value of the Unit Price only - /// - [Test] - public void SelectField() - { - const int productId = 14; - - var query = from product in new SqlLam() - where product.ProductId == productId - select product.UnitPrice; - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, results.Count); - Assert.AreEqual(23.25, results.First()); - } - - /// - /// Find all products for the category Beverages and the Reorder Level 25 - /// - [Test] - public void FindByJoinedEntityValue() - { - const int reorderLevel = 25; - const string categoryName = "Beverages"; - const int categoryId = 1; - - var query = from product in new SqlLam() - join category in new SqlLam() - on product.CategoryId equals category.CategoryId - where product.ReorderLevel == reorderLevel && category.CategoryName == categoryName - select product; - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(3, results.Count); - Assert.IsTrue(results.All(p => p.CategoryId == categoryId)); - } - - /// - /// Get categories sorted by name - /// - [Test] - public void OrderEntitiesByField() - { - var query = from category in new SqlLam() - orderby category.CategoryName - select category; - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal(results[i - 1].CategoryName, results[i].CategoryName) <= 0); - } - } - - /// - /// Get categories sorted by name descending - /// - [Test] - public void OrderEntitiesByFieldDescending() - { - var query = from category in new SqlLam() - orderby category.CategoryName descending - select category; - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal(results[i - 1].CategoryName, results[i].CategoryName) >= 0); - } - } - - /// - /// Select number of products for individual Reorder Levels - /// - [Test] - public void SelectGroupedCounts() - { - var groupSizes = new[] { 24, 8, 7, 10, 8, 12, 8 }; - - var query = from product in new SqlLam() - group product by product.ReorderLevel; - - query.SelectCount(p => p.ProductId); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(groupSizes.Length, results.Count); - - for (int i = 0; i < groupSizes.Length; ++i) - { - Assert.AreEqual(groupSizes[i], results[i]); - } - } - } -} diff --git a/LambdaSqlBuilder.Tests/Properties/AssemblyInfo.cs b/LambdaSqlBuilder.Tests/Properties/AssemblyInfo.cs deleted file mode 100644 index 1e346ed..0000000 --- a/LambdaSqlBuilder.Tests/Properties/AssemblyInfo.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System.Reflection; -using System.Runtime.CompilerServices; -using System.Runtime.InteropServices; - -// General Information about an assembly is controlled through the following -// set of attributes. Change these attribute values to modify the information -// associated with an assembly. -[assembly: AssemblyTitle("LambdaSqlBuilder.Tests")] -[assembly: AssemblyDescription("")] -[assembly: AssemblyConfiguration("")] -[assembly: AssemblyCompany("")] -[assembly: AssemblyProduct("LambdaSqlBuilder.Tests")] -[assembly: AssemblyCopyright("Copyright © 2013")] -[assembly: AssemblyTrademark("")] -[assembly: AssemblyCulture("")] - -// Setting ComVisible to false makes the types in this assembly not visible -// to COM components. If you need to access a type in this assembly from -// COM, set the ComVisible attribute to true on that type. -[assembly: ComVisible(false)] - -// The following GUID is for the ID of the typelib if this project is exposed to COM -[assembly: Guid("62cd49ae-06e0-4598-affe-229ac805341b")] - -// Version information for an assembly consists of the following four values: -// -// Major Version -// Minor Version -// Build Number -// Revision -// -// You can specify all the values or you can default the Build and Revision Numbers -// by using the '*' as shown below: -// [assembly: AssemblyVersion("1.0.*")] -[assembly: AssemblyVersion("1.0.0.0")] -[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/LambdaSqlBuilder.Tests/SqlQueryTests.cs b/LambdaSqlBuilder.Tests/SqlQueryTests.cs deleted file mode 100644 index b7de478..0000000 --- a/LambdaSqlBuilder.Tests/SqlQueryTests.cs +++ /dev/null @@ -1,385 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Configuration; -using System.Data.SqlClient; -using System.Data.SqlServerCe; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Tests.Entities; -using LambdaSqlBuilder.Tests.Infrastructure; -using NUnit.Framework; -using Dapper; - -namespace LambdaSqlBuilder.Tests -{ - [TestFixture] - public class SqlQueryTests : TestBase - { - /// - /// Find the product with name Tofu - /// - [Test] - public void FindByFieldValue() - { - const string productName = "Tofu"; - - var query = new SqlLam(p => p.ProductName == productName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, results.Count); - Assert.AreEqual(productName, results.First().ProductName); - } - - /// - /// Find products with the reorder level being 5, 15, or 25 - /// - [Test] - public void FindByListOfValues() - { - var reorderLevels = new object[] {5, 15, 25}; - - var query = new SqlLam() - .WhereIsIn(p => p.ReorderLevel, reorderLevels); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(30, results.Count); - Assert.IsTrue(results.All(p => reorderLevels.Contains(p.ReorderLevel))); - } - - /// - /// Find products by getting the product Ids first using a subquery - /// - [Test] - public void FindBySubQuery() - { - var productNames = new object[] { "Konbu", "Tofu", "Pavlova" }; - - var subQuery = new SqlLam() - .WhereIsIn(p => p.ProductName, productNames) - .Select(p => p.ProductId); - - var query = new SqlLam() - .WhereIsIn(p => p.ProductId, subQuery); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(3, results.Count); - Assert.IsTrue(results.All(p => productNames.Contains(p.ProductName))); - } - - /// - /// Find products with the reorder level not being 5, 15, or 25 - /// - [Test] - public void FindByListOfValuesNegated() - { - var reorderLevels = new object[] { 5, 15, 25 }; - - var query = new SqlLam() - .WhereNotIn(p => p.ReorderLevel, reorderLevels); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(47, results.Count); - Assert.IsTrue(results.All(p => !reorderLevels.Contains(p.ReorderLevel))); - } - - /// - /// Find products not being included in a subquery - /// - [Test] - public void FindBySubQueryNegated() - { - var productNames = new object[] { "Konbu", "Tofu", "Pavlova" }; - - var subQuery = new SqlLam() - .WhereIsIn(p => p.ProductName, productNames) - .Select(p => p.ProductId); - - var query = new SqlLam() - .WhereNotIn(p => p.ProductId, subQuery); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(74, results.Count); - Assert.IsTrue(results.All(p => !productNames.Contains(p.ProductName))); - } - - /// - /// Get product Tofu by its Id and select the value of the Unit Price only - /// - [Test] - public void SelectField() - { - const int productId = 14; - - var query = new SqlLam(p => p.ProductId == productId) - .Select(p => p.UnitPrice); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, results.Count); - Assert.AreEqual(23.25, results.First()); - } - - /// - /// Get product Tofu by its Id and selects all its properties - /// - [Test] - public void SelectAllFields() - { - const int productId = 14; - - var query = new SqlLam(p => p.ProductId == productId) - .Select(p => p); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(1, results.Count); - } - - /// - /// Get categories sorted by name - /// - [Test] - public void OrderEntitiesByField() - { - var query = new SqlLam() - .OrderBy(p => p.CategoryName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal(results[i - 1].CategoryName, results[i].CategoryName) <= 0); - } - } - - /// - /// Get categories sorted by name descending - /// - [Test] - public void OrderEntitiesByFieldDescending() - { - var query = new SqlLam() - .OrderByDescending(p => p.CategoryName); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - for (int i = 1; i < results.Count; ++i) - { - Assert.IsTrue(String.CompareOrdinal(results[i - 1].CategoryName, results[i].CategoryName) >= 0); - } - } - - /// - /// Get the number of all products - /// - [Test] - public void SelectEntityCount() - { - var query = new SqlLam() - .SelectCount(p => p.ProductId); - - var resultCount = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(77, resultCount); - } - - /// - /// Select number of Product IDs for products with the Reorder Level equal to 25 - /// - [Test] - public void SelectRestrictedEntityCount() - { - var query = new SqlLam() - .SelectCount(p => p.ProductId) - .Where(p => p.ReorderLevel == 25); - - var resultCount = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(12, resultCount); - } - - /// - /// Select number of products for individual Reorder Levels - /// - [Test] - public void SelectGroupedCounts() - { - var groupSizes = new[] {24, 8, 7, 10, 8, 12, 8}; - - var query = new SqlLam() - .SelectCount(p => p.ProductId) - .GroupBy(p => p.ReorderLevel) - .OrderBy(p => p.ReorderLevel); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(groupSizes.Length, results.Count); - - for (int i = 0; i < groupSizes.Length; ++i) - { - Assert.AreEqual(groupSizes[i], results[i]); - } - } - - /// - /// Select all distinct possible values of the Reorder Level - /// - [Test] - public void SelectDistinctValues() - { - var allValues = new[] {0, 5, 10, 15, 20, 25, 30}; - - var query = new SqlLam() - .SelectDistinct(p => p.ReorderLevel) - .OrderBy(p => p.ReorderLevel); - - var results = Connection.Query(query.QueryString, query.QueryParameters).ToList(); - - Assert.AreEqual(allValues.Length, results.Count); - for (int i = 0; i < allValues.Length; ++i) - { - Assert.AreEqual(allValues[i], results[i]); - } - } - - /// - /// Select maximum unit price among all the products - /// - [Test] - public void SelectMaximumValue() - { - const decimal maximumValue = 263.5M; - - var query = new SqlLam() - .SelectMax(p => p.UnitPrice); - - var results = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(maximumValue, results); - } - - /// - /// Select minimum unit price among all the products - /// - [Test] - public void SelectMinimumValue() - { - const decimal minimumValue = 2.5M; - - var query = new SqlLam() - .SelectMin(p => p.UnitPrice); - - var results = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(minimumValue, results); - } - - /// - /// Select average unit price among all the products - /// - [Test] - public void SelectAverageValue() - { - const decimal averageValue = 28.8663M; - - var query = new SqlLam() - .SelectAverage(p => p.UnitPrice); - - var results = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(averageValue, results); - } - - /// - /// Select sum of all unit prices among all the products - /// - [Test] - public void SelectSum() - { - const decimal sum = 2222.71M; - - var query = new SqlLam() - .SelectSum(p => p.UnitPrice); - - var results = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.AreEqual(sum, results); - } - - /// - /// Select the product "Tofu" by listing its individual properties using the 'new' construct - /// - [Test] - public void SelectWithNew() - { - const string productName = "Tofu"; - - var query = new SqlLam() - .Where(p => p.ProductName == productName) - .Select(p => new { - p.ProductId, - p.ProductName, - p.CategoryId, - p.ReorderLevel, - p.UnitPrice - }); - - var results = Connection.Query(query.QueryString, query.QueryParameters).Single(); - - Assert.NotNull(results.ProductId); - Assert.NotNull(results.ProductName); - Assert.NotNull(results.CategoryId); - Assert.NotNull(results.ReorderLevel); - Assert.NotNull(results.UnitPrice); - Assert.Null(results.EnglishName); - } - - /// - /// Load products with reorder level 0 page by page - /// - [Test] - public void PaginateOverResults() - { - const int reorderLevel = 0; - const int pageSize = 5; - const int numberOfPages = 5; - const int lastPageSize = 4; - - var query = new SqlLam(p => p.ReorderLevel == reorderLevel) - .OrderBy(p => p.ProductName); - - for(int page = 1; page < numberOfPages; ++page) - { - var results = Connection.Query(query.QueryStringPage(pageSize, page), query.QueryParameters).ToList(); - Assert.AreEqual(pageSize, results.Count); - Assert.IsTrue(results.All(p => p.ReorderLevel == reorderLevel)); - } - - var lastResults = Connection.Query(query.QueryStringPage(pageSize, numberOfPages), query.QueryParameters).ToList(); - Assert.AreEqual(lastPageSize, lastResults.Count); - Assert.IsTrue(lastResults.All(p => p.ReorderLevel == reorderLevel)); - } - - /// - /// Load first 10 products sorted by the product name with reorder level 0 - /// - [Test] - public void TopTenResults() - { - const int reorderLevel = 0; - const int pageSize = 10; - - var query = new SqlLam(p => p.ReorderLevel == reorderLevel) - .OrderBy(p => p.ProductName); - - var results = Connection.Query(query.QueryStringPage(pageSize), query.QueryParameters).ToList(); - Assert.AreEqual(pageSize, results.Count); - Assert.IsTrue(results.All(p => p.ReorderLevel == reorderLevel)); - } - } -} diff --git a/LambdaSqlBuilder.Tests/packages.config b/LambdaSqlBuilder.Tests/packages.config deleted file mode 100644 index b5e24d7..0000000 --- a/LambdaSqlBuilder.Tests/packages.config +++ /dev/null @@ -1,5 +0,0 @@ - - - - - \ No newline at end of file diff --git a/LambdaSqlBuilder.sln b/LambdaSqlBuilder.sln deleted file mode 100644 index 0fe2e8f..0000000 --- a/LambdaSqlBuilder.sln +++ /dev/null @@ -1,26 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 11.00 -# Visual C# Express 2010 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LambdaSqlBuilder", "LambdaSqlBuilder\LambdaSqlBuilder.csproj", "{3DF62791-F514-40A9-A335-BED1D9CBB34B}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LambdaSqlBuilder.Tests", "LambdaSqlBuilder.Tests\LambdaSqlBuilder.Tests.csproj", "{75D22AB3-B90A-4E91-9888-E7FAB585F393}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Any CPU = Debug|Any CPU - Release|Any CPU = Release|Any CPU - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {3DF62791-F514-40A9-A335-BED1D9CBB34B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {3DF62791-F514-40A9-A335-BED1D9CBB34B}.Debug|Any CPU.Build.0 = Debug|Any CPU - {3DF62791-F514-40A9-A335-BED1D9CBB34B}.Release|Any CPU.ActiveCfg = Release|Any CPU - {3DF62791-F514-40A9-A335-BED1D9CBB34B}.Release|Any CPU.Build.0 = Release|Any CPU - {75D22AB3-B90A-4E91-9888-E7FAB585F393}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {75D22AB3-B90A-4E91-9888-E7FAB585F393}.Debug|Any CPU.Build.0 = Debug|Any CPU - {75D22AB3-B90A-4E91-9888-E7FAB585F393}.Release|Any CPU.ActiveCfg = Release|Any CPU - {75D22AB3-B90A-4E91-9888-E7FAB585F393}.Release|Any CPU.Build.0 = Release|Any CPU - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection -EndGlobal diff --git a/LambdaSqlBuilder/Adapter/ISqlAdapter.cs b/LambdaSqlBuilder/Adapter/ISqlAdapter.cs deleted file mode 100644 index 5ce715f..0000000 --- a/LambdaSqlBuilder/Adapter/ISqlAdapter.cs +++ /dev/null @@ -1,26 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; - -namespace LambdaSqlBuilder.Adapter -{ - /// - /// SQL adapter provides db specific functionality related to db specific SQL syntax - /// - interface ISqlAdapter - { - string QueryString(string selection, string source, string conditions, - string order, string grouping, string having); - - string QueryStringPage(string selection, string source, string conditions, string order, - int pageSize, int pageNumber); - - string QueryStringPage(string selection, string source, string conditions, string order, - int pageSize); - - string Table(string tableName); - string Field(string tableName, string fieldName); - string Parameter(string parameterId); - } -} diff --git a/LambdaSqlBuilder/Adapter/SqlAdapterBase.cs b/LambdaSqlBuilder/Adapter/SqlAdapterBase.cs deleted file mode 100644 index 4ab3f3b..0000000 --- a/LambdaSqlBuilder/Adapter/SqlAdapterBase.cs +++ /dev/null @@ -1,21 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Adapter -{ - /// - /// Provides functionality common to all supported databases - /// - class SqlAdapterBase - { - public string QueryString(string selection, string source, string conditions, string order, string grouping, string having) - { - return string.Format("SELECT {0} FROM {1} {2} {3} {4} {5}", - selection, source, conditions, order, grouping, having); - } - } -} diff --git a/LambdaSqlBuilder/Adapter/SqlServer2008Adapter.cs b/LambdaSqlBuilder/Adapter/SqlServer2008Adapter.cs deleted file mode 100644 index c6f9871..0000000 --- a/LambdaSqlBuilder/Adapter/SqlServer2008Adapter.cs +++ /dev/null @@ -1,25 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Adapter -{ - /// - /// Provides functionality specific to SQL Server 2008 - /// - class SqlServer2008Adapter : SqlServerAdapterBase, ISqlAdapter - { - public string QueryStringPage(string source, string selection, string conditions, string order, - int pageSize, int pageNumber) - { - var innerQuery = string.Format("SELECT {0},ROW_NUMBER() OVER ({1}) AS RN FROM {2} {3}", - selection, order, source, conditions); - - return string.Format("SELECT TOP {0} * FROM ({1}) InnerQuery WHERE RN > {2} ORDER BY RN", - pageSize, innerQuery, pageSize*(pageNumber - 1)); - } - } -} diff --git a/LambdaSqlBuilder/Adapter/SqlServer2012Adapter.cs b/LambdaSqlBuilder/Adapter/SqlServer2012Adapter.cs deleted file mode 100644 index 0b526ec..0000000 --- a/LambdaSqlBuilder/Adapter/SqlServer2012Adapter.cs +++ /dev/null @@ -1,22 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Adapter -{ - /// - /// Provides functionality specific to SQL Server 2012 - /// - class SqlServer2012Adapter : SqlServerAdapterBase, ISqlAdapter - { - public string QueryStringPage(string source, string selection, string conditions, string order, - int pageSize, int pageNumber) - { - return string.Format("SELECT {0} FROM {1} {2} {3} OFFSET {4} ROWS FETCH NEXT {5} ROWS ONLY", - selection, source, conditions, order, pageSize * (pageNumber - 1), pageSize); - } - } -} diff --git a/LambdaSqlBuilder/Adapter/SqlServerAdapterBase.cs b/LambdaSqlBuilder/Adapter/SqlServerAdapterBase.cs deleted file mode 100644 index f7af35e..0000000 --- a/LambdaSqlBuilder/Adapter/SqlServerAdapterBase.cs +++ /dev/null @@ -1,38 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Adapter -{ - /// - /// Provides functionality common to all supported SQL Server versions - /// - class SqlServerAdapterBase : SqlAdapterBase - { - public string QueryStringPage(string source, string selection, string conditions, string order, - int pageSize) - { - return string.Format("SELECT TOP({4}) {0} FROM {1} {2} {3}", - selection, source, conditions, order, pageSize); - } - - - public string Table(string tableName) - { - return string.Format("[{0}]", tableName); - } - - public string Field(string tableName, string fieldName) - { - return string.Format("[{0}].[{1}]", tableName, fieldName); - } - - public string Parameter(string parameterId) - { - return "@" + parameterId; - } - } -} diff --git a/LambdaSqlBuilder/Builder/SqlQueryBuilder.cs b/LambdaSqlBuilder/Builder/SqlQueryBuilder.cs deleted file mode 100644 index fff7611..0000000 --- a/LambdaSqlBuilder/Builder/SqlQueryBuilder.cs +++ /dev/null @@ -1,150 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Dynamic; -using System.Globalization; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Adapter; - -namespace LambdaSqlBuilder.Builder -{ - /// - /// Implements the whole SQL building logic. Continually adds and stores the SQL parts as the requests come. - /// When requested to return the QueryString, the parts are combined and returned as a single query string. - /// The query parameters are stored in a dictionary implemented by an ExpandoObject that can be requested by QueryParameters. - /// - public partial class SqlQueryBuilder - { - internal ISqlAdapter Adapter { get; set; } - - private const string PARAMETER_PREFIX = "Param"; - - private readonly List _tableNames = new List(); - private readonly List _joinExpressions = new List(); - private readonly List _selectionList = new List(); - private readonly List _conditions = new List(); - private readonly List _sortList = new List(); - private readonly List _groupingList = new List(); - private readonly List _havingConditions = new List(); - private readonly List _splitColumns = new List(); - private int _paramIndex; - - public List TableNames { get { return _tableNames; } } - public List JoinExpressions { get { return _joinExpressions; } } - public List SelectionList { get { return _selectionList; } } - public List WhereConditions { get { return _conditions; } } - public List OrderByList { get { return _sortList; } } - public List GroupByList { get { return _groupingList; } } - public List HavingConditions { get { return _havingConditions; } } - public List SplitColumns { get { return _splitColumns; } } - public int CurrentParamIndex { get { return _paramIndex; } } - - private string Source - { - get - { - var joinExpression = string.Join(" ", _joinExpressions); - return string.Format("{0} {1}", Adapter.Table(_tableNames.First()), joinExpression); - } - } - - private string Selection - { - get - { - if (_selectionList.Count == 0) - return string.Format("{0}.*", Adapter.Table(_tableNames.First())); - else - return string.Join(", ", _selectionList); - } - } - - private string Conditions - { - get - { - if (_conditions.Count == 0) - return ""; - else - return "WHERE " + string.Join("", _conditions); - } - } - - private string Order - { - get - { - if (_sortList.Count == 0) - return ""; - else - return "ORDER BY " + string.Join(", ", _sortList); - } - } - - private string Grouping - { - get - { - if (_groupingList.Count == 0) - return ""; - else - return "GROUP BY " + string.Join(", ", _groupingList); - } - } - - private string Having - { - get - { - if (_havingConditions.Count == 0) - return ""; - else - return "HAVING " + string.Join(" ", _havingConditions); - } - } - - public IDictionary Parameters { get; private set; } - - public string QueryString - { - get { return Adapter.QueryString(Selection, Source, Conditions, Grouping, Having, Order); } - } - - public string QueryStringPage(int pageSize, int? pageNumber = null) - { - if (pageNumber.HasValue) - { - if (_sortList.Count == 0) - throw new Exception("Pagination requires the ORDER BY statement to be specified"); - - return Adapter.QueryStringPage(Source, Selection, Conditions, Order, pageSize, pageNumber.Value); - } - - return Adapter.QueryStringPage(Source, Selection, Conditions, Order, pageSize); - } - - internal SqlQueryBuilder(string tableName, ISqlAdapter adapter) - { - _tableNames.Add(tableName); - Adapter = adapter; - Parameters = new ExpandoObject(); - _paramIndex = 0; - } - - #region helpers - private string NextParamId() - { - ++_paramIndex; - return PARAMETER_PREFIX + _paramIndex.ToString(CultureInfo.InvariantCulture); - } - - private void AddParameter(string key, object value) - { - if(!Parameters.ContainsKey(key)) - Parameters.Add(key, value); - } - #endregion - } -} diff --git a/LambdaSqlBuilder/Builder/SqlQueryBuilderExpr.cs b/LambdaSqlBuilder/Builder/SqlQueryBuilderExpr.cs deleted file mode 100644 index cc14955..0000000 --- a/LambdaSqlBuilder/Builder/SqlQueryBuilderExpr.cs +++ /dev/null @@ -1,117 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; -using System.Text.RegularExpressions; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder.Builder -{ - /// - /// Implements the expression buiding for the WHERE statement - /// - partial class SqlQueryBuilder - { - public void BeginExpression() - { - _conditions.Add("("); - } - - public void EndExpression() - { - _conditions.Add(")"); - } - - public void And() - { - if (_conditions.Count > 0) - _conditions.Add(" AND "); - } - - public void Or() - { - if (_conditions.Count > 0) - _conditions.Add(" OR "); - } - - public void Not() - { - _conditions.Add(" NOT "); - } - - public void QueryByField(string tableName, string fieldName, string op, object fieldValue) - { - var paramId = NextParamId(); - string newCondition = string.Format("{0} {1} {2}", - Adapter.Field(tableName, fieldName), - op, - Adapter.Parameter(paramId)); - - _conditions.Add(newCondition); - AddParameter(paramId, fieldValue); - } - - public void QueryByFieldLike(string tableName, string fieldName, string fieldValue) - { - var paramId = NextParamId(); - string newCondition = string.Format("{0} LIKE {1}", - Adapter.Field(tableName, fieldName), - Adapter.Parameter(paramId)); - - _conditions.Add(newCondition); - AddParameter(paramId, fieldValue); - } - - public void QueryByFieldNull(string tableName, string fieldName) - { - _conditions.Add(string.Format("{0} IS NULL", Adapter.Field(tableName, fieldName))); - } - - public void QueryByFieldNotNull(string tableName, string fieldName) - { - _conditions.Add(string.Format("{0} IS NOT NULL", Adapter.Field(tableName, fieldName))); - } - - public void QueryByFieldComparison(string leftTableName, string leftFieldName, string op, - string rightTableName, string rightFieldName) - { - string newCondition = string.Format("{0} {1} {2}", - Adapter.Field(leftTableName, leftFieldName), - op, - Adapter.Field(rightTableName, rightFieldName)); - - _conditions.Add(newCondition); - } - - public void QueryByIsIn(string tableName, string fieldName, SqlLamBase sqlQuery) - { - var innerQuery = sqlQuery.QueryString; - foreach (var param in sqlQuery.QueryParameters) - { - var innerParamKey = "Inner" + param.Key; - innerQuery = Regex.Replace(innerQuery, param.Key, innerParamKey); - AddParameter(innerParamKey, param.Value); - } - - var newCondition = string.Format("{0} IN ({1})", Adapter.Field(tableName, fieldName), innerQuery); - - _conditions.Add(newCondition); - } - - public void QueryByIsIn(string tableName, string fieldName, IEnumerable values) - { - var paramIds = values.Select(x => - { - var paramId = NextParamId(); - AddParameter(paramId, x); - return Adapter.Parameter(paramId); - }); - - var newCondition = string.Format("{0} IN ({1})", Adapter.Field(tableName, fieldName), string.Join(",", paramIds)); - _conditions.Add(newCondition); - } - } -} diff --git a/LambdaSqlBuilder/Builder/SqlQueryBuilderSpec.cs b/LambdaSqlBuilder/Builder/SqlQueryBuilderSpec.cs deleted file mode 100644 index 59ca217..0000000 --- a/LambdaSqlBuilder/Builder/SqlQueryBuilderSpec.cs +++ /dev/null @@ -1,58 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder.Builder -{ - /// - /// Implements the SQL building for JOIN, ORDER BY, SELECT, and GROUP BY - /// - partial class SqlQueryBuilder - { - public void Join(string originalTableName, string joinTableName, string leftField, string rightField) - { - var joinString = string.Format("JOIN {0} ON {1} = {2}", - Adapter.Table(joinTableName), - Adapter.Field(originalTableName, leftField), - Adapter.Field(joinTableName, rightField)); - _tableNames.Add(joinTableName); - _joinExpressions.Add(joinString); - _splitColumns.Add(rightField); - } - - public void OrderBy(string tableName, string fieldName, bool desc = false) - { - var order = Adapter.Field(tableName, fieldName); - if (desc) - order += " DESC"; - - _sortList.Add(order); - } - - public void Select(string tableName) - { - var selectionString = string.Format("{0}.*", Adapter.Table(tableName)); - _selectionList.Add(selectionString); - } - - public void Select(string tableName, string fieldName) - { - _selectionList.Add(Adapter.Field(tableName, fieldName)); - } - - public void Select(string tableName, string fieldName, SelectFunction selectFunction) - { - var selectionString = string.Format("{0}({1})", selectFunction.ToString(), Adapter.Field(tableName, fieldName)); - _selectionList.Add(selectionString); - } - - public void GroupBy(string tableName, string fieldName) - { - _groupingList.Add(Adapter.Field(tableName, fieldName)); - } - } -} diff --git a/LambdaSqlBuilder/LambdaSqlBuilder.csproj b/LambdaSqlBuilder/LambdaSqlBuilder.csproj deleted file mode 100644 index 668c46d..0000000 --- a/LambdaSqlBuilder/LambdaSqlBuilder.csproj +++ /dev/null @@ -1,80 +0,0 @@ - - - - Debug - AnyCPU - 8.0.30703 - 2.0 - {3DF62791-F514-40A9-A335-BED1D9CBB34B} - Library - Properties - LambdaSqlBuilder - LambdaSqlBuilder - v4.0 - 512 - - - true - full - false - bin\Debug\ - DEBUG;TRACE - prompt - 4 - - - pdbonly - true - bin\Release\ - TRACE - prompt - 4 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/LambdaSqlBuilder/Properties/AssemblyInfo.cs b/LambdaSqlBuilder/Properties/AssemblyInfo.cs deleted file mode 100644 index 9dee54f..0000000 --- a/LambdaSqlBuilder/Properties/AssemblyInfo.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System.Reflection; -using System.Runtime.CompilerServices; -using System.Runtime.InteropServices; - -// General Information about an assembly is controlled through the following -// set of attributes. Change these attribute values to modify the information -// associated with an assembly. -[assembly: AssemblyTitle("LambdaSqlBuilder")] -[assembly: AssemblyDescription("")] -[assembly: AssemblyConfiguration("")] -[assembly: AssemblyCompany("")] -[assembly: AssemblyProduct("LambdaSqlBuilder")] -[assembly: AssemblyCopyright("Copyright © 2013")] -[assembly: AssemblyTrademark("")] -[assembly: AssemblyCulture("")] - -// Setting ComVisible to false makes the types in this assembly not visible -// to COM components. If you need to access a type in this assembly from -// COM, set the ComVisible attribute to true on that type. -[assembly: ComVisible(false)] - -// The following GUID is for the ID of the typelib if this project is exposed to COM -[assembly: Guid("9d71aec5-a052-45df-a9a2-645c23dbeb9d")] - -// Version information for an assembly consists of the following four values: -// -// Major Version -// Minor Version -// Build Number -// Revision -// -// You can specify all the values or you can default the Build and Revision Numbers -// by using the '*' as shown below: -// [assembly: AssemblyVersion("1.0.*")] -[assembly: AssemblyVersion("1.0.0.0")] -[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/LikeNode.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/LikeNode.cs deleted file mode 100644 index 5c3fc18..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/LikeNode.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - class LikeNode : Node - { - public LikeMethod Method { get; set; } - public MemberNode MemberNode { get; set; } - public string Value { get; set; } - } -} diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/MemberNode.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/MemberNode.cs deleted file mode 100644 index 5581e14..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/MemberNode.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - class MemberNode : Node - { - public string TableName { get; set; } - public string FieldName { get; set; } - } -} diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/Node.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/Node.cs deleted file mode 100644 index b89df7d..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/Node.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - abstract class Node - { - } -} diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/OperationNode.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/OperationNode.cs deleted file mode 100644 index b7426ac..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/OperationNode.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - class OperationNode : Node - { - public ExpressionType Operator { get; set; } - public Node Left { get; set; } - public Node Right { get; set; } - } -} diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/SingleOperationNode.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/SingleOperationNode.cs deleted file mode 100644 index 7618bfd..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/SingleOperationNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - class SingleOperationNode : Node - { - public ExpressionType Operator { get; set; } - public Node Child { get; set; } - } -} diff --git a/LambdaSqlBuilder/Resolver/ExpressionTree/ValueNode.cs b/LambdaSqlBuilder/Resolver/ExpressionTree/ValueNode.cs deleted file mode 100644 index a320b06..0000000 --- a/LambdaSqlBuilder/Resolver/ExpressionTree/ValueNode.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.Resolver.ExpressionTree -{ - class ValueNode : Node - { - public object Value { get; set; } - } -} diff --git a/LambdaSqlBuilder/Resolver/LambdaResolver.cs b/LambdaSqlBuilder/Resolver/LambdaResolver.cs deleted file mode 100644 index 31335bd..0000000 --- a/LambdaSqlBuilder/Resolver/LambdaResolver.cs +++ /dev/null @@ -1,91 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Reflection; -using System.Runtime.CompilerServices; -using System.Text; -using LambdaSqlBuilder.Builder; - -namespace LambdaSqlBuilder.Resolver -{ - partial class LambdaResolver - { - private Dictionary _operationDictionary = new Dictionary() - { - { ExpressionType.Equal, "="}, - { ExpressionType.NotEqual, "!="}, - { ExpressionType.GreaterThan, ">"}, - { ExpressionType.LessThan, "<"}, - { ExpressionType.GreaterThanOrEqual, ">="}, - { ExpressionType.LessThanOrEqual, "<="} - }; - - private SqlQueryBuilder _builder { get; set; } - - public LambdaResolver(SqlQueryBuilder builder) - { - _builder = builder; - } - - #region helpers - public static string GetColumnName(Expression> selector) - { - return GetColumnName(GetMemberExpression(selector.Body)); - } - - public static string GetColumnName(Expression expression) - { - var member = GetMemberExpression(expression); - var column = member.Member.GetCustomAttributes(false).OfType().FirstOrDefault(); - if (column != null) - return column.Name; - else - return member.Member.Name; - } - - public static string GetTableName() - { - return GetTableName(typeof(T)); - } - - public static string GetTableName(Type type) - { - var column = type.GetCustomAttributes(false).OfType().FirstOrDefault(); - if (column != null) - return column.Name; - else - return type.Name; - } - - private static string GetTableName(MemberExpression expression) - { - return GetTableName(expression.Member.DeclaringType); - } - - private static BinaryExpression GetBinaryExpression(Expression expression) - { - if (expression is BinaryExpression) - return expression as BinaryExpression; - - throw new ArgumentException("Binary expression expected"); - } - - private static MemberExpression GetMemberExpression(Expression expression) - { - switch (expression.NodeType) - { - case ExpressionType.MemberAccess: - return expression as MemberExpression; - case ExpressionType.Convert: - return GetMemberExpression((expression as UnaryExpression).Operand); - } - - throw new ArgumentException("Member expression expected"); - } - - #endregion - } -} diff --git a/LambdaSqlBuilder/Resolver/LambdaResolverIsIn.cs b/LambdaSqlBuilder/Resolver/LambdaResolverIsIn.cs deleted file mode 100644 index 8007c19..0000000 --- a/LambdaSqlBuilder/Resolver/LambdaResolverIsIn.cs +++ /dev/null @@ -1,39 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; - -namespace LambdaSqlBuilder.Resolver -{ - partial class LambdaResolver - { - public void QueryByIsIn(Expression> expression, SqlLamBase sqlQuery) - { - var fieldName = GetColumnName(expression); - _builder.QueryByIsIn(GetTableName(), fieldName, sqlQuery); - } - - public void QueryByIsIn(Expression> expression, IEnumerable values) - { - var fieldName = GetColumnName(expression); - _builder.QueryByIsIn(GetTableName(), fieldName, values); - } - - public void QueryByNotIn(Expression> expression, SqlLamBase sqlQuery) - { - var fieldName = GetColumnName(expression); - _builder.Not(); - _builder.QueryByIsIn(GetTableName(), fieldName, sqlQuery); - } - - public void QueryByNotIn(Expression> expression, IEnumerable values) - { - var fieldName = GetColumnName(expression); - _builder.Not(); - _builder.QueryByIsIn(GetTableName(), fieldName, values); - } - } -} diff --git a/LambdaSqlBuilder/Resolver/LambdaResolverQuery.cs b/LambdaSqlBuilder/Resolver/LambdaResolverQuery.cs deleted file mode 100644 index 7e67afe..0000000 --- a/LambdaSqlBuilder/Resolver/LambdaResolverQuery.cs +++ /dev/null @@ -1,139 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Reflection; -using System.Text; -using LambdaSqlBuilder.Resolver.ExpressionTree; -using LambdaSqlBuilder.ValueObjects; -using System.Diagnostics; - -namespace LambdaSqlBuilder.Resolver -{ - partial class LambdaResolver - { - public void ResolveQuery(Expression> expression) - { - var expressionTree = ResolveQuery((dynamic)expression.Body); - BuildSql(expressionTree); - } - - private Node ResolveQuery(ConstantExpression constantExpression) - { - return new ValueNode() { Value = constantExpression.Value}; - } - - private Node ResolveQuery(UnaryExpression unaryExpression) - { - return new SingleOperationNode() - { - Operator = unaryExpression.NodeType, - Child = ResolveQuery((dynamic) unaryExpression.Operand) - }; - } - - private Node ResolveQuery(BinaryExpression binaryExpression) - { - return new OperationNode - { - Left = ResolveQuery((dynamic) binaryExpression.Left), - Operator = binaryExpression.NodeType, - Right = ResolveQuery((dynamic) binaryExpression.Right) - }; - } - - private Node ResolveQuery(MethodCallExpression callExpression) - { - LikeMethod callFunction; - if (Enum.TryParse(callExpression.Method.Name, true, out callFunction)) - { - var member = callExpression.Object as MemberExpression; - var fieldValue = (string)GetExpressionValue(callExpression.Arguments.First()); - - return new LikeNode() - { - MemberNode = new MemberNode() - { - TableName = GetTableName(member), - FieldName = GetColumnName(callExpression.Object) - }, - Method = callFunction, - Value = fieldValue - }; - } - else - { - var value = ResolveMethodCall(callExpression); - return new ValueNode() { Value = value }; - } - } - - private Node ResolveQuery(MemberExpression memberExpression, MemberExpression rootExpression = null) - { - rootExpression = rootExpression ?? memberExpression; - switch (memberExpression.Expression.NodeType) - { - case ExpressionType.Parameter: - return new MemberNode() - {TableName = GetTableName(rootExpression), FieldName = GetColumnName(rootExpression)}; - case ExpressionType.MemberAccess: - return ResolveQuery(memberExpression.Expression as MemberExpression, rootExpression); - case ExpressionType.Call: - case ExpressionType.Constant: - return new ValueNode() {Value = GetExpressionValue(rootExpression)}; - default: - throw new ArgumentException("Expected member expression"); - } - } - - #region Helpers - - private object GetExpressionValue(Expression expression) - { - switch (expression.NodeType) - { - case ExpressionType.Constant: - return (expression as ConstantExpression).Value; - case ExpressionType.Call: - return ResolveMethodCall(expression as MethodCallExpression); - case ExpressionType.MemberAccess: - var memberExpr = (expression as MemberExpression); - var obj = GetExpressionValue(memberExpr.Expression); - return ResolveValue((dynamic) memberExpr.Member, obj); - default: - throw new ArgumentException("Expected constant expression"); - } - } - - private object ResolveMethodCall(MethodCallExpression callExpression) - { - var arguments = callExpression.Arguments.Select(GetExpressionValue).ToArray(); - var obj = callExpression.Object != null ? GetExpressionValue(callExpression.Object) : arguments.First(); - - return callExpression.Method.Invoke(obj, arguments); - } - - private object ResolveValue(PropertyInfo property, object obj) - { - return property.GetValue(obj, null); - } - - private object ResolveValue(FieldInfo field, object obj) - { - return field.GetValue(obj); - } - - #endregion - - #region Fail functions - - private void ResolveQuery(Expression expression) - { - throw new ArgumentException(string.Format("The provided expression '{0}' is currently not supported", expression.NodeType)); - } - - #endregion - } -} diff --git a/LambdaSqlBuilder/Resolver/LambdaResolverSpec.cs b/LambdaSqlBuilder/Resolver/LambdaResolverSpec.cs deleted file mode 100644 index e3b27aa..0000000 --- a/LambdaSqlBuilder/Resolver/LambdaResolverSpec.cs +++ /dev/null @@ -1,94 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder.Resolver -{ - partial class LambdaResolver - { - public void Join(Expression> expression) - { - var joinExpression = GetBinaryExpression(expression.Body); - var leftExpression = GetMemberExpression(joinExpression.Left); - var rightExpression = GetMemberExpression(joinExpression.Right); - - Join(leftExpression, rightExpression); - } - - public void Join(Expression> leftExpression, Expression> rightExpression) - { - Join(GetMemberExpression(leftExpression.Body), GetMemberExpression(rightExpression.Body)); - } - - public void Join(MemberExpression leftExpression, MemberExpression rightExpression) - { - _builder.Join(GetTableName(), GetTableName(), GetColumnName(leftExpression), GetColumnName(rightExpression)); - } - - public void OrderBy(Expression> expression, bool desc = false) - { - var fieldName = GetColumnName(GetMemberExpression(expression.Body)); - _builder.OrderBy(GetTableName(), fieldName, desc); - } - - public void Select(Expression> expression) - { - Select(expression.Body); - } - - private void Select(Expression expression) - { - switch (expression.NodeType) - { - case ExpressionType.Parameter: - _builder.Select(GetTableName(expression.Type)); - break; - case ExpressionType.Convert: - case ExpressionType.MemberAccess: - Select(GetMemberExpression(expression)); - break; - case ExpressionType.New: - foreach (MemberExpression memberExp in (expression as NewExpression).Arguments) - Select(memberExp); - break; - default: - throw new ArgumentException("Invalid expression"); - } - } - - private void Select(MemberExpression expression) - { - if (expression.Type.IsClass && expression.Type != typeof(String)) - _builder.Select(GetTableName(expression.Type)); - else - _builder.Select(GetTableName(), GetColumnName(expression)); - } - - public void SelectWithFunction(Expression> expression, SelectFunction selectFunction) - { - SelectWithFunction(expression.Body, selectFunction); - } - - private void SelectWithFunction(Expression expression, SelectFunction selectFunction) - { - var fieldName = GetColumnName(GetMemberExpression(expression)); - _builder.Select(GetTableName(), fieldName, selectFunction); - } - - public void GroupBy(Expression> expression) - { - GroupBy(GetMemberExpression(expression.Body)); - } - - private void GroupBy(MemberExpression expression) - { - var fieldName = GetColumnName(GetMemberExpression(expression)); - _builder.GroupBy(GetTableName(), fieldName); - } - } -} diff --git a/LambdaSqlBuilder/Resolver/LambdaResolverTree.cs b/LambdaSqlBuilder/Resolver/LambdaResolverTree.cs deleted file mode 100644 index 6accf71..0000000 --- a/LambdaSqlBuilder/Resolver/LambdaResolverTree.cs +++ /dev/null @@ -1,147 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Linq.Expressions; -using System.Text; -using LambdaSqlBuilder.Resolver.ExpressionTree; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder.Resolver -{ - partial class LambdaResolver - { - void BuildSql(Node node) - { - BuildSql((dynamic)node); - } - - void BuildSql(LikeNode node) - { - if(node.Method == LikeMethod.Equals) - { - _builder.QueryByField(node.MemberNode.TableName, node.MemberNode.FieldName, - _operationDictionary[ExpressionType.Equal], node.Value); - } - else - { - string value = node.Value; - switch (node.Method) - { - case LikeMethod.StartsWith: - value = node.Value + "%"; - break; - case LikeMethod.EndsWith: - value = "%" + node.Value; - break; - case LikeMethod.Contains: - value = "%" + node.Value + "%"; - break; - } - _builder.QueryByFieldLike(node.MemberNode.TableName, node.MemberNode.FieldName, value); - } - } - - void BuildSql(OperationNode node) - { - BuildSql((dynamic)node.Left, (dynamic)node.Right, node.Operator); - } - - void BuildSql(MemberNode memberNode) - { - _builder.QueryByField(memberNode.TableName, memberNode.FieldName, _operationDictionary[ExpressionType.Equal], true); - } - - void BuildSql(SingleOperationNode node) - { - if(node.Operator == ExpressionType.Not) - _builder.Not(); - BuildSql(node.Child); - } - - void BuildSql(MemberNode memberNode, ValueNode valueNode, ExpressionType op) - { - if(valueNode.Value == null) - { - ResolveNullValue(memberNode, op); - } - else - { - _builder.QueryByField(memberNode.TableName, memberNode.FieldName, _operationDictionary[op], valueNode.Value); - } - } - - void BuildSql(ValueNode valueNode, MemberNode memberNode, ExpressionType op) - { - BuildSql(memberNode, valueNode, op); - } - - void BuildSql(MemberNode leftMember, MemberNode rightMember, ExpressionType op) - { - _builder.QueryByFieldComparison(leftMember.TableName, leftMember.FieldName, _operationDictionary[op], rightMember.TableName, rightMember.FieldName); - } - - void BuildSql(SingleOperationNode leftMember, Node rightMember, ExpressionType op) - { - if (leftMember.Operator == ExpressionType.Not) - BuildSql(leftMember as Node, rightMember, op); - else - BuildSql((dynamic)leftMember.Child, (dynamic)rightMember, op); - } - - void BuildSql(Node leftMember, SingleOperationNode rightMember, ExpressionType op) - { - BuildSql(rightMember, leftMember, op); - } - - void BuildSql(Node leftNode, Node rightNode, ExpressionType op) - { - _builder.BeginExpression(); - BuildSql((dynamic)leftNode); - ResolveOperation(op); - BuildSql((dynamic)rightNode); - _builder.EndExpression(); - } - - void ResolveNullValue(MemberNode memberNode, ExpressionType op) - { - switch (op) - { - case ExpressionType.Equal: - _builder.QueryByFieldNull(memberNode.TableName, memberNode.FieldName); - break; - case ExpressionType.NotEqual: - _builder.QueryByFieldNotNull(memberNode.TableName, memberNode.FieldName); - break; - } - } - - void ResolveSingleOperation(ExpressionType op) - { - switch (op) - { - case ExpressionType.Not: - _builder.Not(); - break; - } - } - - void ResolveOperation(ExpressionType op) - { - switch (op) - { - case ExpressionType.And: - case ExpressionType.AndAlso: - _builder.And(); - break; - case ExpressionType.Or: - case ExpressionType.OrElse: - _builder.Or(); - break; - default: - throw new ArgumentException(string.Format("Unrecognized binary expression operation '{0}'", op.ToString())); - } - } - } -} diff --git a/LambdaSqlBuilder/SqlLam.cs b/LambdaSqlBuilder/SqlLam.cs deleted file mode 100644 index 1d565e5..0000000 --- a/LambdaSqlBuilder/SqlLam.cs +++ /dev/null @@ -1,162 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq.Expressions; -using LambdaSqlBuilder.Builder; -using LambdaSqlBuilder.Resolver; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder -{ - /// - /// The single most important LambdaSqlBuilder class. Encapsulates the whole SQL building and lambda expression resolving logic. - /// Serves as a proxy to the underlying SQL builder and the lambda expression resolver. It should be used to continually build the SQL query - /// and then request the QueryString as well as the QueryParameters at the end. - /// - /// Entity type required for lambda expressions as well as for proper resolution of the table name and the column names - public class SqlLam : SqlLamBase - { - public SqlLam() - { - _builder = new SqlQueryBuilder(LambdaResolver.GetTableName(), _defaultAdapter); - _resolver = new LambdaResolver(_builder); - } - - public SqlLam(Expression> expression) : this() - { - Where(expression); - } - - internal SqlLam(SqlQueryBuilder builder, LambdaResolver resolver) - { - _builder = builder; - _resolver = resolver; - } - - public SqlLam Where(Expression> expression) - { - return And(expression); - } - - public SqlLam And(Expression> expression) - { - _builder.And(); - _resolver.ResolveQuery(expression); - return this; - } - - public SqlLam Or(Expression> expression) - { - _builder.Or(); - _resolver.ResolveQuery(expression); - return this; - } - - public SqlLam WhereIsIn(Expression> expression, SqlLamBase sqlQuery) - { - _builder.And(); - _resolver.QueryByIsIn(expression, sqlQuery); - return this; - } - - public SqlLam WhereIsIn(Expression> expression, IEnumerable values) - { - _builder.And(); - _resolver.QueryByIsIn(expression, values); - return this; - } - - public SqlLam WhereNotIn(Expression> expression, SqlLamBase sqlQuery) - { - _builder.And(); - _resolver.QueryByNotIn(expression, sqlQuery); - return this; - } - - public SqlLam WhereNotIn(Expression> expression, IEnumerable values) - { - _builder.And(); - _resolver.QueryByNotIn(expression, values); - return this; - } - - public SqlLam OrderBy(Expression> expression) - { - _resolver.OrderBy(expression); - return this; - } - - public SqlLam OrderByDescending(Expression> expression) - { - _resolver.OrderBy(expression, true); - return this; - } - - public SqlLam Select(params Expression>[] expressions) - { - foreach (var expression in expressions) - _resolver.Select(expression); - return this; - } - - public SqlLam SelectCount(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.COUNT); - return this; - } - - public SqlLam SelectDistinct(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.DISTINCT); - return this; - } - - public SqlLam SelectSum(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.SUM); - return this; - } - - public SqlLam SelectMax(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.MAX); - return this; - } - - public SqlLam SelectMin(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.MIN); - return this; - } - - public SqlLam SelectAverage(Expression> expression) - { - _resolver.SelectWithFunction(expression, SelectFunction.AVG); - return this; - } - - public SqlLam Join(SqlLam joinQuery, - Expression> primaryKeySelector, - Expression> foreignKeySelector, - Func selection) - { - var query = new SqlLam(_builder, _resolver); - _resolver.Join(primaryKeySelector, foreignKeySelector); - return query; - } - - public SqlLam Join(Expression> expression) - { - var joinQuery = new SqlLam(_builder, _resolver); - _resolver.Join(expression); - return joinQuery; - } - - public SqlLam GroupBy(Expression> expression) - { - _resolver.GroupBy(expression); - return this; - } - } -} diff --git a/LambdaSqlBuilder/SqlLamBase.cs b/LambdaSqlBuilder/SqlLamBase.cs deleted file mode 100644 index 586eff0..0000000 --- a/LambdaSqlBuilder/SqlLamBase.cs +++ /dev/null @@ -1,63 +0,0 @@ -/* License: http://www.apache.org/licenses/LICENSE-2.0 */ - -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Adapter; -using LambdaSqlBuilder.Builder; -using LambdaSqlBuilder.Resolver; -using LambdaSqlBuilder.ValueObjects; - -namespace LambdaSqlBuilder -{ - /// - /// Base functionality for the SqlLam class that is not related to any specific entity type - /// - public abstract class SqlLamBase - { - internal static ISqlAdapter _defaultAdapter = new SqlServer2012Adapter(); - internal SqlQueryBuilder _builder; - internal LambdaResolver _resolver; - - public SqlQueryBuilder SqlBuilder { get { return _builder; } } - - public string QueryString - { - get { return _builder.QueryString; } - } - - public string QueryStringPage(int pageSize, int? pageNumber = null) - { - return _builder.QueryStringPage(pageSize, pageNumber); - } - - public IDictionary QueryParameters - { - get { return _builder.Parameters; } - } - - public string[] SplitColumns - { - get { return _builder.SplitColumns.ToArray(); } - } - - public static void SetAdapter(SqlAdapter adapter) - { - _defaultAdapter = GetAdapterInstance(adapter); - } - - private static ISqlAdapter GetAdapterInstance(SqlAdapter adapter) - { - switch (adapter) - { - case SqlAdapter.SqlServer2008: - return new SqlServer2008Adapter(); - case SqlAdapter.SqlServer2012: - return new SqlServer2012Adapter(); - default: - throw new ArgumentException("The specified Sql Adapter was not recognized"); - } - } - } -} diff --git a/LambdaSqlBuilder/SqlLamColumnAttribute.cs b/LambdaSqlBuilder/SqlLamColumnAttribute.cs deleted file mode 100644 index 33ee71b..0000000 --- a/LambdaSqlBuilder/SqlLamColumnAttribute.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace LambdaSqlBuilder -{ - /// - /// Configures the name of the column related to this property. If the attribute is not specified, the property name is used instead. - /// - [AttributeUsage(AttributeTargets.Property)] - public class SqlLamColumnAttribute : Attribute - { - public string Name { get; set; } - } -} diff --git a/LambdaSqlBuilder/SqlLamTableAttribute.cs b/LambdaSqlBuilder/SqlLamTableAttribute.cs deleted file mode 100644 index e4f4f14..0000000 --- a/LambdaSqlBuilder/SqlLamTableAttribute.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace LambdaSqlBuilder -{ - /// - /// Configures the name of the db table related to this entity. If the attribute is not specified, the class name is used instead. - /// - [AttributeUsage(AttributeTargets.Class)] - public class SqlLamTableAttribute : Attribute - { - public string Name { get; set; } - } -} diff --git a/LambdaSqlBuilder/ValueObjects/LikeMethod.cs b/LambdaSqlBuilder/ValueObjects/LikeMethod.cs deleted file mode 100644 index 3cec8a2..0000000 --- a/LambdaSqlBuilder/ValueObjects/LikeMethod.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.ValueObjects -{ - /// - /// An enumeration of the supported string methods for the SQL LIKE statement. The item names should match the related string methods. - /// - public enum LikeMethod - { - StartsWith, - EndsWith, - Contains, - Equals - } -} diff --git a/LambdaSqlBuilder/ValueObjects/SelectFunction.cs b/LambdaSqlBuilder/ValueObjects/SelectFunction.cs deleted file mode 100644 index 2b3ef32..0000000 --- a/LambdaSqlBuilder/ValueObjects/SelectFunction.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; - -namespace LambdaSqlBuilder.ValueObjects -{ - /// - /// An enumeration of the supported aggregate SQL functions. The item names should match the related function names - /// - public enum SelectFunction - { - COUNT, - DISTINCT, - SUM, - MIN, - MAX, - AVG - } -} diff --git a/LambdaSqlBuilder/ValueObjects/SqlAdapter.cs b/LambdaSqlBuilder/ValueObjects/SqlAdapter.cs deleted file mode 100644 index 43bcdbb..0000000 --- a/LambdaSqlBuilder/ValueObjects/SqlAdapter.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using LambdaSqlBuilder.Adapter; - -namespace LambdaSqlBuilder.ValueObjects -{ - /// - /// An enumeration of the available SQL adapters. Can be used to set the backing database for db specific SQL syntax - /// - public enum SqlAdapter - { - SqlServer2008, - SqlServer2012 - } -} diff --git a/License.txt b/License.txt deleted file mode 100644 index 0f33352..0000000 --- a/License.txt +++ /dev/null @@ -1 +0,0 @@ -http://www.apache.org/licenses/LICENSE-2.0 \ No newline at end of file diff --git a/ProjectHome.md b/ProjectHome.md new file mode 100644 index 0000000..c766a8b --- /dev/null +++ b/ProjectHome.md @@ -0,0 +1,72 @@ +## Lambda SQL Builder is a neat .NET library for independent creation of SQL queries in a strongly typed fashion. ## + +# Support # +Apart from standard SQL queries, the currently supported SQL databases are SQL Server 2008 and SQL Server 2012. The minimum .NET version required is 4.0. + +# Motivation # +The inspiration for Lambda SQL Builder came from tools like **Linq2SQL**, **Entity Framework**, and **QueryOver** in NHibernate. I used to be a big fan of these ORMs, although they gave me some serious headaches from time to time. However, nothing lasts forever, and I have recently made a decision to join the new rising trend of using Micro-ORMs instead of those huge mighty frameworks. And I definately did not regret that. But I still felt like there was something missing, something that I had to sacrifice in order to gain the flexibility and performance back after years of using big ORMs. And I soon realized what this thing was: + +**_Using C# code to write my SQL queries._** + +No change tracking, no sessions, it was really just this single feature. I simply hate those SQL strings lying there in my application and forcing me to think twice anytime I want to refactor something. After some research, I have decided to write something on my own, something independent, something that would provide this single feature and nothing more, so I can use it along with **SQLCommand**, or with **Dapper**, or even with Nhibernate if it feels right. It is not my intension to cover the whole SQL world, however, I do believe that it will satisfy most of the common needs. It certainly does in my case, as I was already able to replace 99% of the queries that I needed in my recent projects. + +I will be glad if you like the tool. If you don’t, let me know why, so I can make it better. + +# Usage # +This basic example queries the database for products named „Tofu” using my favorite Micro-ORM called Dapper: +``` +var query = new SqlLam(p => p.ProductName == "Tofu"); +var results = Connection.Query(query.QueryString, query.QueryParameters); +``` + +Of course, you can also do this with SQLCommand and SqlDataReader without using any ORM: +``` +var query = new SqlLam(p => p.ProductName == "Tofu"); + +var selectCommand = new SqlCommand(query.QueryString, Connection); + +foreach (var param in query.QueryParameters) + selectCommand.Parameters.AddWithValue(param.Key, param.Value); + +var result = selectCommand.ExecuteReader(); +``` + +If you prefer using LINQ, you can write something like this: +``` +var query = from product in new SqlLam() + where product.ProductName == "Tofu" + select product; + +var results = Connection.Query(query.QueryString, query.QueryParameters) +``` + +As you can see the QueryString property will return the SQL string itself, while the QueryParameters property refers to a dictionary of SQL parameters. +Most of the time you will create a SqlLam object, call some methods on it, and then request the QueryString and the QueryParameters at the end. You can also call the methods in a chain, if you prefer. Here are some more complicated queries, so you get an idea of what is the tool capable of: +``` +var query = new SqlLam(p => !(p.City == "Seattle" || p.City == "Redmond")) + .Or(p => p.Title != "Sales Representative") + .OrderByDescending(p => p.FirstName); +``` +``` +var query = from product in new SqlLam() + join category in new SqlLam() + on product.CategoryId equals category.CategoryId + where product.ReorderLevel == 25 && category.CategoryName == "Beverages" + select product; +``` +``` +var subQuery = new SqlLam() + .WhereIsIn(c => c.CategoryName, new object[] { "Beverages", "Condiments" }) + .Select(p => p.CategoryId); + +var query = new SqlLam() + .Join((p, c) => p.CategoryId == c.CategoryId) + .WhereIsIn(c => c.CategoryId, subQuery); +``` + +Internally there is a Lambda Resolver that translates the C# code into SQL strings, and a SQL Builder, which collects the SQL strings and stores them as individual SQL clauses (Selection, Join, Order By,...). Everytime you call a method on the SqlLam object, it is translated into a SQL string, which is stored into the related SQL clause in the underlying SQL builder. If the expression contains variables, they are stored into the dictionary of SQL parameters. When requesting the QueryString, the SQL clauses are combined and returned as a single SQL statement. + +There are also additional SQL adapters in development, that should expand the support for database-specific SQL statements. + +# Reference # +There will be later a deeper description of various use cases. Make sure to check out the unit tests for more examples. \ No newline at end of file diff --git a/README.md b/README.md deleted file mode 100644 index 7e880ec..0000000 --- a/README.md +++ /dev/null @@ -1,4 +0,0 @@ -lambda-sql-builder -================== - -A small independent library that will let you use standard C# and Linq to produce SQL queries