|
|
@@ -0,0 +1,358 @@
|
|
|
+/*
|
|
|
+ * Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
|
|
|
+ *
|
|
|
+ * Redistribution and use in source and binary forms, with or without
|
|
|
+ * modification, are permitted provided that the following conditions are met:
|
|
|
+ *
|
|
|
+ * Redistributions of source code must retain the above copyright notice,
|
|
|
+ * this list of conditions and the following disclaimer.
|
|
|
+ * Redistributions in binary form must reproduce the above copyright
|
|
|
+ * notice, this list of conditions and the following disclaimer in the
|
|
|
+ * documentation and/or other materials provided with the distribution.
|
|
|
+ * Neither the name of the dreamlu.net developer nor the names of its
|
|
|
+ * contributors may be used to endorse or promote products derived from
|
|
|
+ * this software without specific prior written permission.
|
|
|
+ * Author: Chill 庄骞 (smallchill@163.com)
|
|
|
+ */
|
|
|
+package org.springblade.common.utils;
|
|
|
+
|
|
|
+
|
|
|
+import org.slf4j.Logger;
|
|
|
+import org.slf4j.LoggerFactory;
|
|
|
+import org.springframework.util.FileCopyUtils;
|
|
|
+import org.springframework.web.multipart.MultipartFile;
|
|
|
+
|
|
|
+import javax.servlet.http.HttpServletRequest;
|
|
|
+import javax.servlet.http.HttpServletResponse;
|
|
|
+import java.io.*;
|
|
|
+import java.net.URLEncoder;
|
|
|
+import java.util.Calendar;
|
|
|
+import java.util.UUID;
|
|
|
+
|
|
|
+/**
|
|
|
+ * 通用工具类
|
|
|
+ *
|
|
|
+ * @author Chill
|
|
|
+ */
|
|
|
+public class CommonUtil {
|
|
|
+ private static Logger logger = LoggerFactory.getLogger(CommonUtil.class);
|
|
|
+
|
|
|
+ public static Integer APPROVED_0=0;//待审核
|
|
|
+ public static Integer APPROVED_1=1;//审核通过
|
|
|
+ public static Integer APPROVED_2=2;//审核不通过
|
|
|
+ public static Integer APPROVED_3=3;//无须审核
|
|
|
+
|
|
|
+ public static Integer ISPUB_0=0;//公开
|
|
|
+ public static Integer ISPUB_1=1;//不公开不分享
|
|
|
+ public static Integer ISPUB_2=2;//不公开要分享
|
|
|
+
|
|
|
+ public static Integer ISDELETE_0=0;//正常
|
|
|
+ public static Integer ISDELETE_1=1;//删除
|
|
|
+
|
|
|
+ /**obj转字符串**/
|
|
|
+ public static String processNull(Object obj){
|
|
|
+ if(obj==null){
|
|
|
+ return "";
|
|
|
+ }else{
|
|
|
+ return String.valueOf(obj);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ public static String dealArr(String[] arr){
|
|
|
+ StringBuffer str=new StringBuffer();
|
|
|
+ if(arr!=null && arr.length>0){
|
|
|
+ for (int i = 0; i <arr.length ; i++) {
|
|
|
+ if (i==arr.length-1){
|
|
|
+ str.append(arr[i]);
|
|
|
+ }else {
|
|
|
+ str.append(arr[i]+",");
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }else{
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+ return str.toString();
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 最大公约数
|
|
|
+ * @param m 数值1
|
|
|
+ * @param n 数值2
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ public static int getMaxGY(int m,int n){
|
|
|
+ if(m==0){
|
|
|
+ return n;
|
|
|
+ }else if(n==0){
|
|
|
+ return m;
|
|
|
+ }
|
|
|
+ //求最大公约数
|
|
|
+ if(m==n){
|
|
|
+ return n;
|
|
|
+ }else{
|
|
|
+ while(m%n!=0){
|
|
|
+ int temp=m%n;
|
|
|
+ m=n;
|
|
|
+ n=temp;
|
|
|
+ }
|
|
|
+ return n;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ public static Integer TENANT_1=1;//1-平台
|
|
|
+ public static Integer TENANT_2=2;//2-机构
|
|
|
+ public static Integer TENANT_3=3;//3-政府
|
|
|
+
|
|
|
+ public static Integer CLASSTYPE_0=0;//3-机构主账号名称
|
|
|
+ public static Integer CLASSTYPE_1=1;//1-学段
|
|
|
+ public static Integer CLASSTYPE_2=2;//2-年级
|
|
|
+ public static Integer CLASSTYPE_3=3;//3-班级
|
|
|
+
|
|
|
+
|
|
|
+ public static String TYPE_GL="gl";//谷类
|
|
|
+ public static String TYPE_SL="sl";//薯类
|
|
|
+ public static String TYPE_SC="sc";//蔬菜
|
|
|
+ public static String TYPE_SG="sg";//水果
|
|
|
+ public static String TYPE_RZP="rzp";//乳制品
|
|
|
+ public static String TYPE_DD="dd";//大豆
|
|
|
+ public static String TYPE_JG="jg";//坚果
|
|
|
+ public static String TYPE_XQL="xql";//畜禽类
|
|
|
+ public static String TYPE_DL="dl";//蛋类
|
|
|
+ public static String TYPE_SCP="scp";//水产品
|
|
|
+ public static String TYPE_SY="sy";//食盐
|
|
|
+ public static String TYPE_SYY="syy";//食用油
|
|
|
+
|
|
|
+ public static String BASE_TYPE="gl,sl,sc,sg,rzp,dd,xql,dl,scp,jg,sy,syy,jzl,yye,xcl,ssl,yll,hjj,mjl,twp,qt";
|
|
|
+
|
|
|
+ public static String BASE_TYPE_NAME="谷类及制品,薯类、淀粉及制品,蔬菜类及制品,水果类及制品,乳类及制品,干豆类及制品,畜禽肉类及制品,蛋类及制品,鱼虾蟹贝类,坚果、种子类,食盐,油脂类,菌藻类,婴幼儿食品,小吃、甜饼,速食食品,饮料类,含酒精饮料,糖、蜜饯类,调味品类,药食两用食物及其他";
|
|
|
+
|
|
|
+ //食盐的固定id
|
|
|
+ /*public static String SY_IDS="";*/
|
|
|
+
|
|
|
+ //分数统计哪些分类
|
|
|
+ public static String BASE_TYPE_COUNT="gl,sl,sc,sg,rzp,dd,xql,dl,scp,jg,sy,syy";
|
|
|
+
|
|
|
+
|
|
|
+ //分数统计哪些营养素
|
|
|
+ public static String TYPE_Nutri="101,102,103,104,201,204,301,303,401,405,406,415";
|
|
|
+
|
|
|
+
|
|
|
+ //带量食谱分类
|
|
|
+ public static String QUANTITY_BASE_TYPE="gl,sl,sc,sg,rzp,dd,xql,dl,scp,jg,sy,syy,jzl,yye,xcl,ssl,yll,hjj,mjl,twp";
|
|
|
+
|
|
|
+
|
|
|
+ //带量食谱展示哪些营养素
|
|
|
+ public static String QUANTITY_TYPE_Nutri="101,102,103,104,501,401,402,405,406,412,415,403,504,201,202,203,204,205,301,303,304,305,308,302";
|
|
|
+
|
|
|
+ //营养摄入量分析
|
|
|
+ public static String NUTRI_TYPE="101,102,103,201,204,301,303,401,405,406,415";
|
|
|
+
|
|
|
+
|
|
|
+ public String logUpload(String viewpath,MultipartFile file,String uploadpath) throws Exception {
|
|
|
+ if (file == null || file.isEmpty()) {
|
|
|
+ throw new Exception("未选择需上传的文件");
|
|
|
+ }
|
|
|
+
|
|
|
+ //String filePath ="logs_app";
|
|
|
+ //获取项目根路径
|
|
|
+ //String a= System.getProperty("user.dir");
|
|
|
+ //a=new File(a).getParent();
|
|
|
+
|
|
|
+ //filePath=uploadpath+File.separator+filePath;
|
|
|
+ String filePath=uploadpath;
|
|
|
+ File fileUpload = new File(filePath);
|
|
|
+ if (!fileUpload.exists()) {
|
|
|
+ fileUpload.mkdirs();
|
|
|
+ }
|
|
|
+
|
|
|
+ //获取文件后缀
|
|
|
+ String extName = file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf(".") + 1);
|
|
|
+ //file.getOriginalFilename()
|
|
|
+ //文件名称
|
|
|
+ String original=UUID.randomUUID()+"."+extName;
|
|
|
+ String savePath =filePath+ File.separator +original;
|
|
|
+ String url=viewpath;
|
|
|
+ try {
|
|
|
+ FileCopyUtils.copy(file.getBytes(),new File(savePath));
|
|
|
+ /*if (savePath.contains("\\")) {
|
|
|
+ savePath = savePath.replace("\\", "/");
|
|
|
+ }*/
|
|
|
+ return url+original;
|
|
|
+ } catch (IOException e) {
|
|
|
+ throw new Exception("上传文件到服务器失败:" + e.toString());
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ public void download(HttpServletRequest request, HttpServletResponse response) {
|
|
|
+
|
|
|
+ //前端页面将自己需要的文件名字拿过来。这个名字直接拼接到文件所在服务器的相对路径。这里为便于测试。我直接把名字写死,以后使用的时候
|
|
|
+
|
|
|
+ //根据实际业务进行修改。
|
|
|
+
|
|
|
+ String fileName = request.getParameter("file");
|
|
|
+
|
|
|
+ System.out.println(fileName);
|
|
|
+
|
|
|
+ try {
|
|
|
+
|
|
|
+ //mac系统,所以路径是这样子的。win系统就是D盘什么什么的
|
|
|
+
|
|
|
+ String path = "C:/Program Files/Apache Software Foundation/Tomcat 8.5/webapps/test"+File.separator+fileName;
|
|
|
+
|
|
|
+ //这里是下载以后的文件叫做什么名字。我这里是以时间来定义名字的。
|
|
|
+
|
|
|
+ downCfg(fileName, request, response);
|
|
|
+
|
|
|
+ OutputStream out;
|
|
|
+
|
|
|
+ FileInputStream inputStream = new FileInputStream(path);
|
|
|
+
|
|
|
+ out = response.getOutputStream();
|
|
|
+
|
|
|
+ byte[] buffer = new byte[1024];
|
|
|
+
|
|
|
+ int len;
|
|
|
+
|
|
|
+ while ((len = inputStream.read(buffer)) != -1) {
|
|
|
+
|
|
|
+ out.write(buffer, 0, len);
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ inputStream.close();
|
|
|
+
|
|
|
+ out.close();
|
|
|
+
|
|
|
+ out.flush();
|
|
|
+
|
|
|
+ } catch (IOException e) {
|
|
|
+
|
|
|
+ e.printStackTrace();
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ private void downCfg(String fileName, HttpServletRequest request, HttpServletResponse response) throws UnsupportedEncodingException {
|
|
|
+
|
|
|
+ // 判断浏览器,进行不同的加密,这样下载的时候保存的文件名就不会乱码
|
|
|
+
|
|
|
+ String userAgent = request.getHeader("User-Agent");
|
|
|
+
|
|
|
+ // 针对IE或者以IE为内核的浏览器:
|
|
|
+
|
|
|
+ if (userAgent.contains("MSIE") || userAgent.contains("Trident")) {
|
|
|
+
|
|
|
+ fileName = URLEncoder.encode(fileName, "UTF-8");
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ // 非IE浏览器的处理:
|
|
|
+
|
|
|
+ fileName = new String(fileName.getBytes("UTF-8"), "ISO-8859-1");
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ response.setHeader("Content-disposition", String.format("attachment; filename=\"%s\"", fileName));
|
|
|
+
|
|
|
+ response.setContentType("application/octet-stream;charset=utf-8");
|
|
|
+
|
|
|
+ response.setCharacterEncoding("UTF-8");
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ //断点续传 文件下载
|
|
|
+ public boolean download(HttpServletRequest request, HttpServletResponse response, String fileName) {
|
|
|
+ //文件目录
|
|
|
+ Calendar calendar = Calendar.getInstance();
|
|
|
+ File serverDir = new File(System.getProperty("user.dir") + File.separator
|
|
|
+ + "uploads" + File.separator
|
|
|
+ + calendar.get(Calendar.YEAR) + File.separator
|
|
|
+ + (calendar.get(Calendar.MONTH) + 1));
|
|
|
+ File file = new File(serverDir + File.separator + fileName);
|
|
|
+
|
|
|
+ //下载开始位置
|
|
|
+ long startByte = 0;
|
|
|
+ //下载结束位置
|
|
|
+ long endByte = file.length() - 1;
|
|
|
+
|
|
|
+ //获取下载范围
|
|
|
+ String range = request.getHeader("range");
|
|
|
+ if (range != null && range.contains("bytes=") && range.contains("-")) {
|
|
|
+ range = range.substring(range.lastIndexOf("=") + 1).trim();
|
|
|
+ String rangeArray[] = range.split("-");
|
|
|
+ if (rangeArray.length == 1) {
|
|
|
+ //Example: bytes=1024-
|
|
|
+ if (range.endsWith("-")) {
|
|
|
+ startByte = Long.parseLong(rangeArray[0]);
|
|
|
+ } else { //Example: bytes=-1024
|
|
|
+ endByte = Long.parseLong(rangeArray[0]);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ //Example: bytes=2048-4096
|
|
|
+ else if (rangeArray.length == 2) {
|
|
|
+ startByte = Long.parseLong(rangeArray[0]);
|
|
|
+ endByte = Long.parseLong(rangeArray[1]);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ long contentLength = endByte - startByte + 1;
|
|
|
+ String contentType = request.getServletContext().getMimeType(fileName);
|
|
|
+
|
|
|
+ //HTTP 响应头设置
|
|
|
+ //断点续传,HTTP 状态码必须为 206,否则不设置,如果非断点续传设置 206 状态码,则浏览器无法下载
|
|
|
+ if (range != null) {
|
|
|
+ response.setStatus(HttpServletResponse.SC_PARTIAL_CONTENT);
|
|
|
+ }
|
|
|
+ response.setContentType(contentType);
|
|
|
+ response.setHeader("Content-Type", contentType);
|
|
|
+ response.setHeader("Content-Length", String.valueOf(contentLength));
|
|
|
+ response.setHeader("Accept-Ranges", "bytes");
|
|
|
+ //Content-Range: 下载开始位置-下载结束位置/文件大小
|
|
|
+ response.setHeader("Content-Range", "bytes " + startByte + "-" + endByte + "/" + file.length());
|
|
|
+ //Content-disposition: inline; filename=xxx.xxx 表示浏览器内嵌显示该文件
|
|
|
+ //Content-disposition: attachment; filename=xxx.xxx 表示浏览器下载该文件
|
|
|
+ response.setHeader("Content-Disposition", "inline; filename=" + fileName);
|
|
|
+
|
|
|
+ //传输文件流
|
|
|
+ BufferedOutputStream outputStream = null;
|
|
|
+ RandomAccessFile randomAccessFile = null;
|
|
|
+ //已传送数据大小
|
|
|
+ long transmittedLength = 0;
|
|
|
+ try {
|
|
|
+ //以只读模式设置文件指针偏移量
|
|
|
+ randomAccessFile = new RandomAccessFile(file, "r");
|
|
|
+ randomAccessFile.seek(startByte);
|
|
|
+
|
|
|
+ outputStream = new BufferedOutputStream(response.getOutputStream());
|
|
|
+ byte[] buff = new byte[4096];
|
|
|
+ int len;
|
|
|
+ while (transmittedLength < contentLength && (len = randomAccessFile.read(buff)) != -1) {
|
|
|
+ outputStream.write(buff, 0, len);
|
|
|
+ transmittedLength += len;
|
|
|
+ }
|
|
|
+
|
|
|
+ outputStream.flush();
|
|
|
+ response.flushBuffer();
|
|
|
+ logger.info("下载完毕: {}-{}: {}", startByte, endByte, transmittedLength);
|
|
|
+ return true;
|
|
|
+
|
|
|
+ } catch (IOException e) {
|
|
|
+ logger.info("下载停止: {}-{}: {}", startByte, endByte, transmittedLength);
|
|
|
+ } finally {
|
|
|
+ try {
|
|
|
+ if (randomAccessFile != null) {
|
|
|
+ randomAccessFile.close();
|
|
|
+ }
|
|
|
+ } catch (IOException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return false;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+}
|