Skip to content

Commit eec2ee6

Browse files
Clean-up IObjectsFactory usages (nhibernate#1781)
IObjectsFactory is meant for instantiating NHibernate dependencies, but it was used in some cases for instantiating value types. Some of its methods are also hard or impossible to implement with many dependency injection frameworks. Follow up to nhibernate#1758
1 parent 97dc207 commit eec2ee6

17 files changed

+116
-29
lines changed

src/NHibernate.Test/Bytecode/ActivatorObjectFactoryFixture.cs

+4-4
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ public void CreateInstanceDefCtor()
4545

4646

4747

48-
[Test]
48+
[Test, Obsolete]
4949
public void CreateInstanceWithNoPublicCtor()
5050
{
5151
IObjectsFactory of = GetObjectsFactory();
@@ -55,7 +55,7 @@ public void CreateInstanceWithNoPublicCtor()
5555
Assert.That(instance, Is.InstanceOf<WithOutPublicParameterLessCtor>());
5656
}
5757

58-
[Test]
58+
[Test, Obsolete]
5959
public void CreateInstanceOfValueType()
6060
{
6161
IObjectsFactory of = GetObjectsFactory();
@@ -64,7 +64,7 @@ public void CreateInstanceOfValueType()
6464
Assert.That(instance, Is.InstanceOf<ValueType>());
6565
}
6666

67-
[Test]
67+
[Test, Obsolete]
6868
public void CreateInstanceWithArguments()
6969
{
7070
IObjectsFactory of = GetObjectsFactory();
@@ -76,4 +76,4 @@ public void CreateInstanceWithArguments()
7676
Assert.That(((WithOutPublicParameterLessCtor)instance).Something, Is.EqualTo(value));
7777
}
7878
}
79-
}
79+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
using NHibernate.Cfg;
2+
using NHibernate.Context;
3+
using NHibernate.Engine;
4+
using NUnit.Framework;
5+
6+
namespace NHibernate.Test.ConnectionTest
7+
{
8+
[TestFixture]
9+
public class CustomCurrentSessionTest : ConnectionManagementTestCase
10+
{
11+
protected override ISession GetSessionUnderTest()
12+
{
13+
var session = OpenSession();
14+
CustomContext.Session = session;
15+
return session;
16+
}
17+
18+
protected override void Configure(Configuration configuration)
19+
{
20+
base.Configure(cfg);
21+
cfg.SetProperty(Environment.CurrentSessionContextClass, typeof(CustomContext).AssemblyQualifiedName);
22+
}
23+
24+
protected override void Release(ISession session)
25+
{
26+
CustomContext.Session = null;
27+
base.Release(session);
28+
}
29+
30+
[Test]
31+
public void ContextIsSetup()
32+
{
33+
Assert.That(Sfi.CurrentSessionContext, Is.InstanceOf<CustomContext>());
34+
Assert.That(
35+
((CustomContext) Sfi.CurrentSessionContext).Factory,
36+
Is.SameAs(((DebugSessionFactory) Sfi).ActualFactory));
37+
}
38+
}
39+
40+
public class CustomContext : ISessionFactoryAwareCurrentSessionContext
41+
{
42+
internal ISessionFactoryImplementor Factory;
43+
internal static ISession Session;
44+
45+
public ISession CurrentSession()
46+
{
47+
return Session;
48+
}
49+
50+
public void SetFactory(ISessionFactoryImplementor factory)
51+
{
52+
Factory = factory;
53+
}
54+
}
55+
}

src/NHibernate.Test/ConnectionTest/MapBasedSessionContextFixture.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -76,4 +76,4 @@ protected override void SetMap(IDictionary value)
7676
_map = value;
7777
}
7878
}
79-
}
79+
}

src/NHibernate.Test/ConnectionTest/ThreadLocalCurrentSessionTest.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -88,4 +88,4 @@ public static bool HasBind()
8888
return context != null && context.ContainsKey(me.factory);
8989
}
9090
}
91-
}
91+
}

src/NHibernate/Async/Tool/hbm2ddl/SchemaExport.cs

+1-4
Original file line numberDiff line numberDiff line change
@@ -187,10 +187,7 @@ private async Task ExecuteInitializedAsync(Action<string> scriptAction, bool exe
187187
cancellationToken.ThrowIfCancellationRequested();
188188
if (dialect.SupportsSqlBatches)
189189
{
190-
var objFactory = Environment.ObjectsFactory;
191-
ScriptSplitter splitter = (ScriptSplitter)objFactory.CreateInstance(typeof(ScriptSplitter), sql);
192-
193-
foreach (string stmt in splitter)
190+
foreach (var stmt in new ScriptSplitter(sql))
194191
{
195192
log.Debug("SQL Batch: {0}", stmt);
196193
cmd.CommandText = stmt;

src/NHibernate/Bytecode/ActivatorObjectsFactory.cs

+5-1
Original file line numberDiff line numberDiff line change
@@ -9,14 +9,18 @@ public object CreateInstance(System.Type type)
99
return Activator.CreateInstance(type);
1010
}
1111

12+
// Since v5.2
13+
[Obsolete("This method has no more usages and will be removed in a future version")]
1214
public object CreateInstance(System.Type type, bool nonPublic)
1315
{
1416
return Activator.CreateInstance(type, nonPublic);
1517
}
1618

19+
// Since v5.2
20+
[Obsolete("This method has no more usages and will be removed in a future version")]
1721
public object CreateInstance(System.Type type, params object[] ctorArgs)
1822
{
1923
return Activator.CreateInstance(type, ctorArgs);
2024
}
2125
}
22-
}
26+
}

src/NHibernate/Bytecode/IObjectsFactory.cs

+8-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
1+
using System;
2+
13
namespace NHibernate.Bytecode
24
{
35
/// <summary>
4-
/// Interface for instantiate all NHibernate objects.
6+
/// Interface for instantiating NHibernate dependencies.
57
/// </summary>
68
public interface IObjectsFactory
79
{
@@ -18,6 +20,8 @@ public interface IObjectsFactory
1820
/// <param name="type">The type of object to create.</param>
1921
/// <param name="nonPublic">true if a public or nonpublic default constructor can match; false if only a public default constructor can match.</param>
2022
/// <returns>A reference to the created object.</returns>
23+
// Since v5.2
24+
[Obsolete("This method has no more usages and will be removed in a future version")]
2125
object CreateInstance(System.Type type, bool nonPublic);
2226

2327
/// <summary>
@@ -27,6 +31,8 @@ public interface IObjectsFactory
2731
/// <param name="type">The type of object to create.</param>
2832
/// <param name="ctorArgs">An array of constructor arguments.</param>
2933
/// <returns>A reference to the created object.</returns>
34+
// Since v5.2
35+
[Obsolete("This method has no more usages and will be removed in a future version")]
3036
object CreateInstance(System.Type type, params object[] ctorArgs);
3137
}
32-
}
38+
}

src/NHibernate/Context/AsyncLocalSessionContext.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -30,4 +30,4 @@ protected override ISession Session
3030
set => _session.Value = value;
3131
}
3232
}
33-
}
33+
}

src/NHibernate/Context/CurrentSessionContext.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -86,4 +86,4 @@ private static CurrentSessionContext GetCurrentSessionContext(ISessionFactory fa
8686
return currentSessionContext;
8787
}
8888
}
89-
}
89+
}

src/NHibernate/Context/ICurrentSessionContext.cs

+17-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
using System;
1+
using NHibernate.Bytecode;
22
using NHibernate.Engine;
33

44
namespace NHibernate.Context
@@ -12,7 +12,8 @@ namespace NHibernate.Context
1212
/// Implementations should adhere to the following:
1313
/// <list type="bullet">
1414
/// <item><description>contain a constructor accepting a single argument of type
15-
/// <see cref="ISessionFactoryImplementor" /></description></item>
15+
/// <see cref="ISessionFactoryImplementor" />, or implement
16+
/// <see cref="ISessionFactoryAwareCurrentSessionContext"/></description></item>
1617
/// <item><description>should be thread safe</description></item>
1718
/// <item><description>should be fully serializable</description></item>
1819
/// </list>
@@ -42,4 +43,18 @@ public interface ICurrentSessionContext
4243
/// locating or creating the current session.</exception>
4344
ISession CurrentSession();
4445
}
46+
47+
/// <summary>
48+
/// An <see cref="ICurrentSessionContext"/> allowing to set its session factory. Implementing
49+
/// this interface allows the <see cref="IObjectsFactory"/> to be used for instantiating the
50+
/// session context.
51+
/// </summary>
52+
public interface ISessionFactoryAwareCurrentSessionContext : ICurrentSessionContext
53+
{
54+
/// <summary>
55+
/// Sets the factory. This method should be called once after creating the context.
56+
/// </summary>
57+
/// <param name="factory">The factory.</param>
58+
void SetFactory(ISessionFactoryImplementor factory);
59+
}
4560
}

src/NHibernate/Context/MapBasedSessionContext.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -64,4 +64,4 @@ private ConcurrentDictionary<ISessionFactoryImplementor, ISession> GetConcreteMa
6464
/// </summary>
6565
protected abstract void SetMap(IDictionary value);
6666
}
67-
}
67+
}

src/NHibernate/Context/WcfOperationSessionContext.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -49,4 +49,4 @@ public class WcfStateExtension : IExtension<OperationContext>
4949
public void Attach(OperationContext owner) { }
5050
public void Detach(OperationContext owner) { }
5151
}
52-
}
52+
}

src/NHibernate/Context/WebSessionContext.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -25,4 +25,4 @@ protected override void SetMap(IDictionary value)
2525
ReflectiveHttpContext.HttpContextCurrentItems[SessionFactoryMapKey] = value;
2626
}
2727
}
28-
}
28+
}

src/NHibernate/Impl/SessionFactoryImpl.cs

+16-3
Original file line numberDiff line numberDiff line change
@@ -1281,9 +1281,22 @@ private ICurrentSessionContext BuildCurrentSessionContext()
12811281

12821282
try
12831283
{
1284-
System.Type implClass = ReflectHelper.ClassForName(impl);
1285-
return
1286-
(ICurrentSessionContext)Environment.ObjectsFactory.CreateInstance(implClass, new object[] { this });
1284+
var implClass = ReflectHelper.ClassForName(impl);
1285+
var constructor = implClass.GetConstructor(new [] { typeof(ISessionFactoryImplementor) });
1286+
ICurrentSessionContext context;
1287+
if (constructor != null)
1288+
{
1289+
context = (ICurrentSessionContext) constructor.Invoke(new object[] { this });
1290+
}
1291+
else
1292+
{
1293+
context = (ICurrentSessionContext) Environment.ObjectsFactory.CreateInstance(implClass);
1294+
}
1295+
if (context is ISessionFactoryAwareCurrentSessionContext sessionFactoryAwareContext)
1296+
{
1297+
sessionFactoryAwareContext.SetFactory(this);
1298+
}
1299+
return context;
12871300
}
12881301
catch (Exception e)
12891302
{

src/NHibernate/Tool/hbm2ddl/SchemaExport.cs

+1-4
Original file line numberDiff line numberDiff line change
@@ -203,10 +203,7 @@ private void ExecuteSql(DbCommand cmd, string sql)
203203
{
204204
if (dialect.SupportsSqlBatches)
205205
{
206-
var objFactory = Environment.ObjectsFactory;
207-
ScriptSplitter splitter = (ScriptSplitter)objFactory.CreateInstance(typeof(ScriptSplitter), sql);
208-
209-
foreach (string stmt in splitter)
206+
foreach (var stmt in new ScriptSplitter(sql))
210207
{
211208
log.Debug("SQL Batch: {0}", stmt);
212209
cmd.CommandText = stmt;

src/NHibernate/Transform/AliasToBeanResultTransformer.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ public override object TransformTuple(object[] tuple, String[] aliases)
8585
{
8686
result = _resultClass.IsClass
8787
? _beanConstructor.Invoke(null)
88-
: Cfg.Environment.ObjectsFactory.CreateInstance(_resultClass, true);
88+
: Activator.CreateInstance(_resultClass, true);
8989

9090
for (int i = 0; i < aliases.Length; i++)
9191
{

src/NHibernate/Tuple/PocoInstantiator.cs

+1-1
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@ private object GetInstance()
103103
}
104104
if (mappedClass.IsValueType)
105105
{
106-
return Cfg.Environment.ObjectsFactory.CreateInstance(mappedClass, true);
106+
return Activator.CreateInstance(mappedClass, true);
107107
}
108108
if (constructor == null)
109109
{

0 commit comments

Comments
 (0)