Merge remote-tracking branch 'origin/master'
This commit is contained in:
4
pom.xml
4
pom.xml
@ -18,12 +18,12 @@
|
|||||||
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
|
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
|
||||||
<java.version>1.8</java.version>
|
<java.version>1.8</java.version>
|
||||||
<mybatis.boot.version>1.3.2</mybatis.boot.version>
|
<mybatis.boot.version>1.3.2</mybatis.boot.version>
|
||||||
<druid.version>1.1.14</druid.version>
|
<druid.version>1.1.23</druid.version>
|
||||||
<bitwalker.version>1.19</bitwalker.version>
|
<bitwalker.version>1.19</bitwalker.version>
|
||||||
<swagger.version>2.9.2</swagger.version>
|
<swagger.version>2.9.2</swagger.version>
|
||||||
<kaptcha.version>2.3.2</kaptcha.version>
|
<kaptcha.version>2.3.2</kaptcha.version>
|
||||||
<pagehelper.boot.version>1.2.5</pagehelper.boot.version>
|
<pagehelper.boot.version>1.2.5</pagehelper.boot.version>
|
||||||
<fastjson.version>1.2.70</fastjson.version>
|
<fastjson.version>1.2.73</fastjson.version>
|
||||||
<oshi.version>3.9.1</oshi.version>
|
<oshi.version>3.9.1</oshi.version>
|
||||||
<commons.io.version>2.5</commons.io.version>
|
<commons.io.version>2.5</commons.io.version>
|
||||||
<commons.fileupload.version>1.3.3</commons.fileupload.version>
|
<commons.fileupload.version>1.3.3</commons.fileupload.version>
|
||||||
|
@ -4,6 +4,7 @@ import java.lang.annotation.ElementType;
|
|||||||
import java.lang.annotation.Retention;
|
import java.lang.annotation.Retention;
|
||||||
import java.lang.annotation.RetentionPolicy;
|
import java.lang.annotation.RetentionPolicy;
|
||||||
import java.lang.annotation.Target;
|
import java.lang.annotation.Target;
|
||||||
|
import java.math.BigDecimal;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 自定义导出Excel数据注解
|
* 自定义导出Excel数据注解
|
||||||
@ -30,7 +31,7 @@ public @interface Excel
|
|||||||
public String dateFormat() default "";
|
public String dateFormat() default "";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 如果是字典类型,请设置字典的type值
|
* 如果是字典类型,请设置字典的type值 (如: sys_user_sex)
|
||||||
*/
|
*/
|
||||||
public String dictType() default "";
|
public String dictType() default "";
|
||||||
|
|
||||||
@ -44,6 +45,16 @@ public @interface Excel
|
|||||||
*/
|
*/
|
||||||
public String separator() default ",";
|
public String separator() default ",";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* BigDecimal 精度 默认:-1(默认不开启BigDecimal格式化)
|
||||||
|
*/
|
||||||
|
public int scale() default -1;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* BigDecimal 舍入规则 默认:BigDecimal.ROUND_HALF_EVEN
|
||||||
|
*/
|
||||||
|
public int roundingMode() default BigDecimal.ROUND_HALF_EVEN;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 导出类型(0数字 1字符串)
|
* 导出类型(0数字 1字符串)
|
||||||
*/
|
*/
|
||||||
@ -89,6 +100,11 @@ public @interface Excel
|
|||||||
*/
|
*/
|
||||||
public String targetAttr() default "";
|
public String targetAttr() default "";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否自动统计数据,在最后追加一行统计数据总和
|
||||||
|
*/
|
||||||
|
public boolean isStatistics() default false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 字段类型(0:导出导入;1:仅导出;2:仅导入)
|
* 字段类型(0:导出导入;1:仅导出;2:仅导入)
|
||||||
*/
|
*/
|
||||||
|
@ -29,7 +29,7 @@ public class GenConstants
|
|||||||
public static final String PARENT_MENU_NAME = "parentMenuName";
|
public static final String PARENT_MENU_NAME = "parentMenuName";
|
||||||
|
|
||||||
/** 数据库字符串类型 */
|
/** 数据库字符串类型 */
|
||||||
public static final String[] COLUMNTYPE_STR = { "char", "varchar", "narchar", "varchar2", "tinytext", "text",
|
public static final String[] COLUMNTYPE_STR = { "char", "varchar", "nvarchar", "varchar2", "tinytext", "text",
|
||||||
"mediumtext", "longtext" };
|
"mediumtext", "longtext" };
|
||||||
|
|
||||||
/** 数据库时间类型 */
|
/** 数据库时间类型 */
|
||||||
|
@ -18,8 +18,8 @@ public class PageDomain
|
|||||||
/** 排序列 */
|
/** 排序列 */
|
||||||
private String orderByColumn;
|
private String orderByColumn;
|
||||||
|
|
||||||
/** 排序的方向 "desc" 或者 "asc". */
|
/** 排序的方向desc或者asc */
|
||||||
private String isAsc;
|
private String isAsc = "asc";
|
||||||
|
|
||||||
public String getOrderBy()
|
public String getOrderBy()
|
||||||
{
|
{
|
||||||
|
@ -6,8 +6,8 @@ import java.io.IOException;
|
|||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
|
import java.text.DecimalFormat;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Comparator;
|
import java.util.Comparator;
|
||||||
@ -15,6 +15,7 @@ import java.util.Date;
|
|||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
import org.apache.poi.hssf.usermodel.HSSFDateUtil;
|
import org.apache.poi.hssf.usermodel.HSSFDateUtil;
|
||||||
@ -102,6 +103,16 @@ public class ExcelUtil<T>
|
|||||||
*/
|
*/
|
||||||
private List<Object[]> fields;
|
private List<Object[]> fields;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 统计列表
|
||||||
|
*/
|
||||||
|
private Map<Integer, Double> statistics = new HashMap<Integer, Double>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 数字格式
|
||||||
|
*/
|
||||||
|
private static final DecimalFormat DOUBLE_FORMAT = new DecimalFormat("######0.00");
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 实体对象
|
* 实体对象
|
||||||
*/
|
*/
|
||||||
@ -341,6 +352,7 @@ public class ExcelUtil<T>
|
|||||||
if (Type.EXPORT.equals(type))
|
if (Type.EXPORT.equals(type))
|
||||||
{
|
{
|
||||||
fillExcelData(index, row);
|
fillExcelData(index, row);
|
||||||
|
addStatisticsRow();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
String filename = encodingFilename(sheetName);
|
String filename = encodingFilename(sheetName);
|
||||||
@ -448,6 +460,15 @@ public class ExcelUtil<T>
|
|||||||
style.setFont(headerFont);
|
style.setFont(headerFont);
|
||||||
styles.put("header", style);
|
styles.put("header", style);
|
||||||
|
|
||||||
|
style = wb.createCellStyle();
|
||||||
|
style.setAlignment(HorizontalAlignment.CENTER);
|
||||||
|
style.setVerticalAlignment(VerticalAlignment.CENTER);
|
||||||
|
Font totalFont = wb.createFont();
|
||||||
|
totalFont.setFontName("Arial");
|
||||||
|
totalFont.setFontHeightInPoints((short) 10);
|
||||||
|
style.setFont(totalFont);
|
||||||
|
styles.put("total", style);
|
||||||
|
|
||||||
return styles;
|
return styles;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -546,15 +567,20 @@ public class ExcelUtil<T>
|
|||||||
{
|
{
|
||||||
cell.setCellValue(convertByExp(Convert.toStr(value), readConverterExp, separator));
|
cell.setCellValue(convertByExp(Convert.toStr(value), readConverterExp, separator));
|
||||||
}
|
}
|
||||||
else if (StringUtils.isNotEmpty(dictType))
|
else if (StringUtils.isNotEmpty(dictType) && StringUtils.isNotNull(value))
|
||||||
{
|
{
|
||||||
cell.setCellValue(convertDictByExp(Convert.toStr(value), dictType, separator));
|
cell.setCellValue(convertDictByExp(Convert.toStr(value), dictType, separator));
|
||||||
}
|
}
|
||||||
|
else if (value instanceof BigDecimal && -1 != attr.scale())
|
||||||
|
{
|
||||||
|
cell.setCellValue((((BigDecimal) value).setScale(attr.scale(), attr.roundingMode())).toString());
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// 设置列类型
|
// 设置列类型
|
||||||
setCellVo(value, attr, cell);
|
setCellVo(value, attr, cell);
|
||||||
}
|
}
|
||||||
|
addStatisticsData(column, Convert.toStr(value), attr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
@ -721,6 +747,53 @@ public class ExcelUtil<T>
|
|||||||
return DictUtils.getDictValue(dictType, dictLabel, separator);
|
return DictUtils.getDictValue(dictType, dictLabel, separator);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 合计统计信息
|
||||||
|
*/
|
||||||
|
private void addStatisticsData(Integer index, String text, Excel entity)
|
||||||
|
{
|
||||||
|
if (entity != null && entity.isStatistics())
|
||||||
|
{
|
||||||
|
Double temp = 0D;
|
||||||
|
if (!statistics.containsKey(index))
|
||||||
|
{
|
||||||
|
statistics.put(index, temp);
|
||||||
|
}
|
||||||
|
try
|
||||||
|
{
|
||||||
|
temp = Double.valueOf(text);
|
||||||
|
}
|
||||||
|
catch (NumberFormatException e)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
statistics.put(index, statistics.get(index) + temp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 创建统计行
|
||||||
|
*/
|
||||||
|
public void addStatisticsRow()
|
||||||
|
{
|
||||||
|
if (statistics.size() > 0)
|
||||||
|
{
|
||||||
|
Cell cell = null;
|
||||||
|
Row row = sheet.createRow(sheet.getLastRowNum() + 1);
|
||||||
|
Set<Integer> keys = statistics.keySet();
|
||||||
|
cell = row.createCell(0);
|
||||||
|
cell.setCellStyle(styles.get("total"));
|
||||||
|
cell.setCellValue("合计");
|
||||||
|
|
||||||
|
for (Integer key : keys)
|
||||||
|
{
|
||||||
|
cell = row.createCell(key);
|
||||||
|
cell.setCellStyle(styles.get("total"));
|
||||||
|
cell.setCellValue(DOUBLE_FORMAT.format(statistics.get(key)));
|
||||||
|
}
|
||||||
|
statistics.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 编码文件名
|
* 编码文件名
|
||||||
*/
|
*/
|
||||||
@ -790,9 +863,9 @@ public class ExcelUtil<T>
|
|||||||
if (StringUtils.isNotEmpty(name))
|
if (StringUtils.isNotEmpty(name))
|
||||||
{
|
{
|
||||||
Class<?> clazz = o.getClass();
|
Class<?> clazz = o.getClass();
|
||||||
String methodName = "get" + name.substring(0, 1).toUpperCase() + name.substring(1);
|
Field field = clazz.getDeclaredField(name);
|
||||||
Method method = clazz.getMethod(methodName);
|
field.setAccessible(true);
|
||||||
o = method.invoke(o);
|
o = field.get(o);
|
||||||
}
|
}
|
||||||
return o;
|
return o;
|
||||||
}
|
}
|
||||||
@ -896,7 +969,14 @@ public class ExcelUtil<T>
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
val = new BigDecimal(val.toString()); // 浮点格式处理
|
if ((Double) val % 1 > 0)
|
||||||
|
{
|
||||||
|
val = new BigDecimal(val.toString());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
val = new DecimalFormat("0").format(val);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (cell.getCellTypeEnum() == CellType.STRING)
|
else if (cell.getCellTypeEnum() == CellType.STRING)
|
||||||
|
@ -79,11 +79,11 @@ public class DataScopeAspect
|
|||||||
}
|
}
|
||||||
// 获取当前的用户
|
// 获取当前的用户
|
||||||
LoginUser loginUser = SpringUtils.getBean(TokenService.class).getLoginUser(ServletUtils.getRequest());
|
LoginUser loginUser = SpringUtils.getBean(TokenService.class).getLoginUser(ServletUtils.getRequest());
|
||||||
SysUser currentUser = loginUser.getUser();
|
if (StringUtils.isNotNull(loginUser))
|
||||||
if (currentUser != null)
|
|
||||||
{
|
{
|
||||||
|
SysUser currentUser = loginUser.getUser();
|
||||||
// 如果是超级管理员,则不过滤数据
|
// 如果是超级管理员,则不过滤数据
|
||||||
if (!currentUser.isAdmin())
|
if (StringUtils.isNotNull(currentUser) && !currentUser.isAdmin())
|
||||||
{
|
{
|
||||||
dataScopeFilter(joinPoint, currentUser, controllerDataScope.deptAlias(),
|
dataScopeFilter(joinPoint, currentUser, controllerDataScope.deptAlias(),
|
||||||
controllerDataScope.userAlias());
|
controllerDataScope.userAlias());
|
||||||
@ -142,10 +142,14 @@ public class DataScopeAspect
|
|||||||
|
|
||||||
if (StringUtils.isNotBlank(sqlString.toString()))
|
if (StringUtils.isNotBlank(sqlString.toString()))
|
||||||
{
|
{
|
||||||
BaseEntity baseEntity = (BaseEntity) joinPoint.getArgs()[0];
|
Object params = joinPoint.getArgs()[0];
|
||||||
|
if (StringUtils.isNotNull(params) && params instanceof BaseEntity)
|
||||||
|
{
|
||||||
|
BaseEntity baseEntity = (BaseEntity) params;
|
||||||
baseEntity.getParams().put(DATA_SCOPE, " AND (" + sqlString.substring(4) + ")");
|
baseEntity.getParams().put(DATA_SCOPE, " AND (" + sqlString.substring(4) + ")");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 是否存在注解,如果存在就获取
|
* 是否存在注解,如果存在就获取
|
||||||
|
@ -88,7 +88,7 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter
|
|||||||
protected void configure(HttpSecurity httpSecurity) throws Exception
|
protected void configure(HttpSecurity httpSecurity) throws Exception
|
||||||
{
|
{
|
||||||
httpSecurity
|
httpSecurity
|
||||||
// CRSF禁用,因为不使用session
|
// CSRF禁用,因为不使用session
|
||||||
.csrf().disable()
|
.csrf().disable()
|
||||||
// 认证失败处理类
|
// 认证失败处理类
|
||||||
.exceptionHandling().authenticationEntryPoint(unauthorizedHandler).and()
|
.exceptionHandling().authenticationEntryPoint(unauthorizedHandler).and()
|
||||||
|
@ -340,7 +340,7 @@ public class GenTableColumn extends BaseEntity
|
|||||||
public static boolean isUsableColumn(String javaField)
|
public static boolean isUsableColumn(String javaField)
|
||||||
{
|
{
|
||||||
// isSuperColumn()中的名单用于避免生成多余Domain属性,若某些属性在生成页面时需要用到不能忽略,则放在此处白名单
|
// isSuperColumn()中的名单用于避免生成多余Domain属性,若某些属性在生成页面时需要用到不能忽略,则放在此处白名单
|
||||||
return StringUtils.equalsAnyIgnoreCase(javaField, "parentId", "orderNum");
|
return StringUtils.equalsAnyIgnoreCase(javaField, "parentId", "orderNum", "remark");
|
||||||
}
|
}
|
||||||
|
|
||||||
public String readConverterExp()
|
public String readConverterExp()
|
||||||
|
@ -140,7 +140,7 @@
|
|||||||
<el-input v-model="form.${field}" placeholder="请输入${comment}" />
|
<el-input v-model="form.${field}" placeholder="请输入${comment}" />
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
#elseif($column.htmlType == "select" && "" != $dictType)
|
#elseif($column.htmlType == "select" && "" != $dictType)
|
||||||
<el-form-item label="${comment}">
|
<el-form-item label="${comment}" prop="${field}">
|
||||||
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
||||||
<el-option
|
<el-option
|
||||||
v-for="dict in ${field}Options"
|
v-for="dict in ${field}Options"
|
||||||
@ -152,7 +152,7 @@
|
|||||||
</el-select>
|
</el-select>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
#elseif($column.htmlType == "select" && $dictType)
|
#elseif($column.htmlType == "select" && $dictType)
|
||||||
<el-form-item label="${comment}">
|
<el-form-item label="${comment}" prop="${field}">
|
||||||
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
||||||
<el-option label="请选择字典生成" value="" />
|
<el-option label="请选择字典生成" value="" />
|
||||||
</el-select>
|
</el-select>
|
||||||
@ -272,9 +272,8 @@ export default {
|
|||||||
#else
|
#else
|
||||||
#set($comment=$column.columnComment)
|
#set($comment=$column.columnComment)
|
||||||
#end
|
#end
|
||||||
#set($comment=$column.columnComment)
|
|
||||||
$column.javaField: [
|
$column.javaField: [
|
||||||
{ required: true, message: "$comment不能为空", trigger: "blur" }
|
{ required: true, message: "$comment不能为空", trigger: #if($column.htmlType == "select")"change"#else"blur"#end }
|
||||||
]#if($velocityCount != $columns.size()),#end
|
]#if($velocityCount != $columns.size()),#end
|
||||||
|
|
||||||
#end
|
#end
|
||||||
|
@ -169,7 +169,7 @@
|
|||||||
<el-input v-model="form.${field}" placeholder="请输入${comment}" />
|
<el-input v-model="form.${field}" placeholder="请输入${comment}" />
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
#elseif($column.htmlType == "select" && "" != $dictType)
|
#elseif($column.htmlType == "select" && "" != $dictType)
|
||||||
<el-form-item label="${comment}">
|
<el-form-item label="${comment}" prop="${field}">
|
||||||
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
||||||
<el-option
|
<el-option
|
||||||
v-for="dict in ${field}Options"
|
v-for="dict in ${field}Options"
|
||||||
@ -181,7 +181,7 @@
|
|||||||
</el-select>
|
</el-select>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
#elseif($column.htmlType == "select" && $dictType)
|
#elseif($column.htmlType == "select" && $dictType)
|
||||||
<el-form-item label="${comment}">
|
<el-form-item label="${comment}" prop="${field}">
|
||||||
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
<el-select v-model="form.${field}" placeholder="请选择${comment}">
|
||||||
<el-option label="请选择字典生成" value="" />
|
<el-option label="请选择字典生成" value="" />
|
||||||
</el-select>
|
</el-select>
|
||||||
@ -306,9 +306,8 @@ export default {
|
|||||||
#else
|
#else
|
||||||
#set($comment=$column.columnComment)
|
#set($comment=$column.columnComment)
|
||||||
#end
|
#end
|
||||||
#set($comment=$column.columnComment)
|
|
||||||
$column.javaField: [
|
$column.javaField: [
|
||||||
{ required: true, message: "$comment不能为空", trigger: "blur" }
|
{ required: true, message: "$comment不能为空", trigger: #if($column.htmlType == "select")"change"#else"blur"#end }
|
||||||
]#if($velocityCount != $columns.size()),#end
|
]#if($velocityCount != $columns.size()),#end
|
||||||
|
|
||||||
#end
|
#end
|
||||||
|
@ -267,13 +267,7 @@ public class SysDeptServiceImpl implements ISysDeptService
|
|||||||
{
|
{
|
||||||
if (hasChild(list, tChild))
|
if (hasChild(list, tChild))
|
||||||
{
|
{
|
||||||
// 判断是否有子节点
|
recursionFn(list, tChild);
|
||||||
Iterator<SysDept> it = childList.iterator();
|
|
||||||
while (it.hasNext())
|
|
||||||
{
|
|
||||||
SysDept n = (SysDept) it.next();
|
|
||||||
recursionFn(list, n);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -76,12 +76,12 @@ public class SysDictTypeServiceImpl implements ISysDictTypeService
|
|||||||
public List<SysDictData> selectDictDataByType(String dictType)
|
public List<SysDictData> selectDictDataByType(String dictType)
|
||||||
{
|
{
|
||||||
List<SysDictData> dictDatas = DictUtils.getDictCache(dictType);
|
List<SysDictData> dictDatas = DictUtils.getDictCache(dictType);
|
||||||
if (StringUtils.isNotNull(dictDatas))
|
if (StringUtils.isNotEmpty(dictDatas))
|
||||||
{
|
{
|
||||||
return dictDatas;
|
return dictDatas;
|
||||||
}
|
}
|
||||||
dictDatas = dictDataMapper.selectDictDataByType(dictType);
|
dictDatas = dictDataMapper.selectDictDataByType(dictType);
|
||||||
if (StringUtils.isNotNull(dictDatas))
|
if (StringUtils.isNotEmpty(dictDatas))
|
||||||
{
|
{
|
||||||
DictUtils.setDictCache(dictType, dictDatas);
|
DictUtils.setDictCache(dictType, dictDatas);
|
||||||
return dictDatas;
|
return dictDatas;
|
||||||
|
@ -178,14 +178,19 @@ public class SysMenuServiceImpl implements ISysMenuService
|
|||||||
public List<SysMenu> buildMenuTree(List<SysMenu> menus)
|
public List<SysMenu> buildMenuTree(List<SysMenu> menus)
|
||||||
{
|
{
|
||||||
List<SysMenu> returnList = new ArrayList<SysMenu>();
|
List<SysMenu> returnList = new ArrayList<SysMenu>();
|
||||||
|
List<Long> tempList = new ArrayList<Long>();
|
||||||
|
for (SysMenu dept : menus)
|
||||||
|
{
|
||||||
|
tempList.add(dept.getMenuId());
|
||||||
|
}
|
||||||
for (Iterator<SysMenu> iterator = menus.iterator(); iterator.hasNext();)
|
for (Iterator<SysMenu> iterator = menus.iterator(); iterator.hasNext();)
|
||||||
{
|
{
|
||||||
SysMenu t = (SysMenu) iterator.next();
|
SysMenu menu = (SysMenu) iterator.next();
|
||||||
// 根据传入的某个父节点ID,遍历该父节点的所有子节点
|
// 如果是顶级节点, 遍历该父节点的所有子节点
|
||||||
if (t.getParentId() == 0)
|
if (!tempList.contains(menu.getParentId()))
|
||||||
{
|
{
|
||||||
recursionFn(menus, t);
|
recursionFn(menus, menu);
|
||||||
returnList.add(t);
|
returnList.add(menu);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (returnList.isEmpty())
|
if (returnList.isEmpty())
|
||||||
@ -406,13 +411,7 @@ public class SysMenuServiceImpl implements ISysMenuService
|
|||||||
{
|
{
|
||||||
if (hasChild(list, tChild))
|
if (hasChild(list, tChild))
|
||||||
{
|
{
|
||||||
// 判断是否有子节点
|
recursionFn(list, tChild);
|
||||||
Iterator<SysMenu> it = childList.iterator();
|
|
||||||
while (it.hasNext())
|
|
||||||
{
|
|
||||||
SysMenu n = (SysMenu) it.next();
|
|
||||||
recursionFn(list, n);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -86,7 +86,7 @@
|
|||||||
"mockjs": "1.0.1-beta3",
|
"mockjs": "1.0.1-beta3",
|
||||||
"plop": "2.3.0",
|
"plop": "2.3.0",
|
||||||
"runjs": "4.3.2",
|
"runjs": "4.3.2",
|
||||||
"sass": "1.26.10",
|
"node-sass": "4.14.1",
|
||||||
"sass-loader": "8.0.2",
|
"sass-loader": "8.0.2",
|
||||||
"script-ext-html-webpack-plugin": "2.1.3",
|
"script-ext-html-webpack-plugin": "2.1.3",
|
||||||
"script-loader": "0.7.2",
|
"script-loader": "0.7.2",
|
||||||
|
@ -1,36 +1,43 @@
|
|||||||
<template>
|
<template>
|
||||||
<div>
|
<div class="editor" ref="editor" :style="styles"></div>
|
||||||
<!-- 图片上传组件辅助 -->
|
|
||||||
<el-upload
|
|
||||||
class="avatar-uploader quill-img"
|
|
||||||
:action="uploadImgUrl"
|
|
||||||
name="file"
|
|
||||||
:headers="headers"
|
|
||||||
:show-file-list="false"
|
|
||||||
:on-success="quillImgSuccess"
|
|
||||||
:on-error="uploadError"
|
|
||||||
:before-upload="quillImgBefore"
|
|
||||||
accept='.jpg,.jpeg,.png,.gif'
|
|
||||||
></el-upload>
|
|
||||||
|
|
||||||
<!-- 富文本组件 -->
|
|
||||||
<quill-editor
|
|
||||||
class="editor"
|
|
||||||
v-model="content"
|
|
||||||
ref="quillEditor"
|
|
||||||
:options="editorOption"
|
|
||||||
@blur="onEditorBlur($event)"
|
|
||||||
@focus="onEditorFocus($event)"
|
|
||||||
@change="onEditorChange($event)"
|
|
||||||
></quill-editor>
|
|
||||||
</div>
|
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import { getToken } from '@/utils/auth'
|
import Quill from "quill";
|
||||||
|
import "quill/dist/quill.core.css";
|
||||||
|
import "quill/dist/quill.snow.css";
|
||||||
|
import "quill/dist/quill.bubble.css";
|
||||||
|
|
||||||
// 工具栏配置
|
export default {
|
||||||
const toolbarOptions = [
|
name: "Editor",
|
||||||
|
props: {
|
||||||
|
/* 编辑器的内容 */
|
||||||
|
value: {
|
||||||
|
type: String,
|
||||||
|
default: "",
|
||||||
|
},
|
||||||
|
/* 高度 */
|
||||||
|
height: {
|
||||||
|
type: Number,
|
||||||
|
default: null,
|
||||||
|
},
|
||||||
|
/* 最小高度 */
|
||||||
|
minHeight: {
|
||||||
|
type: Number,
|
||||||
|
default: null,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
Quill: null,
|
||||||
|
currentValue: "",
|
||||||
|
options: {
|
||||||
|
theme: "snow",
|
||||||
|
bounds: document.body,
|
||||||
|
debug: "warn",
|
||||||
|
modules: {
|
||||||
|
// 工具栏配置
|
||||||
|
toolbar: [
|
||||||
["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线
|
["bold", "italic", "underline", "strike"], // 加粗 斜体 下划线 删除线
|
||||||
["blockquote", "code-block"], // 引用 代码块
|
["blockquote", "code-block"], // 引用 代码块
|
||||||
[{ list: "ordered" }, { list: "bullet" }], // 有序、无序列表
|
[{ list: "ordered" }, { list: "bullet" }], // 有序、无序列表
|
||||||
@ -41,105 +48,68 @@ const toolbarOptions = [
|
|||||||
[{ align: [] }], // 对齐方式
|
[{ align: [] }], // 对齐方式
|
||||||
["clean"], // 清除文本格式
|
["clean"], // 清除文本格式
|
||||||
["link", "image", "video"] // 链接、图片、视频
|
["link", "image", "video"] // 链接、图片、视频
|
||||||
];
|
],
|
||||||
|
|
||||||
import { quillEditor } from "vue-quill-editor";
|
|
||||||
import "quill/dist/quill.core.css";
|
|
||||||
import "quill/dist/quill.snow.css";
|
|
||||||
import "quill/dist/quill.bubble.css";
|
|
||||||
|
|
||||||
export default {
|
|
||||||
props: {
|
|
||||||
/* 编辑器的内容 */
|
|
||||||
value: {
|
|
||||||
type: String
|
|
||||||
},
|
},
|
||||||
/* 图片大小 */
|
|
||||||
maxSize: {
|
|
||||||
type: Number,
|
|
||||||
default: 4000 //kb
|
|
||||||
}
|
|
||||||
},
|
|
||||||
components: { quillEditor },
|
|
||||||
data() {
|
|
||||||
return {
|
|
||||||
content: this.value,
|
|
||||||
uploadImgUrl: "",
|
|
||||||
editorOption: {
|
|
||||||
theme: "snow", // or 'bubble'
|
|
||||||
placeholder: "请输入内容",
|
placeholder: "请输入内容",
|
||||||
modules: {
|
readOnly: false,
|
||||||
toolbar: {
|
|
||||||
container: toolbarOptions,
|
|
||||||
handlers: {
|
|
||||||
image: function(value) {
|
|
||||||
if (value) {
|
|
||||||
// 触发input框选择图片文件
|
|
||||||
document.querySelector(".quill-img input").click();
|
|
||||||
} else {
|
|
||||||
this.quill.format("image", false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
uploadImgUrl: process.env.VUE_APP_BASE_API + "/common/upload", // 上传的图片服务器地址
|
|
||||||
headers: {
|
|
||||||
Authorization: 'Bearer ' + getToken()
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
watch: {
|
computed: {
|
||||||
value: function() {
|
styles() {
|
||||||
this.content = this.value;
|
let style = {};
|
||||||
|
if (this.minHeight) {
|
||||||
|
style.minHeight = `${this.minHeight}px`;
|
||||||
}
|
}
|
||||||
|
if (this.height) {
|
||||||
|
style.height = `${this.height}px`;
|
||||||
|
}
|
||||||
|
return style;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
watch: {
|
||||||
|
value: {
|
||||||
|
handler(val) {
|
||||||
|
if (val !== this.currentValue) {
|
||||||
|
this.currentValue = val === null ? "" : val;
|
||||||
|
if (this.Quill) {
|
||||||
|
this.Quill.pasteHTML(this.currentValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
immediate: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
this.init();
|
||||||
|
},
|
||||||
|
beforeDestroy() {
|
||||||
|
this.Quill = null;
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
onEditorBlur() {
|
init() {
|
||||||
//失去焦点事件
|
const editor = this.$refs.editor;
|
||||||
|
this.Quill = new Quill(editor, this.options);
|
||||||
|
this.Quill.pasteHTML(this.currentValue);
|
||||||
|
this.Quill.on("text-change", (delta, oldDelta, source) => {
|
||||||
|
const html = this.$refs.editor.children[0].innerHTML;
|
||||||
|
const text = this.Quill.getText();
|
||||||
|
const quill = this.Quill;
|
||||||
|
this.currentValue = html;
|
||||||
|
this.$emit("input", html);
|
||||||
|
this.$emit("on-change", { html, text, quill });
|
||||||
|
});
|
||||||
|
this.Quill.on("text-change", (delta, oldDelta, source) => {
|
||||||
|
this.$emit("on-text-change", delta, oldDelta, source);
|
||||||
|
});
|
||||||
|
this.Quill.on("selection-change", (range, oldRange, source) => {
|
||||||
|
this.$emit("on-selection-change", range, oldRange, source);
|
||||||
|
});
|
||||||
|
this.Quill.on("editor-change", (eventName, ...args) => {
|
||||||
|
this.$emit("on-editor-change", eventName, ...args);
|
||||||
|
});
|
||||||
},
|
},
|
||||||
onEditorFocus() {
|
|
||||||
//获得焦点事件
|
|
||||||
},
|
},
|
||||||
onEditorChange() {
|
|
||||||
//内容改变事件
|
|
||||||
this.$emit("input", this.content);
|
|
||||||
},
|
|
||||||
|
|
||||||
// 富文本图片上传前
|
|
||||||
quillImgBefore(file) {
|
|
||||||
let fileType = file.type;
|
|
||||||
if(fileType === 'image/jpeg' || fileType === 'image/png'){
|
|
||||||
return true;
|
|
||||||
}else {
|
|
||||||
this.$message.error('请插入图片类型文件(jpg/jpeg/png)');
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
quillImgSuccess(res, file) {
|
|
||||||
// res为图片服务器返回的数据
|
|
||||||
// 获取富文本组件实例
|
|
||||||
let quill = this.$refs.quillEditor.quill;
|
|
||||||
// 如果上传成功
|
|
||||||
if (res.code == 200) {
|
|
||||||
// 获取光标所在位置
|
|
||||||
let length = quill.getSelection().index;
|
|
||||||
// 插入图片 res.url为服务器返回的图片地址
|
|
||||||
quill.insertEmbed(length, "image", res.url);
|
|
||||||
// 调整光标到最后
|
|
||||||
quill.setSelection(length + 1);
|
|
||||||
} else {
|
|
||||||
this.$message.error("图片插入失败");
|
|
||||||
}
|
|
||||||
},
|
|
||||||
// 富文本图片上传失败
|
|
||||||
uploadError() {
|
|
||||||
// loading动画消失
|
|
||||||
this.$message.error("图片插入失败");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@ -147,7 +117,6 @@ export default {
|
|||||||
.editor {
|
.editor {
|
||||||
white-space: pre-wrap!important;
|
white-space: pre-wrap!important;
|
||||||
line-height: normal !important;
|
line-height: normal !important;
|
||||||
height: 192px;
|
|
||||||
}
|
}
|
||||||
.quill-img {
|
.quill-img {
|
||||||
display: none;
|
display: none;
|
||||||
|
@ -167,7 +167,7 @@ export default {
|
|||||||
display: inline-block;
|
display: inline-block;
|
||||||
vertical-align: middle;
|
vertical-align: middle;
|
||||||
|
|
||||||
::v-deep .el-input__inner {
|
/deep/ .el-input__inner {
|
||||||
border-radius: 0;
|
border-radius: 0;
|
||||||
border: 0;
|
border: 0;
|
||||||
padding-left: 0;
|
padding-left: 0;
|
||||||
|
@ -82,7 +82,7 @@ export default {
|
|||||||
position: relative;
|
position: relative;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
::v-deep {
|
/deep/ {
|
||||||
.el-scrollbar__bar {
|
.el-scrollbar__bar {
|
||||||
bottom: 0px;
|
bottom: 0px;
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
/**
|
/**
|
||||||
* 通用js方法封装处理
|
* 通用js方法封装处理
|
||||||
* Copyright (c) 2019 ruoyi
|
* Copyright (c) 2019 ruoyi
|
||||||
*/
|
*/
|
||||||
@ -131,7 +131,7 @@ export function handleTree(data, id, parentId, children, rootId) {
|
|||||||
id = id || 'id'
|
id = id || 'id'
|
||||||
parentId = parentId || 'parentId'
|
parentId = parentId || 'parentId'
|
||||||
children = children || 'children'
|
children = children || 'children'
|
||||||
rootId = rootId || 0
|
rootId = rootId || Math.min.apply(Math, data.map(item => { return item[parentId] })) || 0
|
||||||
//对源数据深度克隆
|
//对源数据深度克隆
|
||||||
const cloneData = JSON.parse(JSON.stringify(data))
|
const cloneData = JSON.parse(JSON.stringify(data))
|
||||||
//循环所有项
|
//循环所有项
|
||||||
|
@ -159,12 +159,12 @@
|
|||||||
</el-col>
|
</el-col>
|
||||||
<el-col :span="24">
|
<el-col :span="24">
|
||||||
<el-form-item label="内容">
|
<el-form-item label="内容">
|
||||||
<Editor v-model="form.noticeContent" />
|
<editor v-model="form.noticeContent" :min-height="192"/>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
</el-col>
|
</el-col>
|
||||||
</el-row>
|
</el-row>
|
||||||
</el-form>
|
</el-form>
|
||||||
<div slot="footer" class="dialog-footer" style="padding-top:30px">
|
<div slot="footer" class="dialog-footer">
|
||||||
<el-button type="primary" @click="submitForm">确 定</el-button>
|
<el-button type="primary" @click="submitForm">确 定</el-button>
|
||||||
<el-button @click="cancel">取 消</el-button>
|
<el-button @click="cancel">取 消</el-button>
|
||||||
</div>
|
</div>
|
||||||
|
@ -603,7 +603,7 @@ create table sys_notice (
|
|||||||
notice_id int(4) not null auto_increment comment '公告ID',
|
notice_id int(4) not null auto_increment comment '公告ID',
|
||||||
notice_title varchar(50) not null comment '公告标题',
|
notice_title varchar(50) not null comment '公告标题',
|
||||||
notice_type char(1) not null comment '公告类型(1通知 2公告)',
|
notice_type char(1) not null comment '公告类型(1通知 2公告)',
|
||||||
notice_content varchar(2000) default null comment '公告内容',
|
notice_content longblob default null comment '公告内容',
|
||||||
status char(1) default '0' comment '公告状态(0正常 1关闭)',
|
status char(1) default '0' comment '公告状态(0正常 1关闭)',
|
||||||
create_by varchar(64) default '' comment '创建者',
|
create_by varchar(64) default '' comment '创建者',
|
||||||
create_time datetime comment '创建时间',
|
create_time datetime comment '创建时间',
|
Reference in New Issue
Block a user