工具類(類)中使用ApplicationContext獲取bean包空指標
阿新 • • 發佈:2019-01-26
專案中遇到這樣一個問題,當時是要寫一個工具類,裡面有這樣的一段話,
MsgTools是工具類,裡面有一個屬性applicationContext
MsgTools.applicationContext
.getBean(com.cheshangma.operation.wx.service.internal.WeChatServiceImpl.class)
但這樣會報錯,applicationContext一直是null,不能注入進來,聽公司大牛解釋就是,載入MsgTools類時,ApplicationContext類還沒有被spring代理載入,所以不能注入進MsgTools這個類裡面.解決的思路就是要讓ApplicationContext這個類先被spring先管理注入,然後在去載入管理MsgTools這個類.
程式碼如下
package com.cheshangma.operation.wx.common.utils;
import java.util.HashMap;
import java.util.Map;
import org.apache.log4j.Logger;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.ApplicationContext ;
import org.springframework.context.ApplicationContextAware;
import org.springframework.context.annotation.Configuration;
import com.cheshangma.operation.common.enums.MessageType;
import com.cheshangma.operation.entity.NoticeEventEntity;
import com.cheshangma.operation.wx.common.template.CarCertifiMsg ;
import com.cheshangma.operation.wx.common.template.CarIllegalMsg;
import com.cheshangma.operation.wx.common.template.CarNoticeMsg;
import com.cheshangma.operation.wx.common.template.EventReply;
import com.cheshangma.operation.wx.common.template.MsgTemplate;
import com.cheshangma.operation.wx.common.template.OrderNewMsg;
import com.cheshangma.operation.wx.common.template.OrderPayMsg;
import com.cheshangma.operation.wx.common.template.OrderShipMsg;
import com.cheshangma.operation.wx.common.template.WxTemplate;
import com.cheshangma.operation.wx.service.MsgService;
import com.cheshangma.operation.wx.service.NoticeEventService;
/**
* 根據通知型別不同調用不同service傳送訊息
*
* @author yhy
*
*/
@Configuration
public class MsgTools implements ApplicationContextAware {//這裡實現ApplicationContextAware介面
@SuppressWarnings("unused")
private static Logger log = Logger.getLogger(MsgTools.class);
public static int TIME_INTERVAL = 1;
public static int SLEEP_TIME = 10 * 1000;
/** 存入memcached的時間 **/
public static int MEM_TIME = (TIME_INTERVAL + 1) * 60 * 1000;
private static Map<MessageType, Object> map = new HashMap<MessageType, Object>();
private static NoticeEventService noticeEventService = null;
private static MsgTools msgTools = new MsgTools();
private static boolean isReloaded = false;
private static ApplicationContext applicationContext;
public static MsgTools getInstance() {
return msgTools;
}
public boolean sendOneMsg(MessageType msgType, MsgTemplate msgTemplate) {
synchronized (MsgTools.class) {
while (!isReloaded) {//ApplicationContext類沒有載入完,讓執行緒等待
try {
MsgTools.class.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
MsgService msgService = (MsgService) map.get(msgType);
return msgService.sendMsg(msgTemplate);
}
}
@Override
public void setApplicationContext(ApplicationContext arg0) throws BeansException {
//這裡就是讓ApplicationContext載入完後,在使用ApplicationContext來獲得bean
synchronized (MsgTools.class) {
MsgTools.applicationContext = arg0;
isReloaded = true;
map.put(MessageType.MSGTYPE_WEIXIN, MsgTools.applicationContext
.getBean(com.cheshangma.operation.wx.service.internal.WeChatServiceImpl.class));
map.put(MessageType.MSGTYPE_SMS, MsgTools.applicationContext
.getBean(com.cheshangma.operation.wx.service.internal.SmsServiceImpl.class));
map.put(MessageType.MSGTYPE_VOICE, MsgTools.applicationContext
.getBean(com.cheshangma.operation.wx.service.internal.VoiceServiceImpl.class));
noticeEventService =
(NoticeEventService) MsgTools.applicationContext
.getBean(com.cheshangma.operation.wx.service.internal.NoticeEventServiceImpl.class);
MsgTools.class.notifyAll();
}
}
}