Commit 403bc21d authored by 侯力峰's avatar 侯力峰
Browse files

首次开源发布

parent fdfe0676
Pipeline #2762 failed with stages
in 0 seconds
/target
/.settings
/.project
/.classpath
*/target
*/.settings
*/.project
*/.classpath
# spatiotemporal-commons # spatiotemporal-commons
时空开放平台 公用组件 **时空开放平台 公用组件**
\ No newline at end of file
包含以下三个公共组件:
- spatiotemporal-commons-core 时空开放平台 公用组件-核心包
- spatiotemporal-commons-file 时空开放平台 公用组件-文件接口服务
- spatiotemporal-commons-register 时空开放平台 公用组件-服务自注册
## 使用方法
* 在工程pom.xml文件添加以下依赖
```xml
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-core</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-file</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-register</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
```
* 根据所选文件服务器类型,在工程yml配置文件里添加配置段。
```java
uploadservice:
## 文件服务器类型minio/ftp两选一
type: minio
## minio配置段示例
minio:
endpoint: http://192.168.59.120:9000
accessKey: minioadmin
secretKey: minioadmin123456
bucketName: uploads
## ftp配置段示例
ftp:
host: 192.168.59.181
port: 21
username: ftp
password: ftp
requestDir: upload
encoding: GBK
```
+ 文件上传Mapping地址为:`/api/v1/files/upload`
+ 文件删除Mapping地址为:`/api/v1/files/delete`
* 在Application启动类添加`@EnableServerRegister`注解
```java
@EnableServerRegister(autoRegister = true, period = 60)
//参数说明:
// autoRegister:是否启用服务自注册,false-不启用;true-启用(default true)
// period:存续心跳,单位秒。(default 30)
```
## License
时空开放平台是一个基于[Apache 2.0 license](https://www.apache.org/licenses/LICENSE-2.0.html)发布的开源软件。
# spatiotemporal-commons-core
**时空开放平台 公用组件-核心包**
## 使用方法
* 在工程pom.xml文件添加以下依赖
```xml
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-core</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
```
注意选择合适的版本。
## License
时空开放平台是一个基于[Apache 2.0 license](https://www.apache.org/licenses/LICENSE-2.0.html)发布的开源软件。
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons</artifactId>
<version>1.0.0-RELEASE</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>spatiotemporal-commons-core</artifactId>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<java.version>1.8</java.version>
<maven-jar-plugin.version>3.1.1</maven-jar-plugin.version>
</properties>
<dependencies>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.5</version>
</dependency>
</dependencies>
</project>
package cn.spatiotemporal.commons.base;
import java.io.Serializable;
import java.time.LocalDateTime;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.fasterxml.jackson.annotation.JsonInclude;
import lombok.Data;
/**
*
* @ClassName: BaseEntity
* @Description: 基础时间
* @date 2023年9月11日 上午9:20:44
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
@Data
public class BaseEntity implements Serializable {
private static final long serialVersionUID = 1L;
@JsonInclude(value = JsonInclude.Include.NON_NULL)
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private LocalDateTime createTime;
@JsonInclude(value = JsonInclude.Include.NON_NULL)
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private LocalDateTime updateTime;
}
package cn.spatiotemporal.commons.base;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
/**
*
* @ClassName: BasePageQuery
* @Description: 基础分页请求对象
* @date 2023年9月11日 上午9:21:10
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
@Data
@ApiModel
public class BasePageQuery {
@ApiModelProperty(value = "页码", example = "1")
private int pageNum = 1;
@ApiModelProperty(value = "每页记录数", example = "10")
private int pageSize = 10;
}
package cn.spatiotemporal.commons.base;
import lombok.Data;
import lombok.ToString;
import java.io.Serializable;
/**
*
* @ClassName: BaseVO
* @Description: VO 基类
* @date 2023年9月11日 上午9:21:34
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
@Data
@ToString
public class BaseVO implements Serializable {
private static final long serialVersionUID = 1L;
}
package cn.spatiotemporal.commons.base;
import cn.hutool.core.util.ObjectUtil;
import java.util.EnumSet;
import java.util.Objects;
/**
*
* @ClassName: IBaseEnum
* @Description: 枚举通用接口
* @date 2022年3月27日 上午9:21:50
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
public interface IBaseEnum<T> {
T getValue();
String getLabel();
/**
* 根据值获取枚举
*
* @param value
* @param clazz
* @param <E> 枚举
* @return
*/
static <E extends Enum<E> & IBaseEnum> E getEnumByValue(Object value, Class<E> clazz) {
Objects.requireNonNull(value);
EnumSet<E> allEnums = EnumSet.allOf(clazz); // 获取类型下的所有枚举
E matchEnum = allEnums.stream()
.filter(e -> ObjectUtil.equal(e.getValue(), value))
.findFirst()
.orElse(null);
return matchEnum;
}
/**
* 根据文本标签获取值
*
* @param value
* @param clazz
* @param <E>
* @return
*/
static <E extends Enum<E> & IBaseEnum> String getLabelByValue(Object value, Class<E> clazz) {
Objects.requireNonNull(value);
EnumSet<E> allEnums = EnumSet.allOf(clazz); // 获取类型下的所有枚举
E matchEnum = allEnums.stream()
.filter(e -> ObjectUtil.equal(e.getValue(), value))
.findFirst()
.orElse(null);
String label = null;
if (matchEnum != null) {
label = matchEnum.getLabel();
}
return label;
}
/**
* 根据文本标签获取值
*
* @param label
* @param clazz
* @param <E>
* @return
*/
static <E extends Enum<E> & IBaseEnum> Object getValueByLabel(String label, Class<E> clazz) {
Objects.requireNonNull(label);
EnumSet<E> allEnums = EnumSet.allOf(clazz); // 获取类型下的所有枚举
String finalLabel = label;
E matchEnum = allEnums.stream()
.filter(e -> ObjectUtil.equal(e.getLabel(), finalLabel))
.findFirst()
.orElse(null);
Object value = null;
if (matchEnum != null) {
value = matchEnum.getValue();
}
return value;
}
}
package cn.spatiotemporal.commons.constant;
/**
*
* @ClassName: SecurityConstants
* @Description: 安全类常量
* @date 2023年9月11日 上午9:19:45
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
public interface SecurityConstants {
/**
* 黑名单TOKEN Key前缀
*/
String BLACKLIST_TOKEN_PREFIX = "AUTH:BLACKLIST_TOKEN:";
/**
* 验证码key前缀
*/
String VERIFY_CODE_KEY_PREFIX = "AUTH:VERIFY_CODE:";
/**
* 短信验证码key前缀
*/
String SMS_CODE_PREFIX = "SMS_CODE:";
/**
* 接口文档测试客户端ID
*/
String TEST_CLIENT_ID = "client";
/**
* 系统管理 web 客户端ID
*/
String ADMIN_CLIENT_ID = "inzy-admin";
/**
* 移动端(H5/Android/IOS)客户端ID
*/
String APP_CLIENT_ID = "inzy-app";
/**
* 微信小程序客户端ID
*/
String WEAPP_CLIENT_ID = "inzy-weapp";
}
package cn.spatiotemporal.commons.enums;
import lombok.Getter;
import lombok.NoArgsConstructor;
/**
* REST服务返回状态/消息枚举
* @author marquis
*
*/
@Getter
@NoArgsConstructor
public enum ReturnEnum {
// 公共返回状态/消息
// 成功
SUCCESS("200","访问成功"),
SUCCESS_CUSTOM("201","调用成功"),//自定义成功状态
// 一般公共错误信息
ERROR_POST_PARAM("400", "请求参数异常"),
ERROR_ACCOUNT_OR_PASSWORD("408","用户名或密码错误"),
ERROR_EXIST_USERNAME("409","用户名已存在,请直接登录"),
ERROR_USER_NOT_ENABLED("410","用户已停用,请联系管理员"),
ERROR_USER_NOT_EXIST("411","用户不存在"),
ERROR_NO_AUTHORITY("401", "用户未登录,需要登录后才能访问"),
ERROR_OTHER_DEVICE("401.1", "用户已在其他设备登录,需要重新登录后才能访问"),
ERROR_TOKEN_EXPIRED("401.2", "用户授权已过期,需要重新登录后才能访问"),
ERROR_PERMISSION_DENIED("403", "无此访问权限"),
ERROR_NOT_FOUND("404", "访问对象不存在"),
ERROR_METHOD_ERROR("405", "访问方式不正确"),
ERROR_USER_NULL("412","用户名参数为空"),
ERROR_MSG_HAS_CHILD("413","操作失败,当前所选栏目有子栏目信息"),
ERROR_CRON("414","cron表达式不正确"),
// 一般公共异常信息
FAILED("500", "服务器内部异常,请稍后重试"),
;
private String code;
private String message;
ReturnEnum(String code, String message) {
this.code = code;
this.message = message;
}
public String getCode() {
return code;
}
public String getMessage() {
return message;
}
}
package cn.spatiotemporal.commons.enums;
import cn.spatiotemporal.commons.base.IBaseEnum;
import lombok.Getter;
/**
*
* @ClassName: StatusEnum
* @Description: 状态枚举
* @date 2022年10月11日 上午10:26:14
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
public enum StatusEnum implements IBaseEnum<Integer> {
ENABLE(1, "启用"),
DISABLE (0, "禁用");
@Getter
private Integer value;
@Getter
private String label;
StatusEnum(Integer value, String label) {
this.value = value;
this.label = label;
}
}
package cn.spatiotemporal.commons.exception;
import cn.spatiotemporal.commons.enums.ReturnEnum;
/**
* 业务异常类的公共基类
* @author marquis
*
*/
public class BaseBusinessException extends RuntimeException {
/**
*
*/
private static final long serialVersionUID = 4534112171112827815L;
private String code;
public BaseBusinessException(ReturnEnum returnEnum) {
super(returnEnum.getMessage());
this.code = returnEnum.getCode();
}
public BaseBusinessException(String code, String message) {
super(message);
this.code = code;
}
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
}
package cn.spatiotemporal.commons.factory;
import cn.hutool.core.util.StrUtil;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicInteger;
/**
*
* @ClassName: NamedThreadFactory
* @Description: 重命名线程池
* @date 2022年8月11日 下午15:27:23
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
public class NamedThreadFactory implements ThreadFactory {
private final AtomicInteger poolNumber = new AtomicInteger(1);
private final ThreadGroup threadGroup;
private final AtomicInteger threadNumber = new AtomicInteger(1);
public final String namePrefix;
public NamedThreadFactory(String name) {
SecurityManager securityManager = System.getSecurityManager();
if (securityManager != null) {
this.threadGroup = securityManager.getThreadGroup();
} else {
this.threadGroup = Thread.currentThread().getThreadGroup();
}
if (StrUtil.isBlank(name)) {
name = "pool";
}
namePrefix = name + "-" + poolNumber.getAndIncrement() + "-thread-";
}
@Override
public Thread newThread(Runnable r) {
Thread t = new Thread(threadGroup, r, namePrefix + threadNumber.getAndIncrement(), 0);
if (t.isDaemon()) {
t.setDaemon(false);
}
if (t.getPriority() != Thread.NORM_PRIORITY) {
t.setPriority(Thread.NORM_PRIORITY);
}
return t;
}
}
package cn.spatiotemporal.commons.result;
import java.io.Serializable;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
@ApiModel(description= "REST查询条件")
@Data
public class RequestVO<T> implements Serializable {
/**
*
*/
private static final long serialVersionUID = -830863935742261168L;
@ApiModelProperty(value = "每页大小(行数)")
private Long size;
@ApiModelProperty(value = "当前页码")
private Long current;
@ApiModelProperty(value = "查询条件")
private T condition;
@ApiModelProperty(value = "排序")
private String order;
public RequestVO() {
}
public RequestVO(T obj) {
this.condition = obj;
}
public RequestVO(Long size, Long current, T obj) {
this.size = size;
this.current = current;
this.condition = obj;
}
public RequestVO(Long size, Long current, T obj, String order) {
this.size = size;
this.current = current;
this.condition = obj;
this.order = order;
}
}
package cn.spatiotemporal.commons.result;
import java.util.HashMap;
import java.util.Map;
import cn.spatiotemporal.commons.enums.ReturnEnum;
public class ReturnMap extends ReturnVO<Map<String, Object>> {
/**
*
*/
private static final long serialVersionUID = 5440131552722554584L;
public ReturnMap() {
super(new HashMap<String, Object>());
}
public ReturnMap(ReturnEnum returnEnum) {
super(returnEnum, new HashMap<String, Object>());
}
public void put(String key, Object data) {
((Map<String, Object>) this.getData()).put(key, data);
}
}
package cn.spatiotemporal.commons.result;
import java.io.Serializable;
import cn.spatiotemporal.commons.enums.ReturnEnum;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
@ApiModel(description= "REST返回数据")
@Data
public class ReturnVO<T> implements Serializable {
/**
*
*/
private static final long serialVersionUID = 221173669518504486L;
@ApiModelProperty(value = "执行状态码")
private String code;
@ApiModelProperty(value = "返回消息")
private String msg;
@ApiModelProperty(value = "返回数据")
private Object data;
public ReturnVO() {
this.code = ReturnEnum.SUCCESS.getCode();
this.msg = ReturnEnum.SUCCESS.getMessage();
}
public ReturnVO(T obj) {
this.code = ReturnEnum.SUCCESS.getCode();
this.msg = ReturnEnum.SUCCESS.getMessage();
this.data = obj;
}
public ReturnVO(ReturnEnum returnEnum) {
this.code = returnEnum.getCode();
this.msg = returnEnum.getMessage();
}
public ReturnVO(ReturnEnum returnEnum, T obj) {
this.code = returnEnum.getCode();
this.msg = returnEnum.getMessage();
this.data = obj;
}
public ReturnVO(String code, String message) {
this.code = code;
this.msg = message;
}
public ReturnVO(String code, String message, T obj) {
this.code = code;
this.msg = message;
this.data = obj;
}
}
package cn.spatiotemporal.commons.util;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;
/**
*
* @ClassName: ImgUtils
* @Description: 文件工具类
* @date 2023年7月17日 上午9:24:33
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
public class ImgUtils {
private static final String[] imgSuffixArr = { "bmp", "dib", "gif", "jfif", "jpe", "jpeg", "jpg", "png", "tif",
"tiff", "ico" };
/**
* 是否图片判断
*
* @param fileName
* @return
*/
public static boolean isImg(String fileName) {
if (StrUtil.isBlank(fileName)) {
return false;
}
String fileSuffix = FileUtil.getSuffix(fileName);
for (String imgSuffix : imgSuffixArr) {
if (fileSuffix.equals(imgSuffix)) {
return true;
}
}
return false;
}
/**
* 根据图片大小设置压缩比
*
* @param size 图片大小(单位:Bytes)
* @return 压缩比例
*/
public static float getCompressQuality(long size) {
if (size > 0.1 * 1024 * 1024 && size <= 0.5 * 1024 * 1024) {
return 0.8f;
} else if (size > 0.5 * 1024 * 1024 && size <= 1 * 1024 * 1024) {
return 0.6f;
} else if (size > 1 * 1024 * 1024 && size <= 2 * 1024 * 1024) {
return 0.4f;
} else if (size > 2 * 1024 * 1024 && size <= 5 * 1024 * 1024) {
return 0.2f;
} else {
// 大于5M
return 0.1f;
}
}
}
package cn.spatiotemporal.commons.util;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import cn.spatiotemporal.commons.exception.BaseBusinessException;
import lombok.extern.slf4j.Slf4j;
/**
* @ClassName: StrUtil
* @Description: 字符工具类
* @date 2023年9月7日 上午9:35:45
*
* @author Q.JI
* @version
* @since JDK 1.8
*/
@Slf4j
public class StrUtil {
/**
* 转字符串
*
* @param obj
* @return
*/
public static String nvl(Object obj) {
return (obj == null) ? "" : obj.toString();
}
/**
* 为object中的所有String属性去除空格字符
*
* @param object 待处理的实体对象
* @return : java.lang.Object
*/
public static Object replaceBlankSpace(Object object) {
// 获取该类中所有的域(属性)
Field[] fields = object.getClass().getDeclaredFields();
for (Field field : fields) {
// 对所有的属性判断是否为String类型
if (field.getType().equals(String.class)) {
// 将私有属性设置为可访问状态
field.setAccessible(true);
try {
String string = (String) field.get(object);
// 将所有的空格字符用""替换
if (string != null) {
string = string.replaceAll(" ", "");
// 相当于调用了set方法设置属性
field.set(object, string);
}
} catch (IllegalAccessException e) {
e.printStackTrace();
}
}
}
return object;
}
/**
* 为object中的所有String属性去除空格字符,有空格则直接抛出
*
* @param object 待处理的实体对象
* @return : java.lang.Object
*/
public static Object replaceBlankOrThrow(Object object) throws BaseBusinessException, IllegalAccessException {
// 获取该类中所有的域(属性)
Field[] fields = object.getClass().getFields();
for (Field field : fields) {
// 对所有的属性判断是否为String类型
if (field.getType().equals(String.class)) {
// 将私有属性设置为可访问状态
field.setAccessible(true);
String string = (String) field.get(object);
// 将所有的空格字符用""替换
if (string != null) {
string = string.replaceAll(" ", "");
/*
* if (StringUtils.isEmpty(string)) { throw new BaseBusinessException("999999",
* "##### 空字符串,参数异常"); }
*/
}
// 相当于调用了set方法设置属性
field.set(object, string);
}
}
return object;
}
/**
* Object是否包含空字符串
*
* @param object 待处理的实体对象
* @return : Boolean false不包含,true包含
*/
public static Boolean checkContainsEntity(Object object) {
// 获取该类中所有的域(属性)
Class<?> aClass = object.getClass();
Field[] fields = aClass.getDeclaredFields();
List<Field> fieldList = new ArrayList<>(Arrays.asList(fields));
// 获取父类field
Class<?> superclass = aClass.getSuperclass();
Field[] supperFields = superclass.getDeclaredFields();
fieldList.addAll(Arrays.asList(supperFields));
for (Field field : fieldList) {
// 对所有的属性判断是否为String类型
if (field.getType().equals(String.class)) {
// 将私有属性设置为可访问状态
field.setAccessible(true);
String string = null;
try {
string = (String) field.get(object);
// 将所有的空格字符用""替换
if (string != null && string.contains(" ")) {
return true;
}
} catch (IllegalAccessException e) {
log.error("##### {} #####", "checkContainsEntity Object是否包含空字符串 发生错误!");
}
}
}
return false;
}
}
# spatiotemporal-commons-file
**时空开放平台 公用组件-文件接口服务**
实现基于minio/ftp文件服务器的文件服务能力,供其它服务集成调用。
## 使用方法
* 在工程pom.xml文件添加依赖。
```xml
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-file</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
```
* 根据所选文件服务器类型,在工程yml配置文件里添加配置段。
```java
uploadservice:
## 文件服务器类型minio/ftp两选一
type: minio
## minio配置段示例
minio:
endpoint: http://192.168.59.120:9000
accessKey: minioadmin
secretKey: minioadmin123456
bucketName: uploads
## ftp配置段示例
ftp:
host: 192.168.59.181
port: 21
username: ftp
password: ftp
requestDir: upload
encoding: GBK
```
+ 文件上传Mapping地址为:`/api/v1/files/upload`
+ 文件删除Mapping地址为:`/api/v1/files/delete`
## License
时空开放平台是一个基于[Apache 2.0 license](https://www.apache.org/licenses/LICENSE-2.0.html)发布的开源软件。
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons</artifactId>
<version>1.0.0-RELEASE</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>spatiotemporal-commons-file</artifactId>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<java.version>1.8</java.version>
<maven-jar-plugin.version>3.1.1</maven-jar-plugin.version>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>cn.spatiotemporal</groupId>
<artifactId>spatiotemporal-commons-core</artifactId>
<version>1.0.0-RELEASE</version>
</dependency>
<dependency>
<groupId>com.enterprisedt</groupId>
<artifactId>edtFTPj</artifactId>
<version>1.5.3</version>
</dependency>
<dependency>
<groupId>io.minio</groupId>
<artifactId>minio</artifactId>
<version>8.1.0</version>
</dependency>
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-stdlib</artifactId>
<version>1.5.31</version>
</dependency>
</dependencies>
</project>
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment