Является ли Guice @ImplementedBy злом? Это уместно в некоторых случаях? - PullRequest
14 голосов
/ 01 июня 2011

Я слышал заявления о том, что " @ ImplementedBy является злом" на том основании, что он нарушает концепции DI и информирует интерфейс о своих разработчиках.

Это может быть правдой в некоторыхв некоторых случаях, но часто я обнаруживал, что это просто приводит к более чистому коду (больше не нужно поддерживать Модули), но в действительности не наносит вреда чему-либо в процессе.

Как прагматики, а не пуристы, когда вы думаете, что стоит использовать@ImplementedBy

Ответы [ 5 ]

11 голосов
/ 20 апреля 2012

У меня было такое же чувство тьфу, ик, гадость @ImplementedBy, НО в то же время, это очень полезно.Spring должен сканировать все классы в списке пакетов, которые вы ему предоставляете.В Guice вам не нужно настраивать этот список пакетов для сканирования, и @ImplementedBy является ключевым для этого (если вы не используете Binder для привязки, которая есть).КАК он переходит к иерархии объектов на первом Injector.getInstance и попадает в интерфейс, он затем использует @ImplementedBy для поиска реализации по умолчанию (если в Binder нет ничего, переопределяющего это значение по умолчанию).

Мы также используем @ImplementedBy.Мы находим его чрезвычайно полезным в использовании, это немного фуфло, но это просто работает и работает хорошо, и, поскольку это DI, это не очень зависит от реализации, так как вы в любом случае можете переопределить привязки новыми.

В то же время интерфейсы, как правило, используются все реже с инфраструктурами DIВсе интерфейсы DAO исчезли в нашем проекте, и мы все еще можем поменять фиктивные объекты для DAO.Java-классы для начала являются неявными интерфейсами, которые могут быть смоделированы без использования интерфейса.Теперь мы оставляем использование интерфейса для основных API-интерфейсов очень понятным и не загромождаем его кодом реализации.Для ДАО нам это больше не нужно.

9 голосов
/ 01 июня 2011

Обычно вы предпочитаете явные привязки точным привязкам (JIT).Явные привязки позволяют инжектору сканировать граф зависимостей во время создания инжектора.Это позволяет Guice работать быстро, если зависимость отсутствует или недействительна.С привязками точно в срок, такими как @ImplementedBy, Guice не может сообщить о проблеме до тех пор, пока не будет выполнена привязка.

Привязки JIT также плохо взаимодействуют с PrivateModules / дочерними инжекторами.Хотя большинству приложений не нужны эти функции, при этом менее болезненно, если каждая привязка принадлежит определенному модулю.

5 голосов
/ 09 мая 2013

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

3 голосов
/ 08 декабря 2012

Я понимаю, почему Google сделал то, что они сделали, но предпочтительная реализация чего-либо не обязательно является злом. Обратите внимание, что в документации сказано, что это для реализации по умолчанию , а не для only one.

Кстати, я нашел этот вопрос, потому что я искал в Интернете существующие реализации концепции @ ImplementedBy.

Я создал аннотацию @ImplementedBy для размещения на одном из моих интерфейсов. При использовании чистого неинъецированного отражения это самый простой способ сообщить интерфейсу, какую реализацию использовать, особенно при работе с существующими API, которые понимают только интерфейсы. (интерфейс, а не реализация)

Аннотация позволяет мне обобщать некоторые действительно грубые генераторы с одной строкой аннотации и одной строкой внутри декоратора. Мне не нужно использовать структуру зависимостей для такой простой операции.

0 голосов
/ 07 марта 2016

для меня, да, это зло, если вы используете его для жесткой привязки и никогда не используете привязку повторно, потому что вы переворачиваете смысл интерфейса. Я согласен с @thSoft, что это довольно распространенная модель, но мне даже не ясно, почему у нас нет @Implements аннотации. Также может раздражать, что данная реализация по умолчанию не является той, которая используется во время выполнения.

Просто чтобы было ясно, что Google сказал этому

Annotate types tell the injector what their default implementation type is. …

!! Он также отклоняет универсальные интерфейсы, такие как

@ImplementedBy(MyImpl.class)
public interface MyInterface<SIn,SOut> {}

public class MyImpl implements MyInterface<String, Integer> {}

, которые обычно не реализуются только один раз. Подробнее см. Внедрение универсальной реализации с использованием Guice .

...