package com.uas.platform.b2b.model;

import com.alibaba.fastjson.annotation.JSONField;
import com.uas.platform.b2b.support.SystemSession;
import com.uas.platform.core.model.Constant;
import org.codehaus.jackson.annotate.JsonIgnore;
import org.hibernate.annotations.Cache;
import org.hibernate.annotations.CacheConcurrencyStrategy;
import org.hibernate.annotations.NotFound;
import org.hibernate.annotations.NotFoundAction;
import org.springframework.util.CollectionUtils;

import javax.persistence.*;

import com.uas.sso.entity.UserView;
import org.springframework.util.StringUtils;
import java.io.Serializable;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;

@Entity
@Table(name = "sec$users")
@Cacheable
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE, region = "com.uas.platform.b2b.model.User")
public class User implements Serializable {

	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;

	@Id
	@Column(name = "user_uu")
	private Long userUU;

	@Column(name = "user_name", length = 50)
	private String userName;

	@Column(name = "user_pwd", length = 32)
	private String userPwd;

	@Column(name = "user_email", length = 50)
	private String userEmail;

	@Column(name = "user_tel", length = 30)
	private String userTel;

	@Column(name = "user_sex", length = 10)
	private String userSex;

	@Column(name = "user_idcode", length = 20)
	private String userIdcode;

	private Short enable;

	private Short issys;

	@Column(name = "user_imid")
	private Long userIMId;

	public Long getUserIMId() {
		return userIMId;
	}

	public void setUserIMId(Long userIMId) {
		this.userIMId = userIMId;
	}

	/**
	 * 用户类型
	 */
	@Column(name = "user_type", length = 20)
	private String userType;

	/**
	 * 所属公司
	 */
	@ManyToMany(cascade = { CascadeType.REFRESH, CascadeType.REMOVE }, fetch = FetchType.EAGER)
	@JoinTable(name = "sec$userenterprise", joinColumns = @JoinColumn(name = "user_uu", referencedColumnName = "user_uu"), inverseJoinColumns = @JoinColumn(name = "en_uu", referencedColumnName = "en_uu"))
	@OrderBy("uu")
	@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
	private Set<Enterprise> enterprises;

	/**
	 * 所属公司
	 */
	@Transient
	@NotFound(action = NotFoundAction.IGNORE)
	private Enterprise enterprise;

	/**
	 * 角色
	 */
	@ManyToMany(cascade = { CascadeType.PERSIST, CascadeType.MERGE }, fetch = FetchType.EAGER)
	@JoinTable(name = "sec$userrole", joinColumns = @JoinColumn(name = "user_uu", referencedColumnName = "user_uu"), inverseJoinColumns = @JoinColumn(name = "role_id", referencedColumnName = "role_id"))
	@OrderBy("id")
	@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
	private Set<Role> roles;

	/**
	 * 最近登录IP地址
	 */
	@Transient
	@NotFound(action = NotFoundAction.IGNORE)
	private String ip;

	/**
	 * 判断是否被分配
	 */
	@Transient
	private boolean distribute;

	/**
	 * 判断是否被转移权限
	 */
	@Transient
	private boolean transfer;

	public Long getUserUU() {
		return userUU;
	}

	public void setUserUU(Long userUU) {
		this.userUU = userUU;
	}

	public String getUserEmail() {
		return userEmail;
	}

	public void setUserEmail(String userEmail) {
		this.userEmail = userEmail;
	}

	public String getUserTel() {
		return userTel;
	}

	public void setUserTel(String userTel) {
		this.userTel = userTel;
	}

	public String getUserIdcode() {
		return userIdcode;
	}

	public void setUserIccode(String userIdcode) {
		this.userIdcode = userIdcode;
	}

	public String getUserName() {
		return userName;
	}

	public void setUserName(String userName) {
		this.userName = userName;
	}

	@JsonIgnore
	@JSONField(serialize = false)
	public String getUserPwd() {
		return userPwd;
	}

	public void setUserPwd(String userPwd) {
		this.userPwd = userPwd;
	}

	public Short getEnable() {
		return enable;
	}

	public void setEnable(Short enable) {
		this.enable = enable;
	}

	@JsonIgnore
	@JSONField(serialize = false)
	public Short getIssys() {
		return issys;
	}

	public void setIssys(Short issys) {
		this.issys = issys;
	}

	public String getUserSex() {
		return userSex;
	}

	public void setUserSex(String userSex) {
		this.userSex = userSex;
	}

	public Enterprise getEnterprise() {
		return enterprise;
	}

	public void setEnterprise(Enterprise enterprise) {
		this.enterprise = enterprise;
	}

	public String getUserType() {
		return userType;
	}

	public void setUserType(String userType) {
		this.userType = userType;
	}

	public void setUserIdcode(String userIdcode) {
		this.userIdcode = userIdcode;
	}

	@JsonIgnore
	@JSONField(serialize = false)
	public Set<Enterprise> getEnterprises() {
		return enterprises;
	}

	public void setEnterprises(Set<Enterprise> enterprises) {
		this.enterprises = enterprises;
	}

	@JsonIgnore
	@JSONField(serialize = false)
	public boolean enable() {
		return this.getEnable() != null && this.getEnable() == Constant.YES;
	}

	public void setCurrentEnterprise() {
		if (this.enterprises != null && this.enterprises.size() > 0) {
            this.enterprise = this.enterprises.iterator().next();
        }
	}

	public void setCurrentEnterprise(long enUU) {
		if (this.enterprises != null && this.enterprises.size() > 0) {
            for (Enterprise enterprise : enterprises) {
                if (enterprise.getUu() == enUU) {
                    this.enterprise = enterprise;
                    break;
                }
            }
        }
		if (this.enterprise == null) {
            setCurrentEnterprise();
        }
	}

	public void setCurrentEnterprise(Enterprise enterprise) {
		if (!CollectionUtils.isEmpty(SystemSession.getUser().getEnterprises())) {
			Set<Enterprise> enterprises = new HashSet<Enterprise>();
			for (Enterprise en : SystemSession.getUser().getEnterprises()) {
				if (en.equals(enterprise)) {
					enterprises.add(enterprise);
				}
				enterprises.add(en);
			}
			SystemSession.getUser().setEnterprises(enterprises);
			SystemSession.getUser().setCurrentEnterprise(SystemSession.getUser().getEnterprise().getUu());
		}
	}

	public Set<Role> getRoles() {
		return roles;
	}

	public void setRoles(Set<Role> roles) {
		this.roles = roles;
	}

	public void addEnterprise(Enterprise enterprise) {
		if (this.enterprises == null) {
			Set<Enterprise> enterprises = new HashSet<Enterprise>();
			enterprises.add(enterprise);
			this.enterprises = enterprises;
			return;
		}
		if (!this.enterprises.contains(enterprise)) {
			this.enterprises.add(enterprise);
		}
	}

	public void removeEnterprise(Enterprise enterprise) {
		if (this.enterprises.contains(enterprise)) {
			this.enterprises.remove(enterprise);
		}
	}

	public boolean isSys() {
		return getIssys() != null && getIssys() == Constant.YES;
	}

	@JsonIgnore
	@JSONField(serialize = false)
	public String getIp() {
		return ip;
	}

	public void setIp(String ip) {
		this.ip = ip;
	}

	public boolean getDistribute() {
		return distribute;
	}

	public void setDistribute(boolean distribute) {
		this.distribute = distribute;
	}

	public boolean getTransfer() {
		return transfer;
	}

	public void setTransfer(boolean transfer) {
		this.transfer = transfer;
	}

	public User(UserView userView) {
		this.setUserUU(userView.getUserUU());
		this.setUserName(userView.getVipName());
		this.setUserTel(userView.getMobile());
		this.setUserEmail(userView.getEmail());
		this.setUserPwd(userView.getPassword());
		this.setUserIMId(StringUtils.isEmpty(userView.getImId()) ? null : Long.valueOf(userView.getImId()));
		this.setUserSex(userView.getSex());
	}

	public User(Long userUU) {
		this.userUU = userUU;
	}

	public User() {
	}

	/**
	 * 获取用户所属企业UU号
	 * 
	 * @return
	 */
	@JSONField(serialize = false)
	@JsonIgnore
	public Set<Long> getEnUUs() {
		Set<Long> enUUs = new HashSet<Long>();
		if (!CollectionUtils.isEmpty(enterprises)) {
			for (Enterprise en : enterprises) {
				enUUs.add(en.getUu());
			}
		}
		return enUUs;
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result + ((userEmail == null) ? 0 : userEmail.hashCode());
		result = prime * result + ((userTel == null) ? 0 : userTel.hashCode());
		result = prime * result + ((userUU == null) ? 0 : userUU.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj) {
            return true;
        }
		if (obj == null) {
            return false;
        }
		if (getClass() != obj.getClass()) {
            return false;
        }
		User other = (User) obj;
		if (userEmail == null) {
			if (other.userEmail != null) {
                return false;
            }
		} else if (!userEmail.equals(other.userEmail)) {
            return false;
        }
		if (userTel == null) {
			if (other.userTel != null) {
                return false;
            }
		} else if (!userTel.equals(other.userTel)) {
            return false;
        }
		if (userUU == null) {
			if (other.userUU != null) {
                return false;
            }
		} else if (!userUU.equals(other.userUU)) {
            return false;
        }
		return true;
	}

	/**
	 * 设置当前登录企业的角色
	 */
	public void setCurrentEnterpriseRoles() {
		if(!CollectionUtils.isEmpty(this.roles) && this.enterprise != null) {
			Iterator<Role> iterator = this.roles.iterator();
			Long enuu = this.enterprise.getUu();
			while (iterator.hasNext()) {
				Role role = iterator.next();
				if(!role.getEnUU().equals(enuu)) {
					iterator.remove();
				}
			}
		}
	}

}
