using System; using System.Linq; using System.Reflection; using Umbraco.Core.ObjectResolution; using Umbraco.Core.Persistence.Repositories; using Umbraco.Core.Persistence.UnitOfWork; namespace Umbraco.Core.Persistence { /// /// A resolver used to return the current implementation of the RepositoryInstanceFactory /// internal class RepositoryResolver : SingleObjectResolverBase { internal RepositoryResolver(RepositoryFactory registrar) : base(registrar) { } /// /// Can be used by developers at runtime to set their own RepositoryInstanceFactory at app startup /// /// public void SetRepositoryInstanceFactory(RepositoryFactory factory) { Value = factory; } /// /// Returns the RepositoryInstanceFactory object /// internal RepositoryFactory Factory { get { return Value; } } /// /// Return the repository based on the type /// /// /// /// internal TRepository ResolveByType(IUnitOfWork unitOfWork) where TRepository : class, IRepository { var createMethod = this.Value.GetType().GetMethods(BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Public) .First(x => x.Name == "Create" + typeof (TRepository).Name.Substring(1)); if (createMethod.GetParameters().Count() != 1 || !createMethod.GetParameters().Single().ParameterType.IsType()) { throw new FormatException("The method " + createMethod.Name + " must only contain one parameter of type " + typeof(IUnitOfWork).FullName); } if (!createMethod.ReturnType.IsType()) { throw new FormatException("The method " + createMethod.Name + " must return the type " + typeof(TRepository).FullName); } return (TRepository) createMethod.Invoke(this.Value, new object[] {unitOfWork}); } } }