2012-04-18 4 views
3

У меня есть вопрос относительно инъекции зависимостей.Могу ли я вставить объект, созданный динамически

У меня есть класс, скажем:

class MyClass { 
    MyServiceAPI serviceAPI; 
    public setSession(Session session) { 
     serviceAPI = new MyServiceAPI(session);  
    } 
    .... 
} 

Сеанс создается другой класс, который загружает из базы данных во время выполнения.

class MyAnotherClass { 
    Myclass myClass; 

    @Inject 
    MyAnotherClass(MyClass myClass) { 
     this.myClass = myClass; 
    } 

    public someFunction() { 
     String key = <read from database>; 
     Session session = new Session(key); 
     myClass.setSession(); 
     ...... 
    } 
} 

Как описано, экземпляр МойКласс вводится в MyAnotherClass и экземпляр serviceAPI в MyClass создается с помощью нового. Если я хочу добавить ServiceAPI в MyClass, я могу создать его в классе, где создан сеанс, и с помощью установщика установить его в MyClass.

Но вопрос в том, что я не хочу, чтобы MyAnotherClass создавал MyServiceAPI и вводил его в MyClass. Я хочу, чтобы MyAnotherClass не ожидал существования MyServiceAPI.

Есть ли способ, которым я могу это сделать, используя инъектор depdendency, такой как Guice или Spring? Или просто Java?

Большое спасибо.

+0

Да, похоже, что 'MyClass' следует вводить в' MyAnotherClass'. Кроме того, «MyServiceAPI» следует, вероятно, ввести в «MyClass». Такой вопрос трудно ответить, не зная семантики/намерения вашего кода ... – Torious

+0

Да. Я понимаю, что вы имеете в виду. Извините, вопрос немного плохой. Позвольте мне немного изменить его. – Kevin

ответ

1

Если вы хотите сделать инъекцию зависимостей в чистой Java, есть поддержка с Java 6 через встроенный интерфейс поставщика услуг Java. Хотя это требует некоторой сантехники с файлами jar и т. Д. Посмотрите here for Java SPI

1

Возможное решение с изображением и простой фабрикой. MyServiceAPI может быть интерфейсом.

public class MyClass { 

    @Inject 
    private MyServiceFactory factory; 
    private MyServiceAPI myServiceAPI; 

    public void setSession(Session session) { 
     myServiceAPI = factory.createMyServiceAPI(session); 
    } 
} 

public class MyServiceFactory { 

    MyServiceAPI createMyServiceAPI(Session session) { 
     // create with new, inject via Injector, do what you want... :) 
     return <yourobject>; 
    } 
} 
0

Для этого вам просто нужно использовать хорошую фабрику для омоложения.

class MyAnotherClass { 
    MyClassFactory myClassFactory; 

    @Inject 
    MyAnotherClass(MyClassFactory myClassFactory) { 
     this.myClassFactory = myClassFactory; 
    } 

    public void someFunction() { 
     String key = "1"; // read from DB 
     myClass = myClassFactory.getMyClass(key); 
    } 
} 

class MyClassFactory { 
    public MyClass getMyClass(String key) { 
     Session session = new Session(key); 
     MyClass myClass = new MyClass(); 
     myClass.setSession(session); 
     return myClass; 
    } 
} 
0

Я действительно думаю, что вам, возможно, придется переупорядочить ваши зависимости. Опять же, не зная ваш полный код это своего рода трудно, но, глядя на ваш пример, похоже, справедливо следующее:

  • MyClass на самом деле зависит от MyServiceAPI и НЕ на Session. Поэтому вы должны просто ввести MyServiceAPI непосредственно в свой конструктор.

  • Session должен иметь свой sessionId (или что-то еще), введенный в его конструктор. Вы можете привязать его значение в Guice, чтобы получить что-то вроде: @Inject @SessionId public Session(String sessionId). Или у вас могут быть как sessionId, так и некоторые SessionService впрыснуть в Session, чтобы он мог получить свои собственные данные из службы.

  • MyServiceAPI должен иметь в своем распоряжении Session.

Смежные вопросы