package com.iamberry.app.service;

import static com.iamberry.app.config.ImberryConfig.INTER_SMS_KEY;
import static com.iamberry.app.config.ImberryConfig.SMS_PASSWORD;
import static com.iamberry.app.config.ImberryConfig.SMS_TEXT;
import static com.iamberry.app.config.ImberryConfig.SMS_URL;
import static com.iamberry.app.config.ImberryConfig.SMS_USERNAME;
import static com.iamberry.app.config.ImberryConfig.INTER_SMS_KEY;
import static com.iamberry.app.config.ImberryConfig.INTER_SMS_TEXT;
import static com.iamberry.app.config.ImberryConfig.INTER_SMS_URL;







import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.iamberry.app.config.Response;
import net.sf.json.JSONObject;

import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpEntity;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.iamberry.app.core.entity.CodeValid;
import com.iamberry.app.face.CodeService;
import com.iamberry.app.mapper.CodeMapper;
import com.iamberry.app.tool.util.Result;
import com.iamberry.app.ulitity.Utility;
import com.iamberry.wechat.tools.ResponseJson;
import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.StaxDriver;

/**
 * @company	深圳爱贝源科技有限公司
 * @website www.iamberry.com
 * @author 	献
 * @tel		18271840547
 * @date	2016年11月1日
 * @explain	验证码业务实现类
 */
@SuppressWarnings("unused")
@Service
public class CodeServiceImpl implements CodeService {

	@Autowired
	private CodeMapper codeMapper;
	
	private static String ENCODING = "UTF-8";

	@Override
	public ResponseJson sendCode(String phone, int codeScenario) {
		// TODO Auto-generated method stub
		// 第一步,判断使用通道，如果是+86开头，优先使用国内通道,否则默认使用国外通道
		ResponseJson json = new ResponseJson();
		if (StringUtils.isEmpty(phone)) {
			json.setReturnCode(404);
			json.addResponseKeyValue("Phone Empty!");
			return json;
		}
	
		String phones = StringUtils.substringAfter(phone, ","); //截取
		// 第二步,如果是国内，判断是否存在
		CodeValid codeValid = codeMapper.getLast(phones);
		
		// 通道是否是中国的
		boolean IS_CHANNEL_ZH = false;
		if (StringUtils.startsWith(phone, "86,")) {
				IS_CHANNEL_ZH = true;
		} else {
			IS_CHANNEL_ZH = false;
		}
		// 判断通道
		Date now = new Date();
		if (IS_CHANNEL_ZH && codeValid != null) {
			// ** 切换通道需求：每次请求验证码，如果上一次验证码在一分钟以后，三分钟以内没有使用，那么切换通道 **//
			if (now.getTime() <= (codeValid.getCodeValidDate().getTime()) && 
					(now.getTime() - 60000) >= codeValid.getCodeSendDate().getTime() && codeValid.getCodeUse() == 2 && codeValid.getCodeScenario() == codeScenario) {
				// 如果等待三分钟后，那么切换通道
				IS_CHANNEL_ZH = false;
			}
		}
		// 获取验证码
		String code = Utility.getRandomCode(4);
		json = sendCMS(phone, code, IS_CHANNEL_ZH ? 1 : 2);
		if (json.getReturnCode() != 200) {
			json = sendCMS(phone, code, IS_CHANNEL_ZH ? 1 : 2);
		}
		// 保存发送记录
		codeValid = new CodeValid();
		codeValid.setCodeChannel(IS_CHANNEL_ZH ? 1 : 2);
		codeValid.setCodeMsg(json.getReturnMsg().get("returnMsg").toString());
		codeValid.setCodePhone(phones);
		codeValid.setCodeScenario(codeScenario);
		codeValid.setCodeSendDate(now);
		codeValid.setCodeValidDate(new Date(now.getTime() + 180000));
		codeValid.setCodeStatus(json.getReturnCode() == 200 ? 3 : 4);
		codeValid.setCodeUse(2);
		codeValid.setCodeValue(Integer.parseInt(code));
		codeMapper.save(codeValid);
		return json;
	}
	
	/**
	 * @param phone		手机号码
	 * @param code		短信验证码
	 * @param channel	通道 1：主通道；2：备用通道(国外的电话通通使用此)
	 * @return
	 */
	private ResponseJson sendCMS(String phone, String code, int channel) {
		
		// 国内号码
		ResponseJson json = new ResponseJson();
		json.setReturnCode(500);
		String result = null;
		try {
			if (channel == 1) {
				phone = StringUtils.substringAfter(phone, ","); //截取

				// 使用主通道
				result = sendZHCMS(phone, code);
			} else {
				phone = StringUtils.replace(phone,",",""); //替换
				// 使用备用通道
				result = sendOtherCMS(phone, code);
			}
		} catch (Exception e) {
			result = e.getMessage();
		}
		if (StringUtils.equals(result, "SUCCESS")) {
			json.setReturnCode(200);
		}
		json.addResponseKeyValue(result);
		return json;
	}
	
	private String sendOtherCMS(String phone, String code) {
		String text = MessageFormat.format(INTER_SMS_TEXT, code);
		String results = sendSms(text, "+"+phone);
        JSONObject json =  JSONObject.fromObject(results);
        String resultcod  = json.get("code").toString();
        if(resultcod.equals("0")){
        	System.out.println("使用备用通道，发送验证码成功!" + code);
        	return "SUCCESS";
        }else{
        	System.out.println("使用备用通道，发送失败...!" + code);
        	return results;
        }
		
	}
	
	public static String sendSms(String text, String mobile)  {
        Map<String, String> params = new HashMap<String, String>();
        params.put("apikey", INTER_SMS_KEY);
        params.put("text", text);
        params.put("mobile", mobile);
        return post(INTER_SMS_URL, params);
    }
    /** 基于HttpClient 4.3的通用POST方法
    * @param url       提交的URL
    * @param paramsMap 提交<参数，值>Map
    * @return 提交响应
    */

    public static String post(String url, Map<String, String> paramsMap) {
    	
        CloseableHttpClient client = HttpClients.createDefault();
        String responseText = "";
        CloseableHttpResponse response = null;
            try {
                HttpPost method = new HttpPost(url);
                if (paramsMap != null) {
                    List<NameValuePair> paramList = new ArrayList<NameValuePair>();
                    for (Map.Entry<String, String> param : paramsMap.entrySet()) {
                        NameValuePair pair = new BasicNameValuePair(param.getKey(), param.getValue());
                        paramList.add(pair);
                    }
                    method.setEntity(new UrlEncodedFormEntity(paramList, ENCODING));
                }
                response = client.execute(method);
                HttpEntity entity = response.getEntity();
                if (entity != null) {
                    responseText = EntityUtils.toString(entity);
                }
                
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                try {
                    response.close();
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
            return responseText;
        }
	
	
	private String sendZHCMS(String phone, String code) throws Exception {

		CloseableHttpClient client = HttpClients.createDefault();
		Map<String, String> params = new HashMap<String, String>();
		CloseableHttpResponse response = null;
		params.put("username", SMS_USERNAME);
		params.put("password", SMS_PASSWORD);
		params.put("mobile", phone);
		params.put("content", MessageFormat.format(SMS_TEXT, code));
		HttpPost method = new HttpPost(SMS_URL);
		if (params != null) {
			List<NameValuePair> paramList = new ArrayList<NameValuePair>();
			for (Map.Entry<String, String> param : params.entrySet()) {
				NameValuePair pair = new BasicNameValuePair(param.getKey(), param.getValue());
				paramList.add(pair);
			}
			method.setEntity(new UrlEncodedFormEntity(paramList, "UTF-8"));
		}
		response = client.execute(method);
		HttpEntity entity = response.getEntity();
		if (entity != null) {
			String result = EntityUtils.toString(entity);
			XStream xs = new XStream(new StaxDriver());
			xs.alias("result", Result.class);
			Result object = (Result)xs.fromXML(result);
			response.close();
			if (0 == object.getResultcode()) {
				return "SUCCESS";
			} else {
				return object.getResultcode() + ":" + object.getErrordescription();
			}
		}
		return null;
	}

	@Override
	public ResponseJson validCode(String phone, String code, int codeScenario) {
		ResponseJson json = new ResponseJson();
		// 校验
		CodeValid codeValid = codeMapper.getLast(phone);
		if (codeValid == null) {
			// 操作有误
			json.setReturnCode(404);
			json.addResponseKeyValue("Wrong operation");
			return json;
		}
		Date now = new Date();
		if (now.getTime() >= codeValid.getCodeValidDate().getTime()) {
			// 验证码无效
			json.setReturnCode(404);
			json.addResponseKeyValue("Verification code is invalid");
			return json;
		}
		// 必须 验证码正确，并且场景正确
		if (!(codeValid.getCodeValue() == (Integer.parseInt(code)) 
				&& codeScenario == codeValid.getCodeScenario())) {
			// 验证码错误
			json.setReturnCode(404);
			json.addResponseKeyValue("Verification code error");
			return json;
		}
		// 只要校验，表示本次验证码使用
		codeMapper.update(codeValid.getCodeId());
		json.setReturnCode(200);
		json.addResponseKeyValue("SUCCESS");
		return json;
	}
<<<<<<< .mine

	@Override
	public Response interval(String phone) {
		return null;
	}


||||||| .r5272
	
	
	
	
	
	
=======


>>>>>>> .r5562
}
