Compare commits
17 Commits
Author | SHA1 | Date |
---|---|---|
JerryMa1024 | c32a441994 | |
JerryMa1024 | f2883e8577 | |
JerryMa1024 | 937d384fe6 | |
JerryMa1024 | 4a69e0163a | |
wuy | 7683f78159 | |
wuy | 941fbaf8ac | |
JerryMa1024 | f8970525a8 | |
JerryMa1024 | ab3e7dc7a7 | |
JerryMa1024 | 1ca8c8695e | |
yangzhao635226@163.com | a21baf717c | |
JerryMa1024 | 4af05dc763 | |
JerryMa1024 | fdb2496f10 | |
JerryMa1024 | af0c90cd6e | |
JerryMa1024 | b05d770074 | |
JerryMa1024 | 1c213527ba | |
yangzhao635226@163.com | 12997246d8 | |
yangzhao635226@163.com | 1e71b5024a |
|
@ -1,4 +1,4 @@
|
||||||
> v2.1版本发布,可以告别常规SQL和CRUD了! [B站上手视频](https://www.bilibili.com/video/BV17V411r7Cc) 、 [playground弹药包](https://gitee.com/dibo_software/diboot-v2-example/raw/master/playground.zip)
|
> v2.1版本发布,可以告别常规SQL和CRUD了! [B站上手视频](https://www.bilibili.com/video/BV17V411r7Cc) 、 [playground新手体验包](https://gitee.com/dibo_software/diboot-example/raw/master/playground.zip)
|
||||||
|
|
||||||
# diboot - 化繁为简,以简驭繁
|
# diboot - 化繁为简,以简驭繁
|
||||||
<p align="center">
|
<p align="center">
|
||||||
|
@ -32,7 +32,7 @@ diboot v2版本,目前实现: diboot-core高效内核 + diboot-devtools开发
|
||||||
> JsonResult、字符串处理、常用校验、BeanUtils、DateUtils等
|
> JsonResult、字符串处理、常用校验、BeanUtils、DateUtils等
|
||||||
|
|
||||||
基于diboot-core 2.x版本的CRUD和简单关联的常规功能实现,代码量比传统Mybatis项目减少80%+),且实现更高效更易维护。
|
基于diboot-core 2.x版本的CRUD和简单关联的常规功能实现,代码量比传统Mybatis项目减少80%+),且实现更高效更易维护。
|
||||||
更多介绍请查看: [diboot-core README](https://github.com/dibo-software/diboot-v2/tree/master/diboot-core "注解自动绑定多表关联").
|
更多介绍请查看: [diboot-core README](https://github.com/dibo-software/diboot/tree/master/diboot-core "注解自动绑定多表关联").
|
||||||
|
|
||||||
|
|
||||||
## 二、 diboot-devtools 自动化开发助理
|
## 二、 diboot-devtools 自动化开发助理
|
||||||
|
@ -55,14 +55,14 @@ diboot v2版本,目前实现: diboot-core高效内核 + diboot-devtools开发
|
||||||
* 支持基于注解的数据权限实现
|
* 支持基于注解的数据权限实现
|
||||||
* 支持灵活的扩展能力(扩展多种登录方式、灵活替换用户实体类、自定义缓存等)
|
* 支持灵活的扩展能力(扩展多种登录方式、灵活替换用户实体类、自定义缓存等)
|
||||||
|
|
||||||
更多介绍请查看: [iam-base-starter README](https://github.com/dibo-software/diboot-v2/tree/master/iam-base-starter "身份认证管理组件").
|
更多介绍请查看: [iam-base-starter README](https://github.com/dibo-software/diboot/tree/master/iam-base-starter "身份认证管理组件").
|
||||||
|
|
||||||
## 四、diboot-file 文件相关处理组件
|
## 四、diboot-file 文件相关处理组件
|
||||||
|
|
||||||
* EasyExcel轻量封装,支持Java注解校验与@ExcelBind*注解实现字典及关联字段的name-value转换,并提供完善的校验错误提示
|
* EasyExcel轻量封装,支持Java注解校验与@ExcelBind*注解实现字典及关联字段的name-value转换,并提供完善的校验错误提示
|
||||||
* 封装常用的文件本地存储、上传下载、图片压缩水印等常用处理
|
* 封装常用的文件本地存储、上传下载、图片压缩水印等常用处理
|
||||||
|
|
||||||
更多介绍请查看: [diboot-file-starter README](https://github.com/dibo-software/diboot-v2/tree/master/diboot-file-starter "文件组件").
|
更多介绍请查看: [diboot-file-starter README](https://github.com/dibo-software/diboot/tree/master/diboot-file-starter "文件组件").
|
||||||
|
|
||||||
> 其他组件逐步开发中 ...
|
> 其他组件逐步开发中 ...
|
||||||
|
|
||||||
|
|
|
@ -7,11 +7,11 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-root</artifactId>
|
<artifactId>diboot-root</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
<description>diboot core starter project</description>
|
<description>diboot core starter project</description>
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-core</artifactId>
|
<artifactId>diboot-core</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
|
|
|
@ -159,4 +159,4 @@ spring.datasource.hikari.driver-class-name=com.mysql.cj.jdbc.Driver
|
||||||
|
|
||||||
#### 3. 详细文档 - [diboot-core 官方文档](https://www.diboot.com/guide/diboot-core/%E5%AE%89%E8%A3%85.html)
|
#### 3. 详细文档 - [diboot-core 官方文档](https://www.diboot.com/guide/diboot-core/%E5%AE%89%E8%A3%85.html)
|
||||||
|
|
||||||
#### 4. 参考样例 - [diboot-core-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-core-example)
|
#### 4. 参考样例 - [diboot-core-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-core-example)
|
||||||
|
|
|
@ -7,11 +7,11 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-root</artifactId>
|
<artifactId>diboot-root</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<artifactId>diboot-core</artifactId>
|
<artifactId>diboot-core</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
<description>diboot core project</description>
|
<description>diboot core project</description>
|
||||||
|
|
||||||
|
|
|
@ -141,7 +141,25 @@ public abstract class BaseBinder<T> {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
public BaseBinder<T> andLike(String fieldName, String value){
|
public BaseBinder<T> andLike(String fieldName, String value){
|
||||||
queryWrapper.like(S.toSnakeCase(fieldName), formatValue(fieldName, value));
|
fieldName = S.toSnakeCase(fieldName);
|
||||||
|
value = (String)formatValue(fieldName, value);
|
||||||
|
if(S.startsWith(value, "%")){
|
||||||
|
value = S.substringAfter(value, "%");
|
||||||
|
if(S.endsWith(value, "%")){
|
||||||
|
value = S.substringBeforeLast(value, "%");
|
||||||
|
queryWrapper.like(fieldName, value);
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
queryWrapper.likeLeft(fieldName, value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if(S.endsWith(value, "%")){
|
||||||
|
value = S.substringBeforeLast(value, "%");
|
||||||
|
queryWrapper.likeRight(fieldName, value);
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
queryWrapper.like(fieldName, value);
|
||||||
|
}
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
public BaseBinder<T> andIn(String fieldName, Collection valueList){
|
public BaseBinder<T> andIn(String fieldName, Collection valueList){
|
||||||
|
|
|
@ -163,11 +163,12 @@ public class ConditionManager extends BaseConditionManager{
|
||||||
else if(operator instanceof LikeExpression){
|
else if(operator instanceof LikeExpression){
|
||||||
LikeExpression express = (LikeExpression)operator;
|
LikeExpression express = (LikeExpression)operator;
|
||||||
String annoColumn = removeLeftAlias(express.getLeftExpression().toString());
|
String annoColumn = removeLeftAlias(express.getLeftExpression().toString());
|
||||||
|
String value = express.getRightExpression().toString();
|
||||||
if(express.isNot() == false){
|
if(express.isNot() == false){
|
||||||
binder.andLike(annoColumn, express.getStringExpression());
|
binder.andLike(annoColumn, value);
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
binder.andNotLike(annoColumn, express.getStringExpression());
|
binder.andNotLike(annoColumn, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
|
|
|
@ -154,10 +154,10 @@ public class JoinConditionManager extends BaseConditionManager {
|
||||||
currentSegments = middleTableOnSegments;
|
currentSegments = middleTableOnSegments;
|
||||||
}
|
}
|
||||||
if(expression.isNot() == false){
|
if(expression.isNot() == false){
|
||||||
currentSegments.add(left + " LIKE " + expression.getStringExpression());
|
currentSegments.add(left + " LIKE " + expression.getRightExpression().toString());
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
currentSegments.add(left + " NOT LIKE " + expression.getStringExpression());
|
currentSegments.add(left + " NOT LIKE " + expression.getRightExpression().toString());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
|
|
|
@ -343,13 +343,26 @@ public class BeanUtils {
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
public static <T> List<T> buildTree(List<T> allNodes, Object rootNodeId){
|
public static <T> List<T> buildTree(List<T> allNodes, Object rootNodeId){
|
||||||
|
return buildTree(allNodes, rootNodeId, Cons.FieldName.parentId.name(), Cons.FieldName.children.name());
|
||||||
|
}
|
||||||
|
|
||||||
|
/***
|
||||||
|
* 构建指定根节点的上下级关联的树形结构(上级parentId、子节点children)
|
||||||
|
* @param allNodes 所有节点对象
|
||||||
|
* @param rootNodeId 跟节点ID
|
||||||
|
* @param parentIdFieldName 父节点属性名
|
||||||
|
* @param childrenFieldName 子节点集合属性名
|
||||||
|
* @param <T>
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public static <T> List<T> buildTree(List<T> allNodes, Object rootNodeId, String parentIdFieldName, String childrenFieldName){
|
||||||
if(V.isEmpty(allNodes)){
|
if(V.isEmpty(allNodes)){
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
// 提取所有的top level对象
|
// 提取所有的top level对象
|
||||||
List<T> topLevelModels = new ArrayList();
|
List<T> topLevelModels = new ArrayList();
|
||||||
for(T node : allNodes){
|
for(T node : allNodes){
|
||||||
Object parentId = getProperty(node, Cons.FieldName.parentId.name());
|
Object parentId = getProperty(node, parentIdFieldName);
|
||||||
if(parentId == null || V.fuzzyEqual(parentId, rootNodeId)){
|
if(parentId == null || V.fuzzyEqual(parentId, rootNodeId)){
|
||||||
topLevelModels.add(node);
|
topLevelModels.add(node);
|
||||||
}
|
}
|
||||||
|
@ -364,8 +377,8 @@ public class BeanUtils {
|
||||||
// 遍历第一级节点,并挂载 children 子节点
|
// 遍历第一级节点,并挂载 children 子节点
|
||||||
for(T node : allNodes) {
|
for(T node : allNodes) {
|
||||||
Object nodeId = getProperty(node, Cons.FieldName.id.name());
|
Object nodeId = getProperty(node, Cons.FieldName.id.name());
|
||||||
List<T> children = buildTreeChildren(nodeId, allNodes);
|
List<T> children = buildTreeChildren(nodeId, allNodes, parentIdFieldName, childrenFieldName);
|
||||||
setProperty(node, Cons.FieldName.children.name(), children);
|
setProperty(node, childrenFieldName, children);
|
||||||
}
|
}
|
||||||
return topLevelModels;
|
return topLevelModels;
|
||||||
}
|
}
|
||||||
|
@ -374,12 +387,14 @@ public class BeanUtils {
|
||||||
* 递归构建树节点的子节点
|
* 递归构建树节点的子节点
|
||||||
* @param parentId
|
* @param parentId
|
||||||
* @param nodeList
|
* @param nodeList
|
||||||
|
* @param parentIdFieldName 父节点属性名
|
||||||
|
* @param childrenFieldName 子节点集合属性名
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
private static <T> List<T> buildTreeChildren(Object parentId, List<T> nodeList) {
|
private static <T> List<T> buildTreeChildren(Object parentId, List<T> nodeList, String parentIdFieldName, String childrenFieldName) {
|
||||||
List<T> children = null;
|
List<T> children = null;
|
||||||
for(T node : nodeList) {
|
for(T node : nodeList) {
|
||||||
Object nodeParentId = getProperty(node, Cons.FieldName.parentId.name());
|
Object nodeParentId = getProperty(node, parentIdFieldName);
|
||||||
if(nodeParentId != null && V.equals(nodeParentId, parentId)) {
|
if(nodeParentId != null && V.equals(nodeParentId, parentId)) {
|
||||||
if(children == null){
|
if(children == null){
|
||||||
children = new ArrayList<>();
|
children = new ArrayList<>();
|
||||||
|
@ -390,11 +405,11 @@ public class BeanUtils {
|
||||||
if(children != null){
|
if(children != null){
|
||||||
for(T child : children) {
|
for(T child : children) {
|
||||||
Object nodeId = getProperty(child, Cons.FieldName.id.name());
|
Object nodeId = getProperty(child, Cons.FieldName.id.name());
|
||||||
List<T> childNodeChildren = buildTreeChildren(nodeId, nodeList);
|
List<T> childNodeChildren = buildTreeChildren(nodeId, nodeList, parentIdFieldName, childrenFieldName);
|
||||||
if(childNodeChildren == null) {
|
if(childNodeChildren == null) {
|
||||||
childNodeChildren = new ArrayList<>();
|
childNodeChildren = new ArrayList<>();
|
||||||
}
|
}
|
||||||
setProperty(child, Cons.FieldName.children.name(), childNodeChildren);
|
setProperty(child, childrenFieldName, childNodeChildren);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return children;
|
return children;
|
||||||
|
|
|
@ -258,8 +258,22 @@ public class ContextHelper implements ApplicationContextAware {
|
||||||
}
|
}
|
||||||
if(jdbcUrl == null){
|
if(jdbcUrl == null){
|
||||||
String master = environment.getProperty("spring.datasource.dynamic.primary");
|
String master = environment.getProperty("spring.datasource.dynamic.primary");
|
||||||
|
if(master != null){
|
||||||
jdbcUrl = environment.getProperty("spring.datasource.dynamic.datasource."+master+".url");
|
jdbcUrl = environment.getProperty("spring.datasource.dynamic.datasource."+master+".url");
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
if(jdbcUrl == null){
|
||||||
|
String names = environment.getProperty("spring.shardingsphere.datasource.names");
|
||||||
|
if(names != null){
|
||||||
|
jdbcUrl = environment.getProperty("spring.shardingsphere.datasource."+ names.split(",")[0] +".url");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(jdbcUrl == null){
|
||||||
|
String urlConfigItem = environment.getProperty("diboot.datasource.url.config");
|
||||||
|
if(urlConfigItem != null){
|
||||||
|
jdbcUrl = environment.getProperty(urlConfigItem);
|
||||||
|
}
|
||||||
|
}
|
||||||
return jdbcUrl;
|
return jdbcUrl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -31,7 +31,7 @@ import java.util.List;
|
||||||
@Accessors(chain = true)
|
@Accessors(chain = true)
|
||||||
public class DictionaryVO extends Dictionary {
|
public class DictionaryVO extends Dictionary {
|
||||||
|
|
||||||
@BindEntityList(entity= Dictionary.class, condition="this.type=type AND parent_id>0")
|
@BindEntityList(entity= Dictionary.class, condition="this.type=type AND this.id=parent_id")
|
||||||
private List<Dictionary> children;
|
private List<Dictionary> children;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -112,6 +112,7 @@ public class TestEntityListBinder {
|
||||||
// 查询是否创建成功
|
// 查询是否创建成功
|
||||||
LambdaQueryWrapper<Dictionary> queryWrapper = new LambdaQueryWrapper<>();
|
LambdaQueryWrapper<Dictionary> queryWrapper = new LambdaQueryWrapper<>();
|
||||||
queryWrapper.eq(Dictionary::getType, "GENDER");
|
queryWrapper.eq(Dictionary::getType, "GENDER");
|
||||||
|
queryWrapper.eq(Dictionary::getParentId, 0L);
|
||||||
|
|
||||||
Dictionary dictionary = dictionaryService.getSingleEntity(queryWrapper);
|
Dictionary dictionary = dictionaryService.getSingleEntity(queryWrapper);
|
||||||
DictionaryVO vo = Binder.convertAndBindRelations(dictionary, DictionaryVO.class);
|
DictionaryVO vo = Binder.convertAndBindRelations(dictionary, DictionaryVO.class);
|
||||||
|
|
|
@ -35,7 +35,7 @@ public class EntityBinderVO extends User {
|
||||||
private static final long serialVersionUID = 3526115343377985725L;
|
private static final long serialVersionUID = 3526115343377985725L;
|
||||||
|
|
||||||
// 字段关联,相同条件的entity+condition将合并为一条SQL查询
|
// 字段关联,相同条件的entity+condition将合并为一条SQL查询
|
||||||
@BindEntity(entity= Department.class, condition="this.department_id=id AND parent_id >= 0")
|
@BindEntity(entity= Department.class, condition="this.department_id=id AND name like '发'")
|
||||||
private Department department;
|
private Department department;
|
||||||
|
|
||||||
// 通过中间表关联Entity
|
// 通过中间表关联Entity
|
||||||
|
|
|
@ -312,12 +312,30 @@ public class BaseServiceTest {
|
||||||
List<DictionaryVO> voList = dictionaryService.getViewObjectList(queryWrapper, pagination, DictionaryVO.class);
|
List<DictionaryVO> voList = dictionaryService.getViewObjectList(queryWrapper, pagination, DictionaryVO.class);
|
||||||
Assert.assertTrue(voList.size() == 1);
|
Assert.assertTrue(voList.size() == 1);
|
||||||
Assert.assertTrue(pagination.getTotalPage() >= 2);
|
Assert.assertTrue(pagination.getTotalPage() >= 2);
|
||||||
|
Assert.assertTrue(V.isEmpty(voList.get(0).getChildren()));
|
||||||
|
|
||||||
pagination.setPageIndex(2);
|
pagination.setPageIndex(2);
|
||||||
voList = dictionaryService.getViewObjectList(queryWrapper, pagination, DictionaryVO.class);
|
voList = dictionaryService.getViewObjectList(queryWrapper, pagination, DictionaryVO.class);
|
||||||
Assert.assertTrue(voList.size() == 1);
|
Assert.assertTrue(voList.size() == 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testDictVo(){
|
||||||
|
Dictionary dict = new Dictionary();
|
||||||
|
dict.setParentId(0L);
|
||||||
|
dict.setType("GENDER");
|
||||||
|
dict.setEditable(true);
|
||||||
|
|
||||||
|
QueryWrapper<Dictionary> queryWrapper = QueryBuilder.toQueryWrapper(dict);
|
||||||
|
|
||||||
|
List<DictionaryVO> voList = dictionaryService.getViewObjectList(queryWrapper, null, DictionaryVO.class);
|
||||||
|
Assert.assertTrue(voList.size() == 1);
|
||||||
|
Assert.assertTrue(voList.get(0).getChildren().size() == 2);
|
||||||
|
|
||||||
|
List<KeyValue> keyValues = dictionaryService.getKeyValueList("GENDER");
|
||||||
|
Assert.assertTrue(keyValues.size() == 2);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 测试n-n的批量新建/更新
|
* 测试n-n的批量新建/更新
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -174,6 +174,11 @@ public class BeanUtilsTest {
|
||||||
Assert.assertEquals(list.size(), 1);
|
Assert.assertEquals(list.size(), 1);
|
||||||
Assert.assertEquals(list.get(0).getChildren().size(), 5);
|
Assert.assertEquals(list.get(0).getChildren().size(), 5);
|
||||||
|
|
||||||
|
list = BeanUtils.convertList(dictionaryList, DictionaryVO.class);
|
||||||
|
list = BeanUtils.buildTree(list, 0, "parentId", "children");
|
||||||
|
Assert.assertEquals(list.size(), 1);
|
||||||
|
Assert.assertEquals(list.get(0).getChildren().size(), 5);
|
||||||
|
|
||||||
// 异常数据告警
|
// 异常数据告警
|
||||||
Dictionary dict2 = new Dictionary();
|
Dictionary dict2 = new Dictionary();
|
||||||
dict2.setId(1L);
|
dict2.setId(1L);
|
||||||
|
@ -182,6 +187,7 @@ public class BeanUtilsTest {
|
||||||
list = BeanUtils.convertList(dictionaryList, DictionaryVO.class);
|
list = BeanUtils.convertList(dictionaryList, DictionaryVO.class);
|
||||||
try{
|
try{
|
||||||
list = BeanUtils.buildTree(list);
|
list = BeanUtils.buildTree(list);
|
||||||
|
Assert.assertTrue(false);
|
||||||
}
|
}
|
||||||
catch (Exception e){
|
catch (Exception e){
|
||||||
Assert.assertTrue(e.getMessage().contains("请检查"));
|
Assert.assertTrue(e.getMessage().contains("请检查"));
|
||||||
|
|
|
@ -21,7 +21,9 @@ import diboot.core.test.config.SpringMvcConfig;
|
||||||
import org.junit.Assert;
|
import org.junit.Assert;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.junit.runner.RunWith;
|
import org.junit.runner.RunWith;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.boot.test.context.SpringBootTest;
|
import org.springframework.boot.test.context.SpringBootTest;
|
||||||
|
import org.springframework.core.env.Environment;
|
||||||
import org.springframework.test.context.ContextConfiguration;
|
import org.springframework.test.context.ContextConfiguration;
|
||||||
import org.springframework.test.context.junit4.SpringRunner;
|
import org.springframework.test.context.junit4.SpringRunner;
|
||||||
|
|
||||||
|
@ -36,6 +38,9 @@ import org.springframework.test.context.junit4.SpringRunner;
|
||||||
@SpringBootTest(classes = {StartupApplication.class})
|
@SpringBootTest(classes = {StartupApplication.class})
|
||||||
public class PropertiesTest {
|
public class PropertiesTest {
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private Environment environment;
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testGetString(){
|
public void testGetString(){
|
||||||
String str1 = PropertiesUtils.get("spring.datasource.url");
|
String str1 = PropertiesUtils.get("spring.datasource.url");
|
||||||
|
@ -49,4 +54,23 @@ public class PropertiesTest {
|
||||||
Integer num = PropertiesUtils.getInteger("spring.datasource.hikari.maximum-pool-size");
|
Integer num = PropertiesUtils.getInteger("spring.datasource.hikari.maximum-pool-size");
|
||||||
Assert.assertTrue(num > 0 );
|
Assert.assertTrue(num > 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testDatasourceUrl(){
|
||||||
|
String jdbcUrl = null;
|
||||||
|
if(jdbcUrl == null){
|
||||||
|
String names = environment.getProperty("spring.shardingsphere.datasource.names");
|
||||||
|
if(names != null){
|
||||||
|
jdbcUrl = environment.getProperty("spring.shardingsphere.datasource."+ names.split(",")[0] +".url");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(jdbcUrl == null){
|
||||||
|
String urlConfigItem = environment.getProperty("diboot.datasource.url.config");
|
||||||
|
if(urlConfigItem != null){
|
||||||
|
jdbcUrl = environment.getProperty(urlConfigItem);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
System.out.println(jdbcUrl);
|
||||||
|
Assert.assertTrue(jdbcUrl != null);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
*/
|
*/
|
||||||
package diboot.core.test.util;
|
package diboot.core.test.util;
|
||||||
|
|
||||||
|
import com.diboot.core.entity.Dictionary;
|
||||||
import com.diboot.core.util.S;
|
import com.diboot.core.util.S;
|
||||||
import com.diboot.core.util.V;
|
import com.diboot.core.util.V;
|
||||||
import org.junit.Assert;
|
import org.junit.Assert;
|
||||||
|
@ -85,6 +86,11 @@ public class VTest {
|
||||||
Assert.assertTrue(V.equals(list1, list2));
|
Assert.assertTrue(V.equals(list1, list2));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testValidateBean(){
|
||||||
|
String msg = V.validateBean(new Dictionary());
|
||||||
|
System.out.println(msg);
|
||||||
|
Assert.assertTrue(msg != null);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -156,11 +156,11 @@ module.exports = {
|
||||||
items: [
|
items: [
|
||||||
{
|
{
|
||||||
text: 'Gitee',
|
text: 'Gitee',
|
||||||
link: 'https://gitee.com/dibo_software/diboot-v2'
|
link: 'https://gitee.com/dibo_software/diboot'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
text: 'GitHub',
|
text: 'GitHub',
|
||||||
link: 'https://github.com/dibo-software/diboot-v2'
|
link: 'https://github.com/dibo-software/diboot'
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}/*, {
|
}/*, {
|
||||||
|
|
|
@ -18,7 +18,7 @@ diboot-antd-admin前端基础项目,是一个与diboot其他后端组件构成
|
||||||
|
|
||||||
* 基于开源项目[ant-design-pro-vue](https://github.com/sendya/ant-design-pro-vue);
|
* 基于开源项目[ant-design-pro-vue](https://github.com/sendya/ant-design-pro-vue);
|
||||||
* 在**ant-design-pro-vue**项目基础上,进行精简;
|
* 在**ant-design-pro-vue**项目基础上,进行精简;
|
||||||
* 登录、权限、接口对接上,与diboot-v2相关组件构建的后端应用无缝集成且开箱可用;
|
* 登录、权限、接口对接上,与diboot相关组件构建的后端应用无缝集成且开箱可用;
|
||||||
* 提取CRUD页面相关通用属性与方法到mixins文件中,少写代码,多做事情;
|
* 提取CRUD页面相关通用属性与方法到mixins文件中,少写代码,多做事情;
|
||||||
* 菜单到按钮级别的细粒度权限控制;
|
* 菜单到按钮级别的细粒度权限控制;
|
||||||
* 智能化的权限配置方案;
|
* 智能化的权限配置方案;
|
||||||
|
|
|
@ -54,9 +54,9 @@ devServer: {
|
||||||
执行以下命令启动项目
|
执行以下命令启动项目
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
yarn server
|
yarn serve
|
||||||
# OR
|
# OR
|
||||||
npm run server
|
npm run serve
|
||||||
```
|
```
|
||||||
|
|
||||||
运行完成后,点击命令行提示出的地址,打开页面成功,项目启动就完成了。
|
运行完成后,点击命令行提示出的地址,打开页面成功,项目启动就完成了。
|
||||||
|
|
|
@ -89,7 +89,7 @@ private Organization organization;
|
||||||
@BindEntityList(entity = Department.class, condition="department_id=id")
|
@BindEntityList(entity = Department.class, condition="department_id=id")
|
||||||
private List<Department> departmentList;
|
private List<Department> departmentList;
|
||||||
|
|
||||||
// 关联自身,实现无限极分类等
|
// 关联自身,实现加载子级
|
||||||
@BindEntityList(entity = Department.class, condition = "id=parent_id")
|
@BindEntityList(entity = Department.class, condition = "id=parent_id")
|
||||||
private List<Department> children;
|
private List<Department> children;
|
||||||
```
|
```
|
||||||
|
|
|
@ -13,7 +13,7 @@
|
||||||
4. 跨表Join查询无SQL(QueryWrapper自动构建与查询)
|
4. 跨表Join查询无SQL(QueryWrapper自动构建与查询)
|
||||||
5. BaseService扩展增强,支持常规的单表及关联开发场景接口
|
5. BaseService扩展增强,支持常规的单表及关联开发场景接口
|
||||||
6. 其他常用Service接口、工具类的最佳实践封装
|
6. 其他常用Service接口、工具类的最佳实践封装
|
||||||
7. 提供[diboot-core-starter](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-core-example),简化diboot-core的初始化配置(自动配置、自动创建数据字典表)
|
7. 提供[diboot-core-starter](https://github.com/dibo-software/diboot-example/tree/master/diboot-core-example),简化diboot-core的初始化配置(自动配置、自动创建数据字典表)
|
||||||
|
|
||||||
## diboot-core 使用步骤
|
## diboot-core 使用步骤
|
||||||
### 1. 引入依赖
|
### 1. 引入依赖
|
||||||
|
@ -48,7 +48,7 @@ spring.datasource.hikari.driver-class-name=com.mysql.cj.jdbc.Driver
|
||||||
diboot.core.init-sql=false
|
diboot.core.init-sql=false
|
||||||
~~~
|
~~~
|
||||||
|
|
||||||
### 3. 参考样例 - [diboot-core-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-core-example)
|
### 3. 参考样例 - [diboot-core-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-core-example)
|
||||||
|
|
||||||
> diboot-core的最佳实践:建议自定义自己的Base类,避免直接继承core中的Base类,便于后期扩展。
|
> diboot-core的最佳实践:建议自定义自己的Base类,避免直接继承core中的Base类,便于后期扩展。
|
||||||
启用devtools,可一键生成初始Base类代码到本地。
|
启用devtools,可一键生成初始Base类代码到本地。
|
||||||
|
|
|
@ -157,6 +157,6 @@ diboot-devtools在初次运行中,会自动检测安装以diboot_前缀的数
|
||||||
单独为devtools建立一个专属项目,生成代码路径指向你的项目代码,需要使用devtools时启动这个devtools项目。
|
单独为devtools建立一个专属项目,生成代码路径指向你的项目代码,需要使用devtools时启动这个devtools项目。
|
||||||
|
|
||||||
## 参考样例
|
## 参考样例
|
||||||
devtools使用样例(gradle配置) [diboot-devtools-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-devtools-example)
|
devtools使用样例(gradle配置) [diboot-devtools-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-devtools-example)
|
||||||
|
|
||||||
> 使用过程中遇到问题,可加群交流。
|
> 使用过程中遇到问题,可加群交流。
|
|
@ -18,7 +18,7 @@ diboot-element-admin前端基础项目,是一个与diboot其他后端组件构
|
||||||
|
|
||||||
* 基于开源项目[vue-element-admin](https://panjiachen.github.io/vue-element-admin-site/zh/)的基础模板[vue-admin-template](https://github.com/PanJiaChen/vue-admin-template);
|
* 基于开源项目[vue-element-admin](https://panjiachen.github.io/vue-element-admin-site/zh/)的基础模板[vue-admin-template](https://github.com/PanJiaChen/vue-admin-template);
|
||||||
* 在**vue-admin-template**项目基础上,增加了vue-element-admin具有的多页签、菜单搜索、全屏显示、调整布局大小等功能;
|
* 在**vue-admin-template**项目基础上,增加了vue-element-admin具有的多页签、菜单搜索、全屏显示、调整布局大小等功能;
|
||||||
* 登录、权限、接口对接上,与diboot-v2相关组件构建的后端应用无缝集成且开箱可用;
|
* 登录、权限、接口对接上,与diboot相关组件构建的后端应用无缝集成且开箱可用;
|
||||||
* 提取CRUD页面相关通用属性与方法到mixins文件中,少写代码,多做事情;
|
* 提取CRUD页面相关通用属性与方法到mixins文件中,少写代码,多做事情;
|
||||||
* 菜单到按钮级别的细粒度权限控制;
|
* 菜单到按钮级别的细粒度权限控制;
|
||||||
* 智能化的权限配置方案;
|
* 智能化的权限配置方案;
|
||||||
|
|
|
@ -29,9 +29,9 @@ npm install
|
||||||
执行以下命令启动项目
|
执行以下命令启动项目
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
yarn server
|
yarn serve
|
||||||
# OR
|
# OR
|
||||||
npm run server
|
npm run serve
|
||||||
```
|
```
|
||||||
|
|
||||||
运行完成后,点击命令行提示出的地址,打开页面成功,项目启动就完成了。
|
运行完成后,点击命令行提示出的地址,打开页面成功,项目启动就完成了。
|
||||||
|
|
|
@ -163,6 +163,6 @@ ZipHelper.zipFile(String srcRootDir, File file, ZipOutputStream zos, String... m
|
||||||
~~~
|
~~~
|
||||||
|
|
||||||
|
|
||||||
## 4 样例参考 - [diboot-file-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-file-example)
|
## 4 样例参考 - [diboot-file-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-file-example)
|
||||||
|
|
||||||
> 使用过程中遇到问题,可加群交流。
|
> 使用过程中遇到问题,可加群交流。
|
|
@ -18,6 +18,8 @@ compile("com.diboot:diboot-iam-base-spring-boot-starter:{latestVersion}")
|
||||||
|
|
||||||
> 如果使用diboot-devtools,还需要引入devtools相关依赖,可一键生成iam-base相关的controller。
|
> 如果使用diboot-devtools,还需要引入devtools相关依赖,可一键生成iam-base相关的controller。
|
||||||
|
|
||||||
|
注: iam初始化的账号密码为: admin/123456 ,启动成功后请及时修改密码。
|
||||||
|
|
||||||
## 2、参数配置:
|
## 2、参数配置:
|
||||||
|
|
||||||
* 注解配置:
|
* 注解配置:
|
||||||
|
@ -108,6 +110,6 @@ BaseLoginUser loginUser = IamSecurityUtils.getCurrentUser();
|
||||||
// 转型
|
// 转型
|
||||||
~~~
|
~~~
|
||||||
|
|
||||||
## 6、样例参考 - [diboot-iam-example](https://github.com/dibo-software/diboot-v2-example/diboot-iam-example)
|
## 6、样例参考 - [diboot-iam-example](https://github.com/dibo-software/diboot-example/diboot-iam-example)
|
||||||
|
|
||||||
> 使用过程中遇到问题,可加群交流。
|
> 使用过程中遇到问题,可加群交流。
|
|
@ -10,25 +10,44 @@ MyAuthCredential credential = new MyAuthCredential();
|
||||||
String authtoken = AuthServiceFactory.getAuthService("WX_CP").applyToken(credential);
|
String authtoken = AuthServiceFactory.getAuthService("WX_CP").applyToken(credential);
|
||||||
~~~
|
~~~
|
||||||
|
|
||||||
## 2、替换用户类型
|
## 2、替换用户类型或扩展多种用户类型
|
||||||
默认的用户实体为IamUser,获取当前登录用户对象:
|
默认的用户实体为IamUser,获取当前登录用户对象:
|
||||||
~~~java
|
~~~java
|
||||||
IamUser currentUser = IamSecurityUtils.getCurrentUser();
|
IamUser currentUser = IamSecurityUtils.getCurrentUser();
|
||||||
~~~
|
~~~
|
||||||
如果预置属性如果不能满足业务场景需要,可替换用户为你的实体:
|
如果预置属性如果不能满足业务场景需要,可替换用户为你的实体:
|
||||||
|
* 首先在登录的方法中,生成token前传入当前用户类型:
|
||||||
|
(如果有多种用户类型共用登录接口,可以从前端登录页传入"用户类型值")
|
||||||
~~~java
|
~~~java
|
||||||
MyAuthCredential credential = new MyAuthCredential();
|
MyAuthCredential credential = new MyAuthCredential();
|
||||||
credential.setUserTypeClass(Employee.class); // 替换用户类型为自定义
|
credential.setUserTypeClass(Employee.class); // 用户类型为自定义
|
||||||
String authtoken = AuthServiceFactory.getAuthService("WX_CP").applyToken(credential);
|
String authtoken = AuthServiceFactory.getAuthService("WX_CP").applyToken(credential);
|
||||||
~~~
|
~~~
|
||||||
获取用户对象改为:
|
获取用户对象相关代码改为:
|
||||||
~~~java
|
~~~java
|
||||||
Employee currentUser = IamSecurityUtils.getCurrentUser();
|
Employee currentUser = IamSecurityUtils.getCurrentUser();
|
||||||
~~~
|
~~~
|
||||||
|
或多种用户:
|
||||||
|
~~~java
|
||||||
|
// 获取当前登录用户抽象对象
|
||||||
|
BaseLoginUser currentUser = IamSecurityUtils.getCurrentUser();
|
||||||
|
// 查询用户角色
|
||||||
|
IamRoleVO roleVO = null;
|
||||||
|
if(currentUser instanceof IamUser){
|
||||||
|
IamUser user = (IamUser) currentUser;
|
||||||
|
// 角色权限数据
|
||||||
|
roleVO = iamUserService.buildRoleVo4FrontEnd(user);
|
||||||
|
}
|
||||||
|
else if(currentUser instanceof Employee){
|
||||||
|
List<IamRoleVO> roleVOList = iamUserRoleService.getAllRoleVOList(currentUser);
|
||||||
|
roleVO = IamHelper.buildRoleVo4FrontEnd(roleVOList);
|
||||||
|
}
|
||||||
|
...
|
||||||
|
~~~
|
||||||
|
|
||||||
## 3、替换缓存Manager
|
## 3、替换缓存Manager
|
||||||
组件默认缓存类为shiro的内存缓存实现:MemoryConstrainedCacheManager,如果需要替换为redis等自定义缓存,
|
组件默认缓存类为shiro的内存缓存实现:MemoryConstrainedCacheManager,如果需要替换为redis等自定义缓存,
|
||||||
需要创建缓存实现类实现CacheManager接口,并配置参数diboot.iam.cache-manager-class为你的缓存类。
|
需要创建缓存实现类实现CacheManager接口 (可以参考MemoryConstrainedCacheManager的源码),并配置参数diboot.iam.cache-manager-class为你的缓存类。
|
||||||
```
|
```
|
||||||
diboot.iam.cache-manager-class=com.xxx.MyCacheManager
|
diboot.iam.cache-manager-class=com.xxx.MyCacheManager
|
||||||
```
|
```
|
||||||
|
|
|
@ -10,7 +10,7 @@ IAM的后端基础代码由devtools自动生成
|
||||||
* 启动项目,进入devtools的组件初始化页面,选择core及IAM等组件,执行初始化
|
* 启动项目,进入devtools的组件初始化页面,选择core及IAM等组件,执行初始化
|
||||||
* devtools将生成IAM基础的代码到你配置的路径下
|
* devtools将生成IAM基础的代码到你配置的路径下
|
||||||
|
|
||||||
注:[diboot-v2-example](https://github.com/dibo-software/diboot-v2-example) 中包含可供参考的后端示例:diboot-iam-example(IAM示例代码)
|
注:[diboot-example](https://github.com/dibo-software/diboot-example) 中包含可供参考的后端示例:diboot-iam-example(IAM示例代码)
|
||||||
及diboot-online-demo(线上演示项目)。
|
及diboot-online-demo(线上演示项目)。
|
||||||
|
|
||||||
## 如何自定义fastjson配置
|
## 如何自定义fastjson配置
|
||||||
|
@ -176,7 +176,7 @@ public class BaseCustomServiceImpl<M extends BaseCrudMapper<T>, T> extends BaseS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
~~~
|
~~~
|
||||||
## 如何解决数据库无法自动设置更新时间?
|
## 如何解决数据库无法自动设置更新时间
|
||||||
* 通过Mybatis-plus的MetaObjectHandler接口自动填充,示例:
|
* 通过Mybatis-plus的MetaObjectHandler接口自动填充,示例:
|
||||||
~~~java
|
~~~java
|
||||||
@Component
|
@Component
|
||||||
|
@ -187,5 +187,10 @@ public class FillMetaObjectHandler implements MetaObjectHandler {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
~~~
|
~~~
|
||||||
|
## 如何解决无法访问的swagger的问题
|
||||||
|
* 需要设置swagger相关的匿名配置,如下:
|
||||||
|
~~~java
|
||||||
|
diboot.iam.anon-urls=/swagger-ui.html,/swagger-resources/**,/webjars/springfox-swagger-ui/**,/v2/api-docs/**
|
||||||
|
~~~
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -488,7 +488,7 @@ attachMoreList: [
|
||||||
* 更新 *element-ui* 依赖:
|
* 更新 *element-ui* 依赖:
|
||||||
```json
|
```json
|
||||||
{
|
{
|
||||||
"ant-design-vue": "2.13.2"
|
"element-ui": "2.13.2"
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
|
@ -138,6 +138,6 @@ diboot-file组件有以下一个配置项,用于设置本地文件的存储起
|
||||||
files.storage.directory=/myfile
|
files.storage.directory=/myfile
|
||||||
~~~
|
~~~
|
||||||
|
|
||||||
## 样例参考 - [diboot-file-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-file-example)
|
## 样例参考 - [diboot-file-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-file-example)
|
||||||
|
|
||||||
> 使用过程中遇到问题,可加群交流。
|
> 使用过程中遇到问题,可加群交流。
|
|
@ -7,11 +7,11 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>diboot-root</artifactId>
|
<artifactId>diboot-root</artifactId>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<artifactId>diboot-file-spring-boot-starter</artifactId>
|
<artifactId>diboot-file-spring-boot-starter</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
<description>diboot file component project</description>
|
<description>diboot file component project</description>
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<!-- 文件上传 -->
|
<!-- 文件上传 -->
|
||||||
|
|
|
@ -89,6 +89,6 @@ diboot.iam.enable-permission-check=true
|
||||||
diboot.iam.cache-manager-class=org.apache.shiro.cache.MemoryConstrainedCacheManager
|
diboot.iam.cache-manager-class=org.apache.shiro.cache.MemoryConstrainedCacheManager
|
||||||
```
|
```
|
||||||
|
|
||||||
## 7、样例参考 - [diboot-iam-example](https://github.com/dibo-software/diboot-v2-example/tree/master/diboot-iam-example)
|
## 7、样例参考 - [diboot-iam-example](https://github.com/dibo-software/diboot-example/tree/master/diboot-iam-example)
|
||||||
|
|
||||||
> 使用过程中遇到问题,可加群交流。
|
> 使用过程中遇到问题,可加群交流。
|
|
@ -7,11 +7,11 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-root</artifactId>
|
<artifactId>diboot-root</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<artifactId>diboot-iam-base-spring-boot-starter</artifactId>
|
<artifactId>diboot-iam-base-spring-boot-starter</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
<description>diboot IAM base project</description>
|
<description>diboot IAM base project</description>
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.diboot</groupId>
|
<groupId>com.diboot</groupId>
|
||||||
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
<artifactId>diboot-core-spring-boot-starter</artifactId>
|
||||||
<version>2.1.1</version>
|
<version>2.1.2</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.squareup.okhttp3</groupId>
|
<groupId>com.squareup.okhttp3</groupId>
|
||||||
|
|
|
@ -19,6 +19,7 @@ import com.diboot.core.vo.KeyValue;
|
||||||
import com.diboot.iam.entity.IamRole;
|
import com.diboot.iam.entity.IamRole;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* IAM扩展接口
|
* IAM扩展接口
|
||||||
|
@ -32,9 +33,10 @@ public interface IamExtensible {
|
||||||
* 获取用户扩展对象 (如当前岗位)
|
* 获取用户扩展对象 (如当前岗位)
|
||||||
* @param userType
|
* @param userType
|
||||||
* @param userId
|
* @param userId
|
||||||
|
* @param extObj 登录扩展信息
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
KeyValue getUserExtentionObj(String userType, Long userId);
|
KeyValue getUserExtentionObj(String userType, Long userId, Map<String, Object> extObj);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取可扩展的角色
|
* 获取可扩展的角色
|
||||||
|
|
|
@ -130,8 +130,10 @@ public class PwdAuthServiceImpl implements AuthService {
|
||||||
private BaseJwtAuthToken initBaseJwtAuthToken(AuthCredential credential){
|
private BaseJwtAuthToken initBaseJwtAuthToken(AuthCredential credential){
|
||||||
BaseJwtAuthToken token = new BaseJwtAuthToken(getAuthType(), credential.getUserTypeClass());
|
BaseJwtAuthToken token = new BaseJwtAuthToken(getAuthType(), credential.getUserTypeClass());
|
||||||
// 设置账号密码
|
// 设置账号密码
|
||||||
token.setAuthAccount(credential.getAuthAccount()).setAuthSecret(credential.getAuthSecret());
|
token.setAuthAccount(credential.getAuthAccount())
|
||||||
token.setRememberMe(credential.isRememberMe());
|
.setAuthSecret(credential.getAuthSecret())
|
||||||
|
.setRememberMe(credential.isRememberMe())
|
||||||
|
.setExtObj(credential.getExtObj());
|
||||||
// 生成token
|
// 生成token
|
||||||
return token.generateAuthtoken(getExpiresInMinutes());
|
return token.generateAuthtoken(getExpiresInMinutes());
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,6 +22,7 @@ import lombok.experimental.Accessors;
|
||||||
|
|
||||||
import javax.validation.constraints.NotNull;
|
import javax.validation.constraints.NotNull;
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 登录凭证
|
* 登录凭证
|
||||||
|
@ -50,6 +51,12 @@ public abstract class AuthCredential implements Serializable {
|
||||||
* 记住我
|
* 记住我
|
||||||
*/
|
*/
|
||||||
private boolean rememberMe;
|
private boolean rememberMe;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 扩展属性
|
||||||
|
*/
|
||||||
|
private Map<String, Object> extObj;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 账号
|
* 账号
|
||||||
* @return
|
* @return
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
*/
|
*/
|
||||||
package com.diboot.iam.jwt;
|
package com.diboot.iam.jwt;
|
||||||
|
|
||||||
|
import com.diboot.core.vo.KeyValue;
|
||||||
import com.diboot.iam.config.Cons;
|
import com.diboot.iam.config.Cons;
|
||||||
import com.diboot.iam.entity.IamUser;
|
import com.diboot.iam.entity.IamUser;
|
||||||
import com.diboot.iam.util.JwtUtils;
|
import com.diboot.iam.util.JwtUtils;
|
||||||
|
@ -24,6 +25,8 @@ import lombok.experimental.Accessors;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.apache.shiro.authc.RememberMeAuthenticationToken;
|
import org.apache.shiro.authc.RememberMeAuthenticationToken;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Yangzhao
|
* @author Yangzhao
|
||||||
* @version v2.0
|
* @version v2.0
|
||||||
|
@ -55,6 +58,11 @@ public class BaseJwtAuthToken implements RememberMeAuthenticationToken {
|
||||||
*/
|
*/
|
||||||
private boolean rememberMe;
|
private boolean rememberMe;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 扩展属性
|
||||||
|
*/
|
||||||
|
private Map<String, Object> extObj;
|
||||||
|
|
||||||
/**authz token*/
|
/**authz token*/
|
||||||
private String authtoken;
|
private String authtoken;
|
||||||
|
|
||||||
|
@ -96,6 +104,8 @@ public class BaseJwtAuthToken implements RememberMeAuthenticationToken {
|
||||||
return userTypeClass.getSimpleName();
|
return userTypeClass.getSimpleName();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 生成token
|
* 生成token
|
||||||
* @param expiresInMinutes
|
* @param expiresInMinutes
|
||||||
|
|
|
@ -107,7 +107,7 @@ public class BaseJwtRealm extends AuthorizingRealm {
|
||||||
throw new AuthenticationException("用户不存在");
|
throw new AuthenticationException("用户不存在");
|
||||||
}
|
}
|
||||||
if(iamUserRoleService.getIamExtensible() != null){
|
if(iamUserRoleService.getIamExtensible() != null){
|
||||||
KeyValue extentionObj = iamUserRoleService.getIamExtensible().getUserExtentionObj(jwtToken.getUserTypeClass().getSimpleName(), account.getUserId());
|
KeyValue extentionObj = iamUserRoleService.getIamExtensible().getUserExtentionObj(jwtToken.getUserTypeClass().getSimpleName(), account.getUserId(), jwtToken.getExtObj());
|
||||||
if(extentionObj != null){
|
if(extentionObj != null){
|
||||||
loginUser.setExtentionObj(extentionObj);
|
loginUser.setExtentionObj(extentionObj);
|
||||||
}
|
}
|
||||||
|
|
|
@ -71,9 +71,9 @@ public class IamBaseAutoConfig {
|
||||||
*
|
*
|
||||||
* @return
|
* @return
|
||||||
*/
|
*/
|
||||||
@Bean
|
@Bean(name = "shiroCacheManager")
|
||||||
@ConditionalOnMissingBean(CacheManager.class)
|
@ConditionalOnMissingBean(CacheManager.class)
|
||||||
public CacheManager cacheManager() {
|
public CacheManager shiroCacheManager() {
|
||||||
String className = iamBaseProperties.getCacheManagerClass();
|
String className = iamBaseProperties.getCacheManagerClass();
|
||||||
if (V.isEmpty(className)) {
|
if (V.isEmpty(className)) {
|
||||||
return null;
|
return null;
|
||||||
|
@ -87,10 +87,10 @@ public class IamBaseAutoConfig {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Bean
|
@Bean
|
||||||
@DependsOn({"cacheManager"})
|
@DependsOn({"shiroCacheManager"})
|
||||||
public Realm realm() {
|
public Realm realm() {
|
||||||
BaseJwtRealm realm = new BaseJwtRealm();
|
BaseJwtRealm realm = new BaseJwtRealm();
|
||||||
CacheManager cacheManager = cacheManager();
|
CacheManager cacheManager = shiroCacheManager();
|
||||||
if (cacheManager != null) {
|
if (cacheManager != null) {
|
||||||
realm.setCachingEnabled(true);
|
realm.setCachingEnabled(true);
|
||||||
realm.setCacheManager(cacheManager);
|
realm.setCacheManager(cacheManager);
|
||||||
|
|
Loading…
Reference in New Issue