1. 程式人生 > >Spring為什麼@Autowired注入的是介面

Spring為什麼@Autowired注入的是介面

1.Spring怎麼知道注入哪個實現?
As long as there is only a single implementation of the interface and that implementation is annotated with @Component with Spring’s component scan enabled, Spring framework can find out the (interface, implementation) pair. If component scan is not enabled, then you have to define the bean explicitly in your application-config.xml (or equivalent spring configuration file).
如果Spring配置了component scan,並且要注入的介面只有一個實現的話,那麼spring框架可以自動將interface於實現組裝起來。如果沒有配置component scan,那麼你必須在application-config.xml(或等同的配置檔案)定義這個bean。

2.需要@Qualifier和@Resource註解嗎?
Once you have more than one implementation, then you need to qualify each of them and during auto-wiring, you would need to use the @Qualifier annotation to inject the right implementation, along with @Autowired annotation. If you are using @Resource (J2EE semantics), then you should specify the bean name using the name attribute of this annotation.
一旦一個介面有多個實現,那麼就需要每個特殊化識別並且在自動裝載過程中使用@Qualifier和@Autowired一起使用來標明。如果是使用@Resource註解,那麼你應該使用resource中屬性名稱來標註@Autowired.

3.為什麼@Autowired使用在interface上而不是實現類上?
Firstly, it is always a good practice to code to interfaces in general. Secondly, in case of spring, you can inject any implementation at runtime. A typical use case is to inject mock implementation during testing stage.
首先,一般使用介面是很常用並且有益的變成技術。其次,在spring中,你可以在執行過程中注入各種實現。一個很經典的情況就是在測試階段,注入模擬的實現類。

interface IA 
{ 
public void someFunction(); 
}


class B implements IA 
{ 
public void someFunction() 
{ 
//busy code block 
} 
public void someBfunc() 
{ 
//doing b things 
} 
}


class C implements IA 
{ 
public void someFunction() 
{ 
//busy code block 
} 
public void someCfunc() 
{ 
//doing C things 
} 
}


class MyRunner 
{ 
@Autowire 
@Qualifier(“b”)
IA worker;


....
worker.someFunction();
}
Your bean configuration should look like this:





Alternatively, if you enabled component scan on the package where these are present, then you should qualify each class with @Component as follows:


interface IA 
{ 
public void someFunction(); 
}


@Component(value="b") 
class B implements IA 
{ 
public void someFunction() 
{ 
//busy code block 
} 
public void someBfunc() 
{ 
//doing b things 
} 
}


@Component(value="c") 
class C implements IA 
{ 
public void someFunction() 
{ 
//busy code block 
} 
public void someCfunc() 
{ 
//doing C things 
} 
}


@Component 
class MyRunner 
{ 
@Autowire 
@Qualifier(“b”)
IA worker;


....
worker.someFunction();
}