2013-05-01 74 views
38

我有DataPrepareService爲報表準備數據,而且我有一個Enum與報表類型,我需要將ReportService注入Enum或有權從枚舉中訪問ReportService。將bean注入枚舉

我的服務:

@Service 
public class DataPrepareService { 
    // my service 
} 

我枚舉:

public enum ReportType { 

    REPORT_1("name", "filename"), 
    REPORT_2("name", "filename"), 
    REPORT_3("name", "filename") 

    public abstract Map<String, Object> getSpecificParams(); 

    public Map<String, Object> getCommonParams(){ 
     // some code that requires service 
    } 
} 

我試圖用

@Autowired 
DataPrepareService dataPrepareService; 

,但沒有奏效

如何將我的服務注入枚舉?

回答

8

也許是這樣的:

public enum ReportType { 
    @Component 
    public class ReportTypeServiceInjector { 
     @Autowired 
     private DataPrepareService dataPrepareService; 

     @PostConstruct 
     public void postConstruct() { 
      for (ReportType rt : EnumSet.allOf(ReportType.class)) 
       rt.setDataPrepareService(dataPrepareService); 
     } 
    } 

    REPORT_1("name", "filename"), 
    REPORT_2("name", "filename"), 
    ... 
} 
+1

downvote for does not compile – Pranalee 2013-10-31 07:10:32

+0

您應該將內部類更改爲靜態類 – 2017-01-12 09:14:08

1

這將是難以控制的Spring容器已經運行在枚舉被實例化的時間(如果你在測試過這種類型的變量 - case,你的容器通常不會在那裏,即使aspectj自動裝配也沒有幫助)。我建議只是讓dataprepare-service或者什麼東西給你帶有枚舉參數的lookup-method的特定參數。

38
public enum ReportType { 
    @Component 
    public static class ReportTypeServiceInjector { 
     @Autowired 
     private DataPrepareService dataPrepareService; 

     @PostConstruct 
     public void postConstruct() { 
      for (ReportType rt : EnumSet.allOf(ReportType.class)) 
       rt.setDataPrepareService(dataPrepareService); 
     } 
    } 

    REPORT_1("name", "filename"), 
    REPORT_2("name", "filename"), 
    ... 
} 

weekens' answer的作品,如果你改變內部類靜態的,所以春天可以看到它

+1

您節省了我的一天。謝謝! – 2015-10-30 18:06:14

+1

這裏需要注意的是,上面的代碼不會編譯,因爲靜態類是在枚舉常量之前定義的。根據Java規範,enum常量在任何類聲明之前首先出現。簡單地把常數和你的班級放下。 – prettyvoid 2017-10-02 09:04:00

0

Enum s爲靜態的,所以你必須想出一個辦法,從靜態的情況下取得的豆類。

您可以創建一個名爲ApplicationContextProvider的類,該類實現了ApplicationContextAware接口。

import org.springframework.beans.BeansException; 
import org.springframework.context.ApplicationContext; 
import org.springframework.context.ApplicationContextAware; 

public class ApplicationContextProvider implements ApplicationContextAware{ 

private static ApplicationContext appContext = null; 

public static ApplicationContext getApplicationContext() { 
    return appContext; 
} 

public void setApplicationContext(ApplicationContext appContext) throws BeansException { 
    this.appContext = appContext; 
} 
} 

然後添加此應用程序上下文文件:

<bean id="applicationContextProvider" class="xxx.xxx.ApplicationContextProvider"></bean> 

後,你可以訪問應用程序上下文以靜態方式是這樣的:

ApplicationContext appContext = ApplicationContextProvider.getApplicationContext(); 
0

我想這就是你需要

public enum MyEnum { 
    ONE,TWO,THREE; 
} 

自動裝配枚舉按通常

@Configurable 
public class MySpringConfiguredClass { 

      @Autowired 
     @Qualifier("mine") 
      private MyEnum myEnum; 

} 

這是使用方法,使用原廠方法=「的valueOf」,並且確保 懶的init =「假」

因此容器創建bean前期

<bean id="mine" class="foo.bar.MyEnum" factory-method="valueOf" lazy-init="false"> 
    <constructor-arg value="ONE" /> 
</bean> 

你就完成了!