2012-10-08 49 views
4

我有Component註釋的接口和一些類,實現它,如下所示:如何在沒有Spring XML上下文文件的情況下AutoWire對象?

@Component 
public interface A { 
} 

public class B implements A { 
} 
public class C implements A { 
} 

另外,我有一個Autowired變量像這樣的類:

public class Collector { 
    @Autowired 
    private Collection<A> objects; 

    public Collection<A> getObjects() { 
     return objects; 
    } 
} 

我的背景文件由這些定義:

<context:component-scan base-package="org.iust.ce.me"></context:component-scan> 

<bean id="objectCollector" class="org.iust.ce.me.Collector" autowire="byType"/> 

<bean id="b" class="org.iust.ce.me.B"></bean> 
<bean id="c" class="org.iust.ce.me.C"></bean> 

而在主類中,我有一些代碼如下:

ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml"); 
B b = (B) context.getBean("b"); 
C c = (C) context.getBean("c"); 
Collector objectCollector = (Collector) context.getBean("objectCollector"); 

for (A object : objectCollector.getObjects()) { 
    System.out.println(object); 
} 

輸出:

[email protected] 
[email protected] 

這些代碼工作得很好,但由於某些原因,我不願意用XML上下文文件。除此之外,我傾向於使用new運算符創建對象,而不是使用getBean()方法。儘管如此,由於AutoWiring在編程中確實是個好主意,我不想失去它。

現在我有兩個問題!

  1. 我怎麼能AutoWire類,實現了A界面不使用XML上下文文件?
    有沒有可能?

  2. 當我改變從singlton bean的scopeprototype如下:

    <bean id="b" class="org.iust.ce.me.B" scope="prototype"></bean>

    和實例數它的豆子,只有在創造context中實例化的豆,是injectedAutoWired變量。爲什麼?

任何幫助將不勝感激。

回答

9

不知道春天的版本,您正在使用。但目前您可以使用@Configuration來替換.xml。看看@Configuration

下面是在文檔中的代碼

@Configuration 
public class ServiceConfig { 
    private @Autowired RepositoryConfig repositoryConfig; 
    public @Bean TransferService transferService() { 
     return new TransferServiceImpl(repositoryConfig.accountRepository()); 
    } 
} 

@Configuration 
public interface RepositoryConfig { 
    @Bean AccountRepository accountRepository(); 
} 

@Configuration 
public class DefaultRepositoryConfig implements RepositoryConfig { 
    public @Bean AccountRepository accountRepository() { 
     return new JdbcAccountRepository(...); 
    } 
} 

@Configuration 
@Import({ServiceConfig.class, DefaultRepositoryConfig.class}) // import the concrete config! 
public class SystemTestConfig { 
    public @Bean DataSource dataSource() { /* return DataSource */ } 
} 
public static void main(String[] args) { 
    ApplicationContext ctx = new AnnotationConfigApplicationContext(SystemTestConfig.class); 
    TransferService transferService = ctx.getBean(TransferService.class); 
    transferService.transfer(100.00, "A123", "C456"); 
} 
+0

優秀!希望我可以給予超過+1。感謝您查找併發布代碼 - 絕不會讓它在文檔中變得如此之低...... 與Neo4j一起工作非常精彩(通過[this](http://codepitbull.wordpress.com/2013/05/12/bootstrapping -neo4j與 - 彈簧 - 數據 - 不-XML))。 再次,謝謝! – KendallV

0

1-您需要編寫另一個將執行此操作的類。將@Component寫入B和C類。

public static void main(){ 
    ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml"); 
    InitClass initClass = (InitClass) context.getBean("initClass"); 
} 


public class InitClass{ 
    @Autowired 
    public B b; 

    @Autowired 
    public C c; 
} 

用這個,你將得到B和C而不使用xml。

2- http://static.springsource.org/spring/docs/3.0.0.M3/reference/html/ch04s04.html豆類作用域在此處詳述。如果你總是想要一個新的對象,你應該使用原型,但創建一個新的對象將在不同的類中完成。在同一個班級中,您應該添加一個新的參考。

public class InitClass{ 
    @Autowired 
    public A a1; 

    @Autowired 
    public A a2; 

} 
+0

+0.5!很好的答案,但我仍然需要使用XML上下文文件。而且,在你的代碼中,實現'A'接口的類被手動添加到'InitClass'。在我的項目中有幾個實現'A'接口的類,我不想手動處理它們。 – faghani

+0

您必須在啓動時初始化xml一次使用Spring,您將從main方法訪問的第一個Object應該使用context.getBean獲取,如果存在@Autowired,則其他人將被注入。爲了動態創建新對象,你必須使用context.getBean,我認爲春天沒有其他辦法。 – sgpalit

+0

我認爲用'new'運算符創建Spring bean是可能的,但我不知道它是如何完成的。看一看[這個問題](http://stackoverflow.com/questions/10997092/autowiring-in-spring-bean-component-created-with-new-keyword) – faghani

2

提供給管理已經被正確註解類,Spring能夠掃描應用程序的文件來獲得它需要沒有任何XML或Java的信息配置文件。

AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(); 
context.scan("com.something.something.etc"); 
context.refresh(); 
...context.getBean("name_of_bean"); 

AnnotationConfigApplicationContext被實例化不帶任何參數。 context.scan("...");需要一個字符串,告訴Spring在哪裏看。即包裹

com.something.something.etc.one 
com.comething.something.etc.two
將被掃描,並且那些包含 @Component@Autowired等註釋的包中的類將被安裝並在需要時注入。

這種方法似乎沒有很好的記錄。

+0

儘可能提供更多評論。 – Masoud

相關問題