package com.ozs.rpm.controller;

import java.util.List;

import javax.servlet.http.HttpServletResponse;

import com.ozs.rpm.service.ReportService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.DeleteMapping;
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.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestHeader;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import com.ozs.rpm.dto.ReportDTO;
import com.ozs.rpm.dto.ReportKPIDTO;
import com.ozs.rpm.dto.ReportKpiRelUserDTO;
import com.ozs.rpm.dto.ReportRelUserDTO;
import com.ozs.rpm.dto.RpmDimTypeAll;
import com.ozs.rpm.dto.UserDTO;
import com.ozs.rpm.dto.chart.ChartTypeDTO;
import com.ozs.rpm.dto.chart.RichTextFileR;
import com.ozs.rpm.dto.kpim.KpiConfigForListDTO;
import com.ozs.rpm.dto.kpim.TopicZtreeDTO;
import com.ozs.rpm.dto.mdm.MdmInfoColumn;
import com.ozs.rpm.dto.mdm.MdmInfoDatabase;
import com.ozs.rpm.dto.mdm.MdmInfoTable;
import com.ozs.rpm.dto.save.SaveFiveDTO;
import com.ozs.rpm.dto.save.SaveFourDTO;
import com.ozs.rpm.dto.save.SaveOneDTO;
import com.ozs.rpm.dto.save.SaveReportDTO;
import com.ozs.rpm.dto.save.SaveThreeDTO;
import com.ozs.rpm.dto.save.SaveTwoDTO;
import com.ozs.rpm.util.AccountApi;
import com.ozs.rpm.util.KpimApi;
import com.ozs.rpm.util.R;
import com.ozs.rpm.util.S;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;

@Api(tags = { "报表配置接口" })
@RestController
public class ReportController {

	@Autowired
	private ReportService reportService;
	@Autowired
	private KpimApi kpimApi;
	@Autowired
	private AccountApi accountApi;

	@ApiOperation("报表分页列表展示")
	@GetMapping("/report/list")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "reportName", value = "报表名称", required = false, paramType = "query", dataType = "String"),
			@ApiImplicitParam(name = "reportLevel", value = "报表层级", required = false, paramType = "query", dataType = "Integer"),
			@ApiImplicitParam(name = "ifFinish", value = "编辑状态，是否成功", required = false, paramType = "query", dataType = "Integer"),
			@ApiImplicitParam(name = "page", value = "当前页数", required = false, paramType = "query", dataType = "Integer"),
			@ApiImplicitParam(name = "pageSize", value = "每页条数", required = false, paramType = "query", dataType = "Integer"),
			@ApiImplicitParam(name = "sort", value = "排序字段", required = false, paramType = "query", dataType = "String"),
			@ApiImplicitParam(name = "order", value = "排序方式", required = false, paramType = "query", dataType = "String") })
	public R<List<ReportDTO>> listReport(@RequestParam(value = "reportName", required = false) String reportName,
			@RequestParam(value = "reportLevel", required = false) Integer reportLevel,
			@RequestParam(value = "ifFinish", required = false) Integer ifFinish,
			@RequestParam(value = "page", required = false, defaultValue = "1") Integer page,
			@RequestParam(value = "pageSize", required = false, defaultValue = "10") Integer pageSize,
			@RequestParam(value = "sort", required = false, defaultValue = "update_time") String sort,
			@RequestParam(value = "order", required = false) String order) {
		try {
			return reportService.listReport(reportName, reportLevel, ifFinish, page, pageSize, sort, order);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("修改报表状态")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "id", value = "报表ID", required = false, paramType = "path", dataType = "String") })
	@PutMapping("/report/status/{id}")
	public R<String> updateStatus(@PathVariable("id") String id, @RequestBody ReportDTO status) {
		try {
			return reportService.updateStatus(id, status);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("报表删除")
	@ApiImplicitParam(name = "id", value = "报表ID", required = false, paramType = "path", dataType = "String")
	@DeleteMapping("/report/{id}")
	public R<String> removeReport(@PathVariable("id") String id) {
		try {
			return reportService.removeReport(id);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取维表")
	@GetMapping("/report/listType/{typeId}")
	@ApiImplicitParam(name = "typeId", value = "类型描述ID，1:报表类型;2:统计图类型;3:展示系统;4:报表布局;5:搜索条件类型;6:时间条件类型;7:展示方式;8:报表层级;", required = true, paramType = "path", dataType = "Integer")
	public R<List<RpmDimTypeAll>> listReportType(@PathVariable(value = "typeId") Integer typeId) {
		try {
			return reportService.listReportType(typeId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("查询主题树(Ztree格式带检索)")
	@ApiImplicitParam(name = "name", value = "主题名称", required = false, paramType = "query", dataType = "String")
	@GetMapping("/report/topicForZtree")
	public R<List<TopicZtreeDTO>> topicForZtree(@RequestParam(required = false) String name) throws Exception {
		try {
			return kpimApi.topicForZtree(name);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("根据主题查询KPI列表")
	@ApiImplicitParam(name = "topicId", value = "主题ID", required = false, paramType = "path", dataType = "String")
	@GetMapping("/report/listKpiConfigs/{topicId}")
	public R<List<KpiConfigForListDTO>> listKpiConfigsByTopic(@PathVariable String topicId) {
		try {
			return kpimApi.listKpiConfigsByTopic(topicId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("新建报表--第一步")
	@PostMapping("/report/saveOne")
	public R<SaveReportDTO> saveOne(@RequestBody SaveOneDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveOne(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR, "保存失败");
		}
	}

	@ApiOperation("新建报表--第二步")
	@PostMapping("/report/saveTwo")
	public R<SaveReportDTO> saveTwo(@RequestBody SaveTwoDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveTwo(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR, "保存失败");
		}
	}

	@ApiOperation("新建报表--第三步")
	@PostMapping("/report/saveThree")
	public R<SaveReportDTO> saveThree(@RequestBody SaveThreeDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveThree(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR, "保存失败");
		}
	}

	@ApiOperation("新建报表--第四步")
	@PostMapping("/report/saveFour")
	public R<SaveReportDTO> saveFour(@RequestBody SaveFourDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveFour(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR, "保存失败");
		}
	}

	@ApiOperation("新建报表--第五步")
	@PostMapping("/report/saveFive")
	public R<SaveReportDTO> saveFive(@RequestBody SaveFiveDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveFive(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR, "保存失败");
		}
	}

	@ApiOperation("新建报表--第六步，报表保存成功")
	@PostMapping("/report/saveSix")
	public R<String> saveSix(@RequestBody SaveReportDTO saveDto, @RequestHeader("token") String token) {
		try {
			saveDto.setUpdateUserId(accountApi.parseTokenId(token));
			return reportService.saveSix(saveDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取已完成子报表列表")
	@GetMapping("/report/listSonReport")
	public R<List<ReportDTO>> listSonReport() {
		try {
			return reportService.listSonReport();
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取已完成父类报表列表")
	@ApiImplicitParam(name = "menuCode", value = "菜单编号", required = false, paramType = "query", dataType = "String")
	@GetMapping("/report/listPReport")
	public R<List<ReportDTO>> listParentReport(@RequestParam(value = "menuCode", required = false) String menuCode) {
		try {
			return reportService.listParentReport(menuCode);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取用户列表")
	@GetMapping("/report/listUser")
	public R<List<UserDTO>> listUser() {
		try {
			return reportService.listUser();
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取报表用户权限关联")
	@GetMapping("/report/listRelUser/{id}")
	public R<List<ReportKpiRelUserDTO>> listRelUser(@PathVariable("id") String id) {
		try {
			return reportService.listRelUser(id);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("通过报表Id获取报表信息-用于编辑展示")
	@GetMapping("/report/{id}")
	public R<SaveReportDTO> getReportInfoById(@PathVariable("id") String id) {
		try {
			return reportService.getReportInfoById(id);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("报表授权给多个用户接口")
	@PostMapping("/report/reportRelUsers")
	public R<String> reportRelUsers(@RequestBody ReportRelUserDTO reportRelUserDto) {
		try {

			return reportService.reportRelUsers(reportRelUserDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("批量报表授权接口")
	@PostMapping("/report/reportsRelUsers")
	public R<String> reportsRelUsers(@RequestBody ReportRelUserDTO reportRelUserDto) {
		try {

			return reportService.reportsRelUsers(reportRelUserDto);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取菜单下已完成主报表列表")
	@ApiImplicitParam(name = "menuCode", value = "菜单编号", required = false, paramType = "query", dataType = "String")
	@GetMapping("/report/listReportByMenu")
	public R<List<ReportDTO>> listReportByMenu(@RequestParam(value = "menuCode", required = false) String menuCode) {
		try {
			return reportService.listReportByMenu(menuCode);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("查询报表中KPI列表")
	@ApiImplicitParam(name = "reportId", value = "报表ID", required = false, paramType = "path", dataType = "String")
	@GetMapping("/report/listKpiByReportId/{reportId}")
	public R<List<ReportKPIDTO>> listKpiByReportId(@PathVariable String reportId) {
		try {
			return reportService.listKpiByReportId(reportId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取报表已授权的kpi列表")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "reportId", value = "报表ID", required = false, paramType = "query", dataType = "String"),
			@ApiImplicitParam(name = "userId", value = "用户ID", required = false, paramType = "query", dataType = "String") })
	@GetMapping("/report/listKpiByReportAndUser")
	public R<List<ReportKPIDTO>> listKpiByReportAndUser(@RequestParam("reportId") String reportId,
			@RequestParam("userId") String userId) {
		try {
			return reportService.listKpiByReportAndUser(reportId, userId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}
	// ----------------------------添加图表设置---------------------------------------

	@ApiOperation("获取MDM数据库列表-非原始库")
	@ApiImplicitParam(name = "resourceName", value = "资源名称", required = false, paramType = "query", dataType = "String")
	@GetMapping(value = "/appshow/chartInfo/listDatabase")
	public R<List<MdmInfoDatabase>> listDatabase(
			@RequestParam(value = "resourceName", required = false) String resourceName) {
		try {
			return reportService.listDatabase(resourceName);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取根据数据库ID获取数据表信息")
	@ApiImplicitParam(name = "databaseId", value = "数据库ID", required = false, paramType = "query", dataType = "String")
	@GetMapping(value = "/appshow/chartInfo/listTableByDatabaseId")
	public R<List<MdmInfoTable>> listTableByDatabaseId(
			@RequestParam(value = "databaseId", required = false) String databaseId) {
		try {
			return reportService.listTableByDatabaseId(databaseId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取根据数据表ID获取字段信息")
	@ApiImplicitParam(name = "tableId", value = "数据表ID", required = false, paramType = "query", dataType = "String")
	@GetMapping(value = "/appshow/chartInfo/listColumnByTableId")
	public R<List<MdmInfoColumn>> listColumnByTableId(
			@RequestParam(value = "tableId", required = false) String tableId) {
		try {
			return reportService.listColumnByTableId(tableId);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("获取图表类型")
	@GetMapping(value = "/appshow/chartType")
	public R<List<ChartTypeDTO>> listChartType() {
		try {
			return reportService.listChartType();
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation("根据数据库和表信息生成获取DML")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "tableId", value = "表Id", required = false, paramType = "query", dataType = "String"),
			@ApiImplicitParam(name = "columnIds", value = "字段Id，多选逗号隔开的字符串", required = false, paramType = "query", dataType = "String") })
	@GetMapping(value = "/appshow/chartInfo/getDML")
	public R<String> getDML(@RequestParam("tableId") String tableId, @RequestParam("columnIds") String columnIds) {
		try {
			return reportService.getDML(tableId, columnIds);
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation(value = "图表新建上传文件")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "file", value = "图表文件", required = true, paramType = "form", dataType = "__file") })
	@PostMapping(value = "/appshow/chartInfo/loadChartFile", consumes = "multipart/*", headers = "content-type=multipart/form-data")
	public R<String> loadChartFile(@RequestParam("file") MultipartFile file, @RequestHeader("token") String token) {
		try {
			return reportService.loadChartFile(file, accountApi.parseTokenId(token));
		} catch (Exception e) {
			e.printStackTrace();
			return new R<>(S.ERROR);
		}
	}

	@ApiOperation(value = "富文本上传文件")
	@ApiImplicitParams({
			@ApiImplicitParam(name = "dir", value = " 上传类型，分别为image、media、file", required = true, paramType = "form", dataType = "String"),
			@ApiImplicitParam(name = "imgFile", value = "图表文件", required = true, paramType = "form", dataType = "__file") })
	@PostMapping(value = "/appshow/chartInfo/loadRichTextFile", consumes = "multipart/*", headers = "content-type=multipart/form-data", produces = {
			"application/json;charset=UTF-8" })
	public RichTextFileR uploadRichTextFile(@RequestParam("imgFile") MultipartFile imgFile,
			@RequestParam("dir") String dir, @RequestParam("token") String token, HttpServletResponse response) {
		try {
			String userId = accountApi.parseTokenId(token);
			if (token == null || userId == null) {
				return new RichTextFileR(1, "token或秘钥不正确!");
			}
			// 视频文件类型只允许上传.mp4格式
			if ("media".equals(dir) && !imgFile.getOriginalFilename().contains(".mp4")) {
				return new RichTextFileR(1, "视频请上传.mp4文件");
			}
			return reportService.uploadRichTextFile(imgFile, userId);
		} catch (Exception e) {
			e.printStackTrace();
			return new RichTextFileR(1, e.getMessage());
		}
	}
}
