diff --git a/Aspects/DIContainer.cs b/Aspects/DIContainer.cs index b4a6fca..f55623f 100644 --- a/Aspects/DIContainer.cs +++ b/Aspects/DIContainer.cs @@ -325,7 +325,6 @@ public static void Dump( /// /// The container. /// - [Conditional("DEBUG")] public static void DebugDump( this IUnityContainer container) { @@ -334,12 +333,14 @@ public static void DebugDump( using (var writer = new StringWriter(CultureInfo.InvariantCulture)) { container.Dump(writer); - Debug.WriteLine( - "==============================={1}"+ - "{0}{1}"+ - "==============================={1}", - writer.GetStringBuilder(), - writer.NewLine); + Debug.Print( +@"=============================== + +{0} + +=============================== +", + writer.GetStringBuilder()); } } } diff --git a/Aspects/Linq/Expressions/Serialization/NuGet/ExpressionSerialization.nuspec b/Aspects/Linq/Expressions/Serialization/NuGet/ExpressionSerialization.nuspec index 9786e90..c8985df 100644 --- a/Aspects/Linq/Expressions/Serialization/NuGet/ExpressionSerialization.nuspec +++ b/Aspects/Linq/Expressions/Serialization/NuGet/ExpressionSerialization.nuspec @@ -2,7 +2,7 @@ AspectExpressionSerialization - 1.0.23 + 1.0.25 Val Melamed Val Melamed diff --git a/Aspects/Linq/Expressions/Serialization/Properties/AssemblyInfo.cs b/Aspects/Linq/Expressions/Serialization/Properties/AssemblyInfo.cs index 37c134c..85836cc 100644 --- a/Aspects/Linq/Expressions/Serialization/Properties/AssemblyInfo.cs +++ b/Aspects/Linq/Expressions/Serialization/Properties/AssemblyInfo.cs @@ -4,9 +4,9 @@ [assembly: AssemblyTitle("vm.Aspects.Linq.Expressions.Serialization")] [assembly: AssemblyDescription("Serializes and deserializes LINQ expression trees to and from XML documents.")] -[assembly: AssemblyVersion("1.0.23")] -[assembly: AssemblyFileVersion("1.0.23")] -[assembly: AssemblyInformationalVersion("1.0.23")] +[assembly: AssemblyVersion("1.0.25")] +[assembly: AssemblyFileVersion("1.0.25")] +[assembly: AssemblyInformationalVersion("1.0.25")] [assembly: InternalsVisibleTo( "vm.Aspects.Linq.Expressions.Serialization.Test, " + diff --git a/Aspects/Model/DomainEntity.cs b/Aspects/Model/DomainEntity.cs index 6673f17..e4d83ff 100644 --- a/Aspects/Model/DomainEntity.cs +++ b/Aspects/Model/DomainEntity.cs @@ -30,7 +30,7 @@ public abstract partial class DomainEntity : BaseDomainEntity, /// public override bool HasIdentity { - get { return !Key.Equals(default(TKey)); } + get { return !(ReferenceEquals(Key, null) || Key.Equals(default(TKey))); } } #region IHasStoreId Members @@ -144,7 +144,7 @@ public override bool Equals( /// A hash code for the current instance. public override int GetHashCode() { - return Key.GetHashCode(); ; + return HasIdentity ? Key.GetHashCode() : 0; } /// diff --git a/Aspects/Model/EFRepository/EFRepositoryBase.IRepository.cs b/Aspects/Model/EFRepository/EFRepositoryBase.IRepository.cs index 3279a97..de5981e 100644 --- a/Aspects/Model/EFRepository/EFRepositoryBase.IRepository.cs +++ b/Aspects/Model/EFRepository/EFRepositoryBase.IRepository.cs @@ -92,9 +92,9 @@ public virtual void SetDatabaseInitializer() if (initializer != null) // Database.SetInitializer(initializer); typeof(Database) - .GetMethod("SetInitializer") + .GetMethod(nameof(Database.SetInitializer)) .MakeGenericMethod(GetType()) - .Invoke((object)null, new object[] { initializer }); + .Invoke(null, new object[] { initializer }); } /// diff --git a/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGenerator.cs b/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGenerator.cs index 26ddbd8..72d0708 100644 --- a/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGenerator.cs +++ b/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGenerator.cs @@ -8,7 +8,7 @@ namespace vm.Aspects.Model.EFRepository.HiLoIdentity /// /// Class HiLoIdentityGenerator. Implements the Hi-Lo algorithm for generating unique ID-s. /// - public class HiLoIdentityGenerator + public class HiLoIdentityGenerator : BaseDomainEntity, IEquatable { #region Constants /// @@ -75,6 +75,14 @@ public HiLoIdentityGenerator( public int MaxLowValue { get; protected internal set; } #endregion + /// + /// Gets a value indicating whether this instance is already associated with an entity set. + /// + public override bool HasIdentity + { + get { return !string.IsNullOrWhiteSpace(EntitySetName); } + } + #region Methods /// /// Increments the high value and initializes the low value. @@ -100,7 +108,7 @@ internal void IncrementHighValue() /// Gets the next available value for an entity id. If the low values are exhausted the method will return -1L. /// /// The next available value for an entity id. - [SuppressMessage("Microsoft.Design", "CA1024:UsePropertiesWhereAppropriate", Justification="n/a")] + [SuppressMessage("Microsoft.Design", "CA1024:UsePropertiesWhereAppropriate", Justification = "n/a")] public long GetId() { if (HighValue < 1L || LowValue >= MaxLowValue) @@ -109,5 +117,115 @@ public long GetId() return unchecked(((long)(HighValue-1) * MaxLowValue) + ++LowValue); } #endregion + + + #region Identity rules implementation. + #region IEquatable Members + /// + /// Indicates whether the current object is equal to a reference to another object of the same type. + /// + /// A reference to another object of type to compare with the current object. + /// + /// + /// if is equal to , otherwise + /// if refers to this object, otherwise + /// if is not the same type as this object, otherwise + /// if the current object and the are considered to be equal, + /// e.g. their business identities are equal; otherwise, . + /// + /// + /// + /// The and methods and + /// the overloaded operator== and operator!= test for business identity, + /// i.e. they test for business same-ness by comparing the types and the business keys. + /// + public virtual bool Equals(HiLoIdentityGenerator other) + { + if (ReferenceEquals(other, null)) + return false; + if (ReferenceEquals(this, other)) + return true; + if (GetType() != other.GetType()) + return false; + + return EntitySetName == other.EntitySetName; + } + #endregion + + /// + /// Determines whether this instance is equal to the specified reference. + /// + /// The reference to compare with this object. + /// + /// + /// if cannot be cast to , otherwise + /// if is equal to , otherwise + /// if refers to this object, otherwise + /// if is not the same type as this object, otherwise + /// if the current object and the are considered to be equal, + /// e.g. their business identities are equal; otherwise, . + /// + /// + /// + /// The and methods and + /// the overloaded operator== and operator!= test for business identity, + /// i.e. they test for business same-ness by comparing the types and the business keys. + /// + public override bool Equals(object obj) => Equals(obj as HiLoIdentityGenerator); + + /// + /// Serves as a hash function for the objects of and its derived types. + /// + /// A hash code for the current instance. + public override int GetHashCode() + { + var hashCode = Constants.HashInitializer; + + hashCode = Constants.HashMultiplier * hashCode + EntitySetName.GetHashCode(); + + return hashCode; + } + + /// + /// Compares two objects. + /// + /// The left operand. + /// The right operand. + /// + /// if the objects are considered to be equal (); + /// otherwise . + /// + public static bool operator ==(HiLoIdentityGenerator left, HiLoIdentityGenerator right) => ReferenceEquals(left, null) ? ReferenceEquals(right, null) : left.Equals(right); + + /// + /// Compares two objects. + /// + /// The left operand. + /// The right operand. + /// + /// if the objects are not considered to be equal (); + /// otherwise . + /// + public static bool operator !=(HiLoIdentityGenerator left, HiLoIdentityGenerator right) => !(left==right); + #endregion + + /// + /// Indicates whether the current object is equal to a reference to another object of the same type. + /// + /// A reference to another object of type to compare with this object. + /// + /// if is equal to , otherwise + /// if refers to this object, otherwise + /// if the business identities of the current object and the are equal by value, + /// e.g. BusinessKeyProperty == other.BusinessKeyProperty; otherwise, . + /// + /// + /// The method and its overloads as well as the overloaded operator== and operator!= test for business identity, + /// i.e. they test for business same-ness by comparing the business keys. + /// + public override bool Equals(BaseDomainEntity other) + { + return Equals(other as HiLoIdentityGenerator); + } } } diff --git a/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGeneratorConfiguration.cs b/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGeneratorConfiguration.cs index a8140f4..e9bd4b0 100644 --- a/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGeneratorConfiguration.cs +++ b/Aspects/Model/EFRepository/HiLoIdentity/HiLoIdentityGeneratorConfiguration.cs @@ -7,7 +7,7 @@ class HiLoIdentityGeneratorConfiguration : EntityTypeConfiguration g.EntitySetName); diff --git a/Aspects/Model/EFRepository/HiLoIdentity/HiLoStoreIdProvider.cs b/Aspects/Model/EFRepository/HiLoIdentity/HiLoStoreIdProvider.cs index bad19d2..9993bf6 100644 --- a/Aspects/Model/EFRepository/HiLoIdentity/HiLoStoreIdProvider.cs +++ b/Aspects/Model/EFRepository/HiLoIdentity/HiLoStoreIdProvider.cs @@ -6,6 +6,7 @@ using System.Linq; using System.Transactions; using Microsoft.Practices.ServiceLocation; +using Microsoft.Practices.Unity; using vm.Aspects.Facilities; using vm.Aspects.Model.Repository; @@ -98,7 +99,7 @@ Guid IStoreUniqueId.GetNewId(IRepository repository) /// public const string DefaultEntitySetName = "_"; - readonly Func _generatorsRepositoryFactory; + readonly Func _generatorsRepositoryFactory; /// /// Initializes a new instance of the class. @@ -108,10 +109,11 @@ Guid IStoreUniqueId.GetNewId(IRepository repository) /// the constructor will try to resolve it from the service locator with resolve name /// public HiLoStoreIdProvider( - Func generatorsRepositoryFactory) + [Dependency(HiLoGeneratorsRepositoryResolveName)] + Func generatorsRepositoryFactory) { _generatorsRepositoryFactory = generatorsRepositoryFactory ?? - (() => ServiceLocator.Current.GetInstance(HiLoGeneratorsRepositoryResolveName) as EFRepositoryBase); + (() => ServiceLocator.Current.GetInstance(HiLoGeneratorsRepositoryResolveName)); } #region Transaction scope defaults: @@ -177,16 +179,17 @@ HiLoIdentityGenerator CreateOrGetFreshGenerator( // get a fresh generator object from the DB generator = localRepository - .Set() - .FirstOrDefault(g => g.EntitySetName == entitySetName); + .Entities() + .FirstOrDefault(g => g.EntitySetName == entitySetName) + ; if (generator == null) { // create a new generator generator = new HiLoIdentityGenerator(entitySetName, HiLoIdentityGenerator.DefaultMaxLowValue); localRepository - .Set() - .Add(generator); + .Add(generator) + ; } generator.IncrementHighValue(); diff --git a/Aspects/Model/PerCallContextRepositoryCallHandler.cs b/Aspects/Model/PerCallContextRepositoryCallHandler.cs index e5fea24..60f98e9 100644 --- a/Aspects/Model/PerCallContextRepositoryCallHandler.cs +++ b/Aspects/Model/PerCallContextRepositoryCallHandler.cs @@ -1,20 +1,18 @@ using System; +using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; -using System.Linq; +using System.Diagnostics.Contracts; using System.Threading.Tasks; -using vm.Aspects; -using vm.Aspects.Exceptions; using Microsoft.Practices.Unity; using Microsoft.Practices.Unity.InterceptionExtension; -using System.Diagnostics.Contracts; +using vm.Aspects.Exceptions; using vm.Aspects.Model.Repository; -using System.Collections.Generic; namespace vm.Aspects.Model { /// /// The class PerCallContextRepositoryCallHandler is meant to be used as a policy (AOP aspect) in the call context of a WCF call. - /// It is assumed that the repository is resolved from the DI container and has , i.e. all + /// It is assumed that the repository is resolved from the DI container and has , i.e. all /// resolutions for with the same resolve name in the same WCF call context will return one and the same repository object. /// This handler implements two post-call actions: if there are no exceptions, it commits the unit of work, otherwise rolls back the current transaction /// and then removes the repository's lifetime manager from the container. In other words the application developer does not need to worry about @@ -39,7 +37,7 @@ public class PerCallContextRepositoryCallHandler : ICallHandler /// chain. /// Return value from the target. /// Thrown when either or are -s. - [SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification="It's OK here.")] + [SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification = "It's OK here.")] public IMethodReturn Invoke( IMethodInvocation input, GetNextHandlerDelegate getNext) @@ -47,9 +45,9 @@ public IMethodReturn Invoke( Contract.Ensures(Contract.Result() != null); if (input == null) - throw new ArgumentNullException("input"); + throw new ArgumentNullException(nameof(input)); if (getNext == null) - throw new ArgumentNullException("getNext"); + throw new ArgumentNullException(nameof(getNext)); var result = getNext().Invoke(input, getNext); @@ -70,13 +68,13 @@ public IMethodReturn Invoke( #endregion - [SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification="It is re-thrown.")] + [SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification = "It is re-thrown.")] IMethodReturn CommitWork( IMethodInvocation input, IMethodReturn result) { IDictionary registrations; - + lock (DIContainer.Root) registrations = DIContainer.Root.GetRegistrationsSnapshot(); @@ -86,7 +84,7 @@ IMethodReturn CommitWork( if (!registrations.TryGetValue(new RegistrationLookup(typeof(IRepository), RepositoryResolveName), out registration) || !(registration.LifetimeManager is PerCallContextLifetimeManager)) return result; - + try { var repository = registration.LifetimeManager.GetValue() as IRepository; @@ -127,7 +125,7 @@ IMethodReturn CommitWorkAsync( { Contract.Requires(input != null, nameof(input)); Contract.Requires(result != null, nameof(result)); - + var parameters = new DoCommitWorkAsyncParameters { Input = input, @@ -144,22 +142,22 @@ IMethodReturn CommitWorkAsync( var commitWorkAsyncGeneric = typeof(Func<,>).MakeGenericType(typeof(DoCommitWorkAsyncParameters), returnType); // create a delegate out of an instantiated DoCommitWorkAsync - var doCommitWorkAsyncDelegate = GetType().GetMethod("DoCommitWorkAsync") + var doCommitWorkAsyncDelegate = GetType().GetMethod(nameof(DoCommitWorkAsync)) .MakeGenericMethod(returnType) .CreateDelegate(commitWorkAsyncGeneric); // pass the delegate to a Task c-tor var wrappedTask = typeof(Task).MakeGenericType(returnType) .GetConstructor(new Type[] { commitWorkAsyncGeneric }) - .Invoke(new object[] - { - doCommitWorkAsyncDelegate, + .Invoke(new object[] + { + doCommitWorkAsyncDelegate, parameters, }) as Task; wrappedTask.Start(); return input.CreateMethodReturn(wrappedTask); } - [SuppressMessage("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode", Justification="Called via reflection.")] + [SuppressMessage("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode", Justification = "Called via reflection.")] async Task DoCommitWorkAsync( DoCommitWorkAsyncParameters parameters) { diff --git a/Aspects/Model/Properties/AssemblyInfo.cs b/Aspects/Model/Properties/AssemblyInfo.cs index ad35228..f7e9f20 100644 --- a/Aspects/Model/Properties/AssemblyInfo.cs +++ b/Aspects/Model/Properties/AssemblyInfo.cs @@ -3,9 +3,9 @@ [assembly: AssemblyTitle("vm.Aspect.Model")] [assembly: AssemblyDescription("Defines the IRepository and related base classes and utilities - a framework of building domain object model.")] -[assembly: AssemblyVersion("1.0.23")] -[assembly: AssemblyFileVersion("1.0.23")] -[assembly: AssemblyInformationalVersion("1.0.23")] +[assembly: AssemblyVersion("1.0.25")] +[assembly: AssemblyFileVersion("1.0.25")] +[assembly: AssemblyInformationalVersion("1.0.25")] [assembly: System.Runtime.CompilerServices.InternalsVisibleTo( "vm.Aspects.Model.Tests, " + diff --git a/Aspects/Model/Tests/EFRepository/EFSpecificsTests.cs b/Aspects/Model/Tests/EFRepository/EFSpecificsTests.cs index 4488883..c1b99a1 100644 --- a/Aspects/Model/Tests/EFRepository/EFSpecificsTests.cs +++ b/Aspects/Model/Tests/EFRepository/EFSpecificsTests.cs @@ -54,6 +54,7 @@ protected override IOrmSpecifics GetSpecifics() } [TestMethod] + [TestCategory("IntegrationTest")] public void EnlistInAmbientTransactionRolledBack() { var specifics = GetSpecifics(); @@ -90,6 +91,7 @@ public void EnlistInAmbientTransactionRolledBack() } [TestMethod] + [TestCategory("IntegrationTest")] public override void EnlistInAmbientTransaction() { var specifics = GetSpecifics(); @@ -126,6 +128,7 @@ public override void EnlistInAmbientTransaction() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ObjectIsProxyTest() { try @@ -195,6 +198,7 @@ public override void ObjectIsProxyTest() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ObjectIsLoadedTest() { long id; @@ -249,6 +253,7 @@ public override void ObjectIsLoadedTest() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ObjectIsChangeTrackingTest() { var specifics = GetSpecifics(); @@ -281,6 +286,7 @@ public override void ObjectIsChangeTrackingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ExceptionIsOptimisticConcurrencyTest() { var specifics = GetSpecifics(); @@ -291,6 +297,7 @@ public override void ExceptionIsOptimisticConcurrencyTest() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ExceptionIsConnectionRelatedTest() { // SqlException-s cannot be instantiated or mocked. @@ -298,6 +305,7 @@ public override void ExceptionIsConnectionRelatedTest() } [TestMethod] + [TestCategory("IntegrationTest")] public override void ExceptionIsTransientTest() { var specifics = GetSpecifics(); diff --git a/Aspects/Model/Tests/IOrmSpecificsTests.cs b/Aspects/Model/Tests/IOrmSpecificsTests.cs index 07c0b87..59321a4 100644 --- a/Aspects/Model/Tests/IOrmSpecificsTests.cs +++ b/Aspects/Model/Tests/IOrmSpecificsTests.cs @@ -35,6 +35,7 @@ protected IRepository GetInitializedRepository() protected abstract IOrmSpecifics GetSpecifics(); [TestMethod] + [TestCategory("IntegrationTest")] public void FetchTest() { IRepository target; diff --git a/Aspects/Model/Tests/IRepositoryTest.cs b/Aspects/Model/Tests/IRepositoryTest.cs index 4a25fe3..4d6efb0 100644 --- a/Aspects/Model/Tests/IRepositoryTest.cs +++ b/Aspects/Model/Tests/IRepositoryTest.cs @@ -39,6 +39,7 @@ protected IRepository GetInitializedRepository() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void InitializeTest() { try @@ -66,6 +67,7 @@ public virtual void InitializeTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void GetGenericStoreIdTest() { var target = GetInitializedRepository(); @@ -85,6 +87,7 @@ public virtual void GetGenericStoreIdTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void CreateEntityTest() { var target = GetInitializedRepository(); @@ -97,6 +100,7 @@ public virtual void CreateEntityTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void CreateValueTest() { var target = GetInitializedRepository(); @@ -109,6 +113,7 @@ public virtual void CreateValueTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AddTest() { long id; @@ -137,6 +142,7 @@ public virtual void AddTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AddDerivedTest() { long id, id1; @@ -180,6 +186,7 @@ public virtual void AddDerivedTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AddBaseTest() { long id2, id1; @@ -223,6 +230,7 @@ public virtual void AddBaseTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachTest() { long id; @@ -253,6 +261,7 @@ public virtual void AttachTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachModifiedTest() { long id; @@ -285,6 +294,7 @@ public virtual void AttachModifiedTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachAddedExistingTest() { long id; @@ -339,6 +349,7 @@ public virtual void AttachAddedExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachAddedNonExistingTest() { long id; @@ -386,6 +397,7 @@ public virtual void AttachAddedNonExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachDeletedExistingTest() { long id; @@ -418,6 +430,7 @@ public virtual void AttachDeletedExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void AttachDeletedNonExistingTest() { long id; @@ -478,6 +491,7 @@ public virtual void AttachDeletedNonExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void DetachTest() { long id; @@ -510,6 +524,7 @@ public virtual void DetachTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void GetByStoreIdExistingTest() { long id; @@ -542,6 +557,7 @@ public virtual void GetByStoreIdExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void GetByStoreIdNotExistingTest() { long id; @@ -559,6 +575,7 @@ public virtual void GetByStoreIdNotExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void DeleteExistingFromContextTest() { long id; @@ -589,6 +606,7 @@ public virtual void DeleteExistingFromContextTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void DeleteExistingTest() { long id; @@ -629,6 +647,7 @@ public virtual void DeleteExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void DeleteNotExistingTest() { long id; @@ -658,6 +677,7 @@ public virtual void DeleteNotExistingTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void EntitiesTest() { IRepository target; @@ -713,6 +733,7 @@ public virtual void EntitiesTest() } [TestMethod] + [TestCategory("IntegrationTest")] public virtual void DetachedEntitiesTest() { IRepository target; diff --git a/Aspects/Model/packages.config b/Aspects/Model/packages.config index b0add85..caf8468 100644 --- a/Aspects/Model/packages.config +++ b/Aspects/Model/packages.config @@ -5,6 +5,7 @@ + diff --git a/Aspects/Model/vm.Aspects.Model.csproj b/Aspects/Model/vm.Aspects.Model.csproj index e07e1e3..d64bf80 100644 --- a/Aspects/Model/vm.Aspects.Model.csproj +++ b/Aspects/Model/vm.Aspects.Model.csproj @@ -200,6 +200,10 @@ ..\..\packages\EnterpriseLibrary.ExceptionHandling.Logging.6.0.1304.0\lib\NET45\Microsoft.Practices.EnterpriseLibrary.ExceptionHandling.Logging.dll True + + ..\..\..\Almond Bank Core Services\Services\packages\EnterpriseLibrary.ExceptionHandling.WCF.6.0.1304.0\lib\NET45\Microsoft.Practices.EnterpriseLibrary.ExceptionHandling.WCF.dll + True + ..\..\packages\EnterpriseLibrary.Logging.6.0.1304.0\lib\NET45\Microsoft.Practices.EnterpriseLibrary.Logging.dll True @@ -240,6 +244,7 @@ + diff --git a/Aspects/NuGet/vm.Aspects.nuspec b/Aspects/NuGet/vm.Aspects.nuspec index fe72e11..3d61270 100644 --- a/Aspects/NuGet/vm.Aspects.nuspec +++ b/Aspects/NuGet/vm.Aspects.nuspec @@ -2,7 +2,7 @@ vm.Aspects - 1.0.23-beta + 1.0.25-beta Val Melamed Val Melamed @@ -12,8 +12,7 @@ A set of classes, utilities, etc. addressing various common cross-cutting concerns or extending existing similar libraries like Enterprise Library, Unity, etc. - * Added and tested MAC keyed hashers like HMAC-SHA256 or MAC-3DES. - * Added and tested a MAC key importing/exporting utility "MacKey" in the style of EncryptedKey or ProtectedKey. + vm.Aspects.Model: Fixed a bug in the DomainEntity and in the resolution of the HiLoStoreIdProvider. https://github.com/vmelamed/vm/blob/master/LICENSE https://github.com/vmelamed/vm/tree/master/Aspects diff --git a/Aspects/Parsers/Properties/AssemblyInfo.cs b/Aspects/Parsers/Properties/AssemblyInfo.cs index ba38105..af00d27 100644 --- a/Aspects/Parsers/Properties/AssemblyInfo.cs +++ b/Aspects/Parsers/Properties/AssemblyInfo.cs @@ -6,9 +6,9 @@ [assembly: AssemblyTitle("vm.Aspects.Parser")] [assembly: AssemblyDescription("Text parsing readers, e.g. CSV/TSV reader.")] -[assembly: AssemblyVersion("1.0.23")] -[assembly: AssemblyFileVersion("1.0.23")] -[assembly: AssemblyInformationalVersion("1.0.23")] +[assembly: AssemblyVersion("1.0.25")] +[assembly: AssemblyFileVersion("1.0.25")] +[assembly: AssemblyInformationalVersion("1.0.25")] [assembly: System.Runtime.CompilerServices.InternalsVisibleTo( "vm.Aspects.Parsers.Tests, " + diff --git a/Aspects/Properties/AssemblyInfo.cs b/Aspects/Properties/AssemblyInfo.cs index 6461f4e..eba99b7 100644 --- a/Aspects/Properties/AssemblyInfo.cs +++ b/Aspects/Properties/AssemblyInfo.cs @@ -2,9 +2,9 @@ [assembly: AssemblyTitle("vm.Aspects")] [assembly: AssemblyDescription("A set of classes addressing various common cross-cutting concerns.")] -[assembly: AssemblyVersion("1.0.23")] -[assembly: AssemblyFileVersion("1.0.23")] -[assembly: AssemblyInformationalVersion("1.0.23")] +[assembly: AssemblyVersion("1.0.25")] +[assembly: AssemblyFileVersion("1.0.25")] +[assembly: AssemblyInformationalVersion("1.0.25")] [assembly: System.Runtime.CompilerServices.InternalsVisibleTo( diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherAsyncContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherAsyncContract.cs deleted file mode 100644 index 4b0405a..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherAsyncContract.cs +++ /dev/null @@ -1,71 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.IO; -using System.Threading.Tasks; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(ICipherAsync))] - abstract class ICipherAsyncContract : ICipherAsync - { - #region ICipherAsync Members - public Task EncryptAsync(Stream dataStream, Stream encryptedStream) - { - Contract.Requires(dataStream != null, "dataStream"); - Contract.Requires(encryptedStream != null, "encryptedStream"); - Contract.Requires(dataStream.CanRead, "The argument \"dataStream\" cannot be read from."); - Contract.Requires(encryptedStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); - - throw new NotImplementedException(); - } - - public Task DecryptAsync(Stream encryptedStream, Stream dataStream) - { - Contract.Requires(encryptedStream != null, "encryptedStream"); - Contract.Requires(dataStream != null, "dataStream"); - Contract.Requires(encryptedStream.CanRead, "The argument \"dataStream\" cannot be read from."); - Contract.Requires(dataStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); - - throw new NotImplementedException(); - } - #endregion - - #region ICipher Members - public bool Base64Encoded { get; set; } - - public void Encrypt( - Stream dataStream, - Stream encryptedStream) - { - throw new NotImplementedException(); - } - - public void Decrypt( - Stream encryptedStream, - Stream dataStream) - { - throw new NotImplementedException(); - } - - public byte[] Encrypt(byte[] data) - { - throw new NotImplementedException(); - } - - public byte[] Decrypt(byte[] encryptedData) - { - throw new NotImplementedException(); - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherContract.cs deleted file mode 100644 index fb4b1ac..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/ICipherContract.cs +++ /dev/null @@ -1,55 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.IO; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(ICipher))] - abstract class ICipherContract : ICipher - { - #region ICipher Members - public bool Base64Encoded { get; set; } - - public void Encrypt(Stream dataStream, Stream encryptedStream) - { - Contract.Requires(dataStream != null, "dataStream"); - Contract.Requires(encryptedStream != null, "encryptedStream"); - Contract.Requires(dataStream.CanRead, "The argument \"dataStream\" cannot be read from."); - Contract.Requires(encryptedStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); - - throw new NotImplementedException(); - } - - public void Decrypt(Stream encryptedStream, Stream dataStream) - { - Contract.Requires(encryptedStream != null, "encryptedStream"); - Contract.Requires(dataStream != null, "dataStream"); - Contract.Requires(encryptedStream.CanRead, "The argument \"dataStream\" cannot be read from."); - Contract.Requires(dataStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); - - throw new NotImplementedException(); - } - - public byte[] Encrypt(byte[] data) - { - Contract.Ensures(!(data==null ^ Contract.Result()==null)); - - throw new NotImplementedException(); - } - - public byte[] Decrypt(byte[] encryptedData) - { - Contract.Ensures(!(encryptedData==null ^ Contract.Result()==null)); - - throw new NotImplementedException(); - } - #endregion - - #region IDisposable Members - public void Dispose() - { - throw new NotImplementedException(); - } - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IHashAlgorithmFactoryContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IHashAlgorithmFactoryContract.cs deleted file mode 100644 index 76754c2..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IHashAlgorithmFactoryContract.cs +++ /dev/null @@ -1,41 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.Security.Cryptography; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IHashAlgorithmFactory))] - abstract class IHashAlgorithmFactoryContract : IHashAlgorithmFactory - { - #region IHashAlgorithmFactory Members - - public void Initialize( - string hashAlgorithmName) - { - throw new NotImplementedException(); - } - - public HashAlgorithm Create() - { - Contract.Ensures(Contract.Result() != null, "Could not create a hash algorithm."); - - throw new NotImplementedException(); - } - - public string HashAlgorithmName - { - get { throw new NotImplementedException(); } - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherAsyncContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherAsyncContract.cs deleted file mode 100644 index 476fcfe..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherAsyncContract.cs +++ /dev/null @@ -1,77 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.IO; -using System.Threading.Tasks; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IHasherAsync))] - abstract class IHasherAsyncContract : IHasherAsync - { - #region IHasherAsync Members - - public Task HashAsync(Stream dataStream) - { - Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); - Contract.Ensures(!(dataStream==null ^ Contract.Result()==null), "The returned value is invalid."); - - throw new NotImplementedException(); - } - - public Task TryVerifyHashAsync(Stream dataStream, byte[] hash) - { - Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); - Contract.Requires(dataStream==null || hash!=null, "hash"); - Contract.Ensures(dataStream!=null || Contract.Result()==(hash==null), "Invalid return value."); - - throw new NotImplementedException(); - } - - #endregion - - #region IHasher Members - - public int SaltLength - { - get - { - throw new NotImplementedException(); - } - set - { - throw new NotImplementedException(); - } - } - - public byte[] Hash(System.IO.Stream dataStream) - { - throw new NotImplementedException(); - } - - public bool TryVerifyHash(System.IO.Stream dataStream, byte[] hash) - { - throw new NotImplementedException(); - } - - public byte[] Hash(byte[] data) - { - throw new NotImplementedException(); - } - - public bool TryVerifyHash(byte[] data, byte[] hash) - { - throw new NotImplementedException(); - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherContract.cs deleted file mode 100644 index c1d6e93..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IHasherContract.cs +++ /dev/null @@ -1,75 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.IO; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IHasher))] - abstract class IHasherContract : IHasher - { - #region IHasher Members - - public int SaltLength - { - get - { - Contract.Ensures(Contract.Result()==0 || Contract.Result()>=Hasher.DefaultSaltLength, "The salt length should be either 0 or not less than 8 bytes."); - - throw new NotImplementedException(); - } - set - { - Contract.Requires(value==0 || value>=8, "The salt length should be either 0 or not less than 8 bytes."); - - throw new NotImplementedException(); - } - } - - public byte[] Hash( - Stream dataStream) - { - Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); - Contract.Ensures(!(dataStream==null ^ Contract.Result()==null), "The returned value is invalid."); - - throw new NotImplementedException(); - } - - public bool TryVerifyHash( - Stream dataStream, - byte[] hash) - { - Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); - Contract.Requires(dataStream==null || hash!=null, "hash"); - Contract.Ensures(dataStream!=null || Contract.Result()==(hash==null), "Invalid return value."); - - throw new NotImplementedException(); - } - - public byte[] Hash( - byte[] data) - { - Contract.Ensures(!(data==null ^ Contract.Result()==null), "Invalid return value."); - - throw new NotImplementedException(); - } - - public bool TryVerifyHash(byte[] data, byte[] hash) - { - Contract.Requires(data==null || hash!=null, "hash"); - Contract.Ensures(data!=null || Contract.Result()==(hash==null), "Invalid return value."); - - throw new NotImplementedException(); - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyLocationStrategyContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyLocationStrategyContract.cs deleted file mode 100644 index 7e06599..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyLocationStrategyContract.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Diagnostics.Contracts; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IKeyLocationStrategy))] - abstract class IKeyLocationStrategyContract : IKeyLocationStrategy - { - #region IKeyLocationStrategy Members - public string GetKeyLocation(string keyLocation) - { - Contract.Ensures(!string.IsNullOrWhiteSpace(Contract.Result()), "The key location cannot be null, empty or consist of whitespace characters only."); - - throw new NotImplementedException(); - } - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyManagementContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyManagementContract.cs deleted file mode 100644 index 991af43..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyManagementContract.cs +++ /dev/null @@ -1,48 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.Threading.Tasks; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IKeyManagement))] - abstract class IKeyManagementContract : IKeyManagement - { - #region IKeyManagement Members - public string KeyLocation - { - get - { - Contract.Ensures(!String.IsNullOrEmpty(Contract.Result()), "The key location cannot be null, empty or consist of whitespace characters only."); - - throw new NotImplementedException(); - } - } - - public byte[] ExportSymmetricKey() - { - throw new NotImplementedException(); - } - - public Task ExportSymmetricKeyAsync() - { - throw new NotImplementedException(); - } - - public void ImportSymmetricKey(byte[] key) - { - Contract.Requires(key != null, "key"); - Contract.Requires(key.Length > 0, "The length of the imported key is 0"); - - throw new NotImplementedException(); - } - - public Task ImportSymmetricKeyAsync(byte[] key) - { - Contract.Requires(key != null, "key"); - Contract.Requires(key.Length > 0, "The length of the imported key is 0"); - - throw new NotImplementedException(); - } - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageAsyncContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageAsyncContract.cs deleted file mode 100644 index c3e1661..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageAsyncContract.cs +++ /dev/null @@ -1,62 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Diagnostics.Contracts; -using System.Threading.Tasks; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IKeyStorageAsync))] - abstract class IKeyStorageAsyncContract : IKeyStorageAsync - { - #region IKeyStorage Members - public bool KeyLocationExists( - string keyLocation) - { - throw new NotImplementedException(); - } - - [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods", MessageId="0")] - public void PutKey( - byte[] key, - string keyLocation) - { - throw new NotImplementedException(); - } - - public byte[] GetKey( - string keyLocation) - { - throw new NotImplementedException(); - } - - public void DeleteKeyLocation( - string keyLocation) - { - throw new NotImplementedException(); - } - #endregion - - #region IKeyStorageAsync Members - [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods", MessageId="0")] - public Task PutKeyAsync(byte[] key, string keyLocation) - { - Contract.Requires(key != null, "key"); - Contract.Requires(key.Length != 0, "The length of the array in the argument \"key\" cannot be 0."); - Contract.Requires(keyLocation != null, "keyLocation"); - Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); - - throw new NotImplementedException(); - } - - public Task GetKeyAsync(string keyLocation) - { - Contract.Requires(keyLocation != null, "keyLocation"); - Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); - Contract.Ensures(Contract.Result() != null, "The returned value is null."); - Contract.Ensures(Contract.Result().Length != 0, "The returned value has 0 length."); - - throw new NotImplementedException(); - } - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageContract.cs deleted file mode 100644 index c7083b9..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/IKeyStorageContract.cs +++ /dev/null @@ -1,48 +0,0 @@ -using System; -using System.Diagnostics.CodeAnalysis; -using System.Diagnostics.Contracts; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(IKeyStorage))] - abstract class IKeyStorageContract : IKeyStorage - { - #region IKeyStorage Members - - public bool KeyLocationExists(string keyLocation) - { - Contract.Requires(keyLocation != null, "keyLocation"); - Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); - - throw new NotImplementedException(); - } - - [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods", MessageId="0")] - public void PutKey(byte[] key, string keyLocation) - { - Contract.Requires(key != null, "key"); - Contract.Requires(key.Length != 0, "The length of the array in the argument \"key\" cannot be 0."); - Contract.Requires(keyLocation != null, "keyLocation"); - Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); - - throw new NotImplementedException(); - } - - public byte[] GetKey(string keyLocation) - { - Contract.Requires(keyLocation != null, "keyLocation"); - Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); - Contract.Ensures(Contract.Result() != null, "The returned key is null."); - Contract.Ensures(Contract.Result().Length != 0, "The returned key has 0 length."); - - throw new NotImplementedException(); - } - - public void DeleteKeyLocation(string keyLocation) - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/ISymmetricAlgorithmFactoryContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/ISymmetricAlgorithmFactoryContract.cs deleted file mode 100644 index da79404..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/ISymmetricAlgorithmFactoryContract.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.Security.Cryptography; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(ISymmetricAlgorithmFactory))] - abstract class ISymmetricAlgorithmFactoryContract : ISymmetricAlgorithmFactory - { - #region ISymmetricAlgorithmFactory Members - public void Initialize( - string symmetricAlgorithmName) - { - } - - public SymmetricAlgorithm Create() - { - Contract.Ensures(Contract.Result() != null, "Could not create a symmetric algorithm."); - - throw new NotImplementedException(); - } - - public string SymmetricAlgorithmName - { - get { throw new NotImplementedException(); } - } - #endregion - - #region IDisposable Members - public void Dispose() - { - throw new NotImplementedException(); - } - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/SymmetricKeyCipherBaseContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/SymmetricKeyCipherBaseContract.cs deleted file mode 100644 index 60d0294..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/SymmetricKeyCipherBaseContract.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Diagnostics.Contracts; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts -{ - [ContractClassFor(typeof(SymmetricKeyCipherBase))] - abstract class SymmetricKeyCipherBaseContract : SymmetricKeyCipherBase - { - protected SymmetricKeyCipherBaseContract() - : base(null) - { - } - - protected override byte[] EncryptSymmetricKey() - { - Contract.Ensures(Contract.Result() != null && Contract.Result().Length > 0, "The method returned null or empty encrypted key."); - - throw new NotImplementedException(); - } - - protected override void DecryptSymmetricKey( - byte[] encryptedKey) - { - Contract.Requires(encryptedKey != null, "encryptedKey"); - Contract.Requires(encryptedKey.Length > 0, "The argument \"encryptedKey\" cannot be empty."); - - throw new NotImplementedException(); - } - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlCipherContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlCipherContract.cs deleted file mode 100644 index eef1e3d..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlCipherContract.cs +++ /dev/null @@ -1,52 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.Xml; -using vm.Aspects.Security.Cryptography.Ciphers.Xml; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts.Xml -{ - [ContractClassFor(typeof(IXmlCipher))] - abstract class IXmlCipherContract : IXmlCipher - { - #region IXmlCipher Members - - public bool ContentOnly - { - get - { - throw new NotImplementedException(); - } - set - { - throw new NotImplementedException(); - } - } - - public void Encrypt( - XmlDocument document, - string xmlPath = null, - XmlNamespaceManager namespaceManager = null) - { - Contract.Requires(document != null, "document"); - throw new NotImplementedException(); - } - - public void Decrypt( - XmlDocument document) - { - Contract.Requires(document != null, "document"); - throw new NotImplementedException(); - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlSignerContract.cs b/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlSignerContract.cs deleted file mode 100644 index 7144454..0000000 --- a/Aspects/Security/Cryptography/Ciphers/Contracts/Xml/IXmlSignerContract.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.Diagnostics.Contracts; -using System.Xml; -using vm.Aspects.Security.Cryptography.Ciphers.Xml; - -namespace vm.Aspects.Security.Cryptography.Ciphers.Contracts.Xml -{ - [ContractClassFor(typeof(IXmlSigner))] - abstract class IXmlSignerContract : IXmlSigner - { - #region IXmlSigner Members - - public SignatureLocation SignatureLocation - { - get - { - Contract.Ensures(Enum.IsDefined(typeof(SignatureLocation), Contract.Result()), "The value of the property is not a valid SignatureLocation value."); - throw new NotImplementedException(); - } - set - { - Contract.Requires(Enum.IsDefined(typeof(SignatureLocation), value), "The value is not a valid SignatureLocation value."); - throw new NotImplementedException(); - } - } - - public bool IncludeKeyInfo - { - get - { - throw new NotImplementedException(); - } - set - { - throw new NotImplementedException(); - } - } - - public XmlDocument Sign( - XmlDocument document, - string xmlPath = null, - XmlNamespaceManager namespaceManager = null, - Uri documentLocation = null) - { - Contract.Requires(document != null, "document"); - throw new NotImplementedException(); - } - - public bool TryVerifySignature( - XmlDocument document, - XmlDocument signature = null) - { - Contract.Requires(document != null, "document"); - throw new NotImplementedException(); - } - - #endregion - - #region IDisposable Members - - public void Dispose() - { - throw new NotImplementedException(); - } - - #endregion - } -} diff --git a/Aspects/Security/Cryptography/Ciphers/Documents/Ciphers.docx b/Aspects/Security/Cryptography/Ciphers/Documents/Ciphers.docx index 9778279..a882f1e 100644 Binary files a/Aspects/Security/Cryptography/Ciphers/Documents/Ciphers.docx and b/Aspects/Security/Cryptography/Ciphers/Documents/Ciphers.docx differ diff --git a/Aspects/Security/Cryptography/Ciphers/HashAlgorithmFactory.cs b/Aspects/Security/Cryptography/Ciphers/HashAlgorithmFactory.cs index a3b3557..f0d02c7 100644 --- a/Aspects/Security/Cryptography/Ciphers/HashAlgorithmFactory.cs +++ b/Aspects/Security/Cryptography/Ciphers/HashAlgorithmFactory.cs @@ -1,8 +1,6 @@ using System; -using System.Diagnostics.CodeAnalysis; using System.Globalization; using System.Security.Cryptography; -using System.Threading; using Microsoft.Practices.ServiceLocation; namespace vm.Aspects.Security.Cryptography.Ciphers @@ -20,10 +18,6 @@ public sealed class HashAlgorithmFactory : IHashAlgorithmFactory /// The generated hash factory /// Func _hashFactory; - /// - /// A temporary hash algorithm object. - /// - HashAlgorithm _hashAlgorithm; #region IHashAlgorithmFactory members /// @@ -64,9 +58,9 @@ public void Initialize( { // 2. try to resolve the hash algorithm object directly from the CSL _hashFactory = () => ServiceLocatorWrapper.Default.GetInstance(); - _hashAlgorithm = _hashFactory(); - // if we are here, we've got our factory. - return; + using (var hashAlgorithm = _hashFactory()) + // if we are here, we've got our factory. + return; } catch (ActivationException) { @@ -92,14 +86,14 @@ public void Initialize( _hashFactory = () => HashAlgorithm.Create(_hashAlgorithmName); // try it - _hashAlgorithm = _hashFactory(); - if (_hashAlgorithm == null) - // if unsuccessful - throw an exception. - throw new ActivationException( - string.Format( - CultureInfo.InvariantCulture, - "The name \"{0}\" was not recognized as a valid hash algorithm.", - _hashAlgorithmName)); + using (var hashAlgorithm = _hashFactory()) + if (hashAlgorithm == null) + // if unsuccessful - throw an exception. + throw new ActivationException( + string.Format( + CultureInfo.InvariantCulture, + "The name \"{0}\" was not recognized as a valid hash algorithm.", + _hashAlgorithmName)); } /// @@ -114,13 +108,7 @@ public HashAlgorithm Create() if (_hashFactory == null) throw new InvalidOperationException("The factory was not initialized properly. Call Initialize first."); - if (_hashAlgorithm == null) - return _hashFactory(); - - var hashAlgorithm = _hashAlgorithm; - - _hashAlgorithm = null; - return hashAlgorithm; + return _hashFactory(); } /// @@ -132,70 +120,5 @@ public string HashAlgorithmName get { return _hashAlgorithmName; } } #endregion - - #region IDisposable pattern implementation - /// - /// The flag will be set just before the object is disposed. - /// - /// 0 - if the object is not disposed yet, any other value - the object is already disposed. - /// - /// Do not test or manipulate this flag outside of the property or the method . - /// The type of this field is Int32 so that it can be easily passed to the members of the class . - /// - int _disposed; - - /// - /// Returns true if the object has already been disposed, otherwise false. - /// - public bool IsDisposed - { - get { return Volatile.Read(ref _disposed) != 0; } - } - - /// - /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. - /// - /// Invokes the protected virtual . - [SuppressMessage("Microsoft.Design", "CA1063:ImplementIDisposableCorrectly", Justification = "It is correct.")] - public void Dispose() - { - // if it is disposed or in a process of disposing - return. - if (Interlocked.Exchange(ref _disposed, 1) != 0) - return; - - // these will be called only if the instance is not disposed yet or is not in a process of disposing. - Dispose(true); - GC.SuppressFinalize(this); - } - - /// - /// Allows the object to attempt to free resources and perform other cleanup operations before it is reclaimed by garbage collection. - /// - /// Invokes the protected virtual . - ~HashAlgorithmFactory() - { - Dispose(false); - } - - /// - /// Performs the actual job of disposing the object. - /// - /// - /// Passes the information whether this method is called by (explicitly or - /// implicitly at the end of a using statement), or by the . - /// - /// - /// If the method is called with ==true, i.e. from , - /// it will try to release all managed resources (usually aggregated objects which implement as well) - /// and then it will release all unmanaged resources if any. If the parameter is false then - /// the method will only try to release the unmanaged resources. - /// - /*protected virtual*/ - void Dispose(bool disposing) - { - if (disposing && _hashAlgorithm != null) - _hashAlgorithm.Dispose(); - } - #endregion } } diff --git a/Aspects/Security/Cryptography/Ciphers/Hasher.cs b/Aspects/Security/Cryptography/Ciphers/Hasher.cs index 91d2e3a..3f216ac 100644 --- a/Aspects/Security/Cryptography/Ciphers/Hasher.cs +++ b/Aspects/Security/Cryptography/Ciphers/Hasher.cs @@ -35,9 +35,9 @@ public class Hasher : IHasherAsync #region Fields /// - /// Caches the hash algorithm factory + /// The underlying hash algorithm. /// - readonly IHashAlgorithmFactory _hashAlgorithmFactory; + readonly HashAlgorithm _hashAlgorithm; /// /// The salt length. /// @@ -62,8 +62,10 @@ public Hasher( { Contract.Requires(saltLength==0 || saltLength>=DefaultSaltLength, "The salt length should be either 0 or not less than 8 bytes."); - _hashAlgorithmFactory = ServiceLocatorWrapper.Default.GetInstance(); - _hashAlgorithmFactory.Initialize(hashAlgorithmName); + var hashAlgorithmFactory = ServiceLocatorWrapper.Default.GetInstance(); + hashAlgorithmFactory.Initialize(hashAlgorithmName); + + _hashAlgorithm = hashAlgorithmFactory.Create(); _saltLength = saltLength; } @@ -71,20 +73,24 @@ public Hasher( #region Properties /// - /// Gets a value indicating whether the hash should be salted. + /// Gets the name of the hash algorithm. /// - public bool ShouldSalt + public string HashAlgorithmName { - get { return SaltLength > 0; } + get + { + Contract.Ensures(!string.IsNullOrWhiteSpace(Contract.Result())); + + return _hashAlgorithm.GetType().FullName; + } } /// - /// Gets the name of the hash algorithm. + /// Gets a value indicating whether the hash should be salted. /// - /// The name of the hash algorithm. - public string HashAlgorithmName + public bool ShouldSalt { - get { return _hashAlgorithmFactory.HashAlgorithmName; } + get { return SaltLength > 0; } } #endregion @@ -116,13 +122,13 @@ public virtual byte[] Hash( if (!dataStream.CanRead) throw new ArgumentException("The data stream cannot be read.", "dataStream"); - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - using (var hashStream = CreateHashStream(hashAlgorithm)) + _hashAlgorithm.Initialize(); + using (var hashStream = CreateHashStream()) { var salt = WriteSalt(hashStream, null); dataStream.CopyTo(hashStream); - return FinalizeHashing(hashStream, hashAlgorithm, salt); + return FinalizeHashing(hashStream, salt); } } @@ -148,35 +154,38 @@ public virtual bool TryVerifyHash( // save the property value - it may change for this call only depending on the length of the hash var savedSaltLength = SaltLength; - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - try + try + { + _hashAlgorithm.Initialize(); + + // the parameter hash has the length of the expected product from this algorithm, i.e. there is no salt + if (hash.Length == _hashAlgorithm.HashSize/8) + SaltLength = 0; + else { - // the parameter hash has the length of the expected product from this algorithm, i.e. there is no salt - if (hash.Length == hashAlgorithm.HashSize/8) - SaltLength = 0; - else - // the parameter hash has the length of the expected product from this algorithm + the length of the salt, i.e. there is salt in the parameter salt - if (hash.Length > hashAlgorithm.HashSize/8) - SaltLength = hash.Length - hashAlgorithm.HashSize/8; + // the parameter hash has the length of the expected product from this algorithm + the length of the salt, i.e. there is salt in the parameter salt + if (hash.Length > _hashAlgorithm.HashSize/8) + SaltLength = hash.Length - _hashAlgorithm.HashSize/8; else // this is wrong... return false; + } - using (var hashStream = CreateHashStream(hashAlgorithm)) - { - WriteSalt(hashStream, hash); - dataStream.CopyTo(hashStream); + using (var hashStream = CreateHashStream()) + { + WriteSalt(hashStream, hash); + dataStream.CopyTo(hashStream); - byte[] computedHash = FinalizeHashing(hashStream, hashAlgorithm, hash); + byte[] computedHash = FinalizeHashing(hashStream, hash); - return computedHash.ConstantTimeEquals(hash); - } - } - finally - { - // restore the value of the property - SaltLength = savedSaltLength; + return computedHash.ConstantTimeEquals(hash); } + } + finally + { + // restore the value of the property + SaltLength = savedSaltLength; + } } /// @@ -191,13 +200,13 @@ public virtual byte[] Hash( if (data == null) return null; - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - using (var hashStream = CreateHashStream(hashAlgorithm)) + _hashAlgorithm.Initialize(); + using (var hashStream = CreateHashStream()) { var salt = WriteSalt(hashStream, null); hashStream.Write(data, 0, data.Length); - return FinalizeHashing(hashStream, hashAlgorithm, salt); + return FinalizeHashing(hashStream, salt); } } @@ -222,35 +231,38 @@ public virtual bool TryVerifyHash( // save the property value - it may change for this call only var savedSaltLength = SaltLength; - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - try + try + { + _hashAlgorithm.Initialize(); + + // the parameter hash has the length of the expected product from this algorithm, i.e. there is no salt + if (hash.Length == _hashAlgorithm.HashSize/8) + SaltLength = 0; + else { - // the parameter hash has the length of the expected product from this algorithm, i.e. there is no salt - if (hash.Length == hashAlgorithm.HashSize/8) - SaltLength = 0; - else - // the parameter hash has the length of the expected product from this algorithm + the length of the salt, i.e. there is salt in the parameter salt - if (hash.Length > hashAlgorithm.HashSize/8) - SaltLength = hash.Length - hashAlgorithm.HashSize/8; + // the parameter hash has the length of the expected product from this algorithm + the length of the salt, i.e. there is salt in the parameter salt + if (hash.Length > _hashAlgorithm.HashSize/8) + SaltLength = hash.Length - _hashAlgorithm.HashSize/8; else // this is wrong... return false; + } - using (var hashStream = CreateHashStream(hashAlgorithm)) - { - WriteSalt(hashStream, hash); - hashStream.Write(data, 0, data.Length); + using (var hashStream = CreateHashStream()) + { + WriteSalt(hashStream, hash); + hashStream.Write(data, 0, data.Length); - byte[] computedHash = FinalizeHashing(hashStream, hashAlgorithm, hash); + byte[] computedHash = FinalizeHashing(hashStream, hash); - return computedHash.ConstantTimeEquals(hash); - } - } - finally - { - // restore the property value - SaltLength = savedSaltLength; + return computedHash.ConstantTimeEquals(hash); } + } + finally + { + // restore the property value + SaltLength = savedSaltLength; + } } #endregion @@ -269,13 +281,13 @@ public virtual async Task HashAsync( if (dataStream == null) return null; - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - using (var hashStream = CreateHashStream(hashAlgorithm)) + _hashAlgorithm.Initialize(); + using (var hashStream = CreateHashStream()) { var salt = await WriteSaltAsync(hashStream, null); await dataStream.CopyToAsync(hashStream); - return FinalizeHashing(hashStream, hashAlgorithm, salt); + return FinalizeHashing(hashStream, salt); } } @@ -300,35 +312,38 @@ public virtual async Task TryVerifyHashAsync( // save the property value - it may change for this call only depending on the length of the hash var savedSaltLength = SaltLength; - using (var hashAlgorithm = _hashAlgorithmFactory.Create()) - try + try + { + _hashAlgorithm.Initialize(); + + // the hash has the same length as the length of the key - there is no salt + if (hash.Length == _hashAlgorithm.HashSize/8) + SaltLength = 0; + else { - // the hash has the same length as the length of the key - there is no salt - if (hash.Length == hashAlgorithm.HashSize/8) - SaltLength = 0; - else - // the hash has the same length as the length of the key + the length of the salt - there is salt in the parameter salt - if (hash.Length > hashAlgorithm.HashSize/8) - SaltLength = hash.Length - hashAlgorithm.HashSize/8; + // the hash has the same length as the length of the key + the length of the salt - there is salt in the parameter salt + if (hash.Length > _hashAlgorithm.HashSize/8) + SaltLength = hash.Length - _hashAlgorithm.HashSize/8; else // this is wrong... return false; + } - using (var hashStream = CreateHashStream(hashAlgorithm)) - { - await WriteSaltAsync(hashStream, hash); - await dataStream.CopyToAsync(hashStream); + using (var hashStream = CreateHashStream()) + { + await WriteSaltAsync(hashStream, hash); + await dataStream.CopyToAsync(hashStream); - byte[] computedHash = FinalizeHashing(hashStream, hashAlgorithm, hash); + byte[] computedHash = FinalizeHashing(hashStream, hash); - return computedHash.ConstantTimeEquals(hash); - } - } - finally - { - // restore the value of the property - SaltLength = savedSaltLength; + return computedHash.ConstantTimeEquals(hash); } + } + finally + { + // restore the value of the property + SaltLength = savedSaltLength; + } } #endregion @@ -338,12 +353,9 @@ public virtual async Task TryVerifyHashAsync( /// /// CryptoStream. [SuppressMessage("Microsoft.Reliability", "CA2000:Dispose objects before losing scope", Justification = "It will be disposed by the calling code.")] - protected virtual CryptoStream CreateHashStream( - HashAlgorithm hashAlgorithm) + protected virtual CryptoStream CreateHashStream() { - Contract.Requires(hashAlgorithm != null, "hashAlgorithm"); - - return new CryptoStream(new NullStream(), hashAlgorithm, CryptoStreamMode.Write); + return new CryptoStream(new NullStream(), _hashAlgorithm, CryptoStreamMode.Write); } /// @@ -377,7 +389,6 @@ protected virtual byte[] WriteSalt( /// Finalizes the hashing. /// /// The hash stream. - /// The hash algorithm. /// The salt. /// The hash. /// Thrown when is . @@ -386,23 +397,21 @@ protected virtual byte[] WriteSalt( [SuppressMessage("Microsoft.Design", "CA1062:Validate arguments of public methods", MessageId = "2", Justification = "salt is conditionally validated.")] protected virtual byte[] FinalizeHashing( CryptoStream hashStream, - HashAlgorithm hashAlgorithm, byte[] salt) { Contract.Requires(hashStream != null, "hashStream"); Contract.Requires(hashStream.CanWrite, "The argument \"hashStream\" cannot be written to."); - Contract.Requires(hashAlgorithm != null, "hashAlgorithm"); Contract.Requires(!ShouldSalt || salt != null, "salt"); if (!hashStream.HasFlushedFinalBlock) hashStream.FlushFinalBlock(); - var hash = new byte[SaltLength + hashAlgorithm.HashSize/8]; + var hash = new byte[SaltLength + _hashAlgorithm.HashSize/8]; if (SaltLength > 0) salt.CopyTo(hash, 0); - hashAlgorithm.Hash.CopyTo(hash, SaltLength); + _hashAlgorithm.Hash.CopyTo(hash, SaltLength); return hash; } @@ -497,14 +506,14 @@ public void Dispose() protected virtual void Dispose(bool disposing) { if (disposing) - _hashAlgorithmFactory.Dispose(); + _hashAlgorithm.Dispose(); } #endregion [ContractInvariantMethod] void Invariant() { - Contract.Invariant(_hashAlgorithmFactory != null, "The hash algorithm factory cannot be null."); + Contract.Invariant(_hashAlgorithm != null, "The hash algorithm factory cannot be null."); Contract.Invariant(_saltLength==0 || _saltLength>=DefaultSaltLength, "Invalid salt length."); } } diff --git a/Aspects/Security/Cryptography/Ciphers/ICipher.cs b/Aspects/Security/Cryptography/Ciphers/ICipher.cs index 49bb6e6..71b294a 100644 --- a/Aspects/Security/Cryptography/Ciphers/ICipher.cs +++ b/Aspects/Security/Cryptography/Ciphers/ICipher.cs @@ -1,7 +1,6 @@ using System; using System.Diagnostics.Contracts; using System.IO; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -112,4 +111,53 @@ byte[] Encrypt( byte[] Decrypt( byte[] encryptedData); } + + [ContractClassFor(typeof(ICipher))] + abstract class ICipherContract : ICipher + { + #region ICipher Members + public bool Base64Encoded { get; set; } + + public void Encrypt(Stream dataStream, Stream encryptedStream) + { + Contract.Requires(dataStream != null, "dataStream"); + Contract.Requires(encryptedStream != null, "encryptedStream"); + Contract.Requires(dataStream.CanRead, "The argument \"dataStream\" cannot be read from."); + Contract.Requires(encryptedStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); + + throw new NotImplementedException(); + } + + public void Decrypt(Stream encryptedStream, Stream dataStream) + { + Contract.Requires(encryptedStream != null, "encryptedStream"); + Contract.Requires(dataStream != null, "dataStream"); + Contract.Requires(encryptedStream.CanRead, "The argument \"dataStream\" cannot be read from."); + Contract.Requires(dataStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); + + throw new NotImplementedException(); + } + + public byte[] Encrypt(byte[] data) + { + Contract.Ensures(!(data==null ^ Contract.Result()==null)); + + throw new NotImplementedException(); + } + + public byte[] Decrypt(byte[] encryptedData) + { + Contract.Ensures(!(encryptedData==null ^ Contract.Result()==null)); + + throw new NotImplementedException(); + } + #endregion + + #region IDisposable Members + public void Dispose() + { + throw new NotImplementedException(); + } + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/ICipherAsync.cs b/Aspects/Security/Cryptography/Ciphers/ICipherAsync.cs index 91e7542..f685d63 100644 --- a/Aspects/Security/Cryptography/Ciphers/ICipherAsync.cs +++ b/Aspects/Security/Cryptography/Ciphers/ICipherAsync.cs @@ -1,7 +1,7 @@ -using System.Diagnostics.Contracts; +using System; +using System.Diagnostics.Contracts; using System.IO; using System.Threading.Tasks; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -74,4 +74,68 @@ Task DecryptAsync( Stream encryptedStream, Stream dataStream); } + + [ContractClassFor(typeof(ICipherAsync))] + abstract class ICipherAsyncContract : ICipherAsync + { + #region ICipherAsync Members + public Task EncryptAsync(Stream dataStream, Stream encryptedStream) + { + Contract.Requires(dataStream != null, "dataStream"); + Contract.Requires(encryptedStream != null, "encryptedStream"); + Contract.Requires(dataStream.CanRead, "The argument \"dataStream\" cannot be read from."); + Contract.Requires(encryptedStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); + + throw new NotImplementedException(); + } + + public Task DecryptAsync(Stream encryptedStream, Stream dataStream) + { + Contract.Requires(encryptedStream != null, "encryptedStream"); + Contract.Requires(dataStream != null, "dataStream"); + Contract.Requires(encryptedStream.CanRead, "The argument \"dataStream\" cannot be read from."); + Contract.Requires(dataStream.CanWrite, "The argument \"encryptedStream\" cannot be written to."); + + throw new NotImplementedException(); + } + #endregion + + #region ICipher Members + public bool Base64Encoded { get; set; } + + public void Encrypt( + Stream dataStream, + Stream encryptedStream) + { + throw new NotImplementedException(); + } + + public void Decrypt( + Stream encryptedStream, + Stream dataStream) + { + throw new NotImplementedException(); + } + + public byte[] Encrypt(byte[] data) + { + throw new NotImplementedException(); + } + + public byte[] Decrypt(byte[] encryptedData) + { + throw new NotImplementedException(); + } + + #endregion + + #region IDisposable Members + + public void Dispose() + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IHashAlgorithmFactory.cs b/Aspects/Security/Cryptography/Ciphers/IHashAlgorithmFactory.cs index c904116..44357fe 100644 --- a/Aspects/Security/Cryptography/Ciphers/IHashAlgorithmFactory.cs +++ b/Aspects/Security/Cryptography/Ciphers/IHashAlgorithmFactory.cs @@ -1,7 +1,6 @@ using System; using System.Diagnostics.Contracts; using System.Security.Cryptography; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -11,7 +10,7 @@ namespace vm.Aspects.Security.Cryptography.Ciphers /// hash algorithm given choices like, parameters, Common Service Locator registrations, default values, etc. /// [ContractClass(typeof(IHashAlgorithmFactoryContract))] - public interface IHashAlgorithmFactory : IDisposable + public interface IHashAlgorithmFactory { /// /// Initializes the factory with an optional hash algorithm name. @@ -34,4 +33,30 @@ public interface IHashAlgorithmFactory : IDisposable /// The name of the hash algorithm. string HashAlgorithmName { get; } } + + [ContractClassFor(typeof(IHashAlgorithmFactory))] + abstract class IHashAlgorithmFactoryContract : IHashAlgorithmFactory + { + #region IHashAlgorithmFactory Members + + public void Initialize( + string hashAlgorithmName) + { + throw new NotImplementedException(); + } + + public HashAlgorithm Create() + { + Contract.Ensures(Contract.Result() != null, "Could not create a hash algorithm."); + + throw new NotImplementedException(); + } + + public string HashAlgorithmName + { + get { throw new NotImplementedException(); } + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IHasher.cs b/Aspects/Security/Cryptography/Ciphers/IHasher.cs index b504ff5..7b010d5 100644 --- a/Aspects/Security/Cryptography/Ciphers/IHasher.cs +++ b/Aspects/Security/Cryptography/Ciphers/IHasher.cs @@ -1,7 +1,6 @@ using System; using System.Diagnostics.Contracts; using System.IO; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -77,4 +76,73 @@ public interface IHasher : IDisposable /// The hash or the encryption failed. bool TryVerifyHash(byte[] data, byte[] hash); } + + [ContractClassFor(typeof(IHasher))] + abstract class IHasherContract : IHasher + { + #region IHasher Members + + public int SaltLength + { + get + { + Contract.Ensures(Contract.Result()==0 || Contract.Result()>=Hasher.DefaultSaltLength, "The salt length should be either 0 or not less than 8 bytes."); + + throw new NotImplementedException(); + } + set + { + Contract.Requires(value==0 || value>=8, "The salt length should be either 0 or not less than 8 bytes."); + + throw new NotImplementedException(); + } + } + + public byte[] Hash( + Stream dataStream) + { + Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); + Contract.Ensures(!(dataStream==null ^ Contract.Result()==null), "The returned value is invalid."); + + throw new NotImplementedException(); + } + + public bool TryVerifyHash( + Stream dataStream, + byte[] hash) + { + Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); + Contract.Requires(dataStream==null || hash!=null, "hash"); + Contract.Ensures(dataStream!=null || Contract.Result()==(hash==null), "Invalid return value."); + + throw new NotImplementedException(); + } + + public byte[] Hash( + byte[] data) + { + Contract.Ensures(!(data==null ^ Contract.Result()==null), "Invalid return value."); + + throw new NotImplementedException(); + } + + public bool TryVerifyHash(byte[] data, byte[] hash) + { + Contract.Requires(data==null || hash!=null, "hash"); + Contract.Ensures(data!=null || Contract.Result()==(hash==null), "Invalid return value."); + + throw new NotImplementedException(); + } + + #endregion + + #region IDisposable Members + + public void Dispose() + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IHasherAsync.cs b/Aspects/Security/Cryptography/Ciphers/IHasherAsync.cs index 3a3ca09..b8f83c7 100644 --- a/Aspects/Security/Cryptography/Ciphers/IHasherAsync.cs +++ b/Aspects/Security/Cryptography/Ciphers/IHasherAsync.cs @@ -1,7 +1,7 @@ -using System.Diagnostics.Contracts; +using System; +using System.Diagnostics.Contracts; using System.IO; using System.Threading.Tasks; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -52,4 +52,74 @@ public interface IHasherAsync : IHasher /// The hash or the encryption failed. Task TryVerifyHashAsync(Stream dataStream, byte[] hash); } + + [ContractClassFor(typeof(IHasherAsync))] + abstract class IHasherAsyncContract : IHasherAsync + { + #region IHasherAsync Members + + public Task HashAsync(Stream dataStream) + { + Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); + Contract.Ensures(!(dataStream==null ^ Contract.Result()==null), "The returned value is invalid."); + + throw new NotImplementedException(); + } + + public Task TryVerifyHashAsync(Stream dataStream, byte[] hash) + { + Contract.Requires(dataStream==null || dataStream.CanRead, "The \"dataStream\" cannot be read from."); + Contract.Requires(dataStream==null || hash!=null, "hash"); + Contract.Ensures(dataStream!=null || Contract.Result()==(hash==null), "Invalid return value."); + + throw new NotImplementedException(); + } + + #endregion + + #region IHasher Members + + public int SaltLength + { + get + { + throw new NotImplementedException(); + } + set + { + throw new NotImplementedException(); + } + } + + public byte[] Hash(System.IO.Stream dataStream) + { + throw new NotImplementedException(); + } + + public bool TryVerifyHash(System.IO.Stream dataStream, byte[] hash) + { + throw new NotImplementedException(); + } + + public byte[] Hash(byte[] data) + { + throw new NotImplementedException(); + } + + public bool TryVerifyHash(byte[] data, byte[] hash) + { + throw new NotImplementedException(); + } + + #endregion + + #region IDisposable Members + + public void Dispose() + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IKeyLocationStrategy.cs b/Aspects/Security/Cryptography/Ciphers/IKeyLocationStrategy.cs index 0e385e4..487416d 100644 --- a/Aspects/Security/Cryptography/Ciphers/IKeyLocationStrategy.cs +++ b/Aspects/Security/Cryptography/Ciphers/IKeyLocationStrategy.cs @@ -1,5 +1,5 @@ -using System.Diagnostics.Contracts; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; +using System; +using System.Diagnostics.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -36,4 +36,17 @@ public interface IKeyLocationStrategy /// string GetKeyLocation(string keyLocation); } + + [ContractClassFor(typeof(IKeyLocationStrategy))] + abstract class IKeyLocationStrategyContract : IKeyLocationStrategy + { + #region IKeyLocationStrategy Members + public string GetKeyLocation(string keyLocation) + { + Contract.Ensures(!string.IsNullOrWhiteSpace(Contract.Result()), "The key location cannot be null, empty or consist of whitespace characters only."); + + throw new NotImplementedException(); + } + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IKeyManagement.cs b/Aspects/Security/Cryptography/Ciphers/IKeyManagement.cs index de71035..b31c74d 100644 --- a/Aspects/Security/Cryptography/Ciphers/IKeyManagement.cs +++ b/Aspects/Security/Cryptography/Ciphers/IKeyManagement.cs @@ -1,7 +1,7 @@  +using System; using System.Diagnostics.Contracts; using System.Threading.Tasks; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -46,4 +46,46 @@ public interface IKeyManagement /// Task ImportSymmetricKeyAsync(byte[] key); } + + [ContractClassFor(typeof(IKeyManagement))] + abstract class IKeyManagementContract : IKeyManagement + { + #region IKeyManagement Members + public string KeyLocation + { + get + { + Contract.Ensures(!string.IsNullOrEmpty(Contract.Result()), "The key location cannot be null, empty or consist of whitespace characters only."); + + throw new NotImplementedException(); + } + } + + public byte[] ExportSymmetricKey() + { + throw new NotImplementedException(); + } + + public Task ExportSymmetricKeyAsync() + { + throw new NotImplementedException(); + } + + public void ImportSymmetricKey(byte[] key) + { + Contract.Requires(key != null, "key"); + Contract.Requires(key.Length > 0, "The length of the imported key is 0"); + + throw new NotImplementedException(); + } + + public Task ImportSymmetricKeyAsync(byte[] key) + { + Contract.Requires(key != null, "key"); + Contract.Requires(key.Length > 0, "The length of the imported key is 0"); + + throw new NotImplementedException(); + } + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IKeyStorage.cs b/Aspects/Security/Cryptography/Ciphers/IKeyStorage.cs index ae75357..2a37101 100644 --- a/Aspects/Security/Cryptography/Ciphers/IKeyStorage.cs +++ b/Aspects/Security/Cryptography/Ciphers/IKeyStorage.cs @@ -1,5 +1,5 @@ -using System.Diagnostics.Contracts; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; +using System; +using System.Diagnostics.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -37,4 +37,45 @@ public interface IKeyStorage /// The key location name to be deleted. void DeleteKeyLocation(string keyLocation); } + + [ContractClassFor(typeof(IKeyStorage))] + abstract class IKeyStorageContract : IKeyStorage + { + #region IKeyStorage Members + + public bool KeyLocationExists(string keyLocation) + { + Contract.Requires(keyLocation != null, "keyLocation"); + Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); + + throw new NotImplementedException(); + } + + public void PutKey(byte[] key, string keyLocation) + { + Contract.Requires(key != null, "key"); + Contract.Requires(key.Length != 0, "The length of the array in the argument \"key\" cannot be 0."); + Contract.Requires(keyLocation != null, "keyLocation"); + Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); + + throw new NotImplementedException(); + } + + public byte[] GetKey(string keyLocation) + { + Contract.Requires(keyLocation != null, "keyLocation"); + Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); + Contract.Ensures(Contract.Result() != null, "The returned key is null."); + Contract.Ensures(Contract.Result().Length != 0, "The returned key has 0 length."); + + throw new NotImplementedException(); + } + + public void DeleteKeyLocation(string keyLocation) + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/IKeyStorageAsync.cs b/Aspects/Security/Cryptography/Ciphers/IKeyStorageAsync.cs index 6e2d199..51ed3f6 100644 --- a/Aspects/Security/Cryptography/Ciphers/IKeyStorageAsync.cs +++ b/Aspects/Security/Cryptography/Ciphers/IKeyStorageAsync.cs @@ -1,6 +1,6 @@ -using System.Diagnostics.Contracts; +using System; +using System.Diagnostics.Contracts; using System.Threading.Tasks; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -26,4 +26,57 @@ public interface IKeyStorageAsync : IKeyStorage /// A object representing the process of getting the encrypted symmetric key from the storage. Task GetKeyAsync(string keyLocation); } + + [ContractClassFor(typeof(IKeyStorageAsync))] + abstract class IKeyStorageAsyncContract : IKeyStorageAsync + { + #region IKeyStorage Members + public bool KeyLocationExists( + string keyLocation) + { + throw new NotImplementedException(); + } + + public void PutKey( + byte[] key, + string keyLocation) + { + throw new NotImplementedException(); + } + + public byte[] GetKey( + string keyLocation) + { + throw new NotImplementedException(); + } + + public void DeleteKeyLocation( + string keyLocation) + { + throw new NotImplementedException(); + } + #endregion + + #region IKeyStorageAsync Members + public Task PutKeyAsync(byte[] key, string keyLocation) + { + Contract.Requires(key != null, "key"); + Contract.Requires(key.Length != 0, "The length of the array in the argument \"key\" cannot be 0."); + Contract.Requires(keyLocation != null, "keyLocation"); + Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); + + throw new NotImplementedException(); + } + + public Task GetKeyAsync(string keyLocation) + { + Contract.Requires(keyLocation != null, "keyLocation"); + Contract.Requires(!string.IsNullOrWhiteSpace(keyLocation), "The argument \"keyLocation\" cannot be empty or consist of whitespace characters only."); + Contract.Ensures(Contract.Result() != null, "The returned value is null."); + Contract.Ensures(Contract.Result().Length != 0, "The returned value has 0 length."); + + throw new NotImplementedException(); + } + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/ISymmetricAlgorithmFactory.cs b/Aspects/Security/Cryptography/Ciphers/ISymmetricAlgorithmFactory.cs index 0bca206..b5381a3 100644 --- a/Aspects/Security/Cryptography/Ciphers/ISymmetricAlgorithmFactory.cs +++ b/Aspects/Security/Cryptography/Ciphers/ISymmetricAlgorithmFactory.cs @@ -1,7 +1,6 @@ using System; using System.Diagnostics.Contracts; using System.Security.Cryptography; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -11,7 +10,7 @@ namespace vm.Aspects.Security.Cryptography.Ciphers /// symmetric algorithm given choices like, parameters, Common Service Locator registrations, default values, etc. /// [ContractClass(typeof(ISymmetricAlgorithmFactoryContract))] - public interface ISymmetricAlgorithmFactory : IDisposable + public interface ISymmetricAlgorithmFactory { /// /// Initializes the factory with an optional symmetric algorithm name. @@ -34,4 +33,27 @@ public interface ISymmetricAlgorithmFactory : IDisposable /// The name of the symmetric algorithm. string SymmetricAlgorithmName { get; } } + + [ContractClassFor(typeof(ISymmetricAlgorithmFactory))] + abstract class ISymmetricAlgorithmFactoryContract : ISymmetricAlgorithmFactory + { + #region ISymmetricAlgorithmFactory Members + public void Initialize( + string symmetricAlgorithmName) + { + } + + public SymmetricAlgorithm Create() + { + Contract.Ensures(Contract.Result() != null, "Could not create a symmetric algorithm."); + + throw new NotImplementedException(); + } + + public string SymmetricAlgorithmName + { + get { throw new NotImplementedException(); } + } + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/KeyedHashAlgorithmFactory.cs b/Aspects/Security/Cryptography/Ciphers/KeyedHashAlgorithmFactory.cs index d04e081..9e6ebb0 100644 --- a/Aspects/Security/Cryptography/Ciphers/KeyedHashAlgorithmFactory.cs +++ b/Aspects/Security/Cryptography/Ciphers/KeyedHashAlgorithmFactory.cs @@ -20,10 +20,6 @@ public sealed class KeyedHashAlgorithmFactory : IHashAlgorithmFactory /// The generated keyed hash factory /// Func _hashFactory; - /// - /// A temporary keyed hash algorithm object. - /// - KeyedHashAlgorithm _hashAlgorithm; #region IHashAlgorithmFactory members /// @@ -64,9 +60,9 @@ public void Initialize( { // 2. try to resolve the keyed hash algorithm object directly from the CSL _hashFactory = () => ServiceLocatorWrapper.Default.GetInstance(); - _hashAlgorithm = _hashFactory(); - // if we are here, we've got our factory. - return; + using (var hashAlgorithm = _hashFactory()) + // if we are here, we've got our factory. + return; } catch (ActivationException) { @@ -92,14 +88,14 @@ public void Initialize( _hashFactory = () => KeyedHashAlgorithm.Create(_hashAlgorithmName); // try it - _hashAlgorithm = _hashFactory(); - if (_hashAlgorithm == null) - // if unsuccessful - throw an exception. - throw new ActivationException( - string.Format( - CultureInfo.InvariantCulture, - "The name \"{0}\" was not recognized as a valid keyed hash algorithm.", - _hashAlgorithmName)); + using (var hashAlgorithm = _hashFactory()) + if (hashAlgorithm == null) + // if unsuccessful - throw an exception. + throw new ActivationException( + string.Format( + CultureInfo.InvariantCulture, + "The name \"{0}\" was not recognized as a valid keyed hash algorithm.", + _hashAlgorithmName)); } /// @@ -114,13 +110,7 @@ public HashAlgorithm Create() if (_hashFactory == null) throw new InvalidOperationException("The factory was not initialized properly. Call Initialize first."); - if (_hashAlgorithm == null) - return _hashFactory(); - - var hashAlgorithm = _hashAlgorithm; - - _hashAlgorithm = null; - return hashAlgorithm; + return _hashFactory(); } /// @@ -132,69 +122,5 @@ public string HashAlgorithmName get { return _hashAlgorithmName; } } #endregion - - #region IDisposable pattern implementation - /// - /// The flag will be set just before the object is disposed. - /// - /// 0 - if the object is not disposed yet, any other value - the object is already disposed. - /// - /// Do not test or manipulate this flag outside of the property or the method . - /// The type of this field is Int32 so that it can be easily passed to the members of the class . - /// - int _disposed; - - /// - /// Returns true if the object has already been disposed, otherwise false. - /// - public bool IsDisposed - { - get { return Volatile.Read(ref _disposed) != 0; } - } - - /// - /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. - /// - /// Invokes the protected virtual . - [SuppressMessage("Microsoft.Design", "CA1063:ImplementIDisposableCorrectly", Justification = "It is correct.")] - public void Dispose() - { - // if it is disposed or in a process of disposing - return. - if (Interlocked.Exchange(ref _disposed, 1) != 0) - return; - - // these will be called only if the instance is not disposed yet or is not in a process of disposing. - Dispose(true); - GC.SuppressFinalize(this); - } - - /// - /// Allows the object to attempt to free resources and perform other cleanup operations before it is reclaimed by garbage collection. - /// - /// Invokes the protected virtual . - ~KeyedHashAlgorithmFactory() - { - Dispose(false); - } - - /// - /// Performs the actual job of disposing the object. - /// - /// - /// Passes the information whether this method is called by (explicitly or - /// implicitly at the end of a using statement), or by the . - /// - /// - /// If the method is called with ==true, i.e. from , - /// it will try to release all managed resources (usually aggregated objects which implement as well) - /// and then it will release all unmanaged resources if any. If the parameter is false then - /// the method will only try to release the unmanaged resources. - /// - void Dispose(bool disposing) - { - if (disposing && _hashAlgorithm != null) - _hashAlgorithm.Dispose(); - } - #endregion } } diff --git a/Aspects/Security/Cryptography/Ciphers/KeyedHasher .cs b/Aspects/Security/Cryptography/Ciphers/KeyedHasher .cs index 8a5f9e0..ae8e027 100644 --- a/Aspects/Security/Cryptography/Ciphers/KeyedHasher .cs +++ b/Aspects/Security/Cryptography/Ciphers/KeyedHasher .cs @@ -612,9 +612,9 @@ public IHasherAsync CloneLightHasher() var hasher = new KeyedHasher(); hasher._hashAlgorithm = KeyedHashAlgorithm.Create(_hashAlgorithm.GetType().FullName); - hasher._hashAlgorithm.Key = _hashAlgorithm.Key; + hasher._hashAlgorithm.Key = (byte[])_hashAlgorithm.Key.Clone(); hasher.IsHashKeyInitialized = true; - + return hasher; } #endregion diff --git a/Aspects/Security/Cryptography/Ciphers/NuGet/Ciphers.nuspec b/Aspects/Security/Cryptography/Ciphers/NuGet/Ciphers.nuspec index 6525278..7e83d4c 100644 --- a/Aspects/Security/Cryptography/Ciphers/NuGet/Ciphers.nuspec +++ b/Aspects/Security/Cryptography/Ciphers/NuGet/Ciphers.nuspec @@ -2,7 +2,7 @@ Ciphers - 1.11.0 + 1.11.3 Val Melamed Val Melamed @@ -18,10 +18,7 @@ * Built and tested with .NET v4.6. - Added public methods `ResetAsymmetricKeys` and `Duplicate` to the classes `EncryptedKeyCipher` and `KeyedHasher`. - `ResetAsymmetricKeyes` strips the public/private keys from the objects and now they can be used only for encryption/hashing. - This way the objects become lighter and more suitable for caching and using in a big numbers of cryptographic operations. - `Duplicate` creates a copy of the current object, without the public/private keys. + Performance improvements in the algorithm factories. https://github.com/vmelamed/vm/blob/master/LICENSE https://github.com/vmelamed/vm/tree/master/Aspects/Security/Cryptography/Ciphers diff --git a/Aspects/Security/Cryptography/Ciphers/Properties/AssemblyInfo.cs b/Aspects/Security/Cryptography/Ciphers/Properties/AssemblyInfo.cs index 2ca6360..271220f 100644 --- a/Aspects/Security/Cryptography/Ciphers/Properties/AssemblyInfo.cs +++ b/Aspects/Security/Cryptography/Ciphers/Properties/AssemblyInfo.cs @@ -5,9 +5,9 @@ // associated with an assembly. [assembly: AssemblyTitle("vm.Aspects.Security.Cryptography.Ciphers")] [assembly: AssemblyDescription("A set of cipher classes producing cipher-packages and encrypted and/or signed XML documents and elements.")] -[assembly: AssemblyVersion("1.11.0")] -[assembly: AssemblyFileVersion("1.11.0")] -[assembly: AssemblyInformationalVersion("1.11.0")] +[assembly: AssemblyVersion("1.11.3")] +[assembly: AssemblyFileVersion("1.11.3")] +[assembly: AssemblyInformationalVersion("1.11.3")] [assembly: System.Runtime.CompilerServices.InternalsVisibleTo( "vm.Aspects.Security.Cryptography.Ciphers.Tests, " + diff --git a/Aspects/Security/Cryptography/Ciphers/SymmetricAlgorithmFactory.cs b/Aspects/Security/Cryptography/Ciphers/SymmetricAlgorithmFactory.cs index 24cd64e..1ef7fd8 100644 --- a/Aspects/Security/Cryptography/Ciphers/SymmetricAlgorithmFactory.cs +++ b/Aspects/Security/Cryptography/Ciphers/SymmetricAlgorithmFactory.cs @@ -1,8 +1,6 @@ using System; -using System.Diagnostics.CodeAnalysis; using System.Globalization; using System.Security.Cryptography; -using System.Threading; using Microsoft.Practices.ServiceLocation; namespace vm.Aspects.Security.Cryptography.Ciphers @@ -20,10 +18,6 @@ public sealed class SymmetricAlgorithmFactory : ISymmetricAlgorithmFactory /// The generated symmetric factory /// Func _symmetricAlgorithmFactory; - /// - /// A temporary symmetric algorithm object. - /// - SymmetricAlgorithm _symmetricAlgorithm; #region ISymmetricAlgorithmFactory Members @@ -46,9 +40,10 @@ public void Initialize( { // 2. try to resolve the symmetric algorithm object directly from the CSL _symmetricAlgorithmFactory = () => ServiceLocatorWrapper.Default.GetInstance(); - _symmetricAlgorithm = _symmetricAlgorithmFactory(); - // if we are here, we've got our factory. - return; + + using (var symmetricAlgorithm = _symmetricAlgorithmFactory()) + // if we are here, we've got our factory. + return; } catch (ActivationException) { @@ -74,34 +69,27 @@ public void Initialize( _symmetricAlgorithmFactory = () => SymmetricAlgorithm.Create(_symmetricAlgorithmName); // try it, if successful we'll store it and return it in the first call to Create() - _symmetricAlgorithm = _symmetricAlgorithmFactory(); - - if (_symmetricAlgorithm == null) - // if unsuccessful - throw an exception. - throw new ActivationException( - string.Format( - CultureInfo.InvariantCulture, - "The name \"{0}\" was not recognized as a valid symmetric algorithm.", - _symmetricAlgorithmName)); + using (var symmetricAlgorithm = _symmetricAlgorithmFactory()) + if (symmetricAlgorithm == null) + // if unsuccessful - throw an exception. + throw new ActivationException( + string.Format( + CultureInfo.InvariantCulture, + "The name \"{0}\" was not recognized as a valid symmetric algorithm.", + _symmetricAlgorithmName)); } /// - /// Creates a instance. + /// Creates a instance. /// - /// instance. + /// instance. /// public SymmetricAlgorithm Create() { if (_symmetricAlgorithmFactory == null) throw new InvalidOperationException("The factory was not initialized properly. Call Initialize first."); - if (_symmetricAlgorithm == null) - return _symmetricAlgorithmFactory(); - - var symmetricAlgorithm = _symmetricAlgorithm; - - _symmetricAlgorithm = null; - return symmetricAlgorithm; + return _symmetricAlgorithmFactory(); } /// @@ -115,70 +103,5 @@ public string SymmetricAlgorithmName } #endregion - - #region IDisposable pattern implementation - /// - /// The flag will be set just before the object is disposed. - /// - /// 0 - if the object is not disposed yet, any other value - the object is already disposed. - /// - /// Do not test or manipulate this flag outside of the property or the method . - /// The type of this field is Int32 so that it can be easily passed to the members of the class . - /// - int _disposed; - - /// - /// Returns true if the object has already been disposed, otherwise false. - /// - public bool IsDisposed - { - get { return Volatile.Read(ref _disposed) != 0; } - } - - /// - /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources. - /// - /// Invokes the protected virtual . - [SuppressMessage("Microsoft.Design", "CA1063:ImplementIDisposableCorrectly", Justification = "It is correct.")] - public void Dispose() - { - // if it is disposed or in a process of disposing - return. - if (Interlocked.Exchange(ref _disposed, 1) != 0) - return; - - // these will be called only if the instance is not disposed and is not in a process of disposing. - Dispose(true); - GC.SuppressFinalize(this); - } - - /// - /// Allows the object to attempt to free resources and perform other cleanup operations before it is reclaimed by garbage collection. - /// - /// Invokes the protected virtual . - ~SymmetricAlgorithmFactory() - { - Dispose(false); - } - - /// - /// Performs the actual job of disposing the object. - /// - /// - /// Passes the information whether this method is called by (explicitly or - /// implicitly at the end of a using statement), or by the . - /// - /// - /// If the method is called with ==true, i.e. from , - /// it will try to release all managed resources (usually aggregated objects which implement as well) - /// and then it will release all unmanaged resources if any. If the parameter is false then - /// the method will only try to release the unmanaged resources. - /// - /*protected virtual*/ - void Dispose(bool disposing) - { - if (disposing && _symmetricAlgorithm != null) - _symmetricAlgorithm.Dispose(); - } - #endregion } } diff --git a/Aspects/Security/Cryptography/Ciphers/SymmetricKeyCipherBase.cs b/Aspects/Security/Cryptography/Ciphers/SymmetricKeyCipherBase.cs index ca6184c..6294c0d 100644 --- a/Aspects/Security/Cryptography/Ciphers/SymmetricKeyCipherBase.cs +++ b/Aspects/Security/Cryptography/Ciphers/SymmetricKeyCipherBase.cs @@ -5,7 +5,6 @@ using System.Threading; using System.Threading.Tasks; using Microsoft.Practices.ServiceLocation; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts; namespace vm.Aspects.Security.Cryptography.Ciphers { @@ -351,4 +350,29 @@ protected virtual void CopyTo( cipher.ShouldEncryptIV = ShouldEncryptIV; } } + + [ContractClassFor(typeof(SymmetricKeyCipherBase))] + abstract class SymmetricKeyCipherBaseContract : SymmetricKeyCipherBase + { + protected SymmetricKeyCipherBaseContract() + : base(null) + { + } + + protected override byte[] EncryptSymmetricKey() + { + Contract.Ensures(Contract.Result() != null && Contract.Result().Length > 0, "The method returned null or empty encrypted key."); + + throw new NotImplementedException(); + } + + protected override void DecryptSymmetricKey( + byte[] encryptedKey) + { + Contract.Requires(encryptedKey != null, "encryptedKey"); + Contract.Requires(encryptedKey.Length > 0, "The argument \"encryptedKey\" cannot be empty."); + + throw new NotImplementedException(); + } + } } diff --git a/Aspects/Security/Cryptography/Ciphers/Test/ClonedLightHasherTest.cs b/Aspects/Security/Cryptography/Ciphers/Test/ClonedLightHasherTest.cs index d30a171..00b1c12 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/ClonedLightHasherTest.cs +++ b/Aspects/Security/Cryptography/Ciphers/Test/ClonedLightHasherTest.cs @@ -48,6 +48,61 @@ public static void ClassCleanup() File.Delete(keyManagement.KeyLocation); } + [TestMethod] + public void CloneCanVerifyOriginal() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var hasher = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + { + var hash = hasher.Hash(expected); + + using (var clone = hasher.CloneLightHasher()) + Assert.IsTrue(clone.TryVerifyHash(expected, hash)); + } + } + + [TestMethod] + public void OriginalCanVerifyClone() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var hasher = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + using (var clone = hasher.CloneLightHasher()) + { + var hash = clone.Hash(expected); + + Assert.IsTrue(hasher.TryVerifyHash(expected, hash)); + } + } + [TestMethod] + public void CloneCanVerifyClone() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var hasher = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + using (var clone = hasher.CloneLightHasher()) + using (var clone2 = hasher.CloneLightHasher()) + { + var hash = clone.Hash(expected); + + Assert.IsTrue(clone2.TryVerifyHash(expected, hash)); + } + } + + [TestMethod] + public void CloneCanVerifyItsOwn() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var hasher = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + using (var clone = hasher.CloneLightHasher()) + { + var hash = clone.Hash(expected); + + Assert.IsTrue(clone.TryVerifyHash(expected, hash)); + } + } } } diff --git a/Aspects/Security/Cryptography/Ciphers/Test/CreateCertificates.ps1 b/Aspects/Security/Cryptography/Ciphers/Test/CreateCertificates.ps1 index 13516fc..44498c6 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/CreateCertificates.ps1 +++ b/Aspects/Security/Cryptography/Ciphers/Test/CreateCertificates.ps1 @@ -1,34 +1,49 @@ +# ------------------------------------------------------------------------------------------------------------------------------- +# Delete all previously created certificates if needed: +# ------------------------------------------------------------------------------------------------------------------------------- +foreach ($c in Get-ChildItem Cert:\CurrentUser\my | + Where-Object {$_.Subject -imatch "vm\..*UnitTest"}) + { Remove-Item ("Cert:\CurrentUser\my\"+$c.Thumbprint); } + +foreach ($c in Get-ChildItem cert:\CurrentUser\TrustedPublisher | + Where-Object {$_.Subject -imatch "vm\..*UnitTest"}) + { Remove-Item ("cert:\CurrentUser\TrustedPublisher\"+$c.Thumbprint); } + # ------------------------------------------------------------------------------------------------------------------------------- # To test SHA1 only signatures use the following commands to create SHA1 only signing certificates (SHA256 will fail with these): # ------------------------------------------------------------------------------------------------------------------------------- -makecert -r -pe -n "CN=vm.SignatureCipherUnitTest" -m 12 -sky signature -ss my -makecert -r -pe -n "CN=vm.EncryptionCipherUnitTest" -m 12 -sky exchange -ss my +#makecert -r -ss my -pe -n "CN=vm.SignatureCipherUnitTest" -m 12 -sky signature +#makecert -r -pe -n "CN=vm.EncryptionCipherUnitTest" -m 12 -sky exchange -ss my +New-SelfSignedCertificate -CertStoreLocation Cert:\CurrentUser\my -KeyExportPolicy Exportable -Subject "CN=vm.SignatureCipherUnitTest" -KeyUsage DigitalSignature -KeyUsageProperty Sign -HashAlgorithm sha1 -Provider "Microsoft Enhanced RSA and AES Cryptographic Provider" -KeyLength 2048 > $null; +New-SelfSignedCertificate -CertStoreLocation Cert:\CurrentUser\my -KeyExportPolicy Exportable -Subject "CN=vm.EncryptionCipherUnitTest" -KeyUsage DataEncipherment -KeyUsageProperty Decrypt -HashAlgorithm sha1 -Provider "Microsoft Enhanced RSA and AES Cryptographic Provider" -KeyLength 2048 > $null; # ---------------------------------------------------------------------------------------------------- # To test SHA1 and SHA256 signatures use the following commands to create SHA256 signing certificates: # ---------------------------------------------------------------------------------------------------- -makecert -r -pe -n "CN=vm.Sha256SignatureCipherUnitTest" -m 12 -sky signature -ss my -a sha256 -sp "Microsoft Enhanced RSA and AES Cryptographic Provider" -sy 24 -makecert -r -pe -n "CN=vm.Sha256EncryptionCipherUnitTest" -m 12 -sky exchange -ss my -a sha256 -sp "Microsoft Enhanced RSA and AES Cryptographic Provider" -sy 24 +#makecert -r -pe -n "CN=vm.Sha256SignatureCipherUnitTest" -m 12 -sky signature -ss my -a sha256 -sp "Microsoft Enhanced RSA and AES Cryptographic Provider" -sy 24 +#makecert -r -pe -n "CN=vm.Sha256EncryptionCipherUnitTest" -m 12 -sky exchange -ss my -a sha256 -sp "Microsoft Enhanced RSA and AES Cryptographic Provider" -sy 24 +New-SelfSignedCertificate -CertStoreLocation Cert:\CurrentUser\my -KeyExportPolicy Exportable -Subject "CN=vm.Sha256SignatureCipherUnitTest" -KeyUsage DigitalSignature -KeyUsageProperty Sign -HashAlgorithm sha256 -Provider "Microsoft Enhanced RSA and AES Cryptographic Provider" -KeyLength 2048 > $null; +New-SelfSignedCertificate -CertStoreLocation Cert:\CurrentUser\my -KeyExportPolicy Exportable -Subject "CN=vm.Sha256EncryptionCipherUnitTest" -KeyUsage DataEncipherment -KeyUsageProperty Decrypt -HashAlgorithm sha256 -Provider "Microsoft Enhanced RSA and AES Cryptographic Provider" -KeyLength 2048 > $null; # export the created certificates into files, without the private keys -dir cert:\CurrentUser\My | - where-object { $_.Subject -like 'CN=vm.*'} | - foreach-object { - $path = $_.Subject -replace "cn=", ""; - $path = "$($path).cer"; - export-certificate -cert $_ -filepath $path - }; +Get-ChildItem cert:\CurrentUser\My | + where-object { $_.Subject -like 'CN=vm.*'} | + ForEach-Object { + $path = $_.Subject -replace "cn=", ""; + $path = "$($path).cer"; + Export-Certificate -Cert $_ -FilePath $path + }; # import them to "Other People" -dir vm.*.cer | - foreach { - import-certificate $_ -certstorelocation cert:\CurrentUser\TrustedPublisher - } > $null; -# clean-up -del vm.*.cer; +Get-ChildItem vm.*.cer | + foreach { + Import-Certificate $_ -CertStoreLocation cert:\CurrentUser\TrustedPublisher; + } > $null; +# clean-updir +Remove-Item vm.*.cer; if ($Host.Name -eq "ConsoleHost") { - Write-Host "Press any key to continue..."; - $Host.UI.RawUI.FlushInputBuffer(); - $Host.UI.RawUI.ReadKey("NoEcho,IncludeKeyUp") > $null; + Write-Host "Press any key to continue..."; + $Host.UI.RawUI.FlushInputBuffer(); + $Host.UI.RawUI.ReadKey("NoEcho,IncludeKeyUp") > $null; } diff --git a/Aspects/Security/Cryptography/Ciphers/Test/HashAlgorithmFactoryTest.cs b/Aspects/Security/Cryptography/Ciphers/Test/HashAlgorithmFactoryTest.cs index 6c14a45..387bb62 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/HashAlgorithmFactoryTest.cs +++ b/Aspects/Security/Cryptography/Ciphers/Test/HashAlgorithmFactoryTest.cs @@ -49,68 +49,6 @@ public static void CleanupTest() } #endregion - #region IsDisposed tests - [TestMethod] - public void IsDisposedTest() - { - try - { - var target = new HashAlgorithmFactory(); - - Assert.IsNotNull(target); - - using (target as IDisposable) - Assert.IsFalse(target.IsDisposed); - Assert.IsTrue(target.IsDisposed); - - // should do nothing: - target.Dispose(); - } - finally - { - CleanupTest(); - } - } - - [TestMethod] - public void IsDisposedTest2() - { - try - { - var target = new HashAlgorithmFactory(); - - Assert.IsNotNull(target); - - target.Initialize("SHA1"); - - using (target as IDisposable) - Assert.IsFalse(target.IsDisposed); - Assert.IsTrue(target.IsDisposed); - - // should do nothing: - target.Dispose(); - } - finally - { - CleanupTest(); - } - } - - [TestMethod] - [TestCategory("SlowTest")] - public void FinalizerTest() - { - var target = new WeakReference(new HashAlgorithmFactory()); - - Thread.Sleep(1000); - GC.Collect(); - - HashAlgorithmFactory collected; - - Assert.IsFalse(target.TryGetTarget(out collected)); - } - #endregion - [TestMethod] [ExpectedException(typeof(InvalidOperationException))] public void UninitializedTest() diff --git a/Aspects/Security/Cryptography/Ciphers/Test/HasherTest.cs b/Aspects/Security/Cryptography/Ciphers/Test/HasherTest.cs index c729558..0ad264d 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/HasherTest.cs +++ b/Aspects/Security/Cryptography/Ciphers/Test/HasherTest.cs @@ -65,10 +65,9 @@ public async Task PublicWriteSaltAsync( public byte[] PublicFinalizeHashing( CryptoStream hashStream, - HashAlgorithm hashAlgorithm, byte[] salt) { - return base.FinalizeHashing(hashStream, hashAlgorithm, salt); + return base.FinalizeHashing(hashStream, salt); } } @@ -134,7 +133,7 @@ public void WriteSaltNonWritableStreamAsyncTest() public void FinalizeHashingNonWritableCryptoStreamTest() { using (var hasher = GetInheritedHasher()) - hasher.PublicFinalizeHashing(GetCryptoStream(hasher), HashAlgorithm.Create(Algorithms.Hash.Sha256), new byte[8]); + hasher.PublicFinalizeHashing(GetCryptoStream(hasher), new byte[8]); } [TestMethod] @@ -142,7 +141,7 @@ public void FinalizeHashingNonWritableCryptoStreamTest() public void FinalizeHashingNullSaltTest() { using (var hasher = GetInheritedHasher()) - hasher.PublicFinalizeHashing(GetCryptoStream2(hasher), HashAlgorithm.Create(Algorithms.Hash.Sha256), null); + hasher.PublicFinalizeHashing(GetCryptoStream2(hasher), null); } } } diff --git a/Aspects/Security/Cryptography/Ciphers/Test/ReleasedCertificateHasherTest.cs b/Aspects/Security/Cryptography/Ciphers/Test/ReleasedCertificateHasherTest.cs index 8bdbe3c..0b3148f 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/ReleasedCertificateHasherTest.cs +++ b/Aspects/Security/Cryptography/Ciphers/Test/ReleasedCertificateHasherTest.cs @@ -12,12 +12,6 @@ public class ReleasedCertificateHasherTest : GenericHasherTest { const string keyFileName = "releasedCertificateHash.key"; - /// - ///Gets or sets the test context which provides - ///information about and functionality for the current test run. - /// - //public TestContext TestContext { get; set; } - public override IHasherAsync GetHasher() { return new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName).ReleaseCertificate(); @@ -45,6 +39,60 @@ public static void ClassCleanup() File.Delete(keyManagement.KeyLocation); } + [TestMethod] + public void OriginalCanVerifyStripped() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var stripped = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName).ReleaseCertificate()) + using (var original = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + { + var hash = stripped.Hash(expected); + + Assert.IsTrue(original.TryVerifyHash(expected, hash)); + } + } + + [TestMethod] + public void StrippedCanVerifyOriginal() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var original = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName)) + { + var hash = original.Hash(expected); + + var stripped = ((KeyedHasher)original).ReleaseCertificate(); + + Assert.IsTrue(stripped.TryVerifyHash(expected, hash)); + } + } + + [TestMethod] + public void StrippedCanVerifyStripped() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var stripped = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName).ReleaseCertificate()) + using (var stripped2 = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName).ReleaseCertificate()) + { + var hash = stripped.Hash(expected); + + Assert.IsTrue(stripped2.TryVerifyHash(expected, hash)); + } + } + + [TestMethod] + public void StrippedCanVerifyItsOwn() + { + const string expected = "The quick fox jumps over the lazy dog."; + + using (var stripped = new KeyedHasher(CertificateFactory.GetDecryptingCertificate(), null, keyFileName).ReleaseCertificate()) + { + var hash = stripped.Hash(expected); + Assert.IsTrue(stripped.TryVerifyHash(expected, hash)); + } + } } } diff --git a/Aspects/Security/Cryptography/Ciphers/Test/SymmetricAlgorithmFactoryTest.cs b/Aspects/Security/Cryptography/Ciphers/Test/SymmetricAlgorithmFactoryTest.cs index ca977b2..b24dd36 100644 --- a/Aspects/Security/Cryptography/Ciphers/Test/SymmetricAlgorithmFactoryTest.cs +++ b/Aspects/Security/Cryptography/Ciphers/Test/SymmetricAlgorithmFactoryTest.cs @@ -50,54 +50,6 @@ public static void CleanupTest() } #endregion - #region IsDisposed tests - [TestMethod] - public void IsDisposedTest() - { - try - { - var target = new SymmetricAlgorithmFactory(); - - Assert.IsNotNull(target); - - using (target as IDisposable) - Assert.IsFalse(target.IsDisposed); - Assert.IsTrue(target.IsDisposed); - - // should do nothing: - target.Dispose(); - } - finally - { - CleanupTest(); - } - } - - [TestMethod] - public void IsDisposedTest2() - { - try - { - var target = new SymmetricAlgorithmFactory(); - - Assert.IsNotNull(target); - - target.Initialize("DES"); - - using (target as IDisposable) - Assert.IsFalse(target.IsDisposed); - Assert.IsTrue(target.IsDisposed); - - // should do nothing: - target.Dispose(); - } - finally - { - CleanupTest(); - } - } - #endregion - [TestMethod] [ExpectedException(typeof(InvalidOperationException))] public void UninitializedTest() diff --git a/Aspects/Security/Cryptography/Ciphers/Xml/IXmlCipher.cs b/Aspects/Security/Cryptography/Ciphers/Xml/IXmlCipher.cs index 0593abe..5227e49 100644 --- a/Aspects/Security/Cryptography/Ciphers/Xml/IXmlCipher.cs +++ b/Aspects/Security/Cryptography/Ciphers/Xml/IXmlCipher.cs @@ -2,7 +2,6 @@ using System.Diagnostics.CodeAnalysis; using System.Diagnostics.Contracts; using System.Xml; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts.Xml; namespace vm.Aspects.Security.Cryptography.Ciphers.Xml { @@ -39,7 +38,7 @@ public interface IXmlCipher : IDisposable /// /// The specified symmetric algorithm is not supported. Only the TripleDES, DES, AES-128, AES-192 and AES-256 algorithms are supported. /// - [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId="System.Xml.XmlNode", Justification="We need here the whole document.")] + [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId = "System.Xml.XmlNode", Justification = "We need here the whole document.")] void Encrypt(XmlDocument document, string xmlPath = null, XmlNamespaceManager namespaceManager = null); /// @@ -49,7 +48,52 @@ public interface IXmlCipher : IDisposable /// /// The is . /// - [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId="System.Xml.XmlNode", Justification="We need here the whole document.")] + [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId = "System.Xml.XmlNode", Justification = "We need here the whole document.")] void Decrypt(XmlDocument document); } + + [ContractClassFor(typeof(IXmlCipher))] + abstract class IXmlCipherContract : IXmlCipher + { + #region IXmlCipher Members + + public bool ContentOnly + { + get + { + throw new NotImplementedException(); + } + set + { + throw new NotImplementedException(); + } + } + + public void Encrypt( + XmlDocument document, + string xmlPath = null, + XmlNamespaceManager namespaceManager = null) + { + Contract.Requires(document != null, "document"); + throw new NotImplementedException(); + } + + public void Decrypt( + XmlDocument document) + { + Contract.Requires(document != null, "document"); + throw new NotImplementedException(); + } + + #endregion + + #region IDisposable Members + + public void Dispose() + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/Xml/IXmlSigner.cs b/Aspects/Security/Cryptography/Ciphers/Xml/IXmlSigner.cs index a85c7f9..f59148c 100644 --- a/Aspects/Security/Cryptography/Ciphers/Xml/IXmlSigner.cs +++ b/Aspects/Security/Cryptography/Ciphers/Xml/IXmlSigner.cs @@ -2,7 +2,6 @@ using System.Diagnostics.CodeAnalysis; using System.Diagnostics.Contracts; using System.Xml; -using vm.Aspects.Security.Cryptography.Ciphers.Contracts.Xml; namespace vm.Aspects.Security.Cryptography.Ciphers.Xml { @@ -110,7 +109,7 @@ public interface IXmlSigner : IDisposable /// respective elements of the . /// /// - [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId="System.Xml.XmlNode", Justification="We need here the whole document.")] + [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId = "System.Xml.XmlNode", Justification = "We need here the whole document.")] XmlDocument Sign( XmlDocument document, string xmlPath = null, @@ -141,9 +140,70 @@ XmlDocument Sign( /// /// /// - [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId="System.Xml.XmlNode", Justification="We need here the whole document.")] + [SuppressMessage("Microsoft.Design", "CA1059:MembersShouldNotExposeCertainConcreteTypes", MessageId = "System.Xml.XmlNode", Justification = "We need here the whole document.")] bool TryVerifySignature( XmlDocument document, XmlDocument signature = null); } + + [ContractClassFor(typeof(IXmlSigner))] + abstract class IXmlSignerContract : IXmlSigner + { + #region IXmlSigner Members + + public SignatureLocation SignatureLocation + { + get + { + Contract.Ensures(Enum.IsDefined(typeof(SignatureLocation), Contract.Result()), "The value of the property is not a valid SignatureLocation value."); + throw new NotImplementedException(); + } + set + { + Contract.Requires(Enum.IsDefined(typeof(SignatureLocation), value), "The value is not a valid SignatureLocation value."); + throw new NotImplementedException(); + } + } + + public bool IncludeKeyInfo + { + get + { + throw new NotImplementedException(); + } + set + { + throw new NotImplementedException(); + } + } + + public XmlDocument Sign( + XmlDocument document, + string xmlPath = null, + XmlNamespaceManager namespaceManager = null, + Uri documentLocation = null) + { + Contract.Requires(document != null, "document"); + throw new NotImplementedException(); + } + + public bool TryVerifySignature( + XmlDocument document, + XmlDocument signature = null) + { + Contract.Requires(document != null, "document"); + throw new NotImplementedException(); + } + + #endregion + + #region IDisposable Members + + public void Dispose() + { + throw new NotImplementedException(); + } + + #endregion + } } diff --git a/Aspects/Security/Cryptography/Ciphers/vm.Aspects.Security.Cryptography.Ciphers.csproj b/Aspects/Security/Cryptography/Ciphers/vm.Aspects.Security.Cryptography.Ciphers.csproj index 9a11b7f..842cb6e 100644 --- a/Aspects/Security/Cryptography/Ciphers/vm.Aspects.Security.Cryptography.Ciphers.csproj +++ b/Aspects/Security/Cryptography/Ciphers/vm.Aspects.Security.Cryptography.Ciphers.csproj @@ -209,19 +209,6 @@ - - - - - - - - - - - - - diff --git a/Aspects/Wcf/Properties/AssemblyInfo.cs b/Aspects/Wcf/Properties/AssemblyInfo.cs index 2f233af..8d0cefe 100644 --- a/Aspects/Wcf/Properties/AssemblyInfo.cs +++ b/Aspects/Wcf/Properties/AssemblyInfo.cs @@ -3,9 +3,9 @@ [assembly: AssemblyTitle("Wcf")] [assembly: AssemblyDescription("A set of classes and generics simplifying the initial configuration work of creating WCF services.")] -[assembly: AssemblyVersion("1.0.23")] -[assembly: AssemblyFileVersion("1.0.23")] -[assembly: AssemblyInformationalVersion("1.0.23")] +[assembly: AssemblyVersion("1.0.25")] +[assembly: AssemblyFileVersion("1.0.25")] +[assembly: AssemblyInformationalVersion("1.0.25")] [assembly: System.Runtime.CompilerServices.InternalsVisibleTo( "vm.Aspects.Wcf.Test, " +