Authored by chenchao

support xml config

package com.yoho.rfid.controller;
import com.yoho.rfid.model.ClientConfig;
import com.yoho.rfid.model.ManageCommand;
import com.yoho.rfid.service.ManageService;
import com.yoho.rfid.util.ApiResponse;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
... ... @@ -55,8 +58,8 @@ public class ManageController {
@RequestMapping("/setBussinessDate")
@ResponseBody
public ApiResponse setBussinessDate(int open,int close){
manageService.doBusinessDate(open, close);
public ApiResponse setBussinessDate(@RequestBody ClientConfig clientConfig){
manageService.doBusinessDate(clientConfig);
return new ApiResponse.ApiResponseBuilder()
.code(200).message("setBussinessDate success").build();
}
... ...
package com.yoho.rfid.model;
/**
*@author chenchao
*@date 2018年1月24日
*/
public class ClientConfig {
private boolean needFilter = true;
private int sendMailBeginHour = 7;
private int sendMailEndHour = 8;
/**
* 客户端关机时间
*/
private int closeHour = 23;
/**
* 客户端开机时间
*/
private int openHour = 9;
public int getSendMailBeginHour() {
return sendMailBeginHour;
}
public void setSendMailBeginHour(int sendMailBeginHour) {
this.sendMailBeginHour = sendMailBeginHour;
}
public int getSendMailEndHour() {
return sendMailEndHour;
}
public void setSendMailEndHour(int sendMailEndHour) {
this.sendMailEndHour = sendMailEndHour;
}
public int getCloseHour() {
return closeHour;
}
public void setCloseHour(int closeHour) {
this.closeHour = closeHour;
}
public int getOpenHour() {
return openHour;
}
public void setOpenHour(int openHour) {
this.openHour = openHour;
}
public boolean isNeedFilter() {
return needFilter;
}
public void setNeedFilter(boolean needFilter) {
this.needFilter = needFilter;
}
@Override
public String toString() {
return "ClientConfig [needFilter=" + needFilter
+ ", sendMailBeginHour=" + sendMailBeginHour
+ ", sendMailEndHour=" + sendMailEndHour + ", closeHour="
+ closeHour + ", openHour=" + openHour + "]";
}
}
... ...
... ... @@ -15,14 +15,9 @@ public class SystemConfig {
private int sendMailBeginHour = 10;
private int sendMailEndHour = 22;
/**
* 客户端关机时间
*/
private int closeHour = 23;
/**
* 客户端开机时间
*/
private int openHour = 9;
private ClientConfig clientConfig;
private List<IpV4Host> hostWhiteList;
... ... @@ -32,6 +27,9 @@ public class SystemConfig {
ipV4Host.setSegment1(ipV4Host.getSegment1B());
ipV4Host.setType(ipV4Host.getTypeB());
hostWhiteList.add(ipV4Host);
//
clientConfig = new ClientConfig();
}
public boolean isSendMail() {
... ... @@ -66,28 +64,23 @@ public class SystemConfig {
private static SystemConfig systemConfig = new SystemConfig();
}
public int getCloseHour() {
return closeHour;
}
public void setCloseHour(int closeHour) {
this.closeHour = closeHour;
public List getHostWhiteList() {
return hostWhiteList;
}
public int getOpenHour() {
return openHour;
public void setHostWhiteList(List hostWhiteList) {
this.hostWhiteList = hostWhiteList;
}
public void setOpenHour(int openHour) {
this.openHour = openHour;
}
public List getHostWhiteList() {
return hostWhiteList;
public ClientConfig getClientConfig() {
return clientConfig;
}
public void setHostWhiteList(List hostWhiteList) {
this.hostWhiteList = hostWhiteList;
public void setClientConfig(ClientConfig clientConfig) {
this.clientConfig = clientConfig;
}
@Override
... ... @@ -96,8 +89,6 @@ public class SystemConfig {
.append("sendMail", sendMail)
.append("sendMailBeginHour", sendMailBeginHour)
.append("sendMailEndHour", sendMailEndHour)
.append("closeHour", closeHour)
.append("openHour", openHour)
.append("hostWhiteList", hostWhiteList)
.toString();
}
... ...
package com.yoho.rfid.service;
import com.yoho.rfid.model.ClientConfig;
import com.yoho.rfid.util.DateUtil;
import java.util.Date;
/**
*@author chenchao
*@date 2018年1月24日
*/
public abstract class AbstractMonitorService {
//崩溃
protected static final String CRASH = "crash",
//重启完毕
REBOOTED = "rebooted";
protected boolean isTimeout(long timeout, long lastUpdateDT){
long currentDT = System.currentTimeMillis();
long diff = currentDT - lastUpdateDT;
return diff > timeout;
}
protected boolean clientCanSendMail(ClientConfig clientConfig){
boolean cansend = true;
int currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
if(clientConfig.isNeedFilter()){
cansend = currentHour >= clientConfig.getSendMailBeginHour()
&& currentHour<= clientConfig.getSendMailEndHour();
}
return cansend;
}
}
... ...
package com.yoho.rfid.service;
import com.yoho.rfid.model.SystemConfig;
import com.yoho.rfid.util.DateUtil;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import java.util.Date;
import java.util.Properties;
import javax.annotation.Resource;
import javax.mail.MessagingException;
import javax.mail.NoSuchProviderException;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;
import java.util.Date;
import java.util.Properties;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
/**
* Created by sailing on 2017/10/17.
... ... @@ -22,19 +23,24 @@ import java.util.Properties;
@Service
public class MailService {
private Logger logger = LoggerFactory.getLogger(getClass());
private final Logger logger = LoggerFactory.getLogger(getClass());
private String username = "no-reply@yoho.cn";// 邮局用户名(请填写完整的email地址)
private String Password = "Yoho@9646"; //邮局密码
private String username = "no-reply@yoho.cn";// 邮件用户名(请填写完整的email地址)
private String Password = "Yoho@9646"; //邮件密码
private String From = "no-reply@yoho.cn";//邮件发送者email地址
private static String Host = "smtp.exmail.qq.com"; //企业邮局域名
private boolean SMTPAuth = true;// 启用SMTP验证功能
private static String CharSet = "utf-8";//设置邮件编码
private String toAccount = "ben.li@yoho.cn";
private String[] ccAccounts = {"frank.fu@yoho.cn", "xiuchun.luo@yoho.cn", "chao.chen@yoho.cn",
"rongjun.zhou@yoho.cn", "qiqi.zhou@yoho.cn", "jon.huang@yoho.cn"};
@Value(value="${email.toAccount:ben.li@yoho.cn}")
private String toAccount;
//{"frank.fu@yoho.cn", "xiuchun.luo@yoho.cn", "chao.chen@yoho.cn",
//"rongjun.zhou@yoho.cn", "qiqi.zhou@yoho.cn", "jon.huang@yoho.cn"};
@Resource(name="ccAccounts")
private String[] ccAccounts;
private Session getSession(){
return EmailManager.session;
... ... @@ -55,21 +61,7 @@ public class MailService {
}
}
public void send(String msg, boolean forceSend){
if(!forceSend){
SystemConfig systemConfig = SystemConfig.getInstance();
if(!systemConfig.isSendMail()){//不发送一般发生在测试环境
logger.warn("systemConfig.sendMail is set {},u can use manage/sendMail/open to control", systemConfig.isSendMail());
return;
}
//上午10点到晚上22点发送,其他时间不发
int currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
if(currentHour<systemConfig.getSendMailBeginHour() || currentHour >=systemConfig.getSendMailEndHour()){
logger.warn("it's too late, don't need to send mail, thanks developer sailing");
return;
}
}
public void send(String msg){
// 3. 创建一封邮件
RecipientAccount ra = new RecipientAccount();
ra.ccAccounts = ccAccounts;
... ... @@ -81,8 +73,6 @@ public class MailService {
Session session = getSession();
MimeMessage message = createMimeMessage(session, username, ra, msg);
transport = session.getTransport();
// 5. 使用 邮箱账号 和 密码 连接邮件服务器, 这里认证的邮箱必须与 message 中的发件人邮箱一致, 否则报错
//
// PS_01: 成败的判断关键在此一句, 如果连接服务器失败, 都会在控制台输出相应失败原因的 log,
... ...
... ... @@ -3,6 +3,7 @@ package com.yoho.rfid.service;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import com.yoho.rfid.model.ClientConfig;
import com.yoho.rfid.model.SystemConfig;
import org.slf4j.Logger;
... ... @@ -29,7 +30,12 @@ public class ManageService {
}
}
public void doBusinessDate(int openHour, int closeHour){
public void doBusinessDate(ClientConfig clientConfig){
int openHour = clientConfig.getOpenHour();
int closeHour = clientConfig.getCloseHour();
boolean needFilter = clientConfig.isNeedFilter();
int beginHour = clientConfig.getSendMailBeginHour();
int endHour = clientConfig.getSendMailEndHour();
final Lock writelock = lock;
writelock.lock();
try{
... ... @@ -39,8 +45,11 @@ public class ManageService {
return;
}
SystemConfig systemConfig = SystemConfig.getInstance();
systemConfig.setOpenHour(openHour);
systemConfig.setCloseHour(closeHour);
systemConfig.getClientConfig().setOpenHour(openHour);
systemConfig.getClientConfig().setCloseHour(closeHour);
systemConfig.getClientConfig().setNeedFilter(needFilter);
systemConfig.getClientConfig().setSendMailBeginHour(beginHour);
systemConfig.getClientConfig().setSendMailEndHour(endHour);
}finally{
writelock.unlock();
}
... ...
... ... @@ -2,6 +2,7 @@ package com.yoho.rfid.service;
import com.yoho.rfid.constant.BackWorkerType;
import com.yoho.rfid.helper.MonitorHelper;
import com.yoho.rfid.model.ClientConfig;
import com.yoho.rfid.model.MonitorFuture;
import com.yoho.rfid.model.SystemConfig;
import com.yoho.rfid.model.TreadNode;
... ... @@ -9,6 +10,7 @@ import com.yoho.rfid.model.req.AppReportReq;
import com.yoho.rfid.model.req.InfoScreenHeartBeatPacket;
import com.yoho.rfid.thread.MonitorThreadFactory;
import com.yoho.rfid.util.DateUtil;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.MapUtils;
import org.apache.commons.lang3.StringUtils;
... ... @@ -19,6 +21,7 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import javax.annotation.PostConstruct;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.*;
... ... @@ -27,7 +30,7 @@ import java.util.concurrent.*;
* Created by chenchao on 2017/10/16.
*/
@Service
public class MonitorService {
public class MonitorService extends AbstractMonitorService{
private Logger logger = LoggerFactory.getLogger(getClass());
//
... ... @@ -41,10 +44,7 @@ public class MonitorService {
BlockingQueue<Runnable> workQueue = new LinkedBlockingQueue<>();
private ExecutorService executorService = new ThreadPoolExecutor(corePoolSize, maximumPoolSize,
0L, TimeUnit.MILLISECONDS, workQueue, monitorThreadFactory);
//崩溃
private static final String CRASH = "crash",
//重启完毕
REBOOTED = "rebooted";
@Autowired
... ... @@ -227,19 +227,20 @@ public class MonitorService {
continue;
}
long lastUpdateDT = req.getUpdateDateTime();
long currentDT = System.currentTimeMillis();
long diff = currentDT - lastUpdateDT;
if(diff > timeout){
logger.warn("AppReportMap find reeboot, req {},currentDT {}, diff {}, timeout {}",
req, currentDT, diff, timeout);
boolean isTimeout = isTimeout(timeout, lastUpdateDT);
if(isTimeout){
logger.warn("AppReportMap find reboot, req {} timeout {}",
req, timeout);
//reboot
//infoScreenService.reboot(req.getIp(), req.getScreenType());
//TODO use queue to split send mail function, use a thread to send mail
mailService.send(buildMailContent4AppCrash(req.getIp(), req.getScreenType()).toString(),false);
boolean cansend = canSend4GlobalScope() && canSend4AppReport();
if(cansend){
mailService.send(buildMailContent4AppCrash(req.getIp(), req.getScreenType()).toString());
needRemove.add(req.getIp());
}
}
}
//remove from map
if(CollectionUtils.isNotEmpty(needRemove)){
needRemove.stream().forEach(ip -> AppReportMap.remove(ip));
... ... @@ -286,19 +287,20 @@ public class MonitorService {
continue;
}
long lastUpdateDT = packet.getUpdateDateTime();
long currentDT = System.currentTimeMillis();
long diff = currentDT - lastUpdateDT;
boolean isTimeout = isTimeout(timeout, lastUpdateDT);
//todo 合并多个,只发送一封邮件
if(diff > timeout){
if(isTimeout){
//reboot
logger.warn("HeartBeatMap find no heartbeat, req {},currentDT {}, diff {}, timeout {}",
packet, currentDT, diff, timeout);
logger.warn("HeartBeatMap find no heartbeat, req {}, timeout {}",
packet, timeout);
//infoScreenService.reboot(req.getIp(), req.getScreenType());
mailService.send(buildMailContent(packet.getIp(), packet.getScreenType()).toString(), false);
boolean cansend = canSend4GlobalScope() && canSend4HeartBeat();
if(cansend){
mailService.send(buildMailContent(packet.getIp(), packet.getScreenType()).toString());
needRemove.add(packet.getIp());
}
}
}
//remove from map
removeAll(needRemove);
//客户端到23点,早上9点还没有关机就邮件报警
... ... @@ -314,34 +316,42 @@ public class MonitorService {
}
private void sendMailIfExistOpenClient(){
int currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
int currentHour;
SystemConfig systemConfig = SystemConfig.getInstance();
boolean isNotClose = (currentHour >= systemConfig.getCloseHour() || currentHour < systemConfig.getOpenHour())
&& MapUtils.isNotEmpty(HeartBeatMap) && !isNoticedOpenClient;
if (isNotClose){
ClientConfig clientConfig = systemConfig.getClientConfig();
//尚未发送通知
if(!isNoticedOpenClient){
currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
boolean hasData = MapUtils.isNotEmpty(HeartBeatMap);
boolean cansend = clientCanSendMail(clientConfig);
boolean isNotClose = (currentHour >= clientConfig.getCloseHour() || currentHour < clientConfig.getOpenHour());
if (isNotClose && hasData && cansend){
isNoticedOpenClient = true;
List<String> ips = new ArrayList<String>(HeartBeatMap.keySet());
mailService.send(buildMailContentOfExistOpenClient(ips).toString(), true);
mailService.send(buildMailContentOfExistOpenClient(ips).toString());
//移除的意义不大,心跳会不间断地上报
this.removeAll(ips);
logger.info("in sendMailIfExistOpenClient, ips {}", ips);
}
}
//已经发送通知后,需要恢复标识
if(isNoticedOpenClient){
currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
//auto wakeup, reset isNoticedOpenClient if it's false
boolean inBussiness = currentHour < systemConfig.getCloseHour()
&& currentHour >= systemConfig.getOpenHour()
&& isNoticedOpenClient;
boolean inBussiness = currentHour < clientConfig.getCloseHour()
&& currentHour >= clientConfig.getOpenHour();
if(inBussiness){
isNoticedOpenClient = false;
logger.info("in sendMailIfExistOpenClient, reset isNoticedOpenClient success");
}
}
}
public long getAliveDatetime(){
return aliveDatetime;
}
}
StringBuilder buildMailContentOfExistOpenClient(List<String> ips){
StringBuilder sb = new StringBuilder();
String ipsStr = StringUtils.join(ips, ",") ;
... ... @@ -350,6 +360,41 @@ public class MonitorService {
}
private boolean canSend4AppReport(){
SystemConfig systemConfig = SystemConfig.getInstance();
//上午10点到晚上22点发送,其他时间不发
int currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
if(currentHour<systemConfig.getSendMailBeginHour() || currentHour >=systemConfig.getSendMailEndHour()){
logger.warn("in canSend4AppReport,it's too late, don't need to send mail, thanks developer sailing");
return false;
}
return true;
}
private boolean canSend4GlobalScope(){
SystemConfig systemConfig = SystemConfig.getInstance();
if(!systemConfig.isSendMail()){//不发送一般发生在测试环境
logger.warn("in canSend4GlobalScope,systemConfig.sendMail is set {},u can use manage/sendMail/open to control", systemConfig.isSendMail());
return false;
}
return true;
}
private boolean canSend4HeartBeat(){
SystemConfig systemConfig = SystemConfig.getInstance();
//上午10点到晚上22点发送,其他时间不发
int currentHour = DateUtil.getPart(new Date(), DateUtil.TimeUnit.hour);
if(currentHour<systemConfig.getSendMailBeginHour() || currentHour >=systemConfig.getSendMailEndHour()){
logger.warn("in canSend4HeartBeat,it's too late, don't need to send mail, thanks developer sailing");
return false;
}
return true;
}
public static void main(String[] args) {
long cnt = 1 << 31 -1 ;
Boolean flag = cnt == Integer.MAX_VALUE;
... ...
... ... @@ -18,7 +18,15 @@
<context:property-placeholder ignore-resource-not-found="true" location="classpath*:config.properties" />
<context:component-scan base-package="com.yoho.rfid" />
<!-- warn email cc accounts -->
<util:list id="ccAccounts" value-type="java.lang.String">
<value>frank.fu@yoho.cn</value>
<value>xiuchun.luo@yoho.cn</value>
<value>rongjun.zhou@yoho.cn</value>
<value>qiqi.zhou@yoho.cn</value>
<value>jon.huang@yoho.cn</value>
<value>chao.chen@yoho.cn</value>
</util:list>
<!-- 启动SpringMVC的注解功能,完成请求和注解POJO的映射 -->
<mvc:annotation-driven>
<mvc:message-converters register-defaults="false">
... ...
... ... @@ -11,3 +11,7 @@ portal.gateway.url=http://instore.yohobuy.com
web.context=rfid
deploy.home=/home/store/rfid
toAccount=ben.li@yoho.cn
#test or dev
#email.toAccount=chao.chen@yoho.cn
\ No newline at end of file
... ...