Browse Source

update

main
wangshaoping 11 months ago
parent
commit
8e11dbedd2
  1. 131
      io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/function/ArithmeticFunction.java
  2. 31
      io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/po/lib/processor/ArithmeticIndicatorProcessor.java
  3. 31
      io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/po/model/processor/ArithmeticParameterProcessor.java
  4. 5
      io.sc.engine.rule.frontend/.browserslistrc
  5. 14
      io.sc.engine.rule.frontend/.editorconfig
  6. 36
      io.sc.engine.rule.frontend/.eslintrc.cjs
  7. 31
      io.sc.engine.rule.frontend/.gitignore
  8. 0
      io.sc.engine.rule.frontend/.npmignore
  9. 11
      io.sc.engine.rule.frontend/.npmrc
  10. 3
      io.sc.engine.rule.frontend/.prettierignore
  11. 8
      io.sc.engine.rule.frontend/.prettierrc.json
  12. BIN
      io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/assets/iconfont/Anton-Regular.ttf
  13. 2700
      io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/assets/iconfont/demo_index.html
  14. BIN
      io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/css/arrow-down.png
  15. 5
      io.sc.engine.rule.frontend/src/App.vue
  16. 4
      io.sc.engine.rule.frontend/src/views/authorization/Authorization.vue
  17. 83
      io.sc.engine.rule.frontend/src/views/resources/AttachmentDialog.vue
  18. 58
      io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/lib/entity/processor/ArithmeticIndicatorProcessorEntity.java
  19. 26
      io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/lib/vo/processor/ArithmeticIndicatorProcessorVo.java
  20. 33
      io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/migration/support/AllInOne.java
  21. 57
      io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/model/entity/processor/ArithmeticParameterProcessorEntity.java
  22. 26
      io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/model/vo/processor/ArithmeticParameterProcessorVo.java
  23. 66
      io.sc.platform.attachment.api/src/main/java/io/sc/platform/attachment/api/AttachmentVo.java
  24. 60
      io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/controller/AttachmentWebController.java
  25. 118
      io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/jpa/entity/AttachmentEntity.java
  26. 18
      io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/jpa/repository/AttachmentRepository.java
  27. 52
      io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/service/AttachmentService.java
  28. 116
      io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/service/impl/AttachmentServiceImpl.java
  29. 2
      io.sc.platform.orm/src/main/java/io/sc/platform/orm/entity/AuditorEntity.java

131
io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/function/ArithmeticFunction.java

@ -0,0 +1,131 @@
package io.sc.engine.rule.core.function;
import java.math.BigDecimal;
import java.util.Random;
/**
* 算数函数
* @author wangshaoping
*
*/
public class ArithmeticFunction {
/**
* 获取一个 range 范围内的随机整数
* @param range 随机数范围
* @return 随机数
*/
public static int randomInt(int range) {
Random random =new Random();
return random.nextInt(range);
}
/**
* 求最大可比较值
* @param <T> 参数类型
* @param numbers 参数列表
* @return 最大可比较值
*/
@SafeVarargs
public static <T extends Comparable<T>> T max(T... numbers) {
T max =null;
if(numbers!=null) {
for(T number : numbers) {
if(number!=null) {
if(max!=null) {if(number.compareTo(max)>0) {max =number;} }else {max =number;}
}
}
}
return max;
}
/**
* 求最小可比较值
* @param <T> 参数类型
* @param numbers 参数列表
* @return 最小可比较值
*/
@SafeVarargs
public static <T extends Comparable<T>> T min(T... numbers) {
T min =null;
if(numbers!=null) {
for(T number : numbers) {
if(number!=null) {
if(min!=null) {if(number.compareTo(min)<0) {min =number;} }else {min =number;}
}
}
}
return min;
}
/**
* 整数求和
* @param numbers 其他参数列表
* @return
*/
public static Integer sum(Integer... numbers) {
Integer sum =null;
if(numbers!=null) {
for(Integer number : numbers) {
if(number!=null) {
if(sum!=null) { sum +=number;}else {sum =number;}
}
}
}
return sum;
}
/**
* 小数求和
* @param numbers 其他参数列表
* @return
*/
public static Long sum(Long... numbers) {
Long sum =null;
if(numbers!=null) {
for(Long number : numbers) {
if(number!=null) {
if(sum!=null) { sum +=number;}else {sum =number;}
}
}
}
return sum;
}
/**
* 小数求和
* @param numbers 其他参数列表
* @return
*/
public static Double sum(Double... numbers) {
Double sum =null;
if(numbers!=null) {
for(Double number : numbers) {
if(number!=null) {
if(sum!=null) { sum +=number;}else {sum =number;}
}
}
}
return sum;
}
/**
* 小数求和
* @param numbers 其他参数列表
* @return
*/
public static BigDecimal sum(BigDecimal... numbers) {
BigDecimal sum =null;
if(numbers!=null) {
for(BigDecimal number : numbers) {
if(number!=null) {
if(sum!=null) { sum=sum.add(number);}else {sum =number;}
}
}
}
return sum;
}
public static Double transformSequencing(Double value,Double sourceMin,Double sourceMax,Double targetMin,Double targetMax) {
return targetMin + ((value-sourceMin)/(sourceMax-sourceMin))*(targetMax-targetMin);
}
}

31
io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/po/lib/processor/ArithmeticIndicatorProcessor.java

@ -0,0 +1,31 @@
package io.sc.engine.rule.core.po.lib.processor;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.core.po.lib.IndicatorProcessor;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonTypeName;
/**
* 指标处理器算数运算操作
* @author wangshaoping
*
*/
@JsonTypeName("ARITHMETIC")
@JsonIgnoreProperties(ignoreUnknown=true)
public class ArithmeticIndicatorProcessor extends IndicatorProcessor {
private String arithmetic;//算数表达式
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
}

31
io.sc.engine.rule.core/src/main/java/io/sc/engine/rule/core/po/model/processor/ArithmeticParameterProcessor.java

@ -0,0 +1,31 @@
package io.sc.engine.rule.core.po.model.processor;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.core.po.model.ParameterProcessor;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonTypeName;
/**
* 模型参数处理器算数运算操作
* @author wangshaoping
*
*/
@JsonTypeName("ARITHMETIC")
@JsonIgnoreProperties(ignoreUnknown=true)
public class ArithmeticParameterProcessor extends ParameterProcessor {
private String arithmetic;//算数表达式
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
}

5
io.sc.engine.rule.frontend/.browserslistrc

@ -0,0 +1,5 @@
chrome >=89
edge >=88
firefox >=89
safari >=15
ios_saf >=15

14
io.sc.engine.rule.frontend/.editorconfig

@ -0,0 +1,14 @@
#################################################################
# 强制对使用该基本代码的所有人实施一致的编码样式
#################################################################
# 顶级配置(即不集成父配置)
root = true
# 针对所有文件
[*]
charset = utf-8 # 字符集: utf-8
indent_size = 2 # 缩进大小: 2
indent_style = space # 缩进风格: 空格
insert_final_newline = true # 是否在文件的最后插入一个空行
trim_trailing_whitespace = true # 是否删除行尾的空格

36
io.sc.engine.rule.frontend/.eslintrc.cjs

@ -0,0 +1,36 @@
module.exports = {
root: true,
env: {
browser: true,
es2022: true,
"vue/setup-compiler-macros": true,
},
parserOptions:{
ecmaVersion: 2022,
sourceType:"module",
},
extends:[
"eslint:recommended",
"plugin:vue/vue3-recommended",
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended",
],
parser: "vue-eslint-parser",
parserOptions: {
ecmaVersion: 2022,
parser: "@typescript-eslint/parser",
sourceType: "module",
},
rules:{
'semi':[1],
'@typescript-eslint/no-var-requires': 'off',
'@typescript-eslint/no-explicit-any': 'off',
"@typescript-eslint/no-unused-vars": 'off',
'vue/multi-word-component-names': 'off', /* 禁用 vue 组件名称检查规则 */
},
};

31
io.sc.engine.rule.frontend/.gitignore

@ -0,0 +1,31 @@
# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
pnpm-debug.log*
lerna-debug.log*
node_modules
.DS_Store
dist
dist-ssr
coverage
*.local
/cypress/videos/
/cypress/screenshots/
# Editor directories and files
.vscode/*
!.vscode/extensions.json
.idea
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw?
test-results/
playwright-report/

0
io.sc.engine.rule.frontend/.npmignore

11
io.sc.engine.rule.frontend/.npmrc

@ -0,0 +1,11 @@
# npm 仓库地址, 在 npm install 时使用
registry=http://nexus.sc.io:8000/repository/npm-public/
# 用户邮箱
email=
# 注意: 以下 // 不是注释,不能去掉哦
# 登录 npm 仓库的用户认证信息, 在 npm publish 时使用, publish 的 npm registry 在 package.json 文件中 publishConfig 部分配置
# _authToken 可通过以下命令获取
# curl -X PUT -H "Content-Type:application/json" -d '{"_id":"org.couchdb.user:admin","name":"admin","password":"admin"}' http://nexus.sc.io:8000/repository/npm-releases/-/user/org.couchdb.user:admin
//nexus.sc.io:8000/repository/npm-releases/:_authToken=NpmToken.193db44c-7ca5-3cb6-a990-d24b93fb0d10

3
io.sc.engine.rule.frontend/.prettierignore

@ -0,0 +1,3 @@
build
dist
node_modules

8
io.sc.engine.rule.frontend/.prettierrc.json

@ -0,0 +1,8 @@
{
"$schema": "https://json.schemastore.org/prettierrc",
"semi": true,
"tabWidth": 2,
"singleQuote": true,
"printWidth": 160,
"trailingComma": "all"
}

BIN
io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/assets/iconfont/Anton-Regular.ttf

Binary file not shown.

2700
io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/assets/iconfont/demo_index.html

File diff suppressed because it is too large

BIN
io.sc.engine.rule.frontend/public/webjars/luckysheet/2.1.13/css/arrow-down.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 85 B

5
io.sc.engine.rule.frontend/src/App.vue

@ -0,0 +1,5 @@
<template>
<w-platform-page></w-platform-page>
</template>
<script setup lang="ts"></script>

4
io.sc.engine.rule.frontend/src/views/authorization/Authorization.vue

@ -0,0 +1,4 @@
<template>
<div>authorization</div>
</template>
<script setup lang="ts"></script>

83
io.sc.engine.rule.frontend/src/views/resources/AttachmentDialog.vue

@ -0,0 +1,83 @@
<template>
<w-dialog ref="dialogRef" :title="$t('re.resources.dialog.attachment.title')" width="900px" height="500px" :can-maximize="false">
<div class="px-2">
<w-grid
ref="gridRef"
:title="$t('re.resources.dialog.attachment.grid.title')"
selection="multiple"
:full-screen-button="false"
:toolbar-configure="{ noIcon: false }"
:toolbar-actions="[
'refresh',
'add',
'remove',
{
name: 'download',
label: $t('download'),
},
]"
:query-form-fields="[]"
:auto-fetch-data="false"
:fetch-data-url="fetchDataUrl + '?' + foreignKey + '=' + foreignValue"
:data-url="dataUrl"
:columns="[
{ width: 120, name: 'id', label: $t('id'), hidden: true },
{ width: 200, name: 'name', label: $t('name') },
{ width: '100%', name: 'description', label: $t('description') },
{ width: 100, name: 'lastModifier', label: $t('lastModifier') },
{ width: 120, name: 'lastModifyDate', label: $t('lastModifyDate'), format: Formater.dateOnly() },
]"
:editor="{
dialog: {
width: '600px',
height: '300px',
},
form: {
colsNum: 1,
fields: [
{ name: 'bussinessKey', label: $t('bussinessKey'), type: 'text', defaultValue: foreignValue, hidden: true },
{ name: 'name', label: $t('re.resources.grid.entity.name'), type: 'text', required: true },
{ name: 'description', label: $t('re.resources.grid.entity.description'), type: 'text' },
{ name: 'file', label: $t('re.resources.dialog.attachment.grid.entity.file'), type: 'file' },
],
},
}"
></w-grid>
</div>
</w-dialog>
</template>
<script setup lang="ts">
import { ref, nextTick } from 'vue';
import { useI18n } from 'vue-i18n';
import { Environment, Tools, EnumTools, Options, Formater } from 'platform-core';
const props = defineProps({
opener: { type: Object, default: undefined },
fetchDataUrl: { type: String, default: '' },
dataUrl: { type: String, default: '' },
foreignKey: { type: String, default: '' },
foreignValue: { type: String, default: '' },
});
const dialogRef = ref();
const gridRef = ref();
const foreignKeyRef = ref();
const open = (foreignKey: string) => {
foreignKeyRef.value = foreignKey;
dialogRef.value.show();
nextTick(() => {
gridRef.value.refresh();
});
};
const close = () => {
dialogRef.value.hide();
};
defineExpose({
open,
close,
});
</script>

58
io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/lib/entity/processor/ArithmeticIndicatorProcessorEntity.java

@ -0,0 +1,58 @@
package io.sc.engine.rule.server.lib.entity.processor;
import com.fasterxml.jackson.annotation.JsonTypeName;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.core.util.ExpressionReplacer;
import io.sc.engine.rule.server.lib.entity.IndicatorProcessorEntity;
import io.sc.engine.rule.server.lib.vo.processor.ArithmeticIndicatorProcessorVo;
import javax.persistence.Column;
import javax.persistence.DiscriminatorValue;
import javax.persistence.Entity;
import java.util.Map;
/**
* 指标处理器算数运算操作实体类
*/
@Entity
@DiscriminatorValue("ARITHMETIC")
@JsonTypeName("ARITHMETIC")
public class ArithmeticIndicatorProcessorEntity extends IndicatorProcessorEntity {
//算数表达式
@Column(name="ARITHMETIC_")
private String arithmetic;
@Override
public ArithmeticIndicatorProcessorVo toVo() {
ArithmeticIndicatorProcessorVo vo =new ArithmeticIndicatorProcessorVo();
super.toVo(vo);
vo.setType(this.getType());
vo.setArithmetic(this.getArithmetic());
return vo;
}
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
@Override
public boolean replace(Map<String, String> mapping) {
String replaced =ExpressionReplacer.replace(this.arithmetic, mapping);
replaced =(replaced==null?"":replaced);
boolean result =false;
if(!replaced.equals(this.arithmetic)) {
result =true;
}
this.arithmetic =replaced;
return result;
}
}

26
io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/lib/vo/processor/ArithmeticIndicatorProcessorVo.java

@ -0,0 +1,26 @@
package io.sc.engine.rule.server.lib.vo.processor;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.server.lib.vo.IndicatorProcessorVo;
/**
* 指标处理器算数运算操作Vo
*/
public class ArithmeticIndicatorProcessorVo extends IndicatorProcessorVo {
//算数表达式
private String arithmetic;
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
}

33
io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/migration/support/AllInOne.java

@ -0,0 +1,33 @@
package io.sc.engine.rule.server.migration.support;
import java.util.ArrayList;
import java.util.List;
import io.sc.engine.rule.core.po.dictionary.Dictionary;
import io.sc.engine.rule.core.po.lib.Lib;
import io.sc.engine.rule.core.po.resource.Resource;
public class AllInOne {
private List<Resource> resources =new ArrayList<Resource>();
private List<Lib> libs =new ArrayList<Lib>();
private List<Dictionary> dictionaries =new ArrayList<Dictionary>();
public List<Resource> getResources() {
return resources;
}
public void setResources(List<Resource> resources) {
this.resources = resources;
}
public List<Lib> getLibs() {
return libs;
}
public void setLibs(List<Lib> libs) {
this.libs = libs;
}
public List<Dictionary> getDictionaries() {
return dictionaries;
}
public void setDictionaries(List<Dictionary> dictionaries) {
this.dictionaries = dictionaries;
}
}

57
io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/model/entity/processor/ArithmeticParameterProcessorEntity.java

@ -0,0 +1,57 @@
package io.sc.engine.rule.server.model.entity.processor;
import com.fasterxml.jackson.annotation.JsonTypeName;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.core.util.ExpressionReplacer;
import io.sc.engine.rule.server.model.entity.ParameterProcessorEntity;
import io.sc.engine.rule.server.model.vo.processor.ArithmeticParameterProcessorVo;
import javax.persistence.Column;
import javax.persistence.DiscriminatorValue;
import javax.persistence.Entity;
import java.util.Map;
/**
* 模型参数处理器算数运算操作实体类
*/
@Entity
@DiscriminatorValue("ARITHMETIC")
@JsonTypeName("ARITHMETIC")
public class ArithmeticParameterProcessorEntity extends ParameterProcessorEntity {
//算数表达式
@Column(name="ARITHMETIC_")
private String arithmetic;
@Override
public ArithmeticParameterProcessorVo toVo() {
ArithmeticParameterProcessorVo vo =new ArithmeticParameterProcessorVo();
super.toVo(vo);
vo.setArithmetic(this.getArithmetic());
return vo;
}
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
@Override
public boolean replace(Map<String, String> mapping) {
String replaced =ExpressionReplacer.replace(this.arithmetic, mapping);
replaced =(replaced==null?"":replaced);
boolean result =false;
if(!replaced.equals(this.arithmetic)) {
result =true;
}
this.arithmetic =replaced;
return result;
}
}

26
io.sc.engine.rule.server/src/main/java/io/sc/engine/rule/server/model/vo/processor/ArithmeticParameterProcessorVo.java

@ -0,0 +1,26 @@
package io.sc.engine.rule.server.model.vo.processor;
import io.sc.engine.rule.core.enums.ProcessorType;
import io.sc.engine.rule.server.model.vo.ParameterProcessorVo;
/**
* 模型参数处理器算数运算操作Vo
*/
public class ArithmeticParameterProcessorVo extends ParameterProcessorVo {
//算数表达式
private String arithmetic;
@Override
public ProcessorType getType() {
return ProcessorType.ARITHMETIC;
}
public String getArithmetic() {
return arithmetic;
}
public void setArithmetic(String arithmetic) {
this.arithmetic = arithmetic;
}
}

66
io.sc.platform.attachment.api/src/main/java/io/sc/platform/attachment/api/AttachmentVo.java

@ -0,0 +1,66 @@
package io.sc.platform.attachment.api;
import io.sc.platform.attachment.api.enums.PersistenceType;
import io.sc.platform.orm.api.vo.AuditorVo;
public abstract class AttachmentVo extends AuditorVo {
protected String id;
//业务Key
protected String bussinessKey;
//附件持久化类型
protected PersistenceType type;
//名称
protected String name;
//扩展名
protected String extName;
//描述
protected String description;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getBussinessKey() {
return bussinessKey;
}
public void setBussinessKey(String bussinessKey) {
this.bussinessKey = bussinessKey;
}
public PersistenceType getType() {
return type;
}
public void setType(PersistenceType type) {
this.type = type;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getExtName() {
return extName;
}
public void setExtName(String extName) {
this.extName = extName;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
}

60
io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/controller/AttachmentWebController.java

@ -0,0 +1,60 @@
package io.sc.platform.attachment.controller;
import java.io.ByteArrayInputStream;
import java.io.FileInputStream;
import java.io.InputStream;
import java.util.List;
import java.util.Locale;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import io.sc.platform.attachment.api.AttachmentVo;
import io.sc.platform.attachment.api.enums.PersistenceType;
import io.sc.platform.attachment.jpa.entity.AttachmentEntity;
import io.sc.platform.attachment.jpa.entity.DatabaseAttachmentEntity;
import io.sc.platform.attachment.jpa.entity.DiskAttachmentEntity;
import io.sc.platform.attachment.jpa.repository.AttachmentRepository;
import io.sc.platform.attachment.service.AttachmentService;
import io.sc.platform.mvc.controller.support.RestCrudController;
import io.sc.platform.mvc.support.FileDownloader;
import org.springframework.stereotype.Controller;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
@Controller
@RequestMapping("/api/system/attachment")
public class AttachmentWebController extends RestCrudController<AttachmentVo,AttachmentEntity,String, AttachmentRepository, AttachmentService> {
@GetMapping("findByBussinessKey")
@ResponseBody
public List<AttachmentVo> findByBussinessKey(@RequestParam("bussinessKey")String bussinessKey) throws Exception{
return service.findByBussinessKey(bussinessKey);
}
@RequestMapping(value="upload/{bussinessKey}",method = RequestMethod.POST)
@ResponseBody
public void add(HttpServletRequest request,@PathVariable("bussinessKey")String bussinessKey,@RequestParam("file") MultipartFile multipartFile,Locale locale) throws Exception{
service.upload(bussinessKey, request.getParameter("name"), request.getParameter("description"), multipartFile, locale);
}
@RequestMapping(value="download/{id}",method=RequestMethod.GET)
public void download(HttpServletRequest request,HttpServletResponse response, @PathVariable("id")String id) throws Exception {
AttachmentEntity entity =service.findById(id);
if(entity!=null) {
if(PersistenceType.DISK.equals(entity.getType())) {
DiskAttachmentEntity _entity =(DiskAttachmentEntity)entity;
String file =service.getDiskAttachmentFilePath(_entity);
if(StringUtils.hasText(file)) {
InputStream in =new FileInputStream(file);
FileDownloader.download(request, response, _entity.getName(), in);
}
}else {
DatabaseAttachmentEntity _entity =(DatabaseAttachmentEntity)entity;
InputStream in =new ByteArrayInputStream(_entity.getBytes());
FileDownloader.download(request, response, _entity.getName(), in);
}
}
}
}

118
io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/jpa/entity/AttachmentEntity.java

@ -0,0 +1,118 @@
package io.sc.platform.attachment.jpa.entity;
import com.fasterxml.jackson.annotation.JsonSubTypes;
import com.fasterxml.jackson.annotation.JsonTypeInfo;
import io.sc.platform.attachment.api.AttachmentVo;
import io.sc.platform.attachment.api.enums.PersistenceType;
import io.sc.platform.orm.entity.AuditorEntity;
import org.hibernate.annotations.GenericGenerator;
import javax.persistence.*;
import javax.validation.constraints.Size;
/**
* 附件实体类
*/
@Entity
@Table(name="SYS_ATTACHMENT")
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name="PERSISTENCE_TYPE_",discriminatorType=DiscriminatorType.STRING,length=10)
@JsonTypeInfo(use=JsonTypeInfo.Id.NAME, include=JsonTypeInfo.As.PROPERTY, property="type",defaultImpl= DatabaseAttachmentEntity.class)
@JsonSubTypes({
@JsonSubTypes.Type(value= DiskAttachmentEntity.class), //磁盘文件
@JsonSubTypes.Type(value= DatabaseAttachmentEntity.class) //数据库
})
public abstract class AttachmentEntity extends AuditorEntity<AttachmentVo> {
//ID,主键
@Id
@GeneratedValue(generator = "system-uuid")
@GenericGenerator(name = "system-uuid", strategy = "uuid2")
@Column(name="ID_", length=36)
@Size(max=36)
protected String id;
//业务Key
@Column(name="BUSSINESS_KEY_", length=256)
@Size(max=256)
protected String bussinessKey;
//附件持久化类型
@Column(name="PERSISTENCE_TYPE_", insertable=false,updatable=false)
@Enumerated(EnumType.STRING)
protected PersistenceType type;
//名称
@Column(name="NAME_", length=256)
@Size(max=256)
protected String name;
//扩展名
@Column(name="EXT_NAME_", length=10)
@Size(max=10)
protected String extName;
//描述
@Column(name="DESCRIPTION_", length=1024)
@Size(max=1024)
protected String description;
public void toVo(AttachmentVo vo){
if(vo!=null){
super.toVo(vo);
vo.setId(this.getId());
vo.setBussinessKey(this.getBussinessKey());
vo.setType(this.getType());
vo.setName(this.getName());
vo.setExtName(this.getExtName());
vo.setDescription(this.getDescription());
}
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getBussinessKey() {
return bussinessKey;
}
public void setBussinessKey(String bussinessKey) {
this.bussinessKey = bussinessKey;
}
public PersistenceType getType() {
return type;
}
public void setType(PersistenceType type) {
this.type = type;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getExtName() {
return extName;
}
public void setExtName(String extName) {
this.extName = extName;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
}

18
io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/jpa/repository/AttachmentRepository.java

@ -0,0 +1,18 @@
package io.sc.platform.attachment.jpa.repository;
import io.sc.platform.attachment.jpa.entity.AttachmentEntity;
import io.sc.platform.orm.repository.DaoRepository;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import java.util.List;
import java.util.Set;
public interface AttachmentRepository extends DaoRepository<AttachmentEntity,String> {
public List<AttachmentEntity> findByBussinessKeyOrderByName(String bussinessKey);
@Query("select e from AttachmentEntity e where e.bussinessKey in (:bussinessKeys)")
public List<AttachmentEntity> findByBussinessKeys(@Param("bussinessKeys")Set<String> bussinessKeys);
}

52
io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/service/AttachmentService.java

@ -0,0 +1,52 @@
package io.sc.platform.attachment.service;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import io.sc.platform.attachment.api.AttachmentVo;
import io.sc.platform.attachment.api.DiskAttachmentVo;
import io.sc.platform.attachment.jpa.entity.AttachmentEntity;
import io.sc.platform.attachment.jpa.entity.DiskAttachmentEntity;
import io.sc.platform.attachment.jpa.repository.AttachmentRepository;
import io.sc.platform.orm.service.DaoService;
import org.springframework.web.multipart.MultipartFile;
/**
* 附件服务接口
*/
public interface AttachmentService extends DaoService<AttachmentEntity, String, AttachmentRepository> {
/**
* 通过业务Key查找附件列表
* @param bussinessKey 业务Key
* @return 附件列表
*/
public List<AttachmentVo> findByBussinessKey(String bussinessKey);
/**
* 通过业务Key集合查找附件列表
* @param bussinessKeys 业务Key集合
* @return 附件列表Map(Key:bussinessKey,value:附件列表)
*/
public Map<String,List<AttachmentVo>> findByBussinessKeys(Set<String> bussinessKeys);
/**
* 获取磁盘附件的文件路径
* @param entity 附件对象
* @return 磁盘附件的文件路径
*/
public String getDiskAttachmentFilePath(DiskAttachmentEntity entity);
/**
*
* 上传附件
* @param bussinessKey 业务 Key
* @param name 附件名称
* @param description 附件描述
* @param multipartFile 附件
* @param locale 区域
*/
public void upload(String bussinessKey,String name,String description,MultipartFile multipartFile,Locale locale) throws Exception;
}

116
io.sc.platform.attachment/src/main/java/io/sc/platform/attachment/service/impl/AttachmentServiceImpl.java

@ -0,0 +1,116 @@
package io.sc.platform.attachment.service.impl;
import io.sc.platform.attachment.api.AttachmentVo;
import io.sc.platform.attachment.api.enums.PersistenceType;
import io.sc.platform.attachment.jpa.entity.AttachmentEntity;
import io.sc.platform.attachment.jpa.entity.DatabaseAttachmentEntity;
import io.sc.platform.attachment.jpa.entity.DiskAttachmentEntity;
import io.sc.platform.attachment.jpa.repository.AttachmentRepository;
import io.sc.platform.attachment.service.AttachmentService;
import io.sc.platform.core.DirectoryManager;
import io.sc.platform.core.util.FileUtil;
import io.sc.platform.mvc.service.SystemParameterService;
import io.sc.platform.orm.service.impl.DaoServiceImpl;
import io.sc.platform.orm.util.EntityVoUtil;
import org.apache.commons.io.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;
import org.springframework.web.multipart.MultipartFile;
import java.io.*;
import java.util.*;
@Service("frAttachmentService")
public class AttachmentServiceImpl extends DaoServiceImpl<AttachmentEntity, String, AttachmentRepository> implements AttachmentService {
@Autowired private SystemParameterService systemParameterService;
@Override
public List<AttachmentVo> findByBussinessKey(String bussinessKey) {
return EntityVoUtil.toVo(repository.findByBussinessKeyOrderByName(bussinessKey));
}
@Override
public Map<String, List<AttachmentVo>> findByBussinessKeys(Set<String> bussinessKeys) {
if(bussinessKeys!=null && bussinessKeys.size()>0) {
List<AttachmentEntity> entities =repository.findByBussinessKeys(bussinessKeys);
if(entities!=null && entities.size()>0) {
Map<String, List<AttachmentVo>> result =new HashMap<>();
for(AttachmentEntity entity : entities) {
List<AttachmentVo> list =result.get(entity.getBussinessKey());
if(list==null) {
list =new ArrayList<AttachmentVo>();
list.add(entity.toVo());
result.put(entity.getBussinessKey(), list);
}else {
list.add(entity.toVo());
}
}
return result;
}
}
return null;
}
@Override
public String getDiskAttachmentFilePath(DiskAttachmentEntity entity) {
if(entity!=null) {
String path = DirectoryManager.getInstance().getByName("dir.work.web.upload");
String attachmentPath =entity.getPath();
if(StringUtils.hasText(attachmentPath)) {
if(attachmentPath.startsWith("/") || attachmentPath.startsWith("\\")) {
path =path + attachmentPath;
}else {
path =path + File.separator + attachmentPath;
}
}
if(path.endsWith("/") || path.endsWith("\\")) {
path =path + entity.getId() + entity.getExtName();
}else {
path =path + File.separator + entity.getId() + entity.getExtName();
}
return path;
}
return null;
}
@Override
public void upload(String bussinessKey, String name, String description, MultipartFile multipartFile,Locale locale) throws Exception{
if(multipartFile!=null) {
InputStream ins = multipartFile.getInputStream();
byte[] bytes = new byte[ins.available()];
ins.read(bytes);
ins.close();
String attachmentPersistenceType = systemParameterService.getParameter("attachmentPersistenceType");
if (PersistenceType.DISK.equals(PersistenceType.valueOf(attachmentPersistenceType))) {
DiskAttachmentEntity _entity = new DiskAttachmentEntity();
_entity.setPath("/");
_entity.setBussinessKey(bussinessKey);
_entity.setName(name);
_entity.setExtName(FileUtil.getFileExtName(multipartFile.getOriginalFilename()));
_entity.setDescription(description);
AttachmentEntity entity = add(_entity);
persistence2Disk((DiskAttachmentEntity) entity, bytes);
} else {
DatabaseAttachmentEntity _entity = new DatabaseAttachmentEntity();
_entity.setBussinessKey(bussinessKey);
_entity.setName(name);
_entity.setExtName(FileUtil.getFileExtName(multipartFile.getName()));
_entity.setDescription(description);
_entity.setBytes(bytes);
add(_entity);
}
}
}
private void persistence2Disk(DiskAttachmentEntity entity,byte[] bytes) throws FileNotFoundException, IOException {
String file =getDiskAttachmentFilePath(entity);
if(StringUtils.hasText(file)) {
IOUtils.copy(new ByteArrayInputStream(bytes), new FileOutputStream(file));
}
}
}

2
io.sc.platform.orm/src/main/java/io/sc/platform/orm/entity/AuditorEntity.java

@ -55,7 +55,7 @@ public abstract class AuditorEntity<V extends AuditorVo> extends VersionEntity<V
@JsonProperty(index = 1005)
protected Date lastModifyDate;
public void toVo(AuditorVo vo){
public void toVo(V vo){
if(vo!=null){
super.toVo(vo);
vo.setDataComeFrom(this.getDataComeFrom());

Loading…
Cancel
Save