/**
 * Copyright 2008-2009. Chongqing Communications Industry Services Co.,Ltd Information Technology Branch. All rights reserved. <a>http://www.cqcis.com</a>
 */
package com.crunii.micro.service.sysmgr.jdbc;

import cn.hutool.core.util.ObjectUtil;
import com.crunii.micro.common.constants.CommonConstants;
import com.crunii.micro.common.dto.PageReq;
import com.crunii.micro.common.dto.PageRsp;
import com.crunii.micro.common.utils.SqlUtil;
import com.crunii.micro.common.utils.StreamUtils;
import com.crunii.micro.domain.common.jdbc.BaseJdbcTemplate;
import com.crunii.micro.domain.common.jdbc.BaseNPJdbcTemplate;
import com.crunii.micro.domain.dto.TsmRoleDto;
import com.crunii.micro.domain.dto.Worker;
import com.crunii.micro.domain.entity.main.TsmLoginLog;
import com.crunii.micro.domain.entity.main.TsmWorker;
import com.crunii.micro.domain.util.CurrWorkerUtil;
import com.crunii.micro.service.sysmgr.constants.SysmgrConstants;
import com.crunii.micro.service.sysmgr.dto.sysmgr.*;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.stereotype.Repository;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @author 田平 create 2017年8月11日下午12:44:04
 */
@Repository
public class WorkerJdbcDao {

	@Resource(name = "mainJT")
	protected BaseJdbcTemplate JT;

	@Resource(name = "mainNPJT")
	protected BaseNPJdbcTemplate NPJT;

	private static final String pageWorkerBaseSql = "select a.*,d.org_name,d.org_code," +
			" (case a.whether_temporary when 1 then '临时用户' when 0 then '正常用户' else null end) as whetherTemporaryName," +
			" (case a.worker_type when 1 then 'APP端用户' when 2 then '后台管理员' else null end) as workerTypeName," +
			" a.timeout " +
			" from tsm_worker a " +
			" left join (select b.worker_id,min(a.sort) as sort from tsm_post a,tsm_post_worker b where b.post_id = a.id group by b.worker_id) b on a.login_id=b.worker_id " +
			" left join ycq_league c on a.org_id=c.league_id " +
			" left join tsm_org d on a.org_id=cast(d.org_id as varchar)" +
			"  WHERE a.login_id not in ";

	private static final String pageWorkerCountSql = "select count(*) from tsm_worker a where a.login_id not in ";

	public PageRsp<WorkerInfo> pageWorker(PageReq<WorkerReq> req) {
		Worker worker = CurrWorkerUtil.getCurrWorker();
		StringBuilder sb = new StringBuilder(pageWorkerBaseSql).append(CommonConstants.SUPER_LOGIN_IDS_SQL);
		StringBuilder sbCount = new StringBuilder(pageWorkerCountSql).append(CommonConstants.SUPER_LOGIN_IDS_SQL);
		List<Object> params = new ArrayList<>();

		//数据权限
		if (worker!=null && !CommonConstants.SUPER_LOGIN_IDS.contains(worker.getLoginId())){
			// 2024-01-18更改:超级管理员的角色可以查看所有的用户
			List<TsmRoleDto> userRoles = worker.getRoles();
			List<Integer> userRoleIds = StreamUtils.toList(userRoles, TsmRoleDto::getRoleId);
			if (!userRoleIds.contains(SysmgrConstants.SUPER_ADMIN_ROLE_ID)) {
				String jurisdictionSql=" and a.org_id in (select cast(org_id as varchar) from tsm_worker_org_all where worker_id=?)";
				sb.append(jurisdictionSql);
				sbCount.append(jurisdictionSql);
				params.add(worker.getLoginId());
			}
		}
		if(StringUtils.hasText(req.getQuery().getMobile())){
			sb.append(" and a.mobile like concat('%',?,'%') ");
			sbCount.append(" and a.mobile like concat('%',?,'%') ");
			params.add(req.getQuery().getMobile());
		}
		if (Objects.nonNull(req.getQuery().getState())) {
			sb.append(" and a.state=? ");
			sbCount.append(" and a.state=? ");
			params.add(req.getQuery().getState());
		}
		if (StringUtils.hasText(req.getQuery().getOrgId())) {
			sb.append(" and a.org_id=? ");
			sbCount.append(" and a.org_id=? ");
			params.add(req.getQuery().getOrgId());
		}
		if (StringUtils.hasText(req.getQuery().getLoginCode())) {
			sb.append(" and a.login_code=? ");
			sbCount.append(" and a.login_code=? ");
			params.add(req.getQuery().getLoginCode());
		}
		if (StringUtils.hasText(req.getQuery().getWorkerName())) {
			sb.append(" and a.worker_name like concat('%',?,'%') ");
			sbCount.append(" and a.worker_name like concat('%',?,'%') ");
			params.add(req.getQuery().getWorkerName());
		}
		if (req.getQuery().getWorkerType()!=null) {
			sb.append(" and a.worker_type  =? ");
			sbCount.append(" and a.worker_type =? ");
			params.add(req.getQuery().getWorkerType());
		}
		//sb.append(" order by case when b.sort is null then 100000 else b.sort end,a.create_time desc");
		int total = JT.queryForInt(sbCount.toString(), params.toArray());
		List<WorkerInfo> workers = null;
		String dbType = JT.getDbType();
		if (total > 0) {
			//根据数据库类型设置limit
			SqlUtil.appendLimit(dbType, params, sb, req);
			workers = JT.queryForBeans(WorkerInfo.class, sb.toString(), params.toArray());
		} else {
			workers = new ArrayList<>(0);
		}
		PageRsp<WorkerInfo> page = new PageRsp<WorkerInfo>();
		page.setPageNo(req.getPageNo());
		page.setPageSize(req.getPageSize());
		page.setTotalNum(total);
		page.setResult(workers);
		// 为手机计算是否由下一页
		page.next();

		return page;
	}

	public Integer queryWorkerCount(String mobile){
		String sql = "select count(1) from TSM_WORKER where mobile = ? ";
		return JT.queryForRawObject(Integer.class,sql,mobile);
	}

	private static final String getTsmWorkersSql = "select * from tsm_worker where login_id in ";

	public List<WorkerInfo> getTsmWorkers(List<Integer> ids) {
		if (CollectionUtils.isEmpty(ids)) {
			return Collections.emptyList();
		} else {
			String inSql = ids.stream().map(id -> id.toString()).collect(Collectors.joining(",", "(", ")"));
			String sql = getTsmWorkersSql + inSql;
			return JT.queryForBeans(WorkerInfo.class, sql);
		}
	}

	public void delRoleByLoginId(int loginId) {
		String sql = "DELETE FROM TSM_WORKER_ROLE WHERE login_id = ? AND role_id <> 9999";
		JT.update(sql,loginId);
	}

	public List<MemberPhoneVo> getMemberPhone(List<String> collect) {
		String sql = "SELECT phone_number,league_name FROM YCQ_MEMBER WHERE phone_number in(:ids)";
		Map<String, Object> map = new HashMap<>(2);
		map.put("ids", collect);
		return NPJT.queryForBeans(MemberPhoneVo.class,sql,map);
	}

	public PageRsp<PageWorkerVo> pageOrgWorker(PageReq<PageOrgWorkerDto> req, String workerId) {
		StringBuilder sb = new StringBuilder("SELECT a.login_id,a.worker_name,yl.league_name orgName FROM TSM_WORKER a left join YCQ_LEAGUE yl on a.org_id = yl.league_id inner join tsm_worker_org_all twoa on a.org_id=twoa.org_id where twoa.worker_id= ?");
		StringBuilder sbCount = new StringBuilder("SELECT count(1) FROM TSM_WORKER a left join YCQ_LEAGUE yl on a.org_id = yl.league_id inner join tsm_worker_org_all twoa on a.org_id=twoa.org_id where twoa.worker_id= ?");
		List<Object> params = new ArrayList<>();
		params.add(workerId);
		if(StringUtils.hasText(req.getQuery().getWorkerName())){
			sb.append(" and a.worker_name like concat('%',?,'%') ");
			sbCount.append(" and a.worker_name like concat('%',?,'%') ");
			params.add(req.getQuery().getWorkerName());
		}
		int total = JT.queryForInt(sbCount.toString(), params.toArray());
		List<PageWorkerVo> workers;
		String dbType = JT.getDbType();
		if (total > 0) {
			//根据数据库类型设置limit
			SqlUtil.appendLimit(dbType, params, sb, req);
			workers = JT.queryForBeans(PageWorkerVo.class, sb.toString(), params.toArray());
		} else {
			workers = new ArrayList<>(0);
		}
		PageRsp<PageWorkerVo> page = new PageRsp<>();
		page.setPageNo(req.getPageNo());
		page.setPageSize(req.getPageSize());
		page.setTotalNum(total);
		page.setResult(workers);
		// 为手机计算是否由下一页
		page.next();

		return page;
	}

	public List<String> findSubordinateLeagueCodes(String leagueCode) {
		String sql = "SELECT league_code FROM YCQ_LEAGUE START WITH league_code=? CONNECT BY PRIOR  league_code=parent_league_code;";
		return JT.queryForRawObjects(String.class,sql,leagueCode);
	}
	public List<WorkerListRspDto> findWorkerByRestricted(WorkerManageReq req) {
		Worker worker = CurrWorkerUtil.getCurrWorker();
		List<Object> parms=new ArrayList<>();
		String sql = "select * from tsm_worker a,tsm_worker_org_all b where a.org_id=b.org_id and b.worker_id =?";
		parms.add(worker.getLoginId());
		if (ObjectUtil.isNotEmpty(req) && req.getOrgCode()!=null){
			sql+=" and b.org_code=?";
			parms.add(req.getOrgCode());
		}
		return JT.queryForBeans(WorkerListRspDto.class,sql,parms.toArray());
	}

	/**
	 * 查询用户关联的职务
	 * @return
	 */
	public List<WorkerPostVO> findPostByWorker(int workerId) {

		List<Object> parms=new ArrayList<>();
		String sql = " select b.id,b.code,b.name from tsm_post_worker a " +
				" left join tsm_post b on a.post_id=b.id" +
				" where a.worker_id=?";
		parms.add(workerId);
		return JT.queryForBeans(WorkerPostVO.class,sql,parms.toArray());
	}

	/**
	 * 查询用户关联的挂职组织
	 * @return
	 */
	public List<WorkerOrgVO> findPostByTemporaryWorker(int workerId) {

		List<Object> parms=new ArrayList<>();
		String sql = " select b.org_id as id,b.org_code,b.org_name from tsm_worker_org_temporary a " +
				" left join tsm_org b on a.org_id=b.org_id" +
				" where a.login_id=?";
		parms.add(workerId);
		return JT.queryForBeans(WorkerOrgVO.class,sql,parms.toArray());
	}


	public List<WorkerRoleInfo> listRoleInfo(List<Integer> loginIds){
		String sql = "select TW.LOGIN_ID ,LISTAGG(tr.role_name, ',') roleNames from TSM_WORKER  TW LEft join tsm_worker_role twr on tw.login_id  = twr.login_id left join tsm_role tr on twr.role_id = tr.role_id ";
		String collect = loginIds.stream().map(item -> item + "").collect(Collectors.joining(","));
		sql += "where TW.login_id in(" + collect + ") group by TW.login_id";
		return JT.queryForBeans(WorkerRoleInfo.class,sql);
	}

	public TsmWorker findExternalWorker(TsmLoginLog tsmLoginLog) {
		String threePhone = tsmLoginLog.getMobile().substring(0, 3);
		String fourPhone = tsmLoginLog.getMobile().substring(tsmLoginLog.getMobile().length() - 4);
		String sql = " select * from tsm_worker where mobile like '"+threePhone+"%"+fourPhone+"' ";
		return JT.queryForBean(TsmWorker.class,sql);
	}

	public List<LabelResp> getLabelNames(int loginId) {
		String sql = "select b.id as labelId, SPECIALTIES_SPECIALTY_NAME as labelName from TSM_WORKER_LABEL a, YCQ_SNG_STATIC b where a.label_id = b.id and a.login_id = " + loginId;
		return JT.queryForBeans(LabelResp.class, sql);
	}

	public void workerAddLabel(int loginId, List<Long> labelIds){
		if (!CollectionUtils.isEmpty(labelIds)){
			for (Long id : labelIds) {
				String sql = "insert into TSM_WORKER_LABEL (login_id,label_id) values (?,?)";
				JT.update(sql, loginId, id);
			}
		}
	}

	public void workerUpdateLabel(int loginId, List<Long> labelIds){
		String deleteSql = "delete from TSM_WORKER_LABEL where login_id = " + loginId;
		JT.update(deleteSql);
		if (!CollectionUtils.isEmpty(labelIds)){
			for (Long id : labelIds) {
				String sql = "insert into TSM_WORKER_LABEL (login_id,label_id) values (?,?)";
				JT.update(sql, loginId, id);
			}
		}
	}

	public PageRsp<LabelResp> pageLabel(PageReq<LabelReq> req){
		StringBuilder sb = new StringBuilder("select id as labelId, SPECIALTIES_SPECIALTY_NAME as labelName from YCQ_SNG_STATIC where 1 = 1 ");
		StringBuilder sbCount = new StringBuilder("select count(*) from YCQ_SNG_STATIC where 1 = 1 ");
		List<Object> params = new ArrayList<>();
		if (StringUtils.hasText(req.getQuery().getLabelName())) {
			sb.append(" and SPECIALTIES_SPECIALTY_NAME like concat('%',?,'%') ");
			sbCount.append(" and SPECIALTIES_SPECIALTY_NAME like concat('%',?,'%') ");
			params.add(req.getQuery().getLabelName());
		}
		int total = JT.queryForInt(sbCount.toString(), params.toArray());
		List<LabelResp> result;
		String dbType = JT.getDbType();
		if (total > 0) {
			//根据数据库类型设置limit
			SqlUtil.appendLimit(dbType, params, sb, req);

			result = JT.queryForBeans(LabelResp.class, sb.toString(), params.toArray());
		} else {
			result = new ArrayList<>(0);
		}
		PageRsp<LabelResp> page = new PageRsp<>();
		page.setPageNo(req.getPageNo());
		page.setPageSize(req.getPageSize());
		page.setTotalNum(total);
		page.setResult(result);
		page.next();
		return page;
	}

	public List<WorkerListRspDto> getWorkerByOrgId(WorkerManageReq req) {
		Worker worker = CurrWorkerUtil.getCurrWorker();
		List<Object> parms=new ArrayList<>();
		String sql = "select * from tsm_worker where state=1 ";
		if (ObjectUtil.isNotEmpty(req) ){
			if (req.getParentOrgId()!=null && req.getOrgId()!=null){
				sql+=" and (org_id=? or org_id=?)";
				parms.add(req.getOrgId());
				parms.add(req.getParentOrgId());
			}else {
				if (ObjectUtil.isNotEmpty(req) && req.getOrgId()!=null){
					sql+=" and org_id=?";
					parms.add(req.getOrgId());
				}
			}
		}else {
			sql+=" and 1=2 ";
		}

		return JT.queryForBeans(WorkerListRspDto.class,sql,parms.toArray());
	}
}
