package com.yihu.hos.broker.common.scheduler;

import com.mongodb.*;
import com.yihu.hos.broker.common.constants.MonitorConstant;
import com.yihu.hos.broker.daos.BrokerDao;
import com.yihu.hos.broker.models.SystemServiceEndpoint;
import com.yihu.hos.broker.models.SystemServiceFlow;
import com.yihu.hos.broker.services.ServiceMonitorService;
import com.yihu.hos.broker.util.SigarUtil;
import com.yihu.hos.core.datatype.DateUtil;
import com.yihu.hos.core.log.Logger;
import com.yihu.hos.core.log.LoggerFactory;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import org.bson.Document;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.mongodb.core.MongoOperations;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * 服务器性能数据采集定时器
 *
 * @author HZY
 * @vsrsion 1.0
 * Created at 2016/10/11.
 */
@Component
public class MonitorScheduler {

    static private final Logger logger = LoggerFactory.getLogger(MonitorScheduler.class);
    private static String host = SigarUtil.getHost();
    @Value("${hos.tenant.name}")
    private String tenant;
    @Autowired
    private MongoOperations mongoOperations;
    @Autowired
    private Mongo mongo;
    @Resource(name = ServiceMonitorService.BEAN_ID)
    private ServiceMonitorService serviceMonitorService;
    @Autowired
    private BrokerDao brokerDao;

    @Scheduled(cron = "0 0/1 * * * ?") //每分钟执行一次
    public void statusCheck() {
        System.out.println("每分钟执行一次。开始============================================");
        //TODO 采集服务器健康监控指标数据 statusTask.healthCheck();
        collectEnvHealth();
        try {
            collectServiceHealth();
        } catch (Exception e) {
            e.printStackTrace();
        }
        System.out.println("每分钟执行一次。结束。");
    }

    /**
     * 服务器健康指标采集
     *
     * @return
     */
    public String collectEnvHealth() {
        try {
            mongoOperations = new MongoTemplate(mongo, MonitorConstant.MONITOR_DATABASE);
            Document result = null;
            result = new Document();
            result.put("tenant", tenant);
            result.put("create_date", DateUtil.getCurrentString(DateUtil.DEFAULT_YMDHMSDATE_FORMAT));
            result.put("create_time", new Date());
            result.put("host", host);

            //cpu
            JSONObject cpu = JSONObject.fromObject(SigarUtil.cpu());
            result.put("data", cpu);
            result.put("type", MonitorConstant.CPU);
            mongoOperations.insert(result, MonitorConstant.SERVER);


            //内存
            JSONObject memory = JSONObject.fromObject(SigarUtil.memory());
            result.put("data", memory);
            result.put("type", MonitorConstant.MEMORY);
            result.remove("_id");
            mongoOperations.insert(result, MonitorConstant.SERVER);
            //硬盘
            List<JSONObject> files = JSONArray.fromObject(SigarUtil.file());
            result.put("data", files);
            result.put("type", MonitorConstant.FILES);
            result.remove("_id");
            mongoOperations.insert(result, MonitorConstant.SERVER);

            //网络
            JSONObject net = JSONObject.fromObject(SigarUtil.net());
            result.put("data", net);
            result.put("type", MonitorConstant.NET);
            result.remove("_id");
            mongoOperations.insert(result, MonitorConstant.SERVER);

        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";
    }

    public void collectServiceHealth() throws Exception {
        Date now = new Date();
        Date beforeDate = new Date(now.getTime() - 60000);
        String beginTime = DateUtil.toString(beforeDate, DateUtil.DEFAULT_YMDHMSDATE_FORMAT);
        String endTime = DateUtil.toString(now, DateUtil.DEFAULT_YMDHMSDATE_FORMAT);
        List<SystemServiceFlow> flowList = brokerDao.getSystemServiceFlowList();
        List<SystemServiceEndpoint> endpointList = brokerDao.getSystemServiceEndpointList();
        List<String> codeList = new ArrayList<>();
        for (SystemServiceFlow systemServiceFlow : flowList) {
            codeList.add(systemServiceFlow.getCode());
        }

        for (SystemServiceEndpoint systemServiceEndpoint : endpointList) {
            codeList.add(systemServiceEndpoint.getCode());
        }

        serviceMonitorService.bandwidth(beginTime, endTime, codeList);
        serviceMonitorService.qps(beginTime, endTime, codeList);
        serviceMonitorService.delay(beginTime, endTime, codeList);
        serviceMonitorService.usage(beginTime, endTime, codeList);
    }

    /**
     * 服务器列表保存
     */
//    @Scheduled(cron = "0 0 12 * * ?") //每天中午12点触发
    @Scheduled(fixedDelay = 3600 * 24 * 1000, initialDelay = 3000) //每天中午12点触发
    public void checkHost() {
        mongoOperations = new MongoTemplate(mongo, MonitorConstant.MONITOR_DATABASE);
        DBCollection envCollection = mongoOperations.getCollection(MonitorConstant.HOST);
        BasicDBObject queryObject = new BasicDBObject().append(QueryOperators.AND,
                new BasicDBObject[]{
                        new BasicDBObject().append("host", host),
                        new BasicDBObject().append("tenant", tenant)});

        DBCursor cursor = envCollection.find(queryObject);
        if (cursor.size() < 1) {
            try {
                Document result = new Document();
                String host = SigarUtil.getHost();
                String hostName = SigarUtil.getHostName();
                result.put("tenant", tenant);
                result.put("name", hostName);
                result.put("host", host);
                mongoOperations.insert(result, MonitorConstant.HOST);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }

    }

}
