NInject IBindingGenerator и ToProvider
Я создал этот код:
public class AddonsModule : Ninject.Modules.NinjectModule
{
public override void Load()
{
this.Bind(b => b.FromAssembliesMatching("*")
.SelectAllClasses()
.InheritedFrom(typeof(UIExtensibility.AbstractAddon))
.BindWith(new AddonBindingGenerator())
);
}
private class AddonBindingGenerator : IBindingGenerator
{
public System.Collections.Generic.IEnumerable<Ninject.Syntax.IBindingWhenInNamedWithOrOnSyntax<object>> CreateBindings(System.Type type, Ninject.Syntax.IBindingRoot bindingRoot)
{
if (type.IsInterface || type.IsAbstract)
yield break;
yield return bindingRoot.Bind(type).ToProvider(typeof(UIExtensibility.AbstractAddon));
}
}
private class AddonProvider : IProvider<UIExtensibility.AbstractAddon>
{
public object Create(IContext context)
{
return null;
}
public Type Type
{
get { throw new NotImplementedException(); }
}
}
}
AddonProvider, кажется, следует избегать. Это никогда не выполняется.
Когда я выполняю:kernel.GetAll<UIExtensibility.AbstractAddon>()
, AddonProvider.Create
метод никогда не выполняется.
Не могли бы вы сказать мне, что не так? Я очень ценю вашу помощь.
Спасибо за все.
3 ответа
AddOnProvider
наследуется от IProvider<T>
вместо UIExtensibility.AbstractAddon
,
также у вас могут быть проблемы, связанные с закрытыми внутренними классами. делать AddOnProvider
публичный класс высшего уровня.
Вы связываете определенный тип, который наследуется от typeof(UIExtensibility.AbstractAddon)
к провайдеру. Например, может быть class Foo : UIExtensibility.AbstractAddon
, Теперь ваше обязательное соглашение переводится так:
Bind<Foo>().ToProvider<AddonProvider>();
Сейчас, kernel.GetAll<UIExtensibility.AbstractAddon>()
однако ищет привязки, сделанные как:
Bind<UIExtensibility.AbstractAddon>().To...
Почини это
Так что вам нужно изменить строку
bindingRoot.Bind(type).ToProvider(new AddonProvider());
чтобы:
bindingRoot.Bind(typeof(UIExtensibility.AbstractAddon)).ToProvider<AddonProvider>();
более того
- ты линия
object f = bindingRoot.Bind(type).ToProvider(new AddonProvider());
никогда не возвращает привязку (object f
). - делает
UIExtensibility.AbstractAddon
воплощать в жизньIProvider
?
Спасибо за ваш ответ и комментарии.
Я считаю, что проблема в том, что я не совсем понимаю, как работает этот "общий" процесс связывания.
Я попытаюсь написать процесс обработки моих мозговых шагов:
Мне нужно связать каждый
AbstractAddon
реализация внутри папки сборок аддонов. Итак, я думаю, что этот код правильный, но я совсем не уверен.this.Bind(b => b.FromAssembliesMatching("*") .SelectAllClasses() .InheritedFrom(typeof(UIExtensibility.AbstractAddon)) .BindWith(new AddonBindingGenerator()) );
мой
AbstractAddon
как:public abstract class AbstractAddon : IAddon { private object configuration; public AbstractAddon(object configuration) { this.configuration = configuration; } // IAddon interface public abstract string PluginId { get; } public abstract string PluginVersion { get; } public abstract string getCaption(string key); public abstract Type getConfigurationPanelType(); public abstract System.Windows.Forms.UserControl createConfigurationPanel(); }
Я думаю, мне нужно:
foreach implementation of `AbstractAddon` found out, I need to "inject" a configuration object -> So, I guess I need to set a provider and provide this configuration object.
Это было бы моим основным способом мышления для решения этой проблемы.
Я немного изменил свой первый подход. Вместо того, чтобы использовать класс IBindingGenerator, я использовал следующее:
public class AddonsModule : Ninject.Modules.NinjectModule
{
public override void Load()
{
this.Bind(b => b.FromAssembliesMatching("*")
.SelectAllClasses()
.InheritedFrom(typeof(UIExtensibility.AbstractAddon))
.BindAllBaseClasses()
.Configure(c => c.InSingletonScope())
);
this.Bind<object>().ToProvider<ConfigurationProvider>()
.WhenTargetHas<UIExtensibility.ConfigurationAttribute>();
}
Итак, мой ConfigurationProvider это:
private class ConfigurationProvider : IProvider<object>
{
public object Create(IContext context)
{
return "configuration settings";
}
}
И теперь мой конструктор AbstractAddon содержит параметр, аннотированный с помощью ConfigurationAttribute:
public AbstractAddon([Configuration]object configuration)
{
this.configuration = configuration;
}
Проблема сейчас в том, что NInject, похоже, игнорирует провайдера объекта конфигурации. NInject генерирует объект дампа, однако не выполняет ConfigurationProvider.Create
метод...
Что я делаю не так, сейчас? Этот подход действительно лучше, чем предыдущий? Спасибо за все.