package com.ruoyi.index.controller;

import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import org.apache.commons.lang3.text.StrSubstitutor;
import org.apache.poi.ss.usermodel.BorderStyle;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.FillPatternType;
import org.apache.poi.ss.usermodel.Font;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.util.IOUtils;
import org.apache.poi.xssf.streaming.SXSSFWorkbook;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import com.microsoft.sqlserver.jdbc.StringUtils;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.exception.UtilException;
import com.ruoyi.common.utils.ShiroUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.index.domain.IndexS;
import com.ruoyi.index.domain.IndexV;
import com.ruoyi.index.service.IIndexSService;
import com.ruoyi.index.service.IIndexVService;
import com.ruoyi.system.mapper.SSMapper;

/**
 * 展示指标Controller
 * 
 * @author ruoyi
 * @date 2021-12-28
 */
@Controller
@RequestMapping("/index/v")
public class IndexVController extends BaseController {
	private String prefix = "index/v";
	private String numberStyle = "###,###,###,###,###,###,###,##0";

	@Autowired
	private IIndexVService indexVService;

	@Autowired
	private IIndexSService indexSService;

	@Autowired
	private SSMapper ssMapper;

	@RequiresPermissions("index:v:view")
	@GetMapping()
	public String v() {
		return prefix + "/v";
	}

	/**
	 * 查询展示指标列表
	 */
	@RequiresPermissions("index:v:list")
	@PostMapping("/list")
	@ResponseBody
	public TableDataInfo list(IndexV indexV) {
		startPage();
		List<IndexV> list = indexVService.selectIndexVList(indexV);
		return getDataTable(list);
	}

	@GetMapping("/sum")
	public String sum(ModelMap mmap, String platformId, String projectId, Integer year, Long index) {

//		if (ShiroUtils.getSysUser() == null && getSession().getAttribute("loginName") == null) {
//			return "redirect:/";
//		}
//		String plats = (String) getSession().getAttribute("plats");
//		if (ShiroUtils.getSysUser() == null && StringUtils.isEmpty(plats)) {
//			return prefix + "/noauth";
//		}
//		platformId = reset(platformId);
//		projectId = reset(projectId);
//		// String psql = "select * from dim_platform order by platform_name";
//		String psql = "select * from R1917GroupPlatform order by Sequence desc";
//		if (ShiroUtils.getSysUser() == null) {
//			psql = "select * from R1917GroupPlatform where id in ('" + plats.replaceAll(",", "','") + "')";
//			if (("," + plats + ",").indexOf("," + platformId + ",") < 0) {
//				platformId = plats.split(",")[0];
//			}
//		} else {
//			if (ShiroUtils.getSysUser().getDept().getParentId() != 0) {
//				platformId = ShiroUtils.getSysUser().getDeptId().toString();
//				// psql = "select * from dim_platform where id='" + platformId + "'";
//				psql = "select * from R1917GroupPlatform where id='" + platformId + "'";
//
//			}
//		}
//		mmap.put("indexs", indexVService.selectIndexVList(null));
//		mmap.put("indexId", index);
////		List<LinkedHashMap<String, Object>> platforms = ssMapper.selectDetail(psql);
//		List<LinkedHashMap<String, Object>> platforms = new ArrayList<>();
//		mmap.put("platforms", platforms);
//		if (StringUtils.isEmpty(platformId)) {
//			platformId = platforms.get(0).get("ID").toString();
//		}
//		mmap.put("platformId", "1");
//		mmap.put("projects", "");
//		mmap.put("projectId", "");
//		mmap.put("year", year);
//
//		if (index != null) {
////			IndexV v = indexVService.selectIndexVById(index);
//			mmap.put("v", "1");
//
//	//		Map<String, String> summap = new HashMap<>();
//			mmap.put("sList", "");
//
//	//		String valueString = new StrSubstitutor(summap).replace(v.getFormula());
//			mmap.put("value", "");
//
//		}

		return prefix + "/sum";
	}

	private List<IndexS> getSList(Map<String, String> summap, String platformId, String projectId, Integer year,
			IndexV v) {
		DecimalFormat df1 = new DecimalFormat(numberStyle);
		Map<String, String> paramMap = new HashMap<>();
		paramMap.put("platform_id", "'" + platformId + "'");
		paramMap.put("project_id", "'" + projectId + "'");
		paramMap.put("year", year + "");
		StrSubstitutor sub = new StrSubstitutor(paramMap);
		List<IndexS> list = new ArrayList<IndexS>();
		List<String> sList = getSubUtil(v.getFormula());
		int sl = sList.size();
		if (!StringUtils.isEmpty(v.getOthers())) {
			for (String o : v.getOthers().split(",")) {
				if (!StringUtils.isEmpty(o)) {
					sList.add(o);
				}
			}
		}
		for (String s : sList) {
			sl--;
			if (summap.get(s) == null) { // 去重
				IndexS indexS = indexSService.selectIndexSByName(s);
				if (indexS != null) {
					String sql = sub.replace(indexS.getSquery());
					String sort = "";
					if (!StringUtils.isEmpty(indexS.getSort())) {
						sort = " order by " + indexS.getSort();
					}
					indexS.setDetail(ssMapper.selectDetail(sql + sort));
					if (indexS.getDetail().size() > 0) {
						indexS.setKeySet(indexS.getDetail().get(0).keySet());
						indexS.setIsNum(new HashMap<String, Boolean>());
						for (String key : indexS.getKeySet()) {
							indexS.getIsNum().put(key,
									"BigDecimal".equals(indexS.getDetail().get(0).get(key).getClass().getSimpleName()));
						}
					}
					sql = "select sum(" + indexS.getSumcol() + ") from (" + sql + ") a";
					BigDecimal sum = ssMapper.selectSum(sql);
					if (sum == null) {
						sum = new BigDecimal(0);
					}
					indexS.setSum(df1.format(sum));
					if (sum.compareTo(new BigDecimal(0)) >= 0) {
						summap.put(s, sum.toString());
					} else {
						summap.put(s, "(0" + sum.toString() + ")");
					}
					if (sl < 0) {
						indexS.setDelFlag("1");
					}
					list.add(indexS);
				}
			}
		}
		return list;
	}

	private String reset(String v) {
		if (!StringUtils.isEmpty(v)) {
			return v.replaceAll("'", "");
		}
		return "";
	}

	@PostMapping("/exportSum")
	@ResponseBody
	public AjaxResult exportSum(String platformId, String projectId, Integer year, Long index) {
		platformId = reset(platformId);
		projectId = reset(projectId);
		IndexV v = indexVService.selectIndexVById(index);
		if (v == null) {
			return error("参数错误");
		}
		Map<String, String> summap = new HashMap<>();
		List<LinkedHashMap<String, Object>> platforms = ssMapper
				.selectDetail("select * from R1917GroupPlatform where id='" + platformId + "' order by id");
		if (platforms.size() == 0) {
			return error("参数错误");
		}
		// String name = platforms.get(0).get("platform_name").toString();
		String name = platforms.get(0).get("PlatformName").toString();
		if (!StringUtils.isEmpty(projectId)) {
			List<LinkedHashMap<String, Object>> projects = ssMapper
					// .selectDetail("select * from dwd_asset_project where platform_id='" +
					// platformId
					// + "' and project_id='" + projectId + "' order by id");
					.selectDetail(
							"SELECT p.ID as ID,p.ProjectAbbr as ProjectName from R1917BIRoomProject p where p.IsDelete=0 and p.GroupPlatformId='"
									+ platformId + "' and p.ID='" + projectId + "'");
			if (projects.size() == 0) {
				return error("参数错误");
			}
			// name = name + "_" + projects.get(0).get("project_name").toString();
			name = name + "_" + projects.get(0).get("ProjectName").toString();
		}
		name = name + "_" + v.getName();
		return exportExcel(v, getSList(summap, platformId, projectId, year, v), name);
	}

	private AjaxResult exportExcel(IndexV v, List<IndexS> sList, String name) {
		OutputStream out = null;
		Workbook wb = new SXSSFWorkbook(500);

		CellStyle style = wb.createCellStyle();
		Font font = wb.createFont();
		font.setBold(true);
		font.setFontHeightInPoints((short) 16);
		style.setFont(font);

		CellStyle style1 = wb.createCellStyle();
		style1.setBorderBottom(BorderStyle.THIN);
		style1.setBorderTop(BorderStyle.THIN);
		style1.setBorderRight(BorderStyle.THIN);
		style1.setBorderLeft(BorderStyle.THIN);
		style1.setFillForegroundColor(IndexedColors.LIGHT_TURQUOISE.getIndex());
		style1.setFillPattern(FillPatternType.SOLID_FOREGROUND);

		CellStyle style2 = wb.createCellStyle();
		style2.setBorderBottom(BorderStyle.THIN);
		style2.setBorderTop(BorderStyle.THIN);
		style2.setBorderRight(BorderStyle.THIN);
		style2.setBorderLeft(BorderStyle.THIN);

		int n = 0;
		for (IndexS s : sList) {
			String sheetName = s.getName();
			Sheet sheet = wb.createSheet();
			wb.setSheetName(n, sheetName);
			n++;
			Row row = sheet.createRow(0);
			Cell cell = row.createCell(0);

			cell.setCellStyle(style);
			cell.setCellValue(name + "_" + sheetName);

			if (s.getKeySet() != null) {

				row = sheet.createRow(1);
				int c = 0;
				for (String key : s.getKeySet()) {
					cell = row.createCell(c);
					cell.setCellStyle(style1);
					cell.setCellValue(key);
					c++;
				}

				int r = 1;
				for (Map<String, Object> m : s.getDetail()) {
					r++;
					row = sheet.createRow(r);
					c = 0;
					for (String key : s.getKeySet()) {
						cell = row.createCell(c);
						cell.setCellStyle(style2);
						Object o = m.get(key);
						if (o != null) {
							if ("BigDecimal".equals(o.getClass().getSimpleName())) {
								cell.setCellValue(((BigDecimal) o).doubleValue());
							} else {
								cell.setCellValue(o.toString());
							}
						}
						c++;
					}
				}
			}
		}

		try {
			// writeSheet();
			String filename = UUID.randomUUID().toString() + "_" + name + ".xlsx";
			out = new FileOutputStream(getAbsoluteFile(filename));
			wb.write(out);
			return AjaxResult.success(filename);
		} catch (Exception e) {
			// log.error("导出Excel异常{}", e.getMessage());
			throw new UtilException("导出Excel失败，请联系网站管理员！");
		} finally {
			IOUtils.closeQuietly(wb);
			IOUtils.closeQuietly(out);
		}
	}

	/**
	 * 获取下载路径
	 * 
	 * @param filename 文件名称
	 */
	private String getAbsoluteFile(String filename) {
		String downloadPath = RuoYiConfig.getDownloadPath() + filename;
		File desc = new File(downloadPath);
		if (!desc.getParentFile().exists()) {
			desc.getParentFile().mkdirs();
		}
		return downloadPath;
	}

	@PostMapping("/listProject")
	@ResponseBody
	public List<LinkedHashMap<String, Object>> listProject(String platformId) {
		List<LinkedHashMap<String, Object>> list = new ArrayList<>();
		return list;
	}

	private String getValue(String valueString) {
		DecimalFormat df1 = new DecimalFormat(numberStyle);
		String value = "0";
		try {
			if (valueString.indexOf("100%") > -1) {
				value = df1.format(
						CalculatorUtil.arithmetic(valueString.replaceAll("100%", "1")).multiply(new BigDecimal(100)))
						+ "%";
			} else {
				value = df1.format(CalculatorUtil.arithmetic(valueString));
			}
		} catch (Exception e) {

		}
		return value;
	}

	private static List<String> getSubUtil(String soap) {
		Pattern pattern = Pattern.compile("\\$\\{(.*?)\\}");
		Matcher matcher = pattern.matcher(soap);
		List<String> list = new ArrayList<>();
		int i = 1;
		while (matcher.find()) {
			list.add(matcher.group(i));
		}
		return list;
	}

	/**
	 * 导出展示指标列表
	 */
	@RequiresPermissions("index:v:export")
	@Log(title = "展示指标", businessType = BusinessType.EXPORT)
	@PostMapping("/export")
	@ResponseBody
	public AjaxResult export(IndexV indexV) {
		List<IndexV> list = indexVService.selectIndexVList(indexV);
		ExcelUtil<IndexV> util = new ExcelUtil<IndexV>(IndexV.class);
		return util.exportExcel(list, "展示指标数据");
	}

	/**
	 * 新增展示指标
	 */
	@GetMapping("/add")
	public String add() {
		return prefix + "/add";
	}

	/**
	 * 新增保存展示指标
	 */
	@RequiresPermissions("index:v:add")
	@Log(title = "展示指标", businessType = BusinessType.INSERT)
	@PostMapping("/add")
	@ResponseBody
	public AjaxResult addSave(IndexV indexV) {
		return toAjax(indexVService.insertIndexV(indexV));
	}

	/**
	 * 修改展示指标
	 */
	@RequiresPermissions("index:v:edit")
	@GetMapping("/edit/{id}")
	public String edit(@PathVariable("id") Long id, ModelMap mmap) {
		IndexV indexV = indexVService.selectIndexVById(id);
		mmap.put("indexV", indexV);
		return prefix + "/edit";
	}

	/**
	 * 修改保存展示指标
	 */
	@RequiresPermissions("index:v:edit")
	@Log(title = "展示指标", businessType = BusinessType.UPDATE)
	@PostMapping("/edit")
	@ResponseBody
	public AjaxResult editSave(IndexV indexV) {
		return toAjax(indexVService.updateIndexV(indexV));
	}

	/**
	 * 删除展示指标
	 */
	@RequiresPermissions("index:v:remove")
	@Log(title = "展示指标", businessType = BusinessType.DELETE)
	@PostMapping("/remove")
	@ResponseBody
	public AjaxResult remove(String ids) {
		return toAjax(indexVService.deleteIndexVByIds(ids));
	}

	public static void main(String[] args) {
		System.out.print(System.currentTimeMillis());
	}
}
