Больше контроля над созданием универсальных типов? - PullRequest
0 голосов
/ 28 апреля 2010

Я пытаюсь использовать StructureMap для регистрации некоторых типов, которые реализуют универсальный интерфейс и создаются с помощью фабрики.

Мой код:

    public interface IManagerBase<T, TKey> : IDisposable
    {
        // Get Methods
        T GetById(TKey Id);
    }

    public partial interface IServerHostManager : IManagerBase<ServerHost, int>
    {
        // ServerHost Specific Get Methods
    }    

    partial class ServerHostManager : ManagerBase<ServerHost, int>, IServerHostManager
    {
        // Implementation
    }

    public class ManagerFactory : IManagerFactory
    {
        public IServerHostManager GetServerHostManager()
        {
            return new ServerHostManager();
        }
    }

Это прекрасно работает:

 For<IServerHostManager>().HybridHttpOrThreadLocalScoped()
.Use(new ManagerFactory().GetServerHostManager());

Моя фабрика вызывается и возвращается новый экземпляр IServerHostManager.

Можно ли как-то сканировать все универсальные типы и создавать их экземпляры на моей фабрике?

Это не работает из-за того, что ServerHostManager является внутренним классом:

        Scan(x =>
        {
            x.AssemblyContainingType(typeof(IManagerBase<,>));
            x.AddAllTypesOf(typeof(IManagerBase<,>));
            x.ConnectImplementationsToTypesClosing(typeof(IManagerBase<,>))
                .OnAddedPluginTypes(t => t.HybridHttpOrThreadLocalScoped());
        });

Какую команду сканирования я могу использовать, чтобы сообщить SM, чтобы она звонила на мою фабрику?

Спасибо,

Rick

Продолжение добавлено 5/4:

Извините за задержку в последующих действиях.

У меня есть куча объектов менеджера (> 75), созданных шаблоном CodeSmith nHibernate. Доступ к ним обычно осуществляется через фабричный объект. Вместо этого я хотел бы отсканировать их, чтобы они все были зарегистрированы автоматически.

Теперь я регистрирую объекты:

For<IActivityLogManager>().HybridHttpOrThreadLocalScoped() 
.Use(new ManagerFactory().GetActivityLogManager()); 

For<IAspnetUserManager>().HybridHttpOrThreadLocalScoped() 
.Use(new ManagerFactory().GetAspnetUserManager()); 

Вот объекты

public interface IManagerBase<T, TKey> : IDisposable
{
    // Get Methods 
    T GetById(TKey Id);
}

public partial interface IActivityLogManager : IManagerBase<BusinessObjects.ActivityLog, int>
{
    // Get Methods
    IList<ActivityLog> GetByActivityTypeId(System.Int32 activityType);
}

public partial class ActivityLogManager : ManagerBase<BusinessObjects.ActivityLog, int>, IActivityLogManager
{
    public IList<ActivityLog> GetByActivityTypeId(System.Int32 activityType)
    {
        // Code to fetch objects
    }    
}

public partial interface IAspnetUserManager : IManagerBase<BusinessObjects.AspnetUser, System.Guid>
{
    // Get Methods
    IList<ActivityLog> GetByActivityTypeId(System.Int32 activityType);
}

public partial class AspnetUserManager : ManagerBase<BusinessObjects.AspnetUser, System.Guid>, IAspnetUserManager
{
    public IList<AspnetUser> GetAll()
    {
        // Code to fetch objects
    }    
}

Код моего сканирования:

Scan(x => 
    { 
        x.AssemblyContainingType(typeof(IManagerBase<,>)); 
        x.AddAllTypesOf(typeof(IManagerBase<,>)); 
        x.ConnectImplementationsToTypesClosing(typeof(IManagerBase<,>)) 
            .OnAddedPluginTypes(t => t.HybridHttpOrThreadLocalScoped());     
    });

Приведенный выше код сканирования не находит никаких объектов в сборке.

Надеюсь, это прояснит мой сценарий.

Спасибо,

Rick

1 Ответ

1 голос
/ 21 мая 2011

Эту проблему можно решить, сделав сборку другом:

[assembly: InternalsVisibleTo("AssemblyB")]

http://msdn.microsoft.com/en-us/library/0tke9fxk.aspx

...