/src/LinFu.IoC/Configuration/Loaders/PreprocessorLoader.cs
C# | 76 lines | 44 code | 8 blank | 24 comment | 6 complexity | 3da002b0d35c8163b5be8959d9ec15b9 MD5 | raw file
1using System; 2using System.Collections.Generic; 3using System.IO; 4using System.Linq; 5using LinFu.IoC.Interfaces; 6using LinFu.Reflection; 7 8namespace LinFu.IoC.Configuration.Loaders 9{ 10 /// <summary> 11 /// A class that automatically loads <see cref="IPreProcessor" /> 12 /// instances and configures a loader to inject those postprocessors 13 /// into a container upon initialization. 14 /// </summary> 15 internal class PreProcessorLoader : IActionLoader<IServiceContainer, Type> 16 { 17 /// <summary> 18 /// Determines if the plugin loader can load the <paramref name="inputType" />. 19 /// </summary> 20 /// <remarks>The target type must implement the <see cref="IPreProcessor" /> interface before it can be loaded into memory.</remarks> 21 /// <param name="inputType">The target type that might contain the target instance.</param> 22 /// <returns><c>true</c> if the type can be loaded; otherwise, it returns <c>false</c>.</returns> 23 public bool CanLoad(Type inputType) 24 { 25 try 26 { 27 // The type must have a default constructor 28 var defaultConstructor = inputType.GetConstructor(new Type[0]); 29 if (defaultConstructor == null) 30 return false; 31 32 // It must have the PreprocessorAttribute defined 33 var attributes = inputType.GetCustomAttributes(typeof(PreprocessorAttribute), true); 34 var attributeList = attributes.Cast<PreprocessorAttribute>(); 35 36 if (attributeList.Count() == 0) 37 return false; 38 39 return typeof(IPreProcessor).IsAssignableFrom(inputType); 40 } 41 catch (TypeInitializationException) 42 { 43 // Ignore the error 44 return false; 45 } 46 catch (FileNotFoundException) 47 { 48 // Ignore the error 49 return false; 50 } 51 } 52 53 /// <summary> 54 /// Loads a set of <see cref="IPreProcessor" /> instances 55 /// so that they can be loaded into a container upon initialization. 56 /// </summary> 57 /// <param name="inputType">The type that will be used to configure the target loader.</param> 58 /// <returns>A set of <see cref="Action{TTarget}" /> instances. This cannot be <c>null</c>.</returns> 59 public IEnumerable<Action<IServiceContainer>> Load(Type inputType) 60 { 61 var defaultResult = new Action<IServiceContainer>[0]; 62 63 // Create the postprocessor instance 64 var instance = Activator.CreateInstance(inputType) as IPreProcessor; 65 if (instance == null) 66 return defaultResult; 67 68 // Inject the postprocessor into any service containers 69 // that will be configured by the current loader instance 70 Action<IServiceContainer> assignPreprocessor = 71 container => container.PreProcessors.Add(instance); 72 73 return new[] {assignPreprocessor}; 74 } 75 } 76}