diff --git a/Dependify.sln b/Dependify.sln index 72f3193..7b2b53d 100644 --- a/Dependify.sln +++ b/Dependify.sln @@ -9,6 +9,14 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Dependify", "src\Dependify\ EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Dependify.Test", "src\Dependify.Test\Dependify.Test.csproj", "{BD19041B-FC13-456A-9F3E-7823B9EF5E70}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{5A674CE8-0416-4D59-A9F9-CB5987FC21C8}" + ProjectSection(SolutionItems) = preProject + Dependify.sln.DotSettings = Dependify.sln.DotSettings + global.json = global.json + LICENSE = LICENSE + README.md = README.md + EndProjectSection +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU diff --git a/README.md b/README.md index dc7c399..6adcd76 100644 --- a/README.md +++ b/README.md @@ -1 +1,64 @@ -# Dependify \ No newline at end of file +# Dependify + +Library that allows the developer to register his services by adding attributes to class or factory methods. Library works only with Microsoft's `Microsoft.Extensions.DependencyInjection` package. + +Why the name? Because I wanted to contribute to the following [list](http://www.thenameinspector.com/wp-content/uploads/ify-names-chart-20141.pdf). + +# Requirements + +* `.netstandard 2.0` +* `Microsoft.Extensions.DependencyInjection` + +# Usage + +Let's have following interface and class +```c# +public interface ICar { + +} + +public class Audi : ICar { + +} +``` + +## Class Attributes + +### Single interface + +If you want to add `Audi` as an implementation of `ICar` into `IServiceCollection` you just need to add `RegisterTransient`, `RegisterScoped` or `RegisterSingleton` attribute like + +```c# +[RegisterTransient] +public class Audi : ICar { + +} +``` + +and call +```c# +public void ConfigureServices(IServiceCollection services) { + services.AutoRegister(); +} +``` + +### Multiple interfaces + +If your class implements multiple interfaces, you can specify which one should be registered + +```c# +[RegisterTransient(typeof(IFuelConsumer)] +public class Audi : ICar, IFuelConsumer { + +} +``` + +## Factory method attributes + +If you want to add `Audi` as an implementation of `ICar` using factory method, you can do following +```c# +[RegisterTransientFactory(typeof(ICar))] +public Audi CreateAudi(IServiceProvider provider) { + return new Audi(); +} +``` \ No newline at end of file diff --git a/src/Dependify.Test/AutoRegisterTestCases.cs b/src/Dependify.Test/AutoRegisterTestCases.cs index 62a1374..ab5548c 100644 --- a/src/Dependify.Test/AutoRegisterTestCases.cs +++ b/src/Dependify.Test/AutoRegisterTestCases.cs @@ -1,13 +1,16 @@ -using System; -using Dependify; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; using Dependify.Attributes; using ShouldRegisterScoped; using ShouldRegisterSingleton; using ShouldRegisterTransient; public interface IInterface { } - -public interface IInterface2 { } + +public interface IInterface2 { } namespace ShouldRegisterTransient { [RegisterTransient] diff --git a/src/Dependify.Test/AutoRegisterTests.cs b/src/Dependify.Test/AutoRegisterTests.cs index c31bca3..131191f 100644 --- a/src/Dependify.Test/AutoRegisterTests.cs +++ b/src/Dependify.Test/AutoRegisterTests.cs @@ -1,5 +1,10 @@ +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + using System; using System.Linq; +using System.Security.Cryptography.X509Certificates; using Microsoft.Extensions.DependencyInjection; using NUnit.Framework; using ShouldRegisterOneScoped; @@ -9,9 +14,9 @@ using ShouldRegisterScoped; using ShouldRegisterSingleton; using ShouldRegisterTransient; -namespace Dependify.Test { +namespace Dependify.Test { [TestFixture] - public class RegisterAttributeTests { + public class RegisterAttributeTests { [TestCase(nameof(ShouldRegisterTransient), typeof(ImplementationTransient), typeof(IInterface), ServiceLifetime.Transient)] [TestCase(nameof(ShouldRegisterSingleton), typeof(ImplementationSingleton), typeof(IInterface), ServiceLifetime.Singleton)] [TestCase(nameof(ShouldRegisterScoped), typeof(ImplementationScoped), typeof(IInterface), ServiceLifetime.Scoped)] @@ -20,15 +25,14 @@ namespace Dependify.Test { [TestCase(nameof(ShouldRegisterOneScoped), typeof(ImplementationScopedOneInterface), typeof(IInterface2), ServiceLifetime.Scoped)] public void RegisterAttribute_RegistersClass_WhenDefined(string @namespace, Type classType, Type interfaceType, ServiceLifetime serviceLifetime) { IServiceCollection services = new ServiceCollection(); - services.AutoRegister(@namespace); + services.AutoRegister(@namespace); var service = services.First(); Assert.AreEqual(1, services.Count); - Assert.AreEqual(interfaceType, service.ServiceType); + Assert.AreEqual(interfaceType, service.ServiceType); Assert.AreEqual(classType, service.ImplementationType); Assert.AreEqual(serviceLifetime, service.Lifetime); } - - + [TestCase(nameof(ShouldRegisterFactoryTransient), typeof(ImplementationTransient), typeof(IInterface), ServiceLifetime.Transient)] [TestCase(nameof(ShouldRegisterFactorySingleton), typeof(ImplementationSingleton), typeof(IInterface), ServiceLifetime.Singleton)] [TestCase(nameof(ShouldRegisterFactoryScoped), typeof(ImplementationScoped), typeof(IInterface), ServiceLifetime.Scoped)] @@ -41,5 +45,5 @@ namespace Dependify.Test { Assert.NotNull(service.ImplementationFactory); Assert.AreEqual(serviceLifetime, service.Lifetime); } - } + } } \ No newline at end of file diff --git a/src/Dependify/Attributes/Register.cs b/src/Dependify/Attributes/Register.cs index 5c0d1cf..63b0141 100644 --- a/src/Dependify/Attributes/Register.cs +++ b/src/Dependify/Attributes/Register.cs @@ -1,4 +1,8 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; using System.Collections.Generic; namespace Dependify.Attributes { diff --git a/src/Dependify/Attributes/RegisterFactory.cs b/src/Dependify/Attributes/RegisterFactory.cs index d36836b..74707eb 100644 --- a/src/Dependify/Attributes/RegisterFactory.cs +++ b/src/Dependify/Attributes/RegisterFactory.cs @@ -1,4 +1,8 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; namespace Dependify.Attributes { [AttributeUsage(AttributeTargets.Method)] diff --git a/src/Dependify/Attributes/RegisterScoped.cs b/src/Dependify/Attributes/RegisterScoped.cs index e91c665..9da452c 100644 --- a/src/Dependify/Attributes/RegisterScoped.cs +++ b/src/Dependify/Attributes/RegisterScoped.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Classes with this attribute will be registered with lifetime. + /// [AttributeUsage(AttributeTargets.Class)] public class RegisterScoped : Register { public RegisterScoped() { } diff --git a/src/Dependify/Attributes/RegisterScopedFactory.cs b/src/Dependify/Attributes/RegisterScopedFactory.cs index 9dfa737..c539d9a 100644 --- a/src/Dependify/Attributes/RegisterScopedFactory.cs +++ b/src/Dependify/Attributes/RegisterScopedFactory.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Methods with this attribute will be registered as factories for classes with lifetime. + /// [AttributeUsage(AttributeTargets.Method)] public class RegisterScopedFactory : RegisterFactory { public RegisterScopedFactory(Type returnType) : base(returnType) { } diff --git a/src/Dependify/Attributes/RegisterSingleton.cs b/src/Dependify/Attributes/RegisterSingleton.cs index e3d2a25..cc40210 100644 --- a/src/Dependify/Attributes/RegisterSingleton.cs +++ b/src/Dependify/Attributes/RegisterSingleton.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Classes with this attribute will be registered with lifetime. + /// [AttributeUsage(AttributeTargets.Class)] public class RegisterSingleton : Register { public RegisterSingleton() { } diff --git a/src/Dependify/Attributes/RegisterSingletonFactory.cs b/src/Dependify/Attributes/RegisterSingletonFactory.cs index ff68f4a..8d88234 100644 --- a/src/Dependify/Attributes/RegisterSingletonFactory.cs +++ b/src/Dependify/Attributes/RegisterSingletonFactory.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Methods with this attribute will be registered as factories for classes with lifetime. + /// [AttributeUsage(AttributeTargets.Method)] public class RegisterSingletonFactory : RegisterFactory { public RegisterSingletonFactory(Type returnType) : base(returnType) { } diff --git a/src/Dependify/Attributes/RegisterTransient.cs b/src/Dependify/Attributes/RegisterTransient.cs index bbd2e07..48658e6 100644 --- a/src/Dependify/Attributes/RegisterTransient.cs +++ b/src/Dependify/Attributes/RegisterTransient.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Classes with this attribute will be registered with lifetime. + /// [AttributeUsage(AttributeTargets.Class)] public class RegisterTransient : Register { public RegisterTransient() { } diff --git a/src/Dependify/Attributes/RegisterTransientFactory.cs b/src/Dependify/Attributes/RegisterTransientFactory.cs index 410a157..0607d59 100644 --- a/src/Dependify/Attributes/RegisterTransientFactory.cs +++ b/src/Dependify/Attributes/RegisterTransientFactory.cs @@ -1,6 +1,14 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; +using Microsoft.Extensions.DependencyInjection; namespace Dependify.Attributes { + /// + /// Methods with this attribute will be registered as factories for classes with lifetime. + /// [AttributeUsage(AttributeTargets.Method)] public class RegisterTransientFactory : RegisterFactory { public RegisterTransientFactory(Type returnType) : base(returnType) { } diff --git a/src/Dependify/Dependify.csproj b/src/Dependify/Dependify.csproj index e676743..ebdc4da 100644 --- a/src/Dependify/Dependify.csproj +++ b/src/Dependify/Dependify.csproj @@ -5,7 +5,4 @@ - - - \ No newline at end of file diff --git a/src/Dependify/IServiceCollectionExtensions.cs b/src/Dependify/IServiceCollectionExtensions.cs index f4df242..10b979a 100644 --- a/src/Dependify/IServiceCollectionExtensions.cs +++ b/src/Dependify/IServiceCollectionExtensions.cs @@ -1,4 +1,8 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; using System.Collections.Generic; using System.Linq; using System.Reflection; @@ -9,6 +13,11 @@ using Microsoft.Extensions.DependencyInjection; namespace Dependify { // ReSharper disable once InconsistentNaming public static class IServiceCollectionExtensions { + /// + /// Adds all classes with , or attribute to . + /// + /// Service collection. + /// Service collection. public static IServiceCollection AutoRegister(this IServiceCollection services) { var assemblies = AppDomain.CurrentDomain.GetAssemblies(); services.AddFactories(DependifyUtils.GetFactoryMethods(assemblies)); @@ -16,12 +25,24 @@ namespace Dependify { return services; } + /// + /// Adds all classes from specified with , or attribute to . + /// + /// Service collection. + /// Assemblies to scan + /// Service collection. public static IServiceCollection AutoRegister(this IServiceCollection services, params Assembly[] assemblies) { services.AddFactories(DependifyUtils.GetFactoryMethods(assemblies)); services.AddClasses(DependifyUtils.GetClassTypes(assemblies)); return services; } + /// + /// Adds all classes, from namespaces that start with , with , or attribute to . + /// + /// + /// + /// public static IServiceCollection AutoRegister(this IServiceCollection services, string @namespace) { var assemblies = AppDomain.CurrentDomain.GetAssemblies(); services.AddFactories(DependifyUtils.GetFactoryMethodsFromNamespace(assemblies, @namespace)); @@ -51,7 +72,7 @@ namespace Dependify { foreach (var classAttribute in classAttributes) { var registrationType = classAttribute.GetType(); var interfaceTypes = classAttribute.InterfaceTypes == null || !classAttribute.InterfaceTypes.Any() ? classType.GetInterfaces() : classAttribute.InterfaceTypes; - + foreach (var interfaceType in interfaceTypes) { if (registrationType == typeof(RegisterTransient)) services.AddTransient(interfaceType, classType); diff --git a/src/Dependify/Utilities/DependifyUtils.cs b/src/Dependify/Utilities/DependifyUtils.cs index c9c8345..bc99eae 100644 --- a/src/Dependify/Utilities/DependifyUtils.cs +++ b/src/Dependify/Utilities/DependifyUtils.cs @@ -1,4 +1,8 @@ -using System; +// Copyright 2017 Dávid Kaya. All rights reserved. +// Use of this source code is governed by the MIT license, +// as found in the LICENSE file. + +using System; using System.Collections.Generic; using System.Linq; using System.Reflection;