Compare commits
28 Commits
feature/ad
...
39d8eac578
Author | SHA1 | Date | |
---|---|---|---|
39d8eac578 | |||
3858aa16e1 | |||
4d3d0f7cc7 | |||
17b5b55d59 | |||
30f29bb4b3 | |||
104bffb0e8 | |||
62607dc0a4 | |||
fe03b6da4d | |||
0f145e383e | |||
89584d2a48 | |||
f3017e90c0 | |||
f1d16808c6 | |||
8460b9da29 | |||
19fc97362c | |||
d91f818c96 | |||
65d77f35c1 | |||
b14c03fc32 | |||
ba34fa4a2b | |||
b015f5d1c4 | |||
6335fa03b1 | |||
5215fded9c | |||
c30cca8f6a | |||
ea7a8ee6a0 | |||
33d3d86393 | |||
1b551eeb4c | |||
1611bf38e8 | |||
17273b0bc6 | |||
2d02899372 |
@@ -18,4 +18,11 @@
|
||||
|
||||
目前项目还没完成,开发中……
|
||||
|
||||
相关的文档和介绍完善中……
|
||||
相关的文档和介绍完善中……
|
||||
|
||||
## 编码规约
|
||||
### 关于 null
|
||||
1. 方法默认参数不为 `null`,**可以**在 Javadoc 中对参数进行说明,如“...(must not be {@code null}[ or empty string])”。方法内部**必须**做参数校验,如使用 Assert 等工具类。
|
||||
2. 如果参数允许为空,**必须**为参数添加 `@Nullable` 注解,并在 Javadoc 中对参数进行说明,如“...(may be {@code null})”。
|
||||
3. 除极特殊的情况,方法默认**不返回 `null`**,如可能返回一个对象表示值的缺失,则**必须**使用 `Optional`,**绝不在返回类型为 Optional 的方法中返回 `null`**。
|
||||
4. 在极其特殊的情况下,方法需要返回 `null`,**必须**给方法加上 `@Nullable` 注解,并在 Javadoc 中详细说明。
|
||||
|
@@ -1,10 +1,13 @@
|
||||
package xyz.zhouxy.plusone.exception.handler;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler.ExceptionInfoHolder;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.AllExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler.ExceptionInfoHolder;
|
||||
|
||||
/**
|
||||
* AllExceptionHandlerConfig
|
||||
@@ -14,7 +17,7 @@ import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler.ExceptionInfoHo
|
||||
public class AllExceptionHandlerConfig {
|
||||
|
||||
@Bean
|
||||
AllExceptionHandler getAllExceptionHandler(ExceptionInfoHolder exceptionInfoHolder) {
|
||||
AllExceptionHandler getAllExceptionHandler(@Nonnull ExceptionInfoHolder exceptionInfoHolder) {
|
||||
return new AllExceptionHandler(exceptionInfoHolder);
|
||||
}
|
||||
}
|
||||
|
@@ -1,5 +1,7 @@
|
||||
package xyz.zhouxy.plusone.exception.handler;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.springframework.context.support.DefaultMessageSourceResolvable;
|
||||
import org.springframework.core.Ordered;
|
||||
import org.springframework.core.annotation.Order;
|
||||
@@ -11,6 +13,7 @@ import org.springframework.web.bind.annotation.ExceptionHandler;
|
||||
import org.springframework.web.bind.annotation.RestControllerAdvice;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
|
||||
/**
|
||||
@@ -40,7 +43,7 @@ import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
@Order(Ordered.LOWEST_PRECEDENCE - 1)
|
||||
@Slf4j
|
||||
public class DefaultExceptionHandler extends BaseExceptionHandler {
|
||||
public DefaultExceptionHandler(ExceptionInfoHolder exceptionInfoHolder) {
|
||||
public DefaultExceptionHandler(@Nonnull ExceptionInfoHolder exceptionInfoHolder) {
|
||||
super(exceptionInfoHolder);
|
||||
set(IllegalArgumentException.class, 4010000, "格式错误", HttpStatus.FORBIDDEN);
|
||||
set(DataAccessException.class, 6030000, "数据库错误", HttpStatus.INTERNAL_SERVER_ERROR, true);
|
||||
|
@@ -8,6 +8,7 @@ import org.springframework.web.bind.annotation.ExceptionHandler;
|
||||
import org.springframework.web.bind.annotation.RestControllerAdvice;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
import xyz.zhouxy.plusone.exception.SysException;
|
||||
|
||||
@@ -15,7 +16,7 @@ import xyz.zhouxy.plusone.exception.SysException;
|
||||
@Slf4j
|
||||
public class SysExceptionHandler extends BaseExceptionHandler {
|
||||
|
||||
public SysExceptionHandler(ExceptionInfoHolder exceptionInfoHolder) {
|
||||
public SysExceptionHandler(@Nonnull ExceptionInfoHolder exceptionInfoHolder) {
|
||||
super(exceptionInfoHolder);
|
||||
}
|
||||
|
||||
|
@@ -49,7 +49,7 @@
|
||||
<dependency>
|
||||
<groupId>xyz.zhouxy.plusone</groupId>
|
||||
<artifactId>plusone-exception-handler</artifactId>
|
||||
<version>0.0.8-SNAPSHOT</version>
|
||||
<version>0.0.9-SNAPSHOT</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
|
@@ -2,6 +2,8 @@ package xyz.zhouxy.plusone.constant;
|
||||
|
||||
public class ErrorCodeConsts {
|
||||
public static final int DEFAULT_ERROR_CODE = 9999999;
|
||||
public static final int DEFAULT_SYS_ERROR_CODE = 5000000;
|
||||
public static final int DEFAULT_BIZ_ERROR_CODE = 4000000;
|
||||
|
||||
private ErrorCodeConsts() {
|
||||
throw new IllegalStateException("Utility class");
|
||||
|
@@ -1,6 +1,6 @@
|
||||
package xyz.zhouxy.plusone.util;
|
||||
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
import java.security.SecureRandom;
|
||||
|
||||
public final class RandomUtil {
|
||||
private RandomUtil() {
|
||||
@@ -8,7 +8,7 @@ public final class RandomUtil {
|
||||
}
|
||||
|
||||
public static String randomStr(char[] sourceCharacters, int length) {
|
||||
ThreadLocalRandom random = ThreadLocalRandom.current();
|
||||
SecureRandom random = new SecureRandom();
|
||||
char[] result = new char[length];
|
||||
for (int i = 0; i < length; i++) {
|
||||
result[i] = sourceCharacters[random.nextInt(sourceCharacters.length)];
|
||||
|
@@ -24,12 +24,10 @@ public final class EntityStatus extends Enumeration<EntityStatus> {
|
||||
private static final ValueSet<EntityStatus> VALUE_SET = new ValueSet<>(
|
||||
AVAILABLE, DISABLED);
|
||||
|
||||
@Nonnull
|
||||
public static EntityStatus of(int id) {
|
||||
return VALUE_SET.get(id);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static Collection<EntityStatus> constants() {
|
||||
return VALUE_SET.getValues();
|
||||
}
|
||||
|
@@ -5,7 +5,7 @@ import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
import xyz.zhouxy.plusone.constant.ErrorCodeConsts;
|
||||
import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler.ExceptionInfoHolder;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler.ExceptionInfoHolder;
|
||||
|
||||
@Configuration
|
||||
public class PlusoneExceptionHandlerConfig {
|
||||
|
@@ -8,7 +8,7 @@ import java.sql.SQLException;
|
||||
*
|
||||
* <p>
|
||||
* 通过在 {@link #map(ResultSet)} 中配置 {@link ResultSet} 到对象的映射,
|
||||
* 可将 {@link #rowMapper(ResultSet, int)} 的方法应用,
|
||||
* 可将 {@link #rowMapper(ResultSet, int)} 的方法引用,
|
||||
* 直接当成 {@link org.springframework.jdbc.core.RowMapper} 对象传给
|
||||
* {@link org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate}
|
||||
* 的查询方法,
|
||||
|
@@ -1,8 +1,17 @@
|
||||
package xyz.zhouxy.plusone.oss;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.math.BigInteger;
|
||||
import java.security.MessageDigest;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.util.Arrays;
|
||||
import java.util.Objects;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import org.csource.common.MyException;
|
||||
import org.csource.common.NameValuePair;
|
||||
@@ -14,7 +23,11 @@ import org.csource.fastdfs.TrackerServer;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import com.google.common.io.Files;
|
||||
|
||||
import lombok.Getter;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.exception.SysException;
|
||||
|
||||
public class FastDFSUtil {
|
||||
|
||||
@@ -44,7 +57,7 @@ public class FastDFSUtil {
|
||||
* @throws FastDFSException
|
||||
*/
|
||||
public String[] upload(FastDFSFile file) throws FastDFSException {
|
||||
logger.info("File Name: {}, File Length: {}", file.getName(), file.getContent().length);
|
||||
logger.info("File Name: {}, File Length: {}", file.getFileName(), file.getContent().length);
|
||||
|
||||
NameValuePair[] metaList = new NameValuePair[1];
|
||||
metaList[0] = new NameValuePair("author", file.getAuthor());
|
||||
@@ -63,7 +76,7 @@ public class FastDFSUtil {
|
||||
uploadResults[0], uploadResults[1], System.currentTimeMillis() - startTime);
|
||||
|
||||
} catch (IOException e) {
|
||||
throw new FastDFSException("IO Exception when uploadind the file:" + file.getName(), e);
|
||||
throw new FastDFSException("IO Exception when uploadind the file:" + file.getFileName(), e);
|
||||
} catch (MyException e) {
|
||||
throw new FastDFSException(e);
|
||||
}
|
||||
@@ -109,18 +122,72 @@ public class FastDFSUtil {
|
||||
}
|
||||
}
|
||||
|
||||
@Getter
|
||||
public static final class FastDFSFile {
|
||||
private String name;
|
||||
private byte[] content;
|
||||
private String ext;
|
||||
private String md5;
|
||||
private String author;
|
||||
@Getter
|
||||
private final String fileName;
|
||||
private final byte[] content;
|
||||
@Getter
|
||||
private final String ext;
|
||||
@Getter
|
||||
private final String md5;
|
||||
@Getter
|
||||
private final String author;
|
||||
|
||||
public FastDFSFile(String name, byte[] content, String ext) {
|
||||
this.name = name;
|
||||
private FastDFSFile(@Nonnull File file, @Nullable String author) throws IOException {
|
||||
this.fileName = file.getName();
|
||||
this.content = Files.toByteArray(file);
|
||||
this.ext = Files.getFileExtension(fileName);
|
||||
this.md5 = md5Hex(content);
|
||||
this.author = author;
|
||||
}
|
||||
|
||||
private FastDFSFile(@Nonnull String fileName, @Nonnull byte[] content, @Nullable String author) {
|
||||
this.fileName = fileName;
|
||||
this.content = content;
|
||||
this.ext = ext;
|
||||
this.ext = Files.getFileExtension(fileName);
|
||||
this.md5 = md5Hex(content);
|
||||
this.author = author;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@StaticFactoryMethod(FastDFSFile.class)
|
||||
public static FastDFSFile of(@Nonnull File file) throws IOException {
|
||||
return new FastDFSFile(file, null);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@StaticFactoryMethod(FastDFSFile.class)
|
||||
public static FastDFSFile of(@Nonnull File file, @Nullable String author) throws IOException {
|
||||
return new FastDFSFile(file, author);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@StaticFactoryMethod(FastDFSFile.class)
|
||||
public static FastDFSFile of(@Nonnull String fileName, @Nonnull byte[] content) {
|
||||
return new FastDFSFile(fileName, content, null);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@StaticFactoryMethod(FastDFSFile.class)
|
||||
public static FastDFSFile of(@Nonnull String fileName, @Nonnull byte[] content, @Nullable String author) {
|
||||
return new FastDFSFile(fileName, content, author);
|
||||
}
|
||||
|
||||
public byte[] getContent() {
|
||||
return Arrays.copyOf(content, content.length);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
private static String md5Hex(byte[] data) {
|
||||
try {
|
||||
MessageDigest messageDigest = MessageDigest.getInstance("MD5");
|
||||
messageDigest.update(data);
|
||||
byte[] result = messageDigest.digest();
|
||||
var sha512Hex = new BigInteger(1, result).toString(16);
|
||||
return Objects.requireNonNull(sha512Hex);
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
throw new SysException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -1,13 +1,15 @@
|
||||
package xyz.zhouxy.plusone.validator;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.springframework.web.bind.annotation.RestControllerAdvice;
|
||||
|
||||
import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler;
|
||||
|
||||
@RestControllerAdvice
|
||||
public class InvalidInputExceptionHandler extends BaseExceptionHandler {
|
||||
|
||||
public InvalidInputExceptionHandler(ExceptionInfoHolder exceptionInfoHolder) {
|
||||
public InvalidInputExceptionHandler(@Nonnull ExceptionInfoHolder exceptionInfoHolder) {
|
||||
super(exceptionInfoHolder);
|
||||
set(InvalidInputException.class, InvalidInputException.ERROR_CODE, "无效的用户输入");
|
||||
}
|
||||
|
@@ -3,14 +3,10 @@ package xyz.zhouxy.plusone;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
@SpringBootApplication
|
||||
@Slf4j
|
||||
public class PlusoneApplication {
|
||||
|
||||
public static void main(String[] args) {
|
||||
log.debug("Plusone started!");
|
||||
SpringApplication.run(PlusoneApplication.class, args);
|
||||
}
|
||||
|
||||
|
@@ -1,12 +1,11 @@
|
||||
package xyz.zhouxy.plusone;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.File;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.IOException;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
|
||||
@@ -24,10 +23,7 @@ class FastDFSTests {
|
||||
|
||||
@Test
|
||||
void testOSS() throws FileNotFoundException, IOException, FastDFSException {
|
||||
try (FileInputStream in = new FileInputStream("D:\\ZhouXY\\Desktop\\666.png");) {
|
||||
byte[] content = IOUtils.toByteArray(in);
|
||||
String[] upload = fastDFSUtil.upload(new FastDFSFile("666.png", content, "png"));
|
||||
log.info(String.join("/", upload));
|
||||
}
|
||||
String[] upload = fastDFSUtil.upload(FastDFSFile.of(new File("D:\\ZhouXY\\Desktop\\666.png")));
|
||||
log.info(String.join("/", upload));
|
||||
}
|
||||
}
|
||||
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.exception;
|
||||
package xyz.zhouxy.plusone.system.application.common.exception;
|
||||
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.exception;
|
||||
package xyz.zhouxy.plusone.system.application.common.exception;
|
||||
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.exception;
|
||||
package xyz.zhouxy.plusone.system.application.common.exception;
|
||||
|
||||
import xyz.zhouxy.plusone.validator.InvalidInputException;
|
||||
|
@@ -1,14 +1,12 @@
|
||||
package xyz.zhouxy.plusone.system.application.exception.handler;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
package xyz.zhouxy.plusone.system.application.common.exception.handler;
|
||||
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.ExceptionHandler;
|
||||
import org.springframework.web.bind.annotation.RestControllerAdvice;
|
||||
|
||||
import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountLoginException;
|
||||
|
||||
@RestControllerAdvice
|
||||
public class AccountLoginExceptionHandler extends BaseExceptionHandler {
|
||||
@@ -18,7 +16,7 @@ public class AccountLoginExceptionHandler extends BaseExceptionHandler {
|
||||
}
|
||||
|
||||
@ExceptionHandler({ AccountLoginException.class })
|
||||
public ResponseEntity<RestfulResult> handleException(@Nonnull Exception e) {
|
||||
public ResponseEntity<RestfulResult> handleException(Exception e) {
|
||||
return buildExceptionResponse(e);
|
||||
}
|
||||
}
|
@@ -1,4 +1,6 @@
|
||||
package xyz.zhouxy.plusone.system.application.exception.handler;
|
||||
package xyz.zhouxy.plusone.system.application.common.exception.handler;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
@@ -14,7 +16,7 @@ import cn.dev33.satoken.exception.NotSafeException;
|
||||
import cn.dev33.satoken.exception.SaTokenException;
|
||||
import cn.dev33.satoken.exception.SameTokenInvalidException;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import xyz.zhouxy.plusone.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.exception.handler.BaseExceptionHandler;
|
||||
import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
|
||||
/**
|
||||
@@ -27,7 +29,7 @@ import xyz.zhouxy.plusone.commons.util.RestfulResult;
|
||||
public class SaTokenExceptionHandler extends BaseExceptionHandler {
|
||||
|
||||
|
||||
public SaTokenExceptionHandler(ExceptionInfoHolder exceptionInfoHolder) {
|
||||
public SaTokenExceptionHandler(@Nonnull ExceptionInfoHolder exceptionInfoHolder) {
|
||||
super(exceptionInfoHolder);
|
||||
set(NotPermissionException.class, 4030103, "会话未能通过权限认证", HttpStatus.FORBIDDEN);
|
||||
set(NotRoleException.class, 4030103, "会话未能通过角色认证", HttpStatus.FORBIDDEN);
|
@@ -0,0 +1,138 @@
|
||||
package xyz.zhouxy.plusone.system.application.common.model;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import java.util.OptionalInt;
|
||||
import java.util.OptionalLong;
|
||||
import java.util.OptionalDouble;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import xyz.zhouxy.plusone.exception.BizException;
|
||||
|
||||
public class AuthenticationInfo<T> {
|
||||
|
||||
/** token 值 */
|
||||
private final String token;
|
||||
|
||||
/** 此 token 对应的LoginId,未登录时不会构建此类的实例 */
|
||||
private final T loginId;
|
||||
|
||||
/** 账号类型 */
|
||||
private final String loginType;
|
||||
|
||||
/** 登录设备类型 */
|
||||
private final String deviceType;
|
||||
|
||||
/** 自定义数据 */
|
||||
@Nonnull
|
||||
private final Map<String, Object> metadata;
|
||||
|
||||
private AuthenticationInfo(String token, T loginId, String loginType, String deviceType,
|
||||
@Nonnull Map<String, Object> metadata) {
|
||||
this.token = token;
|
||||
this.loginId = loginId;
|
||||
this.loginType = loginType;
|
||||
this.deviceType = deviceType;
|
||||
this.metadata = metadata;
|
||||
}
|
||||
|
||||
public String getToken() {
|
||||
return token;
|
||||
}
|
||||
|
||||
public T getLoginId() {
|
||||
return loginId;
|
||||
}
|
||||
|
||||
public String getLoginType() {
|
||||
return loginType;
|
||||
}
|
||||
|
||||
public String getDeviceType() {
|
||||
return deviceType;
|
||||
}
|
||||
|
||||
private Object getObjFromMetadata(String key) {
|
||||
if (this.metadata.containsKey(key)) {
|
||||
return this.metadata.get(key);
|
||||
}
|
||||
throw new BizException(String.format("不存在 key 为 \"%s\"的元数据。", key));
|
||||
}
|
||||
|
||||
public OptionalDouble getMetadataAsDouble(String key) {
|
||||
Object valObj = getObjFromMetadata(key);
|
||||
if (valObj instanceof Double val) {
|
||||
return OptionalDouble.of(val.doubleValue());
|
||||
}
|
||||
return OptionalDouble.empty();
|
||||
}
|
||||
|
||||
public OptionalLong getMetadataAsLong(String key) {
|
||||
Object valObj = getObjFromMetadata(key);
|
||||
if (valObj instanceof Long val) {
|
||||
return OptionalLong.of(val.longValue());
|
||||
}
|
||||
return OptionalLong.empty();
|
||||
}
|
||||
|
||||
public OptionalInt getMetadataAsInt(String key) {
|
||||
Object valObj = getObjFromMetadata(key);
|
||||
if (valObj instanceof Integer val) {
|
||||
return OptionalInt.of(val.intValue());
|
||||
}
|
||||
return OptionalInt.empty();
|
||||
}
|
||||
|
||||
public Optional<String> getMetadataAsString(String key) {
|
||||
Object valObj = getObjFromMetadata(key);
|
||||
if (valObj instanceof String val) {
|
||||
return Optional.of(val);
|
||||
}
|
||||
return Optional.empty();
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public <C> Optional<C> getMetadata(String key, Class<C> type) {
|
||||
Object valObj = getObjFromMetadata(key);
|
||||
if (valObj == null || !type.isAssignableFrom(valObj.getClass())) {
|
||||
return Optional.empty();
|
||||
}
|
||||
return Optional.of((C) valObj);
|
||||
}
|
||||
|
||||
// ==========================================
|
||||
// builder
|
||||
|
||||
public static <T> Builder<T> builder(String token, T loginId, String loginType, String deviceType) {
|
||||
return new Builder<>(token, loginId, loginType, deviceType);
|
||||
}
|
||||
|
||||
public static final class Builder<T> {
|
||||
private final String token;
|
||||
private final T loginId;
|
||||
private final String loginType;
|
||||
private final String deviceType;
|
||||
|
||||
@Nonnull
|
||||
private final Map<String, Object> meta = new ConcurrentHashMap<>();
|
||||
|
||||
private Builder(String token, T loginId, String loginType, String deviceType) {
|
||||
this.token = token;
|
||||
this.loginId = loginId;
|
||||
this.loginType = loginType;
|
||||
this.deviceType = deviceType;
|
||||
}
|
||||
|
||||
public <C> Builder<T> putMetadata(String key, @Nullable C value) {
|
||||
this.meta.put(key, value);
|
||||
return this;
|
||||
}
|
||||
|
||||
public AuthenticationInfo<T> build() {
|
||||
return new AuthenticationInfo<>(token, loginId, loginType, deviceType, meta);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,21 @@
|
||||
package xyz.zhouxy.plusone.system.application.common.model;
|
||||
|
||||
public class PlusoneContext {
|
||||
private static final ThreadLocal<AuthenticationInfo<Long>> context = new ThreadLocal<>();
|
||||
|
||||
public static void setContext(AuthenticationInfo<Long> value) {
|
||||
context.set(value);
|
||||
}
|
||||
|
||||
public static AuthenticationInfo<Long> getContext() {
|
||||
return context.get();
|
||||
}
|
||||
|
||||
public static void remove() {
|
||||
context.remove();
|
||||
}
|
||||
|
||||
private PlusoneContext() {
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
}
|
@@ -2,6 +2,8 @@ package xyz.zhouxy.plusone.system.application.query;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.util.PageDTO;
|
||||
@@ -23,6 +25,7 @@ public interface AccountQueries {
|
||||
return PageDTO.of(content, total);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
List<AccountOverview> queryAccountOverview(AccountQueryParams queryParams);
|
||||
|
||||
long count(AccountQueryParams queryParams);
|
||||
|
@@ -8,9 +8,9 @@ import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import cn.dev33.satoken.stp.StpLogic;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.UnsupportedPrincipalTypeException;
|
||||
import xyz.zhouxy.plusone.system.application.common.util.PrincipalUtil;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.query.AccountQueries;
|
||||
import xyz.zhouxy.plusone.system.application.query.result.AccountDetails;
|
||||
import xyz.zhouxy.plusone.system.application.query.result.MenuViewObject;
|
||||
|
@@ -16,7 +16,7 @@ import org.springframework.web.bind.annotation.PathVariable;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.util.PageDTO;
|
||||
import xyz.zhouxy.plusone.exception.DataNotExistException;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.application.query.AccountQueries;
|
||||
import xyz.zhouxy.plusone.system.application.query.params.AccountQueryParams;
|
||||
import xyz.zhouxy.plusone.system.application.query.result.AccountDetails;
|
||||
@@ -94,7 +94,6 @@ public class AccountManagementService {
|
||||
Account account = accountRepository.find(id)
|
||||
.orElseThrow(() -> new DataNotExistException("该账号不存在"));
|
||||
account.setAccountInfo(command.getNickname(), command.getAvatar(), Sex.of(command.getSex()));
|
||||
account.setUpdatedBy(adminAuthLogic.getLoginIdAsLong());
|
||||
accountRepository.save(account);
|
||||
}
|
||||
|
||||
|
@@ -6,10 +6,10 @@ import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import cn.hutool.core.lang.Assert;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.UnsupportedPrincipalTypeException;
|
||||
import xyz.zhouxy.plusone.system.application.common.util.PrincipalType;
|
||||
import xyz.zhouxy.plusone.system.application.common.util.PrincipalUtil;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.query.AccountQueries;
|
||||
import xyz.zhouxy.plusone.system.application.query.result.LoginInfoViewObject;
|
||||
import xyz.zhouxy.plusone.system.application.service.command.LoginByOtpCommand;
|
||||
|
@@ -9,8 +9,8 @@ import org.springframework.util.Assert;
|
||||
import cn.hutool.core.util.RandomUtil;
|
||||
import xyz.zhouxy.plusone.mail.MailService;
|
||||
import xyz.zhouxy.plusone.sms.SmsService;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountLoginException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.domain.model.account.AccountRepository;
|
||||
import xyz.zhouxy.plusone.system.domain.model.account.Email;
|
||||
import xyz.zhouxy.plusone.system.domain.model.account.MobilePhone;
|
||||
|
@@ -16,7 +16,7 @@ import org.springframework.util.Assert;
|
||||
import xyz.zhouxy.plusone.constant.EntityStatus;
|
||||
import xyz.zhouxy.plusone.domain.IWithOrderNumber;
|
||||
import xyz.zhouxy.plusone.exception.DataNotExistException;
|
||||
import xyz.zhouxy.plusone.system.application.exception.UnsupportedMenuTypeException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.UnsupportedMenuTypeException;
|
||||
import xyz.zhouxy.plusone.system.application.query.result.MenuViewObject;
|
||||
import xyz.zhouxy.plusone.system.application.service.command.CreateMenuCommand;
|
||||
import xyz.zhouxy.plusone.system.application.service.command.UpdateMenuCommand;
|
||||
|
@@ -5,10 +5,10 @@ import java.util.Set;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.application.common.exception.UnsupportedPrincipalTypeException;
|
||||
import xyz.zhouxy.plusone.system.application.common.util.PrincipalType;
|
||||
import xyz.zhouxy.plusone.system.application.common.util.PrincipalUtil;
|
||||
import xyz.zhouxy.plusone.system.application.exception.AccountRegisterException;
|
||||
import xyz.zhouxy.plusone.system.application.service.command.RegisterAccountCommand;
|
||||
import xyz.zhouxy.plusone.system.domain.model.account.Account;
|
||||
import xyz.zhouxy.plusone.system.domain.model.account.AccountInfo;
|
||||
|
@@ -0,0 +1,20 @@
|
||||
package xyz.zhouxy.plusone.system.application.web.config;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.web.servlet.HandlerInterceptor;
|
||||
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
|
||||
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
|
||||
|
||||
@Configuration
|
||||
public class InterceptorConfig implements WebMvcConfigurer {
|
||||
@Autowired
|
||||
HandlerInterceptor[] interceptors;
|
||||
|
||||
@Override
|
||||
public void addInterceptors(InterceptorRegistry registry) {
|
||||
for (var interceptor : interceptors) {
|
||||
registry.addInterceptor(interceptor);
|
||||
}
|
||||
}
|
||||
}
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;
|
||||
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;
|
||||
import static xyz.zhouxy.plusone.commons.util.RestfulResult.success;
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.commons.util.RestfulResult.success;
|
||||
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;
|
||||
import static xyz.zhouxy.plusone.commons.util.RestfulResult.success;
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;
|
||||
import static xyz.zhouxy.plusone.commons.util.RestfulResult.success;
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import static xyz.zhouxy.plusone.commons.util.RestfulResult.success;
|
||||
|
@@ -1,4 +1,4 @@
|
||||
package xyz.zhouxy.plusone.system.application.controller;
|
||||
package xyz.zhouxy.plusone.system.application.web.controller;
|
||||
|
||||
import javax.validation.Valid;
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;
|
@@ -0,0 +1,32 @@
|
||||
package xyz.zhouxy.plusone.system.application.web.interceptor;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
import org.springframework.core.annotation.Order;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.servlet.HandlerInterceptor;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import xyz.zhouxy.plusone.system.application.common.model.PlusoneContext;
|
||||
import static xyz.zhouxy.plusone.system.constant.AuthLogic.adminAuthLogic;;
|
||||
|
||||
@Slf4j
|
||||
@Order(1)
|
||||
@Component
|
||||
public class HttpContextInterceptor implements HandlerInterceptor {
|
||||
|
||||
@Override
|
||||
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
|
||||
throws Exception {
|
||||
log.info("" + adminAuthLogic.isLogin());
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
|
||||
throws Exception {
|
||||
PlusoneContext.remove();
|
||||
log.info("拦截器清理 ThreadLocal,防止内存泄漏");
|
||||
}
|
||||
}
|
@@ -0,0 +1,7 @@
|
||||
/**
|
||||
* 拦截器
|
||||
*
|
||||
* @author <a href="https://gitee.com/zhouxy108">ZhouXY</a>
|
||||
* @since 1.0
|
||||
*/
|
||||
package xyz.zhouxy.plusone.system.application.web.interceptor;
|
@@ -1,15 +1,12 @@
|
||||
package xyz.zhouxy.plusone.system.util;
|
||||
|
||||
import java.math.BigInteger;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.security.MessageDigest;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.util.Arrays;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
import com.google.common.hash.Hashing;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import xyz.zhouxy.plusone.constant.ErrorCodeConsts;
|
||||
import xyz.zhouxy.plusone.exception.BizException;
|
||||
import xyz.zhouxy.plusone.util.RandomUtil;
|
||||
|
||||
/**
|
||||
@@ -17,7 +14,6 @@ import xyz.zhouxy.plusone.util.RandomUtil;
|
||||
*
|
||||
* @author <a href="https://gitee.com/zhouxy108">ZhouXY</a>
|
||||
*/
|
||||
@Slf4j
|
||||
public final class PasswordUtil {
|
||||
private static final char[] SALT_BASE_CHAR_ARRAY = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ~`!@#$%^&*()_-+={}[]|\\:;\"',.<>?/"
|
||||
.toCharArray();
|
||||
@@ -29,18 +25,18 @@ public final class PasswordUtil {
|
||||
* @param salt 随机盐
|
||||
* @return 哈希加密的结果
|
||||
*/
|
||||
@Nonnull
|
||||
public static String hashPassword(@Nonnull String password, @Nonnull String salt) {
|
||||
int length = salt.length();
|
||||
int i = length > 0 ? length / 2 : 0;
|
||||
var passwordWithSalt = salt.substring(0, i)
|
||||
+ password
|
||||
+ salt.substring(1);
|
||||
String sha512Hex = sha512Hex(passwordWithSalt);
|
||||
if (sha512Hex == null) {
|
||||
throw new BizException(ErrorCodeConsts.DEFAULT_ERROR_CODE, "未知错误:哈希加密失败!");
|
||||
}
|
||||
return sha512Hex;
|
||||
public static String hashPassword(String password, String salt) {
|
||||
Assert.notNull(password, "Password must not be null");
|
||||
Assert.notNull(salt, "Salt must not be null");
|
||||
return Hashing.sha512().newHasher()
|
||||
.putInt(Arrays.hashCode(salt.toCharArray()))
|
||||
.putString(password, StandardCharsets.UTF_8)
|
||||
.putInt(password.length())
|
||||
.putBoolean(password.length() % 2 == 0)
|
||||
.putString(salt, StandardCharsets.UTF_8)
|
||||
.putInt(Arrays.hashCode(password.toCharArray()))
|
||||
.hash()
|
||||
.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -56,16 +52,4 @@ public final class PasswordUtil {
|
||||
// 不允许实例化
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
|
||||
private static String sha512Hex(String data) {
|
||||
try {
|
||||
MessageDigest messageDigest = MessageDigest.getInstance("SHA-512");
|
||||
messageDigest.update(data.getBytes(StandardCharsets.UTF_8));
|
||||
byte[] result = messageDigest.digest();
|
||||
return new BigInteger(1, result).toString(16);
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
log.error("{}", e);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
@@ -6,6 +6,7 @@ import java.util.Optional;
|
||||
import java.util.Set;
|
||||
|
||||
import lombok.ToString;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.domain.AggregateRoot;
|
||||
import xyz.zhouxy.plusone.domain.IWithVersion;
|
||||
import xyz.zhouxy.plusone.exception.UserOperationException;
|
||||
@@ -164,6 +165,7 @@ public class Account extends AggregateRoot<Long> implements IWithVersion {
|
||||
return newInstance;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Account.class)
|
||||
public static Account register(
|
||||
Username username,
|
||||
Email email,
|
||||
@@ -193,6 +195,7 @@ public class Account extends AggregateRoot<Long> implements IWithVersion {
|
||||
password, status, accountInfo, roleRefs, createdBy, updatedBy, version);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Account.class)
|
||||
public static Account newInstance(
|
||||
String username,
|
||||
String email,
|
||||
@@ -210,6 +213,7 @@ public class Account extends AggregateRoot<Long> implements IWithVersion {
|
||||
return newInstance;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Account.class)
|
||||
public static Account register(
|
||||
String username,
|
||||
String email,
|
||||
@@ -265,10 +269,6 @@ public class Account extends AggregateRoot<Long> implements IWithVersion {
|
||||
return Optional.ofNullable(updatedBy);
|
||||
}
|
||||
|
||||
public void setUpdatedBy(long updatedBy) {
|
||||
this.updatedBy = updatedBy;
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getVersion() {
|
||||
return this.version;
|
||||
|
@@ -31,7 +31,6 @@ public final class AccountStatus extends Enumeration<AccountStatus> implements I
|
||||
return VALUE_SET.get(id);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static Collection<AccountStatus> constants() {
|
||||
return VALUE_SET.getValues();
|
||||
}
|
||||
|
@@ -4,6 +4,7 @@ import java.util.Objects;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import cn.hutool.core.util.DesensitizedUtil;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.constant.PatternConsts;
|
||||
|
||||
/**
|
||||
@@ -26,10 +27,12 @@ public class Email extends Principal {
|
||||
}
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Email.class)
|
||||
public static Email of(String email) {
|
||||
return new Email(email);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Email.class)
|
||||
public static Email ofNullable(String email) {
|
||||
return Objects.nonNull(email) ? new Email(email) : null;
|
||||
}
|
||||
|
@@ -4,6 +4,7 @@ import java.util.Objects;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import cn.hutool.core.util.DesensitizedUtil;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.constant.PatternConsts;
|
||||
|
||||
/**
|
||||
@@ -26,10 +27,12 @@ public class MobilePhone extends Principal {
|
||||
}
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(MobilePhone.class)
|
||||
public static MobilePhone of(String mobilePhone) {
|
||||
return new MobilePhone(mobilePhone);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(MobilePhone.class)
|
||||
public static MobilePhone ofNullable(String mobilePhone) {
|
||||
return Objects.nonNull(mobilePhone) ? new MobilePhone(mobilePhone) : null;
|
||||
}
|
||||
|
@@ -3,6 +3,7 @@ package xyz.zhouxy.plusone.system.domain.model.account;
|
||||
import java.util.Objects;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.constant.PatternConsts;
|
||||
import xyz.zhouxy.plusone.domain.ValidatableStringRecord;
|
||||
|
||||
@@ -26,10 +27,12 @@ public class Nickname extends ValidatableStringRecord {
|
||||
}
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Nickname.class)
|
||||
public static Nickname of(String nickname) {
|
||||
return new Nickname(nickname);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Nickname.class)
|
||||
public static Nickname ofNullable(String nickname) {
|
||||
return Objects.nonNull(nickname) ? new Nickname(nickname) : null;
|
||||
}
|
||||
|
@@ -3,14 +3,11 @@ package xyz.zhouxy.plusone.system.domain.model.account;
|
||||
import java.util.Objects;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.constant.PatternConsts;
|
||||
import xyz.zhouxy.plusone.constant.ErrorCodeConsts;
|
||||
import xyz.zhouxy.plusone.domain.IValueObject;
|
||||
import xyz.zhouxy.plusone.exception.BizException;
|
||||
import xyz.zhouxy.plusone.system.util.PasswordUtil;
|
||||
|
||||
/**
|
||||
@@ -23,43 +20,35 @@ public class Password implements IValueObject {
|
||||
private static final Pattern PATTERN = PatternConsts.PASSWORD;
|
||||
private static final String DEFAULT_PASSWORD = "A1b2C3d4";
|
||||
|
||||
@Nonnull
|
||||
private final String passwordVal;
|
||||
@Nonnull
|
||||
private final String saltVal;
|
||||
|
||||
private Password(String password) {
|
||||
if (password == null) {
|
||||
throw new IllegalArgumentException("密码不能为空");
|
||||
}
|
||||
if (!PATTERN.matcher(password).matches()) {
|
||||
throw new IllegalArgumentException("密码格式不符合要求");
|
||||
}
|
||||
var salt = PasswordUtil.generateRandomSalt();
|
||||
if (salt == null) {
|
||||
throw new BizException(ErrorCodeConsts.DEFAULT_ERROR_CODE, "未知错误:生成随机盐失败");
|
||||
}
|
||||
Assert.notNull(password, "密码不能为空");
|
||||
Assert.isTrue(PATTERN.matcher(password).matches(), "密码格式不符合要求");
|
||||
String salt = PasswordUtil.generateRandomSalt();
|
||||
this.saltVal = salt;
|
||||
this.passwordVal = PasswordUtil.hashPassword(password, salt);
|
||||
}
|
||||
|
||||
private Password(String password, String salt) {
|
||||
if (password == null || salt == null) {
|
||||
throw new IllegalArgumentException("password 和 salt 不能为空");
|
||||
}
|
||||
Assert.isTrue(password != null && salt != null, "password 和 salt 不能为空");
|
||||
this.passwordVal = password;
|
||||
this.saltVal = salt;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Password.class)
|
||||
public static Password of(String password, String salt) {
|
||||
return new Password(password, salt);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Password.class)
|
||||
public static Password newPassword(String newPassword, String passwordConfirmation) {
|
||||
Assert.isTrue(Objects.equals(newPassword, passwordConfirmation), "两次输入的密码不一致");
|
||||
return newPassword(newPassword);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Password.class)
|
||||
public static Password newPassword(String newPassword) {
|
||||
return new Password(newPassword);
|
||||
}
|
||||
@@ -80,6 +69,7 @@ public class Password implements IValueObject {
|
||||
return saltVal;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Nickname.class)
|
||||
public static Password newDefaultPassword() {
|
||||
return newPassword(DEFAULT_PASSWORD);
|
||||
}
|
||||
|
@@ -4,6 +4,7 @@ import java.util.Collection;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.util.Enumeration;
|
||||
import xyz.zhouxy.plusone.domain.IValueObject;
|
||||
|
||||
@@ -26,12 +27,11 @@ public final class Sex extends Enumeration<Sex> implements IValueObject {
|
||||
|
||||
private static final ValueSet<Sex> VALUE_SET = new ValueSet<>(UNSET, MALE, FEMALE);
|
||||
|
||||
@Nonnull
|
||||
@StaticFactoryMethod(Sex.class)
|
||||
public static Sex of(int value) {
|
||||
return VALUE_SET.get(value);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static Collection<Sex> constants() {
|
||||
return VALUE_SET.getValues();
|
||||
}
|
||||
|
@@ -2,6 +2,7 @@ package xyz.zhouxy.plusone.system.domain.model.account;
|
||||
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.commons.constant.PatternConsts;
|
||||
|
||||
/**
|
||||
@@ -24,6 +25,7 @@ public class Username extends Principal {
|
||||
}
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Username.class)
|
||||
public static Username of(String username) {
|
||||
return new Username(username);
|
||||
}
|
||||
|
@@ -8,6 +8,7 @@ import java.util.Optional;
|
||||
import java.util.Set;
|
||||
|
||||
import lombok.ToString;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.domain.AggregateRoot;
|
||||
import xyz.zhouxy.plusone.domain.IWithLabel;
|
||||
import xyz.zhouxy.plusone.domain.IWithVersion;
|
||||
@@ -70,12 +71,14 @@ public class Dict extends AggregateRoot<Long> implements IWithLabel, IWithVersio
|
||||
this.version = version;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Dict.class)
|
||||
public static Dict newInstance(
|
||||
String dictType,
|
||||
String dictLabel) {
|
||||
return new Dict(null, dictType, dictLabel, Collections.emptySet(), 0);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Dict.class)
|
||||
public static Dict newInstance(
|
||||
String dictType,
|
||||
String dictLabel,
|
||||
@@ -83,6 +86,7 @@ public class Dict extends AggregateRoot<Long> implements IWithLabel, IWithVersio
|
||||
return new Dict(null, dictType, dictLabel, values, 0);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Dict.class)
|
||||
public static Dict newInstance(
|
||||
String dictType,
|
||||
String dictLabel,
|
||||
|
@@ -4,6 +4,7 @@ import java.util.Objects;
|
||||
|
||||
import lombok.Getter;
|
||||
import lombok.ToString;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.domain.IValueObject;
|
||||
|
||||
/**
|
||||
@@ -25,6 +26,7 @@ public class DictValue implements IValueObject {
|
||||
this.label = label;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(DictValue.class)
|
||||
public static DictValue of(int key, String label) {
|
||||
return new DictValue(key, label);
|
||||
}
|
||||
|
@@ -2,6 +2,7 @@ package xyz.zhouxy.plusone.system.domain.model.menu;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.constant.EntityStatus;
|
||||
import xyz.zhouxy.plusone.system.domain.model.menu.Menu.MenuType;
|
||||
|
||||
@@ -16,6 +17,7 @@ public class MenuConstructor {
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Menu.class)
|
||||
public static Menu newMenuItem(
|
||||
long parentId,
|
||||
String path,
|
||||
@@ -39,6 +41,7 @@ public class MenuConstructor {
|
||||
remarks, component, cache, resource, actions, 0L);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Menu.class)
|
||||
public static Menu newMenuList(
|
||||
long parentId,
|
||||
String path,
|
||||
|
@@ -3,6 +3,7 @@ package xyz.zhouxy.plusone.system.domain.model.permission;
|
||||
import java.util.Optional;
|
||||
|
||||
import lombok.Getter;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.domain.Entity;
|
||||
import xyz.zhouxy.plusone.domain.IWithLabel;
|
||||
import xyz.zhouxy.plusone.domain.IWithVersion;
|
||||
@@ -20,7 +21,7 @@ public class Action extends Entity<Long> implements IWithLabel, IWithVersion {
|
||||
@Getter String label;
|
||||
@Getter long version;
|
||||
|
||||
public Action(Long id, String resource, String identifier, String label, long version) {
|
||||
private Action(Long id, String resource, String identifier, String label, long version) {
|
||||
this.id = id;
|
||||
this.resource = resource;
|
||||
this.identifier = identifier;
|
||||
@@ -28,10 +29,12 @@ public class Action extends Entity<Long> implements IWithLabel, IWithVersion {
|
||||
this.version = version;
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Action.class)
|
||||
static Action newInstance(String resource, String identifier, String label) {
|
||||
return new Action(null, resource, identifier, label, 0L);
|
||||
}
|
||||
|
||||
@StaticFactoryMethod(Action.class)
|
||||
static Action existingInstance(Long id, String resource, String action, String label, Long version) {
|
||||
return new Action(id, resource, action, label, version);
|
||||
}
|
||||
|
@@ -6,6 +6,7 @@ import java.util.Objects;
|
||||
import java.util.Optional;
|
||||
|
||||
import lombok.Getter;
|
||||
import xyz.zhouxy.plusone.commons.annotation.StaticFactoryMethod;
|
||||
import xyz.zhouxy.plusone.domain.AggregateRoot;
|
||||
import xyz.zhouxy.plusone.domain.IWithVersion;
|
||||
|
||||
@@ -37,6 +38,7 @@ public class Permission extends AggregateRoot<Long> implements IWithVersion {
|
||||
|
||||
// ==================== 实例化 ====================
|
||||
|
||||
@StaticFactoryMethod(Permission.class)
|
||||
public static Permission newInstance(String resource) {
|
||||
return new Permission(
|
||||
null, resource,
|
||||
|
2
pom.xml
2
pom.xml
@@ -25,7 +25,7 @@
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
|
||||
<spring-boot.version>2.7.10</spring-boot.version>
|
||||
<spring-boot.version>2.7.11</spring-boot.version>
|
||||
<sa-token.version>1.34.0</sa-token.version>
|
||||
<hutool.version>5.8.16</hutool.version>
|
||||
<mybatis-starter.version>3.0.1</mybatis-starter.version>
|
||||
|
Reference in New Issue
Block a user