package com.zzwtec.third.common;

import com.zzwtec.third.utils.StringUtil;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * create by Jomchen on 2018/12/3
 * 此类的逻辑处理是根据  zzw 的 microsoft 项目的 web 模块参考修改的
 */
public class TokenServiceSupport {

    public static final String SSO_TOKEN_ATTR = "SSOTokenAttr";
    public static final String SSO_TOKEN_ID = "SSOTokenID";
    private static final String COOKIE_PATH = "/";
    private static final boolean COOKIE_SECURE = false;
    private static final int COOKIE_MAXAGE = -1;
    public static final String SSO_COOKIE_MAXAGE = "sso_cookie_maxage";

    /**
     * 根据cookieName获取Cookie
     */
    public static Cookie findCookieByName(HttpServletRequest request, String cookieName) {
        Cookie[] cookies = request.getCookies();
        if (cookies == null)
            return null;
        for (int i = 0; i < cookies.length; i++) {
            if (cookies[i].getName().equals(cookieName)) {
                return cookies[i];
            }
        }
        return null;
    }

    /**
     * 获取当前请求 JsonToken
     */
    protected static String getJsonToken( HttpServletRequest request, String cookieName ) {
        Cookie uid = TokenServiceSupport.findCookieByName(request, cookieName);
        String jsonToken = null;
        if(uid != null){
            jsonToken = uid.getValue();
        }
        return jsonToken;
    }

    /**
     * 获取webtokenId
     */
    public static String getWebTokenIdFromCookie(HttpServletRequest request) {
        String tokenId = (String)request.getSession().getAttribute(SSO_TOKEN_ID);
        if(StringUtil.isEmpty(tokenId)) {
            tokenId = getJsonToken(request, WebPrefixAndConstant.UID);
        }
        return tokenId;
    }

    /**
     * 设置tokenId到Cookie
     */
    public static void setWebTokenIdToCookie(HttpServletRequest request, HttpServletResponse response, String tokenId) {
        try {
            request.getSession(true).setAttribute(SSO_TOKEN_ID, tokenId);
            Cookie ck = TokenServiceSupport.generateCookie(request, tokenId);
            TokenServiceSupport.addCookie(response, ck);
        } catch ( Exception e ) {
        }
    }


    /**
     * 生成 cookie
     */
    private static Cookie generateCookie( HttpServletRequest request,String tokenId) {
        try {
            String jt = tokenId;
            Cookie cookie = new Cookie("uid", jt);
            cookie.setPath(COOKIE_PATH);
            cookie.setSecure(COOKIE_SECURE);

             // 有些浏览器 localhost 无法设置 cookie
            String domain = request.getServerName();
            System.out.println("domain:"+domain);
            cookie.setDomain(domain);
            if ( "".equals(domain) || domain.contains("localhost") ) {
            }

            // 设置cookie超时时间
            int maxAge = COOKIE_MAXAGE;
            Integer attrMaxAge = (Integer) request.getAttribute(SSO_COOKIE_MAXAGE);
            if (attrMaxAge != null) {
                maxAge = attrMaxAge;
            }
            if ( maxAge >= 0 ) {
                cookie.setMaxAge(maxAge);
            }
            return cookie;
        } catch ( Exception e ) {
            return null;
        }
    }

    /**
     * 添加 cookie
     * @param response
     * @param cookie
     */
    public static void addCookie(HttpServletResponse response,Cookie cookie){
        int maxAge = cookie.getMaxAge();
        String path = cookie.getPath();
        String domain = cookie.getDomain();
        boolean isSecure = cookie.getSecure();
        boolean httpOnly = cookie.isHttpOnly();

        // 不设置该参数默认 当前所在域
        if (domain != null && !"".equals(domain)) {
            cookie.setDomain(domain);
        }
        cookie.setPath(path);
        cookie.setMaxAge(maxAge);

        // Cookie 只在Https协议下传输设置
        if (isSecure) {
            cookie.setSecure(isSecure);
        }

        // Cookie 只读设置
        if (httpOnly) {
            addHttpOnlyCookie(response, cookie);
        } else {
            response.addCookie(cookie);
        }
    }

    /**
     * 解决 servlet 3.0 以下版本不支持 HttpOnly
     * @param response HttpServletResponse类型的响应
     * @param cookie 要设置httpOnly的cookie对象
     */
    public static void addHttpOnlyCookie(HttpServletResponse response, Cookie cookie) {
        if (cookie == null) { return; }

        // 依次取得cookie中的名称、值、 最大生存时间、路径、域和是否为安全协议信息
        String cookieName = cookie.getName();
        String cookieValue = cookie.getValue();
        int maxAge = cookie.getMaxAge();
        String path = cookie.getPath();
        String domain = cookie.getDomain();
        boolean isSecure = cookie.getSecure();
        StringBuffer sf = new StringBuffer();
        sf.append(cookieName + "=" + cookieValue + ";");

        if (maxAge >= 0) {
            sf.append("Max-Age=" + cookie.getMaxAge() + ";");
        }

        if (domain != null) {
            sf.append("domain=" + domain + ";");
        }

        if (path != null) {
            sf.append("path=" + path + ";");
        }

        if (isSecure) {
            sf.append("secure;HTTPOnly;");
        } else {
            sf.append("HTTPOnly;");
        }
        response.addHeader("Set-Cookie", sf.toString());
    }

}
