diff --git a/src/NHibernate.Test/Async/TypesTest/BooleanTypeFixture.cs b/src/NHibernate.Test/Async/TypesTest/BooleanTypeFixture.cs index ae41f04a43a..85b11c47f27 100644 --- a/src/NHibernate.Test/Async/TypesTest/BooleanTypeFixture.cs +++ b/src/NHibernate.Test/Async/TypesTest/BooleanTypeFixture.cs @@ -8,8 +8,10 @@ //------------------------------------------------------------------------------ -using System; +using System.Data.Common; +using NHibernate.Engine; using NHibernate.Type; +using NSubstitute; using NUnit.Framework; namespace NHibernate.Test.TypesTest @@ -21,10 +23,7 @@ namespace NHibernate.Test.TypesTest [TestFixture] public class BooleanTypeFixtureAsync : TypeFixtureBase { - protected override string TypeName - { - get { return "Boolean"; } - } + protected override string TypeName => "Boolean"; [Test] public async Task ReadWriteAsync() @@ -48,4 +47,4 @@ public async Task ReadWriteAsync() s.Close(); } } -} \ No newline at end of file +} diff --git a/src/NHibernate.Test/TypesTest/BooleanTypeFixture.cs b/src/NHibernate.Test/TypesTest/BooleanTypeFixture.cs index c9c217a81e4..cd124b00d0e 100644 --- a/src/NHibernate.Test/TypesTest/BooleanTypeFixture.cs +++ b/src/NHibernate.Test/TypesTest/BooleanTypeFixture.cs @@ -1,5 +1,7 @@ -using System; +using System.Data.Common; +using NHibernate.Engine; using NHibernate.Type; +using NSubstitute; using NUnit.Framework; namespace NHibernate.Test.TypesTest @@ -10,10 +12,7 @@ namespace NHibernate.Test.TypesTest [TestFixture] public class BooleanTypeFixture : TypeFixtureBase { - protected override string TypeName - { - get { return "Boolean"; } - } + protected override string TypeName => "Boolean"; /// /// Verify Equals will correctly determine when the property @@ -22,7 +21,7 @@ protected override string TypeName [Test] public void Equals() { - BooleanType type = (BooleanType) NHibernateUtil.Boolean; + BooleanType type = NHibernateUtil.Boolean; Assert.IsTrue(type.IsEqual(true, true)); Assert.IsTrue(type.IsEqual(false, false)); @@ -50,5 +49,65 @@ public void ReadWrite() s.Flush(); s.Close(); } + + [Theory] + public void GetByIndex(bool expected) + { + const int index0 = 0; + const int index1 = 1; + BooleanType type = NHibernateUtil.Boolean; + var session = Substitute.For(); + var reader = Substitute.For(); + reader[index0].Returns(expected); + reader[index1].Returns(expected); + + var result0 = type.Get(reader, index0, session); + var result1 = type.Get(reader, index1, session); + + Assert.AreEqual(expected, (bool) result0); + Assert.AreSame(result0, result1); + } + + [Theory] + public void GetByName(bool expected) + { + const string name0 = "name0"; + const string name1 = "name1"; + BooleanType type = NHibernateUtil.Boolean; + var session = Substitute.For(); + var reader = Substitute.For(); + reader[name0].Returns(expected); + reader[name1].Returns(expected); + + var result0 = type.Get(reader, name0, session); + var result1 = type.Get(reader, name1, session); + + Assert.AreEqual(expected, (bool) result0); + Assert.AreSame(result0, result1); + } + + [Test] + public void DefaultValue() + { + BooleanType type = NHibernateUtil.Boolean; + + var result0 = type.DefaultValue; + var result1 = type.DefaultValue; + + Assert.IsFalse((bool) result0); + Assert.AreSame(result0, result1); + } + + [Theory] + public void StringToObject(bool expected) + { + BooleanType type = NHibernateUtil.Boolean; + + var result0 = type.StringToObject(expected.ToString()); + var result1 = type.StringToObject(expected.ToString()); + + Assert.AreEqual(expected, result0); + Assert.AreSame(result0, result1); + } } -} \ No newline at end of file +} diff --git a/src/NHibernate.Test/TypesTest/CharBooleanTypeFixture.cs b/src/NHibernate.Test/TypesTest/CharBooleanTypeFixture.cs new file mode 100644 index 00000000000..d4448ad6023 --- /dev/null +++ b/src/NHibernate.Test/TypesTest/CharBooleanTypeFixture.cs @@ -0,0 +1,71 @@ +using System.Data.Common; +using NHibernate.Engine; +using NHibernate.SqlTypes; +using NHibernate.Type; +using NSubstitute; +using NUnit.Framework; + +namespace NHibernate.Test.TypesTest +{ + [TestFixture] + public sealed class CharBooleanTypeFixture + { + [Theory] + public void GetByIndex(bool expected) + { + const int index0 = 0; + const int index1 = 1; + CharBooleanType type =new CharBooleanTypeStub(); + var session = Substitute.For(); + var reader = Substitute.For(); + reader[index0].Returns(expected.ToString()); + reader[index1].Returns(expected.ToString()); + + var result0 = type.Get(reader, index0, session); + var result1 = type.Get(reader, index1, session); + + Assert.AreEqual(expected, (bool) result0); + Assert.AreSame(result0, result1); + } + + [Theory] + public void GetByName(bool value) + { + const string name = "0"; + const int index = 0; + object expected = value; + CharBooleanType type = Substitute.ForPartsOf(); + var session = Substitute.For(); + var reader = Substitute.For(); + reader.GetOrdinal(name).Returns(index); + type.Get(reader, index, Arg.Any()).Returns(expected); + + var result = type.Get(reader, name, session); + + Assert.AreSame(expected, result); + } + + [Theory] + public void StringToObject(bool expected) + { + CharBooleanType type = new CharBooleanTypeStub(); + + var result0 = type.StringToObject(expected.ToString()); + var result1 = type.StringToObject(expected.ToString()); + + Assert.AreEqual(expected, result0); + Assert.AreSame(result0, result1); + } + + public class CharBooleanTypeStub : CharBooleanType + { + public CharBooleanTypeStub() : base(new AnsiStringFixedLengthSqlType()) + { + } + + protected override string TrueString => true.ToString(); + + protected override string FalseString => false.ToString(); + } + } +} diff --git a/src/NHibernate/Type/BooleanType.cs b/src/NHibernate/Type/BooleanType.cs index f3333f805b9..2a154211b7b 100644 --- a/src/NHibernate/Type/BooleanType.cs +++ b/src/NHibernate/Type/BooleanType.cs @@ -1,6 +1,7 @@ using System; using System.Data; using System.Data.Common; +using System.Runtime.CompilerServices; using NHibernate.Engine; using NHibernate.SqlTypes; @@ -13,6 +14,9 @@ namespace NHibernate.Type [Serializable] public class BooleanType : PrimitiveType, IDiscriminatorType { + protected static readonly object TrueObject = true; + protected static readonly object FalseObject = false; + /// /// Initialize a new instance of the BooleanType /// @@ -36,38 +40,26 @@ public BooleanType(AnsiStringFixedLengthSqlType sqlType) : base(sqlType) public override object Get(DbDataReader rs, int index, ISessionImplementor session) { - return Convert.ToBoolean(rs[index]); + return GetBooleanAsObject(Convert.ToBoolean(rs[index])); } public override object Get(DbDataReader rs, string name, ISessionImplementor session) { - return Convert.ToBoolean(rs[name]); + return GetBooleanAsObject(Convert.ToBoolean(rs[name])); } - public override System.Type PrimitiveClass - { - get { return typeof(bool); } - } + public override System.Type PrimitiveClass => typeof(bool); - public override System.Type ReturnedClass - { - get { return typeof(bool); } - } + public override System.Type ReturnedClass => typeof(bool); public override void Set(DbCommand cmd, object value, int index, ISessionImplementor session) { cmd.Parameters[index].Value = (bool) value; } - public override string Name - { - get { return "Boolean"; } - } + public override string Name => "Boolean"; - public override object DefaultValue - { - get { return false; } - } + public override object DefaultValue => FalseObject; public override string ObjectToSQLString(object value, Dialect.Dialect dialect) { @@ -89,7 +81,13 @@ public virtual object StringToObject(string xml) [Obsolete("This method has no more usages and will be removed in a future version.")] public override object FromStringValue(string xml) { - return bool.Parse(xml); + return GetBooleanAsObject(bool.Parse(xml)); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + internal static object GetBooleanAsObject(bool value) + { + return value ? TrueObject : FalseObject; } } } diff --git a/src/NHibernate/Type/CharBooleanType.cs b/src/NHibernate/Type/CharBooleanType.cs index 9cde87c6697..53dc6a9abb3 100644 --- a/src/NHibernate/Type/CharBooleanType.cs +++ b/src/NHibernate/Type/CharBooleanType.cs @@ -3,7 +3,6 @@ using System.Data.Common; using NHibernate.Engine; using NHibernate.SqlTypes; -using NHibernate.Util; namespace NHibernate.Type { @@ -37,7 +36,7 @@ public override object Get(DbDataReader rs, int index, ISessionImplementor sessi } else { - return code.Equals(TrueString, StringComparison.InvariantCultureIgnoreCase); + return GetBooleanAsObject(code.Equals(TrueString, StringComparison.InvariantCultureIgnoreCase)); } } @@ -68,11 +67,11 @@ public override object StringToObject(String xml) { if (string.Equals(TrueString, xml, StringComparison.InvariantCultureIgnoreCase)) { - return true; + return TrueObject; } else if (string.Equals(FalseString, xml, StringComparison.InvariantCultureIgnoreCase)) { - return false; + return FalseObject; } else {