/* * DynamORM - Dynamic Object-Relational Mapping library. * Copyright (c) 2012-2026, Grzegorz Russek (grzegorz.russek@gmail.com) * All rights reserved. */ using System.Text.RegularExpressions; using DynamORM.Tests.Helpers; using DynamORM.TypedSql; using NUnit.Framework; namespace DynamORM.Tests.TypedSql { [TestFixture] public class TypedSqlScopeDslTests : TestsBase { private static string NormalizeSql(string sql) { int index = 0; return Regex.Replace(sql, @"\[\$[^\]]+\]", m => string.Format("[${0}]", index++)); } [SetUp] public void SetUp() { CreateTestDatabase(); CreateDynamicDatabase( DynamicDatabaseOptions.SingleConnection | DynamicDatabaseOptions.SingleTransaction | DynamicDatabaseOptions.SupportLimitOffset | DynamicDatabaseOptions.SupportNoLock); } [TearDown] public void TearDown() { DestroyDynamicDatabase(); DestroyTestDatabase(); } [Test] public void TestScopeBuilderSupportsTwoTableSelectAndWhere() { var cmd = Database.FromTypedScope("u") .Join(j => j.Left().As("c").OnSql((u, c) => u.Col(x => x.IdUser).Eq(c.Col(x => x.UserId)))) .SelectSql( (u, c) => u.Col(x => x.IdUser).As("user_id"), (u, c) => c.Col(x => x.Users).As("users")) .WhereSql((u, c) => u.Col(x => x.Active).Eq(1).And(c.Col(x => x.Deleted).Eq(0))); Assert.AreEqual( "SELECT u.\"Id_User\" AS \"user_id\", c.\"Users\" AS \"users\" FROM \"dbo\".\"Users\" AS u LEFT JOIN \"dbo\".\"UserClients\" AS c ON (u.\"Id_User\" = c.\"User_Id\") WHERE ((u.\"Active\" = [$0]) AND (c.\"Deleted\" = [$1]))", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsJoinOnPreviousJoinedAlias() { var cmd = Database.FromTypedScope("u") .Join(j => j.Left().As("c").OnSql((u, c) => u.Col(x => x.IdUser).Eq(c.Col(x => x.UserId)))) .Join(j => j.Left().As("r").OnSql((u, c, r) => c.Col(x => x.UserId).Eq(r.Col(x => x.UserId)))) .SelectSql( (u, c, r) => u.Col(x => x.IdUser), (u, c, r) => c.Col(x => x.Users).As("users"), (u, c, r) => r.Col(x => x.RoleName).As("role_name")) .OrderBySql( (u, c, r) => c.Col(x => x.Users).Asc(), (u, c, r) => r.Col(x => x.RoleName).Desc()); Assert.AreEqual( "SELECT u.\"Id_User\", c.\"Users\" AS \"users\", r.\"Role_Name\" AS \"role_name\" FROM \"dbo\".\"Users\" AS u LEFT JOIN \"dbo\".\"UserClients\" AS c ON (u.\"Id_User\" = c.\"User_Id\") LEFT JOIN \"dbo\".\"UserRoles\" AS r ON (c.\"User_Id\" = r.\"User_Id\") ORDER BY c.\"Users\" ASC, r.\"Role_Name\" DESC", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsCustomJoinTypeAndNoLock() { var cmd = Database.FromTypedScope("u") .Join(j => j.Type("CROSS APPLY").As("c").NoLock()) .SelectSql( (u, c) => u.Col(x => x.IdUser), (u, c) => c.All()); Assert.AreEqual( "SELECT u.\"Id_User\", c.* FROM \"dbo\".\"Users\" AS u CROSS APPLY \"dbo\".\"UserClients\" AS c WITH(NOLOCK)", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsHavingAcrossFourJoinedTables() { var cmd = Database.FromTypedScope("u") .Join(j => j.Left().As("c").OnSql((u, c) => u.Col(x => x.IdUser).Eq(c.Col(x => x.UserId)))) .Join(j => j.Left().As("r").OnSql((u, c, r) => u.Col(x => x.IdUser).Eq(r.Col(x => x.UserId)))) .Join(j => j.Left().As("g").OnSql((u, c, r, g) => r.Col(x => x.UserId).Eq(g.Col(x => x.UserId)))) .SelectSql( (u, c, r, g) => u.Col(x => x.IdUser), (u, c, r, g) => Sql.Count(g.Col(x => x.RegionId)).As("region_count")) .GroupBySql((u, c, r, g) => u.Col(x => x.IdUser)) .HavingSql((u, c, r, g) => Sql.Count(g.Col(x => x.RegionId)).Gt(0)); Assert.AreEqual( "SELECT u.\"Id_User\", COUNT(g.\"Region_Id\") AS \"region_count\" FROM \"dbo\".\"Users\" AS u LEFT JOIN \"dbo\".\"UserClients\" AS c ON (u.\"Id_User\" = c.\"User_Id\") LEFT JOIN \"dbo\".\"UserRoles\" AS r ON (u.\"Id_User\" = r.\"User_Id\") LEFT JOIN \"dbo\".\"UserRegions\" AS g ON (r.\"User_Id\" = g.\"User_Id\") GROUP BY u.\"Id_User\" HAVING (COUNT(g.\"Region_Id\") > [$0])", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsFiveTypedTables() { var cmd = Database.FromTypedScope("u") .Join(j => j.Left().As("c").OnSql((u, c) => u.Col(x => x.IdUser).Eq(c.Col(x => x.UserId)))) .Join(j => j.Left().As("r").OnSql((u, c, r) => c.Col(x => x.UserId).Eq(r.Col(x => x.UserId)))) .Join(j => j.Left().As("g").OnSql((u, c, r, g) => r.Col(x => x.UserId).Eq(g.Col(x => x.UserId)))) .Join(j => j.Left().As("d").OnSql((u, c, r, g, d) => g.Col(x => x.RegionId).Eq(d.Col(x => x.RegionId)))) .SelectSql( (u, c, r, g, d) => u.Col(x => x.IdUser).As("user_id"), (u, c, r, g, d) => d.Col(x => x.DepartmentName).As("department_name")) .WhereSql((u, c, r, g, d) => d.Col(x => x.DepartmentId).Gt(0)) .OrderBySql((u, c, r, g, d) => d.Col(x => x.DepartmentName).Asc()); Assert.AreEqual( "SELECT u.\"Id_User\" AS \"user_id\", d.\"Department_Name\" AS \"department_name\" FROM \"dbo\".\"Users\" AS u LEFT JOIN \"dbo\".\"UserClients\" AS c ON (u.\"Id_User\" = c.\"User_Id\") LEFT JOIN \"dbo\".\"UserRoles\" AS r ON (c.\"User_Id\" = r.\"User_Id\") LEFT JOIN \"dbo\".\"UserRegions\" AS g ON (r.\"User_Id\" = g.\"User_Id\") LEFT JOIN \"dbo\".\"UserDepartments\" AS d ON (g.\"Region_Id\" = d.\"Region_Id\") WHERE (d.\"Department_Id\" > [$0]) ORDER BY d.\"Department_Name\" ASC", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsTenTypedTables() { var cmd = Database.FromTypedScope("a") .Join(j => j.Left().As("b").OnSql((a, b) => a.Col(x => x.Id).Eq(b.Col(x => x.Id)))) .Join(j => j.Left().As("c").OnSql((a, b, c) => b.Col(x => x.Id).Eq(c.Col(x => x.Id)))) .Join(j => j.Left().As("d").OnSql((a, b, c, d) => c.Col(x => x.Id).Eq(d.Col(x => x.Id)))) .Join(j => j.Left().As("e").OnSql((a, b, c, d, e) => d.Col(x => x.Id).Eq(e.Col(x => x.Id)))) .Join(j => j.Left().As("f").OnSql((a, b, c, d, e, f) => e.Col(x => x.Id).Eq(f.Col(x => x.Id)))) .Join(j => j.Left().As("g").OnSql((a, b, c, d, e, f, g) => f.Col(x => x.Id).Eq(g.Col(x => x.Id)))) .Join(j => j.Left().As("h").OnSql((a, b, c, d, e, f, g, h) => g.Col(x => x.Id).Eq(h.Col(x => x.Id)))) .Join(j => j.Left().As("i").OnSql((a, b, c, d, e, f, g, h, i) => h.Col(x => x.Id).Eq(i.Col(x => x.Id)))) .Join(j => j.Left().As("j").OnSql((a, b, c, d, e, f, g, h, i, j) => i.Col(x => x.Id).Eq(j.Col(x => x.Id)))) .SelectSql( (a, b, c, d, e, f, g, h, i, j) => a.Col(x => x.Id).As("root_id"), (a, b, c, d, e, f, g, h, i, j) => j.Col(x => x.Code).As("last_code")) .WhereSql((a, b, c, d, e, f, g, h, i, j) => j.Col(x => x.Code).IsNotNull()) .OrderBySql((a, b, c, d, e, f, g, h, i, j) => j.Col(x => x.Code).Asc()); Assert.AreEqual( "SELECT a.\"id_user\" AS \"root_id\", j.\"user_code\" AS \"last_code\" FROM \"sample_users\" AS a LEFT JOIN \"sample_users\" AS b ON (a.\"id_user\" = b.\"id_user\") LEFT JOIN \"sample_users\" AS c ON (b.\"id_user\" = c.\"id_user\") LEFT JOIN \"sample_users\" AS d ON (c.\"id_user\" = d.\"id_user\") LEFT JOIN \"sample_users\" AS e ON (d.\"id_user\" = e.\"id_user\") LEFT JOIN \"sample_users\" AS f ON (e.\"id_user\" = f.\"id_user\") LEFT JOIN \"sample_users\" AS g ON (f.\"id_user\" = g.\"id_user\") LEFT JOIN \"sample_users\" AS h ON (g.\"id_user\" = h.\"id_user\") LEFT JOIN \"sample_users\" AS i ON (h.\"id_user\" = i.\"id_user\") LEFT JOIN \"sample_users\" AS j ON (i.\"id_user\" = j.\"id_user\") WHERE (j.\"user_code\" IS NOT NULL) ORDER BY j.\"user_code\" ASC", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeBuilderSupportsSixteenTypedTables() { var cmd = Database.FromTypedScope("a") .Join(j => j.Left().As("b").OnSql((a, b) => a.Col(x => x.Id).Eq(b.Col(x => x.Id)))) .Join(j => j.Left().As("c").OnSql((a, b, c) => b.Col(x => x.Id).Eq(c.Col(x => x.Id)))) .Join(j => j.Left().As("d").OnSql((a, b, c, d) => c.Col(x => x.Id).Eq(d.Col(x => x.Id)))) .Join(j => j.Left().As("e").OnSql((a, b, c, d, e) => d.Col(x => x.Id).Eq(e.Col(x => x.Id)))) .Join(j => j.Left().As("f").OnSql((a, b, c, d, e, f) => e.Col(x => x.Id).Eq(f.Col(x => x.Id)))) .Join(j => j.Left().As("g").OnSql((a, b, c, d, e, f, g) => f.Col(x => x.Id).Eq(g.Col(x => x.Id)))) .Join(j => j.Left().As("h").OnSql((a, b, c, d, e, f, g, h) => g.Col(x => x.Id).Eq(h.Col(x => x.Id)))) .Join(j => j.Left().As("i").OnSql((a, b, c, d, e, f, g, h, i) => h.Col(x => x.Id).Eq(i.Col(x => x.Id)))) .Join(j => j.Left().As("j").OnSql((a, b, c, d, e, f, g, h, i, j) => i.Col(x => x.Id).Eq(j.Col(x => x.Id)))) .Join(j => j.Left().As("k").OnSql((a, b, c, d, e, f, g, h, i, j, k) => j.Col(x => x.Id).Eq(k.Col(x => x.Id)))) .Join(j => j.Left().As("l").OnSql((a, b, c, d, e, f, g, h, i, j, k, l) => k.Col(x => x.Id).Eq(l.Col(x => x.Id)))) .Join(j => j.Left().As("m").OnSql((a, b, c, d, e, f, g, h, i, j, k, l, m) => l.Col(x => x.Id).Eq(m.Col(x => x.Id)))) .Join(j => j.Left().As("n").OnSql((a, b, c, d, e, f, g, h, i, j, k, l, m, n) => m.Col(x => x.Id).Eq(n.Col(x => x.Id)))) .Join(j => j.Left().As("o").OnSql((a, b, c, d, e, f, g, h, i, j, k, l, m, n, o) => n.Col(x => x.Id).Eq(o.Col(x => x.Id)))) .Join(j => j.Left().As("p").OnSql((a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) => o.Col(x => x.Id).Eq(p.Col(x => x.Id)))) .SelectSql( (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) => a.Col(x => x.Id).As("root_id"), (a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) => p.Col(x => x.Code).As("tail_code")) .WhereSql((a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p) => p.Col(x => x.Code).IsNotNull()); Assert.AreEqual( "SELECT a.\"id_user\" AS \"root_id\", p.\"user_code\" AS \"tail_code\" FROM \"sample_users\" AS a LEFT JOIN \"sample_users\" AS b ON (a.\"id_user\" = b.\"id_user\") LEFT JOIN \"sample_users\" AS c ON (b.\"id_user\" = c.\"id_user\") LEFT JOIN \"sample_users\" AS d ON (c.\"id_user\" = d.\"id_user\") LEFT JOIN \"sample_users\" AS e ON (d.\"id_user\" = e.\"id_user\") LEFT JOIN \"sample_users\" AS f ON (e.\"id_user\" = f.\"id_user\") LEFT JOIN \"sample_users\" AS g ON (f.\"id_user\" = g.\"id_user\") LEFT JOIN \"sample_users\" AS h ON (g.\"id_user\" = h.\"id_user\") LEFT JOIN \"sample_users\" AS i ON (h.\"id_user\" = i.\"id_user\") LEFT JOIN \"sample_users\" AS j ON (i.\"id_user\" = j.\"id_user\") LEFT JOIN \"sample_users\" AS k ON (j.\"id_user\" = k.\"id_user\") LEFT JOIN \"sample_users\" AS l ON (k.\"id_user\" = l.\"id_user\") LEFT JOIN \"sample_users\" AS m ON (l.\"id_user\" = m.\"id_user\") LEFT JOIN \"sample_users\" AS n ON (m.\"id_user\" = n.\"id_user\") LEFT JOIN \"sample_users\" AS o ON (n.\"id_user\" = o.\"id_user\") LEFT JOIN \"sample_users\" AS p ON (o.\"id_user\" = p.\"id_user\") WHERE (p.\"user_code\" IS NOT NULL)", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeSubQueryHelperSupportsScopedJoinChain() { var cmd = Database.FromTyped("u") .SelectSql(u => Sql.SubQueryScope( Database, sq => sq .Join(j => j.Left().As("c").OnSql((x, c) => x.Col(a => a.IdUser).Eq(c.Col(a => a.UserId)))) .Join(j => j.Left().As("r").OnSql((x, c, r) => c.Col(a => a.UserId).Eq(r.Col(a => a.UserId)))) .SelectSql((x, c, r) => r.Col(a => a.RoleName)), "x").As("role_name")); Assert.AreEqual( "SELECT (SELECT r.\"Role_Name\" FROM \"dbo\".\"Users\" AS x LEFT JOIN \"dbo\".\"UserClients\" AS c ON (x.\"Id_User\" = c.\"User_Id\") LEFT JOIN \"dbo\".\"UserRoles\" AS r ON (c.\"User_Id\" = r.\"User_Id\")) AS \"role_name\" FROM \"sample_users\" AS u", NormalizeSql(cmd.CommandText())); } [Test] public void TestScopeExistsHelperSupportsScopedJoinChain() { var cmd = Database.FromTyped("u") .WhereSql(u => Sql.ExistsScope( Database, sq => sq .Join(j => j.Left().As("c").OnSql((x, c) => x.Col(a => a.IdUser).Eq(c.Col(a => a.UserId)))) .Join(j => j.Left().As("r").OnSql((x, c, r) => c.Col(a => a.UserId).Eq(r.Col(a => a.UserId)))) .SelectSql((x, c, r) => r.Col(a => a.RoleId)), "x")) .SelectSql(u => u.Col(x => x.Id)); Assert.AreEqual( "SELECT u.\"id_user\" FROM \"sample_users\" AS u WHERE (EXISTS (SELECT r.\"Role_Id\" FROM \"dbo\".\"Users\" AS x LEFT JOIN \"dbo\".\"UserClients\" AS c ON (x.\"Id_User\" = c.\"User_Id\") LEFT JOIN \"dbo\".\"UserRoles\" AS r ON (c.\"User_Id\" = r.\"User_Id\")))", NormalizeSql(cmd.CommandText())); } } }