commit 39f6b38e048263fa8071cec442b53c935380e43b Author: jieyuu <645634619@qq.com> Date: Sun Dec 29 21:57:47 2024 +0800 first commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..5ff6309 --- /dev/null +++ b/.gitignore @@ -0,0 +1,38 @@ +target/ +!.mvn/wrapper/maven-wrapper.jar +!**/src/main/**/target/ +!**/src/test/**/target/ + +### IntelliJ IDEA ### +.idea/modules.xml +.idea/jarRepositories.xml +.idea/compiler.xml +.idea/libraries/ +*.iws +*.iml +*.ipr + +### Eclipse ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache + +### NetBeans ### +/nbproject/private/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ +build/ +!**/src/main/**/build/ +!**/src/test/**/build/ + +### VS Code ### +.vscode/ + +### Mac OS ### +.DS_Store \ No newline at end of file diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..13566b8 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,8 @@ +# Default ignored files +/shelf/ +/workspace.xml +# Editor-based HTTP Client requests +/httpRequests/ +# Datasource local storage ignored files +/dataSources/ +/dataSources.local.xml diff --git a/.idea/encodings.xml b/.idea/encodings.xml new file mode 100644 index 0000000..e2ccb78 --- /dev/null +++ b/.idea/encodings.xml @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..385fcc6 --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,19 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/.idea/uiDesigner.xml b/.idea/uiDesigner.xml new file mode 100644 index 0000000..2b63946 --- /dev/null +++ b/.idea/uiDesigner.xml @@ -0,0 +1,124 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..94a25f7 --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/common/pom.xml b/common/pom.xml new file mode 100644 index 0000000..3619516 --- /dev/null +++ b/common/pom.xml @@ -0,0 +1,73 @@ + + + 4.0.0 + + net.carbon + CarbonNeutrality + 1.0-SNAPSHOT + + + common + + + org.projectlombok + lombok + + + + + org.springframework.boot + spring-boot-starter-web + + + + com.baomidou + mybatis-plus-boot-starter + + + + + io.springfox + springfox-boot-starter + + + + + org.apache.commons + commons-lang3 + + + + + commons-codec + commons-codec + + + + + io.jsonwebtoken + jjwt + + + + org.testng + testng + RELEASE + compile + + + + com.alibaba + fastjson + + + + + + 8 + 8 + UTF-8 + + + \ No newline at end of file diff --git a/common/src/main/java/net/carbon/config/MybatisPlusPageConfig.java b/common/src/main/java/net/carbon/config/MybatisPlusPageConfig.java new file mode 100644 index 0000000..4333bdb --- /dev/null +++ b/common/src/main/java/net/carbon/config/MybatisPlusPageConfig.java @@ -0,0 +1,30 @@ +package net.carbon.config; + + +import com.baomidou.mybatisplus.annotation.DbType; +import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor; +import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; + +@Configuration +public class MybatisPlusPageConfig { + + /* 旧版本配置 + @Bean + public PaginationInterceptor paginationInterceptor(){ + return new PaginationInterceptor(); + }*/ + + /** + * 新的分页插件,一缓和二缓遵循mybatis的规则, + * 需要设置 MybatisConfiguration#useDeprecatedExecutor = false 避免缓存出现问题 + */ + @Bean + public MybatisPlusInterceptor mybatisPlusInterceptor() { + MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor(); + interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL)); + return interceptor; + } + +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/config/SwaggerConfiguration.java b/common/src/main/java/net/carbon/config/SwaggerConfiguration.java new file mode 100644 index 0000000..3647f8a --- /dev/null +++ b/common/src/main/java/net/carbon/config/SwaggerConfiguration.java @@ -0,0 +1,118 @@ +package net.carbon.config; + + +import lombok.Data; +import org.springframework.context.annotation.Bean; +import org.springframework.http.HttpMethod; +import org.springframework.stereotype.Component; +import springfox.documentation.builders.*; +import springfox.documentation.oas.annotations.EnableOpenApi; +import springfox.documentation.schema.ScalarType; +import springfox.documentation.service.*; +import springfox.documentation.spi.DocumentationType; +import springfox.documentation.spring.web.plugins.Docket; + +import java.util.ArrayList; +import java.util.List; + +@Component +@EnableOpenApi +@Data +public class SwaggerConfiguration { + + + /** + * C端文档 + * @return + */ + @Bean + public Docket webApiDoc() { + + + return new Docket(DocumentationType.OAS_30) + .groupName("用户端接口文档") + .pathMapping("/") + // 定义是否开启swagger,false为关闭,可以通过变量控制,线上关闭 + .enable(true) + //配置api文档元信息 + .apiInfo(apiInfo()) + // 选择哪些接口作为swagger的doc发布 + .select() + .apis(RequestHandlerSelectors.basePackage("net.carbon")) + //正则匹配请求路径,并分配至当前分组 + .paths(PathSelectors.ant("/api/**")) + .build() + //新版swagger3.0配置 + .globalRequestParameters(getGlobalRequestParameters()) + .globalResponses(HttpMethod.GET, getGlobalResponseMessage()) + .globalResponses(HttpMethod.POST, getGlobalResponseMessage()); + } + + + private ApiInfo apiInfo() { + return new ApiInfoBuilder() + .title("碳中和") + .description("接口文档") + .contact(new Contact("jieyuu", "https://106.52.88.120", "645634619@qq.com")) + .version("12") + .build(); + } + + /** + * 管理端文档 + * @return + */ + @Bean + public Docket adminApiDoc() { + return new Docket(DocumentationType.OAS_30) + .groupName("管理端接口文档") + .pathMapping("/") + // 定义是否开启swagger,false为关闭,可以通过变量控制,线上关闭 + .enable(true) + //配置api文档元信息 + .apiInfo(apiInfo()) + // 选择哪些接口作为swagger的doc发布 + .select() + .apis(RequestHandlerSelectors.basePackage("net.jieyuu")) + //正则匹配请求路径,并分配至当前分组 + .paths(PathSelectors.ant("/admin/**")) + .build(); + } + + /** + * 生成全局通用参数, 支持配置多个响应参数 + * @return + */ + private List getGlobalRequestParameters() { + List parameters = new ArrayList<>(); + parameters.add(new RequestParameterBuilder() + .name("token") + .description("登录令牌") + .in(ParameterType.HEADER) + .query(q -> q.model(m -> m.scalarModel(ScalarType.STRING))) + .required(false) + .build()); + +// parameters.add(new RequestParameterBuilder() +// .name("version") +// .description("版本号") +// .required(true) +// .in(ParameterType.HEADER) +// .query(q -> q.model(m -> m.scalarModel(ScalarType.STRING))) +// .required(false) +// .build()); + return parameters; + } + + /** + * 生成通用响应信息 + * + * @return + */ + private List getGlobalResponseMessage() { + List responseList = new ArrayList<>(); + responseList.add(new ResponseBuilder().code("4xx").description("请求错误,根据code和msg检查").build()); + return responseList; + } + +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/enums/BizCodeEnum.java b/common/src/main/java/net/carbon/enums/BizCodeEnum.java new file mode 100644 index 0000000..dead2cf --- /dev/null +++ b/common/src/main/java/net/carbon/enums/BizCodeEnum.java @@ -0,0 +1,62 @@ +package net.carbon.enums; + +import lombok.Getter; + +/** + * @Description 状态码定义约束,共6位数,前三位代表服务,后4位代表接口 + * 比如 商品服务210,购物车是220、用户服务230,403代表权限 + **/ +public enum BizCodeEnum { + + + /** + * 通用操作码 + */ + OPS_REPEAT(110001, "重复操作"), + + /** + * 验证码 + */ + CODE_TO_ERROR(240001, "接收号码不合规"), + + CODE_LIMITED(240002, "验证码发送过快"), + + CODE_ERROR(240003, "验证码错误"), + + CODE_CAPTCHA(240101, "图形验证码错误"), + + /** + * 账号 + */ + ACCOUNT_REPEAT(250001, "账号已经存在"), + + ACCOUNT_UNREGISTER(250002, "账号不存在"), + + ACCOUNT_PWD_ERROR(250003, "账号或者密码错误"), + + ACCOUNT_UNLOGIN(250004, "账号未登录"), + + ILLEGAL_ARGUMENT(250005, "参数非法"), + + + /** + * 流控操作 + */ + + CONTROL_FLOW(500101, "限流控制"), + + CONTROL_DEGRADE(500201, "降级控制"), + + CONTROL_AUTH(500301, "认证控制"); + + @Getter + private int code; + + @Getter + private String message; + + private BizCodeEnum(int code, String message) { + this.code = code; + this.message = message; + } +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/exception/BizException.java b/common/src/main/java/net/carbon/exception/BizException.java new file mode 100644 index 0000000..1f79ff9 --- /dev/null +++ b/common/src/main/java/net/carbon/exception/BizException.java @@ -0,0 +1,25 @@ +package net.carbon.exception; + + +import lombok.Data; +import net.carbon.enums.BizCodeEnum; + +@Data +public class BizException extends RuntimeException { + + private Integer code; + private String msg; + + public BizException(Integer code, String message) { + super(message); + this.code = code; + this.msg = message; + } + + public BizException(BizCodeEnum bizCodeEnum) { + super(bizCodeEnum.getMessage()); + this.code = bizCodeEnum.getCode(); + this.msg = bizCodeEnum.getMessage(); + } + +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/handler/CustomExceptionHandle.java b/common/src/main/java/net/carbon/handler/CustomExceptionHandle.java new file mode 100644 index 0000000..ff9599a --- /dev/null +++ b/common/src/main/java/net/carbon/handler/CustomExceptionHandle.java @@ -0,0 +1,30 @@ +package net.carbon.handler; + +import lombok.extern.slf4j.Slf4j; +import net.carbon.exception.BizException; + +import net.carbon.utils.JsonData; +import org.springframework.web.bind.annotation.ControllerAdvice; +import org.springframework.web.bind.annotation.ExceptionHandler; +import org.springframework.web.bind.annotation.ResponseBody; + +@ControllerAdvice +@Slf4j +public class CustomExceptionHandle { + + @ExceptionHandler(value = Exception.class) + @ResponseBody + public JsonData Handle(Exception e) { + + if (e instanceof BizException) { + BizException bizException = (BizException) e; + log.info("[业务异常]{}", e); + return JsonData.buildCodeAndMsg(bizException.getCode(), bizException.getMsg()); + + } else { + log.info("[系统异常]{}", e); + return JsonData.buildError("全局异常,未知错误"); + } + + } +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/interceptor/LoginInterceptor.java b/common/src/main/java/net/carbon/interceptor/LoginInterceptor.java new file mode 100644 index 0000000..91e3ee7 --- /dev/null +++ b/common/src/main/java/net/carbon/interceptor/LoginInterceptor.java @@ -0,0 +1,66 @@ +package net.carbon.interceptor; + +import io.jsonwebtoken.Claims; +import lombok.extern.slf4j.Slf4j; + +import net.carbon.enums.BizCodeEnum; +import net.carbon.model.LoginUser; +import net.carbon.utils.CommonUtil; +import net.carbon.utils.JWTUtil; +import net.carbon.utils.JsonData; +import org.apache.commons.lang3.StringUtils; +import org.springframework.web.servlet.HandlerInterceptor; +import org.springframework.web.servlet.ModelAndView; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + + +@Slf4j +public class LoginInterceptor implements HandlerInterceptor { + + public static ThreadLocal threadLocal = new ThreadLocal<>(); + + @Override + public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { + String accessToken = request.getHeader("token"); + + if (accessToken == null) { + accessToken = request.getParameter("token"); + } + + //不为空 + if (StringUtils.isNotBlank(accessToken)) { + Claims claims = JWTUtil.checkJWT(accessToken); + if (claims == null) { + //未登录 + CommonUtil.sendJsonMessage(response, JsonData.buildResult(BizCodeEnum.ACCOUNT_UNLOGIN)); + return false; + } + long userId = Long.valueOf(claims.get("id").toString()); + String name = (String) claims.get("username"); + +// LoginUser loginUser = new LoginUser(); + + LoginUser loginUser = LoginUser.builder() + .id(userId) + .username(name) + .build(); + + //通过threadlocal传递用户信息 + threadLocal.set(loginUser); + return true; + } + //未登录 + CommonUtil.sendJsonMessage(response, JsonData.buildResult(BizCodeEnum.ACCOUNT_UNLOGIN)); + return false; + } + + @Override + public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { + } + + @Override + public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { + } +} diff --git a/common/src/main/java/net/carbon/model/LoginUser.java b/common/src/main/java/net/carbon/model/LoginUser.java new file mode 100644 index 0000000..dc0d3fe --- /dev/null +++ b/common/src/main/java/net/carbon/model/LoginUser.java @@ -0,0 +1,23 @@ +package net.carbon.model; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +@Data +@AllArgsConstructor +@NoArgsConstructor +@Builder +public class LoginUser { + /** + * 主键 + */ + private Long id; + + /** + * 名称 + */ + private String username; + +} diff --git a/common/src/main/java/net/carbon/result/Result.java b/common/src/main/java/net/carbon/result/Result.java new file mode 100644 index 0000000..4113008 --- /dev/null +++ b/common/src/main/java/net/carbon/result/Result.java @@ -0,0 +1,39 @@ +package net.carbon.result; + +import lombok.Data; + +import java.io.Serializable; + +/** + * 后端统一返回结果 + * + * @param + */ +@Data +public class Result implements Serializable { + + private Integer code; // 编码:1成功,0和其它数字为失败 + private String msg; // 错误信息 + private T data; // 数据 + + public static Result success() { + Result result = new Result(); + result.code = 1; + return result; + } + + public static Result success(T object) { + Result result = new Result(); + result.data = object; + result.code = 1; + return result; + } + + public static Result error(String msg) { + Result result = new Result<>(); + result.msg = msg; + result.code = 0; + return result; + } + +} diff --git a/common/src/main/java/net/carbon/utils/CheckUtil.java b/common/src/main/java/net/carbon/utils/CheckUtil.java new file mode 100644 index 0000000..01e8ec7 --- /dev/null +++ b/common/src/main/java/net/carbon/utils/CheckUtil.java @@ -0,0 +1,83 @@ +package net.carbon.utils; + +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +public class CheckUtil { + + /** + * 邮箱正则 + */ + private static final Pattern MAIL_PATTERN = Pattern.compile("^([a-z0-9A-Z]+[-|\\.]?)+[a-z0-9A-Z]@([a-z0-9A-Z]+(-[a-z0-9A-Z]+)?\\.)+[a-zA-Z]{2,}$"); + + /** + * 手机号正则,暂时未用 + */ + private static final Pattern PHONE_PATTERN = Pattern.compile("^((13[0-9])|(15[^4,\\D])|(18[0,5-9]))\\d{8}$"); + + /** + * 密码正则 + * 只能包含字母(大小写)和数字。 + * 长度必须在6到16个字符之间。 + */ + private static final Pattern PASSWORD_PATTERN = Pattern.compile("^[a-zA-Z0-9]{6,16}$"); + + /** + * 用户名正则 + * 用户名只能包含字母(大小写)和数字。 + * 用户名长度必须在6到16个字符之间。 + */ + private static final Pattern USERNAME_PATTERN = Pattern.compile("^[a-zA-Z0-9]{6,16}$"); + /** + * @param email + * @return + */ + public static boolean isEmail(String email) { + if (null == email || "".equals(email)) { + return false; + } + Matcher m = MAIL_PATTERN.matcher(email); + return m.matches(); + } + + /** + * 手机号验证 + * @param phone + * @return + */ + public static boolean isPhone(String phone) { + if (null == phone || "".equals(phone)) { + return false; + } + Matcher m = PHONE_PATTERN.matcher(phone); + return m.matches(); + + } + + /** + * 密码验证 + * @param password + * @return + */ + public static boolean isPassword(String password) { + if (null == password || "".equals(password)) { + return false; + } + Matcher m = PASSWORD_PATTERN.matcher(password); + return m.matches(); + } + + /** + * 用户名验证 + * @param username + * @return + */ + public static boolean isUsername(String username) { + if (null == username || "".equals(username)) { + return false; + } + Matcher m = USERNAME_PATTERN.matcher(username); + return m.matches(); + } + +} \ No newline at end of file diff --git a/common/src/main/java/net/carbon/utils/CommonUtil.java b/common/src/main/java/net/carbon/utils/CommonUtil.java new file mode 100644 index 0000000..c5abf48 --- /dev/null +++ b/common/src/main/java/net/carbon/utils/CommonUtil.java @@ -0,0 +1,165 @@ +package net.carbon.utils; + +import com.fasterxml.jackson.databind.ObjectMapper; +import lombok.extern.slf4j.Slf4j; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import java.io.IOException; +import java.io.PrintWriter; +import java.net.InetAddress; +import java.net.UnknownHostException; +import java.security.MessageDigest; +import java.util.Random; +import java.util.UUID; + +@Slf4j +public class CommonUtil { + + /** + * 获取ip + * + * @param request + * @return + */ + public static String getIpAddr(HttpServletRequest request) { + String ipAddress = null; + try { + ipAddress = request.getHeader("x-forwarded-for"); + if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) { + ipAddress = request.getHeader("Proxy-Client-IP"); + } + if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) { + ipAddress = request.getHeader("WL-Proxy-Client-IP"); + } + if (ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) { + ipAddress = request.getRemoteAddr(); + if (ipAddress.equals("127.0.0.1")) { + // 根据网卡取本机配置的IP + InetAddress inet = null; + try { + inet = InetAddress.getLocalHost(); + } catch (UnknownHostException e) { + e.printStackTrace(); + } + ipAddress = inet.getHostAddress(); + } + } + // 对于通过多个代理的情况,第一个IP为客户端真实IP,多个IP按照','分割 + if (ipAddress != null && ipAddress.length() > 15) { + // "***.***.***.***".length() + // = 15 + if (ipAddress.indexOf(",") > 0) { + ipAddress = ipAddress.substring(0, ipAddress.indexOf(",")); + } + } + } catch (Exception e) { + ipAddress = ""; + } + return ipAddress; + } + + + /** + * MD5加密 + * + * @param data + * @return + */ + public static String MD5(String data) { + try { + MessageDigest md = MessageDigest.getInstance("MD5"); + byte[] array = md.digest(data.getBytes("UTF-8")); + StringBuilder sb = new StringBuilder(); + for (byte item : array) { + sb.append(Integer.toHexString((item & 0xFF) | 0x100).substring(1, 3)); + } + + return sb.toString().toUpperCase(); + } catch (Exception exception) { + } + return null; + + } + + /** + * 生成随机数 + * + * @param length + * @return + */ + + public static String getRandomCode(int length) { + String sources = "0123456789"; + Random random = new Random(); + StringBuilder stringBuilder = new StringBuilder(); + for (int i = 0; i < length; i++) { + stringBuilder.append(sources.charAt(random.nextInt(9))); + } + return stringBuilder.toString(); + + } + + /** + * 生成UUID + * + * @return + */ + public static String generateUUID() { + return UUID.randomUUID().toString() + //删除- + .replaceAll("-", "") + //截取前32位 + .substring(0, 32); + } + + /** + * 获取当前时间戳 + * + * @return + */ + public static long getCurrentTimestamp() { + return System.currentTimeMillis(); + } + + /** + * 生成指定长度随机串 + * + * @param length + * @return + */ + private static final String ALL_CHAR_NUM = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + + public static String getStringNumRandom(int length) { + //生成随机数字和字母, + Random random = new Random(); + StringBuilder saltString = new StringBuilder(length); + for (int i = 1; i <= length; ++i) { + saltString.append(ALL_CHAR_NUM.charAt(random.nextInt(ALL_CHAR_NUM.length()))); + } + return saltString.toString(); + } + + /** + * 响应json数据给前端 + * @param response + * @param obj + */ + public static void sendJsonMessage(HttpServletResponse response, Object obj) { + ObjectMapper objectMapper = new ObjectMapper(); + + response.setContentType("application/json; charset=utf-8"); + + try(PrintWriter writer=response.getWriter()){ + writer.print(objectMapper.writeValueAsString(obj)); + writer.close(); + + response.flushBuffer(); + + }catch(IOException e){ + log.warn("响应json数据给前端异常:{}",e); + } + + } + +} diff --git a/common/src/main/java/net/carbon/utils/JWTUtil.java b/common/src/main/java/net/carbon/utils/JWTUtil.java new file mode 100644 index 0000000..ac3bb15 --- /dev/null +++ b/common/src/main/java/net/carbon/utils/JWTUtil.java @@ -0,0 +1,76 @@ +package net.carbon.utils; + + +import io.jsonwebtoken.Claims; +import io.jsonwebtoken.Jwts; +import io.jsonwebtoken.SignatureAlgorithm; +import lombok.extern.slf4j.Slf4j; +import net.carbon.model.LoginUser; + +import java.util.Date; + + +@Slf4j +public class JWTUtil { + + /** + * 过期时间 + * 1000毫秒 * 60秒 * 60分钟 * 24小时 * 7天 * 10 + */ + private static final long EXPIRE = 1000 * 60 * 60 * 24 * 7 * 10; + + /** + * 加密密钥 + */ + private static final String SECRET = "net.carbon.xyz"; + /** + * 令牌前缀 + */ + private static final String TOKEN_PREFIX = "carbon"; + + /** + * 令牌前缀 + */ + private static final String SUBJECT = "carbonemission"; + + /** + * 根据用户信息,生成令牌 + * + * @param user + * @return + */ + public static String geneJsonWebToken(LoginUser user) { + Long userId = user.getId(); + String token = Jwts.builder().setSubject(SUBJECT) + .claim("id", userId) + .claim("username", user.getUsername()) + .setIssuedAt(new Date()) + .setExpiration(new Date(System.currentTimeMillis() + EXPIRE)) + .signWith(SignatureAlgorithm.HS256, SECRET).compact(); + + token = TOKEN_PREFIX + token; + return token; + } + + + /** + * 校验token的方法 + * + * @param token + * @return + */ + public static Claims checkJWT(String token) { + try { + final Claims claims = Jwts.parser() + .setSigningKey(SECRET) + .parseClaimsJws(token.replace(TOKEN_PREFIX, "")) + .getBody(); + + return claims; + + } catch (Exception e) { + log.info("jwt token解密失败"); + return null; + } + } +} diff --git a/common/src/main/java/net/carbon/utils/JsonData.java b/common/src/main/java/net/carbon/utils/JsonData.java new file mode 100644 index 0000000..67b4255 --- /dev/null +++ b/common/src/main/java/net/carbon/utils/JsonData.java @@ -0,0 +1,90 @@ +package net.carbon.utils; + +import com.alibaba.fastjson.JSON; +import com.alibaba.fastjson.TypeReference; +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; +import net.carbon.enums.BizCodeEnum; + +@Data +@AllArgsConstructor +@NoArgsConstructor +public class JsonData { + + /** + * 状态码 0 表示成功,1表示处理中,-1表示失败 + */ + private Integer code; + + /** + * 数据 + */ + private Object data; + + /** + * 描述 + */ + private String msg; + + + /** + * 获取远程调用数据对象 + * 注意 支持多单词下划线转驼峰(序列化和反序列化) + * 空对象不序列化 + */ + public T getData(TypeReference typeReference) { + return JSON.parseObject(JSON.toJSONString(data), typeReference); + } + + /** + * 成功,传入数据 + * + * @return + */ + public static JsonData buildSuccess() { + return new JsonData(0, null, null); + } + + /** + * 成功,传入数据 + * + * @param data + * @return + */ + public static JsonData buildSuccess(Object data) { + return new JsonData(0, data, null); + } + + /** + * 失败,传入描述信息 + * + * @param msg + * @return + */ + public static JsonData buildError(String msg) { + return new JsonData(-1, null, msg); + } + + + /** + * 自定义状态码和错误信息 + * + * @param code + * @param msg + * @return + */ + public static JsonData buildCodeAndMsg(int code, String msg) { + return new JsonData(code, null, msg); + } + + /** + * 传入枚举,返回信息 + * + * @param codeEnum + * @return + */ + public static JsonData buildResult(BizCodeEnum codeEnum) { + return JsonData.buildCodeAndMsg(codeEnum.getCode(), codeEnum.getMessage()); + } +} \ No newline at end of file diff --git a/pom.xml b/pom.xml new file mode 100644 index 0000000..f3e2ca8 --- /dev/null +++ b/pom.xml @@ -0,0 +1,173 @@ + + + 4.0.0 + + net.carbon + CarbonNeutrality + 1.0-SNAPSHOT + pom + + + common + server + + + + 1.8 + 8 + 8 + UTF-8 + + 2.3.3.RELEASE + 3.4.0 + 1.18.16 + 3.9 + 1.15 + 3.0.0 + 0.7.0 + 2.0 + 1.2.62 + + + true + + + + + + + + + org.springframework.boot + spring-boot-dependencies + ${spring.boot.version} + pom + import + + + + + + com.baomidou + mybatis-plus-boot-starter + ${mybatisplus.boot.starter.version} + + + + + + org.projectlombok + lombok + ${lombok.version} + + + + + + org.apache.commons + commons-lang3 + ${commons.lang3.version} + + + + + + commons-codec + commons-codec + ${commons.codec.version} + + + + + io.springfox + springfox-boot-starter + ${springfox.boot.starter.version} + + + + io.jsonwebtoken + jjwt + ${jjwt.version} + + + + + org.springframework.boot + spring-boot-starter-test + ${spring.boot.version} + + + + + org.apache.velocity + velocity-engine-core + ${velocity-engine-core.version} + + + + com.alibaba + fastjson + ${fastjson.version} + + + + + io.springfox + springfox-boot-starter + ${springfox.boot.starter.version} + + + + + + + + + maven-ali + http://maven.aliyun.com/nexus/content/groups/public/ + + true + + + true + always + fail + + + + + + + + public + aliyun nexus + http://maven.aliyun.com/nexus/content/groups/public/ + + true + + + false + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/server/pom.xml b/server/pom.xml new file mode 100644 index 0000000..e37d28c --- /dev/null +++ b/server/pom.xml @@ -0,0 +1,55 @@ + + + 4.0.0 + + net.carbon + CarbonNeutrality + 1.0-SNAPSHOT + + + server + + + 8 + 8 + UTF-8 + + + + + + net.carbon + common + 1.0-SNAPSHOT + + + + + + org.springframework.boot + spring-boot-starter-test + + + + + com.baomidou + mybatis-plus-generator + 3.4.1 + + + + + org.apache.velocity + velocity-engine-core + + + + mysql + mysql-connector-java + + + + + \ No newline at end of file diff --git a/server/src/main/java/net/carbon/ServerApplication.java b/server/src/main/java/net/carbon/ServerApplication.java new file mode 100644 index 0000000..883f6d1 --- /dev/null +++ b/server/src/main/java/net/carbon/ServerApplication.java @@ -0,0 +1,18 @@ +package net.carbon; + + +import org.mybatis.spring.annotation.MapperScan; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.transaction.annotation.EnableTransactionManagement; + + +@SpringBootApplication +@EnableTransactionManagement +@MapperScan("net.carbon.mapper") +public class ServerApplication { + + public static void main(String[] args) { + SpringApplication.run(ServerApplication.class, args); + } +} diff --git a/server/src/main/java/net/carbon/config/InterceptorConfig.java b/server/src/main/java/net/carbon/config/InterceptorConfig.java new file mode 100644 index 0000000..2c25a01 --- /dev/null +++ b/server/src/main/java/net/carbon/config/InterceptorConfig.java @@ -0,0 +1,24 @@ +package net.carbon.config; + +import lombok.extern.slf4j.Slf4j; +import net.carbon.interceptor.LoginInterceptor; +import org.springframework.context.annotation.Configuration; +import org.springframework.web.servlet.config.annotation.InterceptorRegistry; +import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; + +@Configuration +@Slf4j +public class InterceptorConfig implements WebMvcConfigurer { + + @Override + public void addInterceptors(InterceptorRegistry registry) { + registry + .addInterceptor(new LoginInterceptor()) + //拦截的路径 +// .addPathPatterns("/api/user/*/**", "/api/**/*/**") + //放行的路径 + .excludePathPatterns("/api/user/*/register", "/api/user/*/login"); + + WebMvcConfigurer.super.addInterceptors(registry); + } +} diff --git a/server/src/main/java/net/carbon/controller/CarbonEmissionController.java b/server/src/main/java/net/carbon/controller/CarbonEmissionController.java new file mode 100644 index 0000000..f6a967c --- /dev/null +++ b/server/src/main/java/net/carbon/controller/CarbonEmissionController.java @@ -0,0 +1,48 @@ +package net.carbon.controller; + + +import net.carbon.service.CarbonEmissionService; +import net.carbon.utils.JsonData; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.*; + +/** + *

+ * 前端控制器 + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +@RestController +@RequestMapping("/api/carbon/v1") +public class CarbonEmissionController { + + @Autowired + private CarbonEmissionService carbonEmissionService; + + /** + * 及时预警接口 + * + * @param city + * @return + */ + @GetMapping("timelyAlert") + public JsonData timelyAlert(@RequestBody String city) { + return JsonData.buildSuccess(carbonEmissionService.timelyAlert(city)); + } + + /** + * 获取数据 + * + * @param city + * @return + */ + @GetMapping("getCarbonEmissionData") + public JsonData getCarbonEmissionData(@RequestBody String city) { + return JsonData.buildSuccess(carbonEmissionService.getCarbonEmissionData(city)); + } + + +} + diff --git a/server/src/main/java/net/carbon/controller/UserController.java b/server/src/main/java/net/carbon/controller/UserController.java new file mode 100644 index 0000000..f570796 --- /dev/null +++ b/server/src/main/java/net/carbon/controller/UserController.java @@ -0,0 +1,57 @@ + + +// 用户登录demo +package net.carbon.controller; + + +import io.swagger.annotations.ApiOperation; +import io.swagger.annotations.ApiParam; +import net.carbon.request.UserRegisterRequest; +import net.carbon.request.UserLoginRequest; +import net.carbon.service.UserService; +import net.carbon.utils.JsonData; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/api/user/v1") +public class UserController { + + @Autowired + private UserService userService; + + /** + * 用户注册 + * + * @param registerRequest + * @return + */ + @ApiOperation("用户注册") + @PostMapping(value = "register") + public JsonData register( + @ApiParam(value = "用户注册对象", required = true) + @RequestBody UserRegisterRequest registerRequest) { + JsonData jsonData = userService.register(registerRequest); + + return jsonData; + } + + /** + * 用户登录 + * + * @param loginRequest + * @return + */ + + @ApiOperation("用户登录") + @PostMapping("login") + public JsonData userLogin(@ApiParam("用户登陆对象") @RequestBody UserLoginRequest loginRequest) { + + JsonData jsonData = userService.login(loginRequest); + return jsonData; + } + +} \ No newline at end of file diff --git a/server/src/main/java/net/carbon/mapper/CarbonEmissionMapper.java b/server/src/main/java/net/carbon/mapper/CarbonEmissionMapper.java new file mode 100644 index 0000000..d43c724 --- /dev/null +++ b/server/src/main/java/net/carbon/mapper/CarbonEmissionMapper.java @@ -0,0 +1,16 @@ +package net.carbon.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import net.carbon.model.CarbonEmissionDO; + +/** + *

+ * Mapper 接口 + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +public interface CarbonEmissionMapper extends BaseMapper { + +} diff --git a/server/src/main/java/net/carbon/mapper/UserMapper.java b/server/src/main/java/net/carbon/mapper/UserMapper.java new file mode 100644 index 0000000..615066a --- /dev/null +++ b/server/src/main/java/net/carbon/mapper/UserMapper.java @@ -0,0 +1,17 @@ +package net.carbon.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import net.carbon.model.UserDO; + + +/** + *

+ * Mapper 接口 + *

+ * + * @author jieyuu + * @since 2024-11-23 + */ +public interface UserMapper extends BaseMapper { + +} diff --git a/server/src/main/java/net/carbon/model/CarbonEmissionDO.java b/server/src/main/java/net/carbon/model/CarbonEmissionDO.java new file mode 100644 index 0000000..0d9e62c --- /dev/null +++ b/server/src/main/java/net/carbon/model/CarbonEmissionDO.java @@ -0,0 +1,61 @@ +package net.carbon.model; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; +import lombok.EqualsAndHashCode; + +import java.io.Serializable; +import java.math.BigDecimal; + +/** + *

+ * + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +@Data +@EqualsAndHashCode(callSuper = false) +@TableName("carbon_emission") +public class CarbonEmissionDO implements Serializable { + + private static final long serialVersionUID = 1L; + + @TableId(value = "id", type = IdType.AUTO) + private Integer id; + + private String city; + + private BigDecimal wastewaterDischargeTotal; + + private BigDecimal airQualityAchievementRate; + + private BigDecimal gdpElectricityConsumption; + + private BigDecimal wasteResourceIndustryValue; + + private BigDecimal forestCoverageRate; + + private BigDecimal ecologicalIndex; + + private BigDecimal importExportTotal; + + private Integer foreignInvestmentEnterprises; + + private BigDecimal tourismIncome; + + private Integer overnightTourists; + + private BigDecimal publicManagementDensity; + + private BigDecimal perCapitaServiceFunds; + + private BigDecimal averageAnnualSalary; + + private BigDecimal urbanPerCapitaIncome; + + +} diff --git a/server/src/main/java/net/carbon/model/UserDO.java b/server/src/main/java/net/carbon/model/UserDO.java new file mode 100644 index 0000000..310a22b --- /dev/null +++ b/server/src/main/java/net/carbon/model/UserDO.java @@ -0,0 +1,31 @@ +package net.carbon.model; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; +import lombok.EqualsAndHashCode; + +import java.io.Serializable; + +/** + *

+ * + *

+ * + * @author jieyuu + * @since 2024-11-23 + */ +@Data +@EqualsAndHashCode(callSuper = false) +@TableName("user") +public class UserDO implements Serializable { + + private static final long serialVersionUID = 1L; + @TableId(value = "id", type = IdType.AUTO) + private Long id; + + private String username; + + private String password; +} diff --git a/server/src/main/java/net/carbon/request/UserLoginRequest.java b/server/src/main/java/net/carbon/request/UserLoginRequest.java new file mode 100644 index 0000000..1da367b --- /dev/null +++ b/server/src/main/java/net/carbon/request/UserLoginRequest.java @@ -0,0 +1,20 @@ +package net.carbon.request; + +import io.swagger.annotations.ApiModel; +import io.swagger.annotations.ApiModelProperty; +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; + +@Data +@ApiModel(value = "登录对象", description = "用户登录请求对象") +@AllArgsConstructor +@NoArgsConstructor +public class UserLoginRequest { + + @ApiModelProperty(value = "用户名", example = "jieyuu") + private String username; + + @ApiModelProperty(value = "密码", example = "123456") + private String password; +} diff --git a/server/src/main/java/net/carbon/request/UserRegisterRequest.java b/server/src/main/java/net/carbon/request/UserRegisterRequest.java new file mode 100644 index 0000000..d285996 --- /dev/null +++ b/server/src/main/java/net/carbon/request/UserRegisterRequest.java @@ -0,0 +1,17 @@ +package net.carbon.request; + +import io.swagger.annotations.ApiModel; +import io.swagger.annotations.ApiModelProperty; +import lombok.Data; + +@Data +@ApiModel(value = "用户注册实体类") +public class UserRegisterRequest { + + @ApiModelProperty(value = "用户名", example = "123456") + private String username; + + @ApiModelProperty(value = "密码", example = "123456") + private String password; + +} diff --git a/server/src/main/java/net/carbon/service/CarbonEmissionService.java b/server/src/main/java/net/carbon/service/CarbonEmissionService.java new file mode 100644 index 0000000..18cbf14 --- /dev/null +++ b/server/src/main/java/net/carbon/service/CarbonEmissionService.java @@ -0,0 +1,22 @@ +package net.carbon.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import net.carbon.model.CarbonEmissionDO; +import net.carbon.vo.CarbonVO; + + +/** + *

+ * 服务类 + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +public interface CarbonEmissionService extends IService { + + public Object timelyAlert(String city); + + + CarbonVO getCarbonEmissionData(String city); +} diff --git a/server/src/main/java/net/carbon/service/UserService.java b/server/src/main/java/net/carbon/service/UserService.java new file mode 100644 index 0000000..a0e911c --- /dev/null +++ b/server/src/main/java/net/carbon/service/UserService.java @@ -0,0 +1,36 @@ +package net.carbon.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import net.carbon.model.UserDO; + +import net.carbon.request.UserRegisterRequest; +import net.carbon.request.UserLoginRequest; +import net.carbon.utils.JsonData; + + +/** + *

+ * 服务类 + *

+ * + * @author jieyuu + * @since 2024-11-23 + */ +public interface UserService extends IService { + + /** + * 用户注册 + * + * @param userRegisterRequest + * @return + */ + JsonData register(UserRegisterRequest userRegisterRequest); + + /** + * 用户登录 + * + * @param loginRequest + * @return + */ + JsonData login(UserLoginRequest loginRequest); +} diff --git a/server/src/main/java/net/carbon/service/impl/CarbonEmissionServiceImpl.java b/server/src/main/java/net/carbon/service/impl/CarbonEmissionServiceImpl.java new file mode 100644 index 0000000..9a76b8c --- /dev/null +++ b/server/src/main/java/net/carbon/service/impl/CarbonEmissionServiceImpl.java @@ -0,0 +1,63 @@ +package net.carbon.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import net.carbon.mapper.CarbonEmissionMapper; +import net.carbon.model.CarbonEmissionDO; +import net.carbon.service.CarbonEmissionService; + + +import net.carbon.vo.CarbonTimelyAlertVO; +import net.carbon.vo.CarbonVO; +import org.apache.commons.lang3.StringUtils; +import org.springframework.beans.BeanUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +/** + *

+ * 服务实现类 + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +@Service +public class CarbonEmissionServiceImpl extends ServiceImpl implements CarbonEmissionService { + + @Autowired + private CarbonEmissionMapper carbonEmissionMapper; + + @Override + public CarbonTimelyAlertVO timelyAlert(String city) { + if (city == null || StringUtils.isBlank(city)) { + return null; + } + QueryWrapper queryWrapper = new QueryWrapper<>(); + queryWrapper.like("city", city); + + CarbonEmissionDO carbonEmissionDO = carbonEmissionMapper.selectOne(queryWrapper); + + CarbonTimelyAlertVO result = new CarbonTimelyAlertVO(); + BeanUtils.copyProperties(carbonEmissionDO, result); + + return result; + } + + @Override + public CarbonVO getCarbonEmissionData(String city) { + if (city == null || StringUtils.isBlank(city)) { + return null; + } + QueryWrapper queryWrapper = new QueryWrapper<>(); + queryWrapper.like("city", city); + + CarbonEmissionDO carbonEmissionDO = carbonEmissionMapper.selectOne(queryWrapper); + + CarbonVO result = new CarbonVO(); + BeanUtils.copyProperties(carbonEmissionDO, result); + + return result; + } +} diff --git a/server/src/main/java/net/carbon/service/impl/UserServiceImpl.java b/server/src/main/java/net/carbon/service/impl/UserServiceImpl.java new file mode 100644 index 0000000..0d82257 --- /dev/null +++ b/server/src/main/java/net/carbon/service/impl/UserServiceImpl.java @@ -0,0 +1,122 @@ +package net.carbon.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; + +import lombok.extern.slf4j.Slf4j; +import net.carbon.enums.BizCodeEnum; +import net.carbon.mapper.UserMapper; +import net.carbon.model.LoginUser; +import net.carbon.model.UserDO; + +import net.carbon.request.UserRegisterRequest; +import net.carbon.request.UserLoginRequest; +import net.carbon.service.UserService; +import net.carbon.utils.CheckUtil; +import net.carbon.utils.CommonUtil; +import net.carbon.utils.JWTUtil; +import net.carbon.utils.JsonData; +import org.apache.commons.codec.digest.Md5Crypt; +import org.springframework.beans.BeanUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Propagation; +import org.springframework.transaction.annotation.Transactional; + +import java.util.List; + +/** + *

+ * 服务实现类 + *

+ * + * @author jieyuu + * @since 2024-11-23 + */ +@Service +@Slf4j +public class UserServiceImpl extends ServiceImpl implements UserService { + + @Autowired + private UserMapper userMapper; + + @Override + @Transactional(rollbackFor = RuntimeException.class, propagation = Propagation.REQUIRED) + public JsonData register(UserRegisterRequest registerRequest) { + UserDO userDO = new UserDO(); + + BeanUtils.copyProperties(registerRequest, userDO); + String cryptPwd = CommonUtil.MD5(userDO.getPassword()); + userDO.setPassword(cryptPwd); + + if (CheckUtil.isUsername(registerRequest.getUsername()) || + CheckUtil.isPassword(registerRequest.getPassword())) { + + //账号唯一性检查 + if (checkUnique(userDO.getUsername())) { + //插入数据库 + int rows = userMapper.insert(userDO); + log.info("rows:{},注册成功{}", rows, userDO.toString()); + + return JsonData.buildSuccess(); + } else { + return JsonData.buildResult(BizCodeEnum.ACCOUNT_REPEAT); + } + } else { + return JsonData.buildResult(BizCodeEnum.ILLEGAL_ARGUMENT); + } + } + + + /** + * 校验用户账号唯一 + * + * @param username + * @return + */ + private boolean checkUnique(String username) { + QueryWrapper queryWrapper = new QueryWrapper().eq("username", username); + + List list = userMapper.selectList(queryWrapper); + + return list.size() > 0 ? false : true; + } + + /** + * 用户登陆注册 + *

+ * 判断用户注册情况 + * + * @param loginRequest + * @return + */ + @Override + public JsonData login(UserLoginRequest loginRequest) { + List userDOList = userMapper.selectList(new QueryWrapper().eq("username", loginRequest.getUsername())); + + if (userDOList != null && userDOList.size() == 1) { + //已经注册 + UserDO userDO = userDOList.get(0); + + String cryptPwd = CommonUtil.MD5(loginRequest.getPassword()); + if (cryptPwd.equals(userDO.getPassword())) { + //登陆成功 + //生成token令牌并且返回 + LoginUser loginUser = LoginUser.builder().build(); + BeanUtils.copyProperties(userDO, loginUser); + //accessToken + String accessToken = JWTUtil.geneJsonWebToken(loginUser); + // accessToken过期时间 + //UUID生成一个token + return JsonData.buildSuccess(accessToken); + } else { + return JsonData.buildResult(BizCodeEnum.ACCOUNT_PWD_ERROR); + } + + } else { + //未注册 + //这里选择 账号或密码错误,防止被爆破 + return JsonData.buildResult(BizCodeEnum.ACCOUNT_PWD_ERROR); + } + } +} diff --git a/server/src/main/java/net/carbon/vo/CarbonTimelyAlertVO.java b/server/src/main/java/net/carbon/vo/CarbonTimelyAlertVO.java new file mode 100644 index 0000000..6130840 --- /dev/null +++ b/server/src/main/java/net/carbon/vo/CarbonTimelyAlertVO.java @@ -0,0 +1,50 @@ +package net.carbon.vo; + +import lombok.Data; +import lombok.EqualsAndHashCode; + +import java.math.BigDecimal; + +/** + *

+ * + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ + +@Data +@EqualsAndHashCode(callSuper = false) +public class CarbonTimelyAlertVO { + private String city; + + private BigDecimal wastewaterDischargeTotal; + + private BigDecimal airQualityAchievementRate; + + private BigDecimal gdpElectricityConsumption; + + private BigDecimal wasteResourceIndustryValue; + + private BigDecimal forestCoverageRate; + + private BigDecimal ecologicalIndex; + + private BigDecimal importExportTotal; + + private Integer foreignInvestmentEnterprises; + + private BigDecimal tourismIncome; + + private Integer overnightTourists; + + private BigDecimal publicManagementDensity; + + private BigDecimal perCapitaServiceFunds; + + private BigDecimal averageAnnualSalary; + + private BigDecimal urbanPerCapitaIncome; + +} diff --git a/server/src/main/java/net/carbon/vo/CarbonVO.java b/server/src/main/java/net/carbon/vo/CarbonVO.java new file mode 100644 index 0000000..b87bccb --- /dev/null +++ b/server/src/main/java/net/carbon/vo/CarbonVO.java @@ -0,0 +1,42 @@ +package net.carbon.vo; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; +import lombok.EqualsAndHashCode; + +import java.io.Serializable; +import java.math.BigDecimal; + +/** + *

+ * + *

+ * + * @author jieyuu + * @since 2024-12-29 + */ +@Data +@EqualsAndHashCode(callSuper = false) +public class CarbonVO { + + private String city; + + private BigDecimal wastewaterDischargeTotal; + + private BigDecimal airQualityAchievementRate; + + private BigDecimal gdpElectricityConsumption; + + private BigDecimal wasteResourceIndustryValue; + + private BigDecimal forestCoverageRate; + + private BigDecimal ecologicalIndex; + + private BigDecimal importExportTotal; + + private Integer foreignInvestmentEnterprises; + +} diff --git a/server/src/main/resources/application.yml b/server/src/main/resources/application.yml new file mode 100644 index 0000000..2306418 --- /dev/null +++ b/server/src/main/resources/application.yml @@ -0,0 +1,19 @@ +server: + port: 8089 + +spring: + datasource: + driver-class-name: com.mysql.cj.jdbc.Driver + url: jdbc:mysql://106.52.88.120:3306/demo?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai + username: root + password: 59ae8683c59fead903132a8d440bd7d9fd4936529d1d6f45f9d41111d7537bdd + +#配置plus打印sql日志 +mybatis-plus: + configuration: + log-impl: org.apache.ibatis.logging.stdout.StdOutImpl + +#设置日志级别,ERROR/WARN/INFO/DEBUG,默认是INFO以上才显示 +logging: + level: + root: INFO diff --git a/server/src/main/resources/mapper/CarbonEmissionMapper.xml b/server/src/main/resources/mapper/CarbonEmissionMapper.xml new file mode 100644 index 0000000..649a828 --- /dev/null +++ b/server/src/main/resources/mapper/CarbonEmissionMapper.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + id, city, wastewater_discharge_total, air_quality_achievement_rate, gdp_electricity_consumption, waste_resource_industry_value, forest_coverage_rate, ecological_index, import_export_total, foreign_investment_enterprises, tourism_income, overnight_tourists, public_management_density, per_capita_service_funds, average_annual_salary, urban_per_capita_income + + + diff --git a/server/src/main/resources/mapper/UserMapper.xml b/server/src/main/resources/mapper/UserMapper.xml new file mode 100644 index 0000000..10f4150 --- /dev/null +++ b/server/src/main/resources/mapper/UserMapper.xml @@ -0,0 +1,18 @@ + + + + + + + + + + + + + + id + , username, password + + + diff --git a/server/src/test/java/biz/MyBatisPlusGenerator.java b/server/src/test/java/biz/MyBatisPlusGenerator.java new file mode 100644 index 0000000..e4f5ffc --- /dev/null +++ b/server/src/test/java/biz/MyBatisPlusGenerator.java @@ -0,0 +1,91 @@ +package net.jieyuu.db; + +import com.baomidou.mybatisplus.annotation.DbType; +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.generator.AutoGenerator; +import com.baomidou.mybatisplus.generator.config.DataSourceConfig; +import com.baomidou.mybatisplus.generator.config.GlobalConfig; +import com.baomidou.mybatisplus.generator.config.PackageConfig; +import com.baomidou.mybatisplus.generator.config.StrategyConfig; +import com.baomidou.mybatisplus.generator.config.rules.DateType; +import com.baomidou.mybatisplus.generator.config.rules.NamingStrategy; + +public class MyBatisPlusGenerator { + + public static void main(String[] args) { + //1. 全局配置 + GlobalConfig config = new GlobalConfig(); + // 是否支持AR模式 + config.setActiveRecord(true) + // 作者 + .setAuthor("jieyuu") + // 生成路径,最好使用绝对路径,window路径是不一样的 + .setOutputDir("D:\\workspace\\project\\CarbonNeutrality\\server\\src\\main\\java") + // 文件覆盖 + .setFileOverride(true) + // 主键策略 + .setIdType(IdType.AUTO) + + .setDateType(DateType.ONLY_DATE) + // 设置生成的service接口的名字的首字母是否为I,默认Service是以I开头的 + .setServiceName("%sService") + + //实体类结尾名称 + .setEntityName("%sDO") + + //生成基本的resultMap + .setBaseResultMap(true) + + //不使用AR模式 + .setActiveRecord(false) + + //生成基本的SQL片段 + .setBaseColumnList(true); + + //2. 数据源配置 + DataSourceConfig dsConfig = new DataSourceConfig(); + // 设置数据库类型 + dsConfig.setDbType(DbType.MYSQL) + .setDriverName("com.mysql.cj.jdbc.Driver") + .setUrl("jdbc:mysql://106.52.88.120:3306/demo?useSSL=false") + .setUsername("root") + .setPassword("59ae8683c59fead903132a8d440bd7d9fd4936529d1d6f45f9d41111d7537bdd"); + + //3. 策略配置globalConfiguration中 + StrategyConfig stConfig = new StrategyConfig(); + + //全局大写命名 + stConfig.setCapitalMode(true) + // 数据库表映射到实体的命名策略 + .setNaming(NamingStrategy.underline_to_camel) + + //使用lombok + .setEntityLombokModel(true) + + //使用restcontroller注解 + .setRestControllerStyle(true) + + // 生成的表, 支持多表一起生成,以数组形式填写 + .setInclude("carbon_emission"); + + //4. 包名策略配置 + PackageConfig pkConfig = new PackageConfig(); + pkConfig.setParent("net.jieyuu") + .setMapper("mapper") + .setService("service") + .setController("controller") + .setEntity("model") + .setXml("mapper"); + + //5. 整合配置 + AutoGenerator ag = new AutoGenerator(); + ag.setGlobalConfig(config) + .setDataSource(dsConfig) + .setStrategy(stConfig) + .setPackageInfo(pkConfig); + + //6. 执行操作 + ag.execute(); + System.out.println("======= Done 相关代码生成完毕 ========"); + } +} \ No newline at end of file