You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ibatis.apache.org by gb...@apache.org on 2007/01/04 22:28:11 UTC
svn commit: r492753 - in /ibatis/trunk/cs/mapper:
IBatisNet.DataMapper.Test/Domain/
IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/
IBatisNet.DataMapper.Test/NUnit/SqlMapTests/
IBatisNet.DataMapper/MappedStatements/PropertStrategy/
IBatisNet.DataMapper...
Author: gbayon
Date: Thu Jan 4 13:28:10 2007
New Revision: 492753
URL: http://svn.apache.org/viewvc?view=rev&rev=492753
Log:
- Fixed for iIBATISNET-182 : Allow lazy load on simple class
Modified:
ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Account.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Order.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/Order.xml
ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/NUnit/SqlMapTests/StatementTest.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectGenericListStrategy.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectListStrategy.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectObjectStrategy.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyFactoryBuilder.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadInterceptor.cs
ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadProxyFactory.cs
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Account.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Account.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Account.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Account.cs Thu Jan 4 13:28:10 2007
@@ -35,7 +35,7 @@
_document = document;
}
- public int Id
+ public virtual int Id
{
get { return id; }
set { id = value; }
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Order.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Order.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Order.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Domain/Order.cs Thu Jan 4 13:28:10 2007
@@ -146,26 +146,14 @@
public string City
{
- get
- {
- return _city;
- }
- set
- {
- _city = value;
- }
+ get { return _city; }
+ set { _city = value; }
}
public string Street
{
- get
- {
- return _street;
- }
- set
- {
- _street = value;
- }
+ get { return _street; }
+ set { _street = value; }
}
public string CardExpiry
@@ -204,16 +192,10 @@
}
}
- public Account Account
+ public virtual Account Account
{
- get
- {
- return _account;
- }
- set
- {
- _account = value;
- }
+ get { return _account; }
+ set { _account = value; }
}
public int Id
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/Order.xml
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/Order.xml?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/Order.xml (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/Maps/MSSQL/SqlClient/Order.xml Thu Jan 4 13:28:10 2007
@@ -151,6 +151,19 @@
<result property="Province" column="Order_Province"/>
<result property="PostalCode" column="Order_PostalCode"/>
</resultMap>
+
+ <resultMap id="order-JIRA182" class="Order" >
+ <result property="Id" column="Order_ID"/>
+ <result property="Account" column="Account_ID" lazyLoad="true" select="GetAccountViaColumnName"/>
+ <result property="Date" column="Order_Date"/>
+ <result property="CardExpiry" column="Order_CardExpiry"/>
+ <result property="CardType" column="Order_CardType"/>
+ <result property="CardNumber" column="Order_CardNumber"/>
+ <result property="Street" column="Order_Street"/>
+ <result property="City" column="Order_City"/>
+ <result property="Province" column="Order_Province"/>
+ <result property="PostalCode" column="Order_PostalCode"/>
+ </resultMap>
<resultMap id="credit-card-result" class="string">
<result property="value" column="Order_CardNumber"/>
@@ -772,34 +785,32 @@
<select id="GetOrderConstructor8"
parameterClass="Integer"
resultMap="order-result-constructor8">
- select
- Order_ID,
- Order_Date,
- Order_CardExpiry,
- Order_CardType,
- Order_CardNumber,
- Order_Street,
- Order_City,
- Order_Province,
- Order_PostalCode,
- acc.Account_ID,
- acc.Account_FirstName,
- acc.Account_LastName,
- acc.Account_Email,
- acc.Account_Banner_Option,
- acc.Account_Cart_Option
- from Orders as ord
- LEFT OUTER JOIN Accounts as acc on acc.Account_ID = ord.Account_ID
- where Order_ID = #value#
- </select>
-
-
+ select
+ Order_ID,
+ Order_Date,
+ Order_CardExpiry,
+ Order_CardType,
+ Order_CardNumber,
+ Order_Street,
+ Order_City,
+ Order_Province,
+ Order_PostalCode,
+ acc.Account_ID,
+ acc.Account_FirstName,
+ acc.Account_LastName,
+ acc.Account_Email,
+ acc.Account_Banner_Option,
+ acc.Account_Cart_Option
+ from Orders as ord
+ LEFT OUTER JOIN Accounts as acc on acc.Account_ID = ord.Account_ID
+ where Order_ID = #value#
+ </select>
- <select id="GetOrderConstructor9"
- extends="GetOrderConstructor8"
- parameterClass="Integer"
- resultMap="order-joined-with-account-constructor">
- </select>
+ <select id="GetOrderConstructor9"
+ extends="GetOrderConstructor8"
+ parameterClass="Integer"
+ resultMap="order-joined-with-account-constructor">
+ </select>
<select id="GetOrderConstructor10"
parameterClass="Integer"
@@ -823,8 +834,26 @@
from Orders as ord
LEFT OUTER JOIN Accounts as acc on acc.Account_ID = ord.Account_ID
where Order_ID = #value#
- </select>
-
+ </select>
+
+ <select id="JIRA182"
+ parameterClass="Integer"
+ resultMap="order-JIRA182">
+ select
+ Order_ID,
+ Order_Date,
+ Order_CardExpiry,
+ Order_CardType,
+ Order_CardNumber,
+ Order_Street,
+ Order_City,
+ Order_Province,
+ Order_PostalCode,
+ Account_ID
+ from Orders
+ where Order_ID = #value#
+ </select>
+
</statements>
<parameterMaps>
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/NUnit/SqlMapTests/StatementTest.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/NUnit/SqlMapTests/StatementTest.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/NUnit/SqlMapTests/StatementTest.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper.Test/NUnit/SqlMapTests/StatementTest.cs Thu Jan 4 13:28:10 2007
@@ -1225,6 +1225,19 @@
#region JIRA Tests
/// <summary>
+ /// Test a constructor argument with select tag.
+ /// </remarks>
+ [Test]
+ public void TestJIRA182()
+ {
+ Order order = sqlMap.QueryForObject("JIRA182", 5) as Order;
+
+ Assert.IsTrue(order.Id == 5);
+ Assert.IsNotNull(order.Account);
+ Assert.AreEqual(5, order.Account.Id);
+ }
+
+ /// <summary>
/// QueryForDictionary does not process select property
/// </summary>
[Test]
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectGenericListStrategy.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectGenericListStrategy.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectGenericListStrategy.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectGenericListStrategy.cs Thu Jan 4 13:28:10 2007
@@ -29,7 +29,6 @@
using System.Data;
using IBatisNet.DataMapper.Configuration.ResultMapping;
-using IBatisNet.DataMapper.Proxy;
using IBatisNet.DataMapper.Scope;
namespace IBatisNet.DataMapper.MappedStatements.PropertyStrategy
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectListStrategy.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectListStrategy.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectListStrategy.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectListStrategy.cs Thu Jan 4 13:28:10 2007
@@ -27,7 +27,6 @@
using System.Collections;
using System.Data;
using IBatisNet.DataMapper.Configuration.ResultMapping;
-using IBatisNet.DataMapper.Proxy;
using IBatisNet.DataMapper.Scope;
namespace IBatisNet.DataMapper.MappedStatements.PropertyStrategy
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectObjectStrategy.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectObjectStrategy.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectObjectStrategy.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/MappedStatements/PropertStrategy/SelectObjectStrategy.cs Thu Jan 4 13:28:10 2007
@@ -64,8 +64,16 @@
postSelect.Target = target;
postSelect.ResultProperty = mapping;
- postSelect.Method = PostBindind.ExecuteMethod.ExecuteQueryForObject;
- request.QueueSelect.Enqueue(postSelect);
+ if (mapping.IsLazyLoad)
+ {
+ object values = mapping.LazyFactory.CreateProxy(selectStatement, keys, target, mapping.SetAccessor);
+ mapping.SetAccessor.Set(target, values);
+ }
+ else
+ {
+ postSelect.Method = PostBindind.ExecuteMethod.ExecuteQueryForObject;
+ request.QueueSelect.Enqueue(postSelect);
+ }
}
/// <summary>
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyFactoryBuilder.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyFactoryBuilder.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyFactoryBuilder.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyFactoryBuilder.cs Thu Jan 4 13:28:10 2007
@@ -38,7 +38,7 @@
/// </summary>
public class LazyFactoryBuilder
{
- IDictionary _factory = new HybridDictionary();
+ private IDictionary _factory = new HybridDictionary();
/// <summary>
/// Initializes a new instance of the <see cref="LazyFactoryBuilder"/> class.
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadInterceptor.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadInterceptor.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadInterceptor.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadInterceptor.cs Thu Jan 4 13:28:10 2007
@@ -31,7 +31,9 @@
using System.Reflection;
using Castle.DynamicProxy;
using IBatisNet.Common.Logging;
+using IBatisNet.Common.Utilities.Objects;
using IBatisNet.Common.Utilities.Objects.Members;
+using IBatisNet.Common.Utilities.Proxy;
using IBatisNet.DataMapper.MappedStatements;
#if dotnet2
using System.Collections.Generic;
@@ -51,10 +53,11 @@
private object _param = null;
private object _target = null;
private ISetAccessor _setAccessor= null;
- private ISqlMapper _sqlMap = null;
+ private ISqlMapper _sqlMap = null;
private string _statementName = string.Empty;
private bool _loaded = false;
- private IList _innerList = null;
+ private object _lazyLoadedItem = null;
+ //private IList _innerList = null;
private object _loadLock = new object();
private static ArrayList _passthroughMethods = new ArrayList();
@@ -69,7 +72,6 @@
static LazyLoadInterceptor()
{
_passthroughMethods.Add("GetType");
- _passthroughMethods.Add("ToString");
}
/// <summary>
@@ -80,13 +82,13 @@
/// <param name="setAccessor">The proxified member accessor.</param>
/// <param name="target">The target object which contains the property proxydied.</param>
internal LazyLoadInterceptor(IMappedStatement mappedSatement, object param,
- object target, ISetAccessor setAccessor)
+ object target, ISetAccessor setAccessor)
{
_param = param;
_statementName = mappedSatement.Id;
_sqlMap = mappedSatement.SqlMap;
_target = target;
- _setAccessor = setAccessor;
+ _setAccessor = setAccessor;
}
#endregion
@@ -113,13 +115,23 @@
{
_logger.Debug("Proxyfying call, query statement " + _statementName);
}
- _innerList = _sqlMap.QueryForList(_statementName, _param);
+
+ //Perform load
+ if (typeof(IList).IsAssignableFrom(_setAccessor.MemberType))
+ {
+ _lazyLoadedItem = _sqlMap.QueryForList(_statementName, _param);
+ }
+ else
+ {
+ _lazyLoadedItem = _sqlMap.QueryForObject(_statementName, _param);
+ }
+
_loaded = true;
- _setAccessor.Set(_target, _innerList);
+ _setAccessor.Set(_target, _lazyLoadedItem);
}
}
- object returnValue = invocation.Method.Invoke( _innerList, arguments);
+ object returnValue = invocation.Method.Invoke( _lazyLoadedItem, arguments);
if (_logger.IsDebugEnabled)
{
Modified: ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadProxyFactory.cs
URL: http://svn.apache.org/viewvc/ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadProxyFactory.cs?view=diff&rev=492753&r1=492752&r2=492753
==============================================================================
--- ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadProxyFactory.cs (original)
+++ ibatis/trunk/cs/mapper/IBatisNet.DataMapper/Proxy/LazyLoadProxyFactory.cs Thu Jan 4 13:28:10 2007
@@ -24,13 +24,11 @@
#endregion
using System;
-using System.Collections;
using System.Reflection;
using Castle.DynamicProxy;
using IBatisNet.Common.Logging;
using IBatisNet.Common.Utilities.Objects.Members;
using IBatisNet.Common.Utilities.Proxy;
-using IBatisNet.DataMapper.Exceptions;
using IBatisNet.DataMapper.MappedStatements;
namespace IBatisNet.DataMapper.Proxy
@@ -38,21 +36,12 @@
/// <summary>
/// This class is responsible of create lazy load proxies for a concrete class with virtual method.
/// </summary>
- public class LazyLoadProxyFactory :ILazyFactory
+ public class LazyLoadProxyFactory : ILazyFactory
{
#region Fields
private static readonly ILog _logger = LogManager.GetLogger( MethodBase.GetCurrentMethod().DeclaringType );
#endregion
- #region Constructor
- /// <summary>
- /// constructor
- /// </summary>
- public LazyLoadProxyFactory()
- {
- }
- #endregion
-
#region ILazyFactory Members
/// <summary>
/// Builds the specified lazy load proxy for a concrete class with virtual method.
@@ -65,94 +54,27 @@
public object CreateProxy(IMappedStatement selectStatement, object param,
object target, ISetAccessor setAccessor)
{
- object proxy = null;
Type typeProxified = setAccessor.MemberType;
- //bool isIList = typeof(IList).IsAssignableFrom(setAccessor.MemberType) || setAccessor.MemberType.IsSubclassOf(typeof(IList));
- //Type returnedTypeByStatement = LazyLoadProxyFactory.GetTypeReturnedByStatemet(selectStatement, isIList);
-
- ////Test if the result of the lazy load is assigable to property, test now load time instead
- ////wait to error when the method of proxy are called
- //if (typeProxified.IsAssignableFrom(returnedTypeByStatement) == false)
- //{
- // throw new DataMapperException("Error building LazyLoad proxy for " + target.GetType() + "." + setAccessor.Name + " can not assing " + typeProxified + " to " + returnedTypeByStatement);
- //}
+ if (_logger.IsDebugEnabled)
+ {
+ _logger.Debug(string.Format("Statement '{0}', create proxy for member {1}.", selectStatement.Id, setAccessor.MemberType));
+ }
- ////Build the proxy
+ // Build the proxy
IInterceptor handler = new LazyLoadInterceptor(selectStatement, param, target, setAccessor);
- //if (isIList)
- //{
- // if (_logger.IsDebugEnabled)
- // {
- // _logger.Debug(string.Format("Statement '{0}', create list proxy for member {1}.", selectStatement.Id, setAccessor.MemberType));
- // }
-
- // if (selectStatement.Statement.ListClass == null)
- // {
- // proxy = ProxyGeneratorFactory.GetProxyGenerator().CreateProxy(typeof(IList), handler, new ArrayList());
- // }
- // else
- // {
- // if you want to proxy concrete classes, there are also two requirements:
- // the class can not be sealed and only virtual methods can be intercepted.
- // The reason is that DynamicProxy will create a subclass of your class overriding all methods
- // so it can dispatch the invocations to the interceptor.
- proxy = ProxyGeneratorFactory.GetProxyGenerator().CreateClassProxy(typeProxified, handler, Type.EmptyTypes);
- // }
- //}
- //else
- //{
- // throw new DataMapperException(string.Format("Only proxy on IList type are supported, the member type ({0}) cannot be proxyfied.", typeProxified) );
- //}
+ // if you want to proxy concrete classes, there are also 2 main requirements :
+ // the class can not be sealed and only virtual methods can be intercepted.
+ // The reason is that DynamicProxy will create a subclass of your class overriding all methods
+ // so it can dispatch the invocations to the interceptor.
+
+ // The proxified type must also have an empty constructor
+ object proxy = ProxyGeneratorFactory.GetProxyGenerator().CreateClassProxy(typeProxified, handler, Type.EmptyTypes);
+
return proxy;
}
#endregion
-
- /// <summary>
- /// Gets the type returned by statemet.
- /// </summary>
- /// <param name="mappedStatement">The mapped statement.</param>
- /// <param name="isIList">if set to <c>true</c> [is Ilist].</param>
- /// <returns>The type object return by the statement.</returns>
- private static Type GetTypeReturnedByStatemet(IMappedStatement mappedStatement,
- bool isIList)
- {
- Type returnedType = null;
-
- if ( isIList )
- {
- if (mappedStatement.Statement.ListClass != null)
- {
- //Strongly type collection
- returnedType = mappedStatement.Statement.ListClass;
- }
- else
- {
- //Generic List, IList is the return type of ExecuteQueryForList(..)
- returnedType = typeof(IList);
- }
- }
- else
- {
- //Property to proxified is a simple object
- if (mappedStatement.Statement.ResultClass != null)
- {
- returnedType = mappedStatement.Statement.ResultClass;
- }
- else if (mappedStatement.Statement.ParameterMap != null)
- {
- returnedType = mappedStatement.Statement.ParameterMap.Class;
- }
- else
- {
- throw new DataMapperException("We must never get here !");
- }
- }
-
- return returnedType;
- }
-
}
}