|
From: <ric...@us...> - 2010-05-10 11:24:38
|
Revision: 4980
http://nhibernate.svn.sourceforge.net/nhibernate/?rev=4980&view=rev
Author: ricbrown
Date: 2010-05-10 11:24:31 +0000 (Mon, 10 May 2010)
Log Message:
-----------
Added IResultTransformer method to IQueryOver.
Modified Paths:
--------------
trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverOrderBuilder.cs
trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverProjectionBuilder.cs
trunk/nhibernate/src/NHibernate/Criterion/ProjectionsExtensions.cs
trunk/nhibernate/src/NHibernate/Criterion/QueryOver.cs
trunk/nhibernate/src/NHibernate/IQueryOver.cs
trunk/nhibernate/src/NHibernate/Impl/ExpressionProcessor.cs
trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/IntegrationFixture.cs
trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/LambdaFixtureBase.cs
trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/Model.cs
trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/ProjectionsFixture.cs
trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/QueryOverFixture.cs
Modified: trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverOrderBuilder.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverOrderBuilder.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverOrderBuilder.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -15,7 +15,7 @@
public QueryOverOrderBuilder(QueryOver<TRoot,TSubType> root, Expression<Func<TSubType, object>> path) : base(root, path)
{}
- public QueryOverOrderBuilder(QueryOver<TRoot,TSubType> root, Expression<Func<object>> path) : base(root, path)
+ public QueryOverOrderBuilder(QueryOver<TRoot,TSubType> root, Expression<Func<object>> path, bool isAlias) : base(root, path, isAlias)
{}
}
@@ -26,7 +26,7 @@
public IQueryOverOrderBuilder(IQueryOver<TRoot,TSubType> root, Expression<Func<TSubType, object>> path) : base(root, path)
{}
- public IQueryOverOrderBuilder(IQueryOver<TRoot,TSubType> root, Expression<Func<object>> path) : base(root, path)
+ public IQueryOverOrderBuilder(IQueryOver<TRoot,TSubType> root, Expression<Func<object>> path, bool isAlias) : base(root, path, isAlias)
{}
}
@@ -36,24 +36,27 @@
protected TReturn root;
protected LambdaExpression path;
+ protected bool isAlias;
protected QueryOverOrderBuilderBase(TReturn root, Expression<Func<TSubType, object>> path)
{
this.root = root;
this.path = path;
+ this.isAlias = false;
}
- protected QueryOverOrderBuilderBase(TReturn root, Expression<Func<object>> path)
+ protected QueryOverOrderBuilderBase(TReturn root, Expression<Func<object>> path, bool isAlias)
{
this.root = root;
this.path = path;
+ this.isAlias = isAlias;
}
public TReturn Asc
{
get
{
- this.root.UnderlyingCriteria.AddOrder(ExpressionProcessor.ProcessOrder(path, Order.Asc));
+ this.root.UnderlyingCriteria.AddOrder(ExpressionProcessor.ProcessOrder(path, Order.Asc, isAlias));
return this.root;
}
}
@@ -62,7 +65,7 @@
{
get
{
- this.root.UnderlyingCriteria.AddOrder(ExpressionProcessor.ProcessOrder(path, Order.Desc));
+ this.root.UnderlyingCriteria.AddOrder(ExpressionProcessor.ProcessOrder(path, Order.Desc, isAlias));
return this.root;
}
}
Modified: trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverProjectionBuilder.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverProjectionBuilder.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/Criterion/Lambda/QueryOverProjectionBuilder.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -46,7 +46,7 @@
/// </summary>
public QueryOverProjectionBuilder<T> WithAlias(Expression<Func<object>> alias)
{
- string aliasContainer = ExpressionProcessor.FindMemberExpression(alias.Body);
+ string aliasContainer = ExpressionProcessor.FindPropertyExpression(alias.Body);
lastProjection = Projections.Alias(lastProjection, aliasContainer);
return this;
}
Modified: trunk/nhibernate/src/NHibernate/Criterion/ProjectionsExtensions.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/Criterion/ProjectionsExtensions.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/Criterion/ProjectionsExtensions.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -16,7 +16,7 @@
public static IProjection WithAlias(this IProjection projection,
Expression<Func<object>> alias)
{
- string aliasContainer = ExpressionProcessor.FindMemberExpression(alias.Body);
+ string aliasContainer = ExpressionProcessor.FindPropertyExpression(alias.Body);
return Projections.Alias(projection, aliasContainer);
}
}
Modified: trunk/nhibernate/src/NHibernate/Criterion/QueryOver.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/Criterion/QueryOver.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/Criterion/QueryOver.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -7,6 +7,7 @@
using NHibernate.Engine;
using NHibernate.Impl;
using NHibernate.SqlCommand;
+using NHibernate.Transform;
namespace NHibernate.Criterion
{
@@ -330,9 +331,14 @@
public QueryOverOrderBuilder<TRoot,TSubType> OrderBy(Expression<Func<object>> path)
{
- return new QueryOverOrderBuilder<TRoot,TSubType>(this, path);
+ return new QueryOverOrderBuilder<TRoot,TSubType>(this, path, false);
}
+ public QueryOverOrderBuilder<TRoot,TSubType> OrderByAlias(Expression<Func<object>> path)
+ {
+ return new QueryOverOrderBuilder<TRoot,TSubType>(this, path, true);
+ }
+
public QueryOverOrderBuilder<TRoot,TSubType> ThenBy(Expression<Func<TSubType, object>> path)
{
return new QueryOverOrderBuilder<TRoot,TSubType>(this, path);
@@ -340,15 +346,26 @@
public QueryOverOrderBuilder<TRoot,TSubType> ThenBy(Expression<Func<object>> path)
{
- return new QueryOverOrderBuilder<TRoot,TSubType>(this, path);
+ return new QueryOverOrderBuilder<TRoot,TSubType>(this, path, false);
}
+ public QueryOverOrderBuilder<TRoot,TSubType> ThenByAlias(Expression<Func<object>> path)
+ {
+ return new QueryOverOrderBuilder<TRoot,TSubType>(this, path, true);
+ }
+
public QueryOver<TRoot,TSubType> ClearOrders()
{
criteria.ClearOrders();
return this;
}
+ public QueryOver<TRoot,TSubType> TransformUsing(IResultTransformer resultTransformer)
+ {
+ criteria.SetResultTransformer(resultTransformer);
+ return this;
+ }
+
public QueryOver<TRoot,TSubType> Skip(int firstResult)
{
criteria.SetFirstResult(firstResult);
@@ -671,17 +688,26 @@
{ return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path); }
IQueryOverOrderBuilder<TRoot,TSubType> IQueryOver<TRoot,TSubType>.OrderBy(Expression<Func<object>> path)
- { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path); }
+ { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path, false); }
+ IQueryOverOrderBuilder<TRoot,TSubType> IQueryOver<TRoot,TSubType>.OrderByAlias(Expression<Func<object>> path)
+ { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path, true); }
+
IQueryOverOrderBuilder<TRoot,TSubType> IQueryOver<TRoot,TSubType>.ThenBy(Expression<Func<TSubType, object>> path)
{ return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path); }
IQueryOverOrderBuilder<TRoot,TSubType> IQueryOver<TRoot,TSubType>.ThenBy(Expression<Func<object>> path)
- { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path); }
+ { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path, false); }
+ IQueryOverOrderBuilder<TRoot,TSubType> IQueryOver<TRoot,TSubType>.ThenByAlias(Expression<Func<object>> path)
+ { return new IQueryOverOrderBuilder<TRoot,TSubType>(this, path, true); }
+
IQueryOver<TRoot,TSubType> IQueryOver<TRoot, TSubType>.ClearOrders()
{ return ClearOrders(); }
+ IQueryOver<TRoot,TSubType> IQueryOver<TRoot,TSubType>.TransformUsing(IResultTransformer resultTransformer)
+ { return TransformUsing(resultTransformer); }
+
IQueryOver<TRoot,TSubType> IQueryOver<TRoot,TSubType>.Skip(int firstResult)
{ return Skip(firstResult); }
Modified: trunk/nhibernate/src/NHibernate/IQueryOver.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/IQueryOver.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/IQueryOver.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -6,6 +6,7 @@
using NHibernate.Criterion;
using NHibernate.Criterion.Lambda;
using NHibernate.SqlCommand;
+using NHibernate.Transform;
namespace NHibernate
{
@@ -262,6 +263,13 @@
IQueryOverOrderBuilder<TRoot,TSubType> OrderBy(Expression<Func<object>> path);
/// <summary>
+ /// Add order for an aliased projection expressed as a lambda expression
+ /// </summary>
+ /// <param name="path">Lambda expression</param>
+ /// <returns>criteria instance</returns>
+ IQueryOverOrderBuilder<TRoot,TSubType> OrderByAlias(Expression<Func<object>> path);
+
+ /// <summary>
/// Add order expressed as a lambda expression
/// </summary>
/// <param name="path">Lambda expression</param>
@@ -276,11 +284,23 @@
IQueryOverOrderBuilder<TRoot,TSubType> ThenBy(Expression<Func<object>> path);
/// <summary>
+ /// Add order for an aliased projection expressed as a lambda expression
+ /// </summary>
+ /// <param name="path">Lambda expression</param>
+ /// <returns>criteria instance</returns>
+ IQueryOverOrderBuilder<TRoot,TSubType> ThenByAlias(Expression<Func<object>> path);
+
+ /// <summary>
/// Clear all orders from the query.
/// </summary>
IQueryOver<TRoot, TSubType> ClearOrders();
/// <summary>
+ /// Transform the results using the supplied IResultTransformer
+ /// </summary>
+ IQueryOver<TRoot,TSubType> TransformUsing(IResultTransformer resultTransformer);
+
+ /// <summary>
/// Set the first result to be retrieved
/// </summary>
/// <param name="firstResult"></param>
Modified: trunk/nhibernate/src/NHibernate/Impl/ExpressionProcessor.cs
===================================================================
--- trunk/nhibernate/src/NHibernate/Impl/ExpressionProcessor.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate/Impl/ExpressionProcessor.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -174,6 +174,17 @@
}
/// <summary>
+ /// Retrieves the name of the property from a member expression (without leading member access)
+ /// </summary>
+ public static string FindPropertyExpression(Expression expression)
+ {
+ string memberExpression = FindMemberExpression(expression);
+ int periodPosition = memberExpression.LastIndexOf('.') + 1;
+ string property = (periodPosition <= 0) ? memberExpression : memberExpression.Substring(periodPosition);
+ return property;
+ }
+
+ /// <summary>
/// Retrieves a detached criteria from an appropriate lambda expression
/// </summary>
/// <param name="expression">Expresson for detached criteria using .As<>() extension"/></param>
@@ -458,11 +469,13 @@
/// </summary>
/// <param name="expression">The lambda expression to convert</param>
/// <param name="orderDelegate">The appropriate order delegate (order direction)</param>
+ /// <param name="isAlias">Indicates if the path is an aliased projection</param>
/// <returns>NHibernate Order</returns>
public static Order ProcessOrder( LambdaExpression expression,
- Func<string, Order> orderDelegate)
+ Func<string, Order> orderDelegate,
+ bool isAlias)
{
- string property = FindMemberExpression(expression.Body);
+ string property = isAlias ? FindPropertyExpression(expression.Body) : FindMemberExpression(expression.Body);
Order order = orderDelegate(property);
return order;
}
Modified: trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/IntegrationFixture.cs
===================================================================
--- trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/IntegrationFixture.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/IntegrationFixture.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -146,6 +146,38 @@
}
[Test]
+ public void Project_TransformToDto()
+ {
+ using (ISession s = OpenSession())
+ using (ITransaction t = s.BeginTransaction())
+ {
+ s.Save(new Person() { Name = "test person 1", Age = 20 });
+ s.Save(new Person() { Name = "test person 1", Age = 30 });
+ s.Save(new Person() { Name = "test person 2", Age = 40 });
+ t.Commit();
+ }
+
+ using (ISession s = OpenSession())
+ {
+ PersonSummary summary = null;
+ var actual =
+ s.QueryOver<Person>()
+ .Select(list => list
+ .SelectGroup(p => p.Name).WithAlias(() => summary.Name)
+ .Select(Projections.RowCount()).WithAlias(() => summary.Count))
+ .OrderByAlias(() => summary.Name).Asc
+ .TransformUsing(Transformers.AliasToBean<PersonSummary>())
+ .List<PersonSummary>();
+
+ Assert.That(actual.Count, Is.EqualTo(2));
+ Assert.That(actual[0].Name, Is.EqualTo("test person 1"));
+ Assert.That(actual[0].Count, Is.EqualTo(2));
+ Assert.That(actual[1].Name, Is.EqualTo("test person 2"));
+ Assert.That(actual[1].Count, Is.EqualTo(1));
+ }
+ }
+
+ [Test]
public void UniqueResult()
{
using (ISession s = OpenSession())
@@ -244,7 +276,7 @@
.Select(list => list
.Select(p => p.Name)
.SelectSubQuery(childCountQuery).WithAlias(() => childCountAlias))
- .OrderBy(() => childCountAlias).Desc
+ .OrderByAlias(() => childCountAlias).Desc
.List<object[]>()
.Select(props => new {
Name = (string)props[0],
Modified: trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/LambdaFixtureBase.cs
===================================================================
--- trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/LambdaFixtureBase.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/LambdaFixtureBase.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -157,6 +157,13 @@
return;
}
+ if (expected is ConstructorInfo)
+ {
+ Assert.AreEqual(expected.ToString(), actual.ToString());
+ _fieldPath.Pop();
+ return;
+ }
+
while (expectedType != null)
{
foreach (FieldInfo fieldInfo in expectedType.GetFields(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic))
Modified: trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/Model.cs
===================================================================
--- trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/Model.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/Model.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -75,5 +75,11 @@
}
+ public class PersonSummary
+ {
+ public string Name { get; set; }
+ public int Count { get; set; }
+ }
+
}
Modified: trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/ProjectionsFixture.cs
===================================================================
--- trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/ProjectionsFixture.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/ProjectionsFixture.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -41,7 +41,7 @@
.SetProjection(Projections.ProjectionList()
.Add(Projections.Alias(Projections.Avg("Age"), "personAgeProjectionAlias"))
.Add(Projections.Avg("Age"), "personAgeProjectionAlias")
- .Add(Projections.Avg("personAlias.Age"))
+ .Add(Projections.Avg("personAlias.Age"), "Age")
.Add(Projections.Count("Age"))
.Add(Projections.Count("personAlias.Age"))
.Add(Projections.CountDistinct("Age"))
@@ -65,7 +65,7 @@
.Select(Projections.ProjectionList()
.Add(Projections.Avg<Person>(p => p.Age).WithAlias(() => personAgeProjectionAlias))
.Add(Projections.Avg<Person>(p => p.Age), () => personAgeProjectionAlias)
- .Add(Projections.Avg(() => personAlias.Age))
+ .Add(Projections.Avg(() => personAlias.Age).WithAlias(() => personAlias.Age))
.Add(Projections.Count<Person>(p => p.Age))
.Add(Projections.Count(() => personAlias.Age))
.Add(Projections.CountDistinct<Person>(p => p.Age))
@@ -93,7 +93,7 @@
.SetProjection(Projections.ProjectionList()
.Add(Projections.Alias(Projections.Avg("Age"), "personAgeProjectionAlias"))
.Add(Projections.Avg("Age"))
- .Add(Projections.Avg("personAlias.Age"))
+ .Add(Projections.Avg("personAlias.Age"), "Age")
.Add(Projections.Count("Age"))
.Add(Projections.Count("personAlias.Age"))
.Add(Projections.CountDistinct("Age"))
@@ -117,7 +117,7 @@
.Select(list => list
.SelectAvg(p => p.Age).WithAlias(() => personAgeProjectionAlias)
.Select(Projections.Avg("Age")) // allows private properties
- .SelectAvg(() => personAlias.Age)
+ .SelectAvg(() => personAlias.Age).WithAlias(() => personAlias.Age)
.SelectCount(p => p.Age)
.SelectCount(() => personAlias.Age)
.SelectCountDistinct(p => p.Age)
Modified: trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/QueryOverFixture.cs
===================================================================
--- trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/QueryOverFixture.cs 2010-05-07 22:44:13 UTC (rev 4979)
+++ trunk/nhibernate/src/NHibernate.Test/Criteria/Lambda/QueryOverFixture.cs 2010-05-10 11:24:31 UTC (rev 4980)
@@ -354,15 +354,20 @@
.AddOrder(Order.Asc("Name"))
.AddOrder(Order.Desc("Age"))
.AddOrder(Order.Desc("personAlias.Name"))
- .AddOrder(Order.Asc("personAlias.Age"));
+ .AddOrder(Order.Asc("personAlias.Age"))
+ .AddOrder(Order.Asc("summary"))
+ .AddOrder(Order.Desc("Count"));
Person personAlias = null;
+ PersonSummary summary = null;
IQueryOver<Person> actual =
CreateTestQueryOver<Person>(() => personAlias)
.OrderBy(p => p.Name).Asc
.ThenBy(p => p.Age).Desc
.ThenBy(() => personAlias.Name).Desc
- .ThenBy(() => personAlias.Age).Asc;
+ .ThenBy(() => personAlias.Age).Asc
+ .OrderByAlias(() => summary).Asc
+ .ThenByAlias(() => summary.Count).Desc;
AssertCriteriaAreEqual(expected, actual);
}
@@ -454,6 +459,20 @@
}
[Test]
+ public void ResultTransformer()
+ {
+ ICriteria expected =
+ CreateTestCriteria(typeof(Person))
+ .SetResultTransformer(Transformers.AliasToBean<Person>());
+
+ IQueryOver<Person> actual =
+ CreateTestQueryOver<Person>()
+ .TransformUsing(Transformers.AliasToBean<Person>());
+
+ AssertCriteriaAreEqual(expected, actual);
+ }
+
+ [Test]
public void LockAlias()
{
ICriteria expected =
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|