2016-10-02 1 views
0

Я использую Кинжал-2 (версия: 2.7) и Автозаводская (версия: 1.0-бета3). Я столкнулся с особой проблемой.Вопросы, реализующие Ассоциированные инъекции при использовании Dagger-2 и Автозаводской

У меня есть аа класс MyRequest кто к т е р принимает 2 параметра, как:

  1. ConnectivityManager conmgr
  2. INT SomeValue

Я создал CTOR, как

@Autofactory 
public MyRequest(@Provider ConnectivityManager conmgr, int somevalue){ 
// 
} 

У меня есть модуль, содержащий следующие данные:

@Provides 
@SystemScope 
public final ConnectivityManager provideConnectivityManager(App app) { 
return (ConnectivityManager)  
app.getSystemService(Context.CONNECTIVITY_SERVICE); 
} 

В том же модуле, я следующий

@Provides 
@SystemScope 
public final MyRequestFactory providesMyRequestFactory(ConnectivityManager connectivityManager { 
    return new MyRequestFactory(connectivityManager); 
} 

Я получаю ошибку сборки несовместимых типов: ConnectivityManager не может быть преобразован в Provider < ConnectivityManager>.

Любая идея, как решить эту проблему?

ответ

2

Как и в AutoFactory example, если ваш конструктор принимает Foo, ваш сгенерированный конструктор AutoFactory примет вместо этого Provider<Foo>. Это значит, что ваш завод запросит у нового Foo (или ConnectivityManager) один раз для каждого звонка до get без необходимости совместного использования экземпляров между ними.

Это может быть случай, когда вы хотите Foo или ConnectivityManager быть тот же экземпляр для всех экземпляров созданного объекта (MyRequest здесь), но это для вас и Dagger диктовать, не Автозаводской. Следовательно, AutoFactory всегда будет генерировать код, который берет Провайдеров, независимо от того, используете ли вы их таким образом или нет.

К счастью, исправить это очень легко: Dagger может придать Provider<ConnectivityManager> так же легко, как это может впрыснуть ConnectivityManager (как она может для любого связывания), так что вы можете просто изменить метод @Provides как так ...

@Provides 
@SystemScope 
public final MyRequestFactory providesMyRequestFactory(
     Provider<ConnectivityManager> connectivityManagerProvider { 
    return new MyRequestFactory(connectivityManagerProvider); 
} 

... а потому, что ваш генерироваться завод будет иметь @Inject аннотацию, вы, вероятно, будет лучше удалить метод @Provides полностью и позволяя Dagger использовать этот конструктор для MyRequestFactory инъекций. Хотя вы потеряете аннотацию области @SystemScope по методу @Provides, это не проблема: с помощью инъекции Provider<ConnectivityManager> вам не нужно беспокоиться о жизненном цикле сгенерированной фабрики, поэтому вы можете вернуться к предоставленному по умолчанию резервному обеспечению.

+0

Спасибо за хорошее объяснение. И по уважительным причинам, почему мне не нужно «@Provides» для «MyRequest». Однако вы могли бы дать представление о том, как Dagger-2 будет внедрять Provider , хотя я предоставляю только ConnectivityManger, используя «@Provides ConnectivityManager» в моем модуле (а не в Провайдере shyguy

+0

@shyguy. Добро пожаловать!И вам, вероятно, понадобится @Provides для MyRequest, но не для MyRequestFactory. Вы можете увидеть раздел [«Привязки в графе» руководства пользователя Dagger 2] (http://google.github.io/dagger/users-guide.html#bindings-in-the-graph) для получения подробной информации, но достаточно сказать, что Dagger будет обрабатывать запросы для «Provider », 'Lazy ', или даже 'Provider >' для любого 'T', который вы предоставляете с помощью метода' @ Provides' или иначе. –

+0

Извините за опечатку Я имел в виду только MyRequestFactory. Я обязательно перейду по предложенной вами ссылке. Еще раз спасибо @Jeff Bowman – shyguy