烽火云长椿街3.21 1:52

master
DanielDeng 4 months ago
parent 615c0558d9
commit 3c47fd0adc

@ -4,6 +4,7 @@ import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.annotation.ComponentScan;
/**
* @author dch
@ -12,6 +13,10 @@ import org.springframework.cloud.openfeign.EnableFeignClients;
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients
@ComponentScan(basePackages = {
"com.mashibing.api",
"com.mashibing.common"
})
public class ApiStarterApp {
public static void main(String[] args) {

@ -5,6 +5,7 @@ import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import java.util.Map;
import java.util.Set;
/**
* @author dch
@ -16,4 +17,13 @@ public interface BeaconCacheClient {
@GetMapping("/cache/hgetall/{key}")
Map hGetAll(@PathVariable(value = "key")String key);
@GetMapping("/cache/hget/{key}/{field}")
public Object hget(@PathVariable(value = "key")String key,@PathVariable(value = "field")String field);
@GetMapping("/cache/hget/{key}/{field}")
public String hgetString(@PathVariable(value = "key")String key,@PathVariable(value = "field")String field);
@GetMapping("/cache/smember/{key}")
Set<Map> smember(@PathVariable(value = "key")String key);
}

@ -0,0 +1,32 @@
package com.mashibing.api.config;
/**
* @author dch
* @create 2024-03-21 0:19
*/
import com.mashibing.common.constant.RabbitMQConstants;
import org.springframework.amqp.core.Queue;
import org.springframework.amqp.core.QueueBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
/**
* &
* @author zjw
* @description
*/
@Configuration
public class RabbitMQConfig {
/**
*
* @return
*/
@Bean
public Queue preSendQueue(){
return QueueBuilder.durable(RabbitMQConstants.SMS_PRE_SEND).build();
}
}

@ -0,0 +1,60 @@
package com.mashibing.api.config;
/**
* @author dch
* @create 2024-03-21 0:31
*/
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
/**
* RabbitTemplateconfirm&return
* @author zjw
* @description
*/
@Configuration
@Slf4j
public class RabbitTemplateConfig {
@Bean
public RabbitTemplate rabbitTemplate(ConnectionFactory connectionFactory){
//1、构建RabbitTemplate对象
RabbitTemplate rabbitTemplate = new RabbitTemplate();
//2、设置connectionFactory
rabbitTemplate.setConnectionFactory(connectionFactory);
//3、配置confirm机制
rabbitTemplate.setConfirmCallback(new RabbitTemplate.ConfirmCallback(){
@Override
public void confirm(CorrelationData correlationData, boolean ack, String cause) {
// ack为false代表消息没有发送到exchange。
if(!ack){
log.error("【接口模块-发送消息】 消息没有发送到交换机correlationData = {}cause = {}",correlationData,cause);
}
}
});
//4、配置return机制
rabbitTemplate.setReturnCallback(new RabbitTemplate.ReturnCallback(){
// 触发这个回调,说明交换机没有把消息路由到指定的队列中
@Override
public void returnedMessage(Message message, int replyCode, String replyText, String exchange, String routingKey) {
log.error("【接口模块-发送消息】 消息没有路由到指定的Queue。 message = {},exchange = {},routingKey = {}",
new String(message.getBody()),exchange,routingKey);
}
});
//5、返回
return rabbitTemplate;
}
}

@ -5,9 +5,13 @@ import com.mashibing.api.filter.CheckFilterContext;
import com.mashibing.api.form.SingleSendForm;
import com.mashibing.api.util.R;
import com.mashibing.api.vo.ResultVO;
import com.mashibing.common.constant.RabbitMQConstants;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.model.StandardSubmit;
import com.mashibing.common.util.SnowFlakeUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
@ -30,6 +34,12 @@ import javax.servlet.http.HttpServletRequest;
@Slf4j
public class SmsController {
@Autowired
private SnowFlakeUtil snowFlakeUtil;
@Autowired
private RabbitTemplate rabbitTemplate;
/**
* IP','
*/
@ -75,7 +85,13 @@ public class SmsController {
checkFilterContext.check(submit);
//============================基于雪花算法生成唯一标识sequenceId=================================
submit.setSequenceId(snowFlakeUtil.nextId());
//=========================发送到MQ交给策略模块处理=========================================
rabbitTemplate.convertAndSend(RabbitMQConstants.SMS_PRE_SEND,submit,new CorrelationData(submit.getSequenceId().toString()));
return R.ok();
}

@ -1,8 +1,14 @@
package com.mashibing.api.filter.impl;
import com.mashibing.api.client.BeaconCacheClient;
import com.mashibing.api.filter.CheckFilter;
import com.mashibing.common.constant.ApiConstant;
import com.mashibing.common.constant.CacheConstant;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import com.mashibing.common.model.StandardSubmit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
/**
@ -14,9 +20,49 @@ import org.springframework.stereotype.Service;
@Slf4j
public class FeeCheckFilter implements CheckFilter {
@Autowired
private BeaconCacheClient cacheClient;
/**
* 70
*/
private final int MAX_LENGTH = 70;
/**
* 7067/
*/
private final int LOOP_LENGTH = 67;
private final String BALANCE = "balance";
@Override
public void check(StandardSubmit submit) {
log.info("【接口模块-校验客户余额】 校验ing…………");
//1、从submit中获取到短信内容
int length = submit.getText().length();
//2、判断短信内容的长度如果小于等于70算作一条如果大于70字按照67字/条,算出来当前短信的费用
if(length <= MAX_LENGTH){
// 当前短信内容是一条
submit.setFee(ApiConstant.SINGLE_FEE);
}else{
int strip = length % LOOP_LENGTH == 0 ? length / LOOP_LENGTH : length / LOOP_LENGTH + 1;
submit.setFee(ApiConstant.SINGLE_FEE * strip);
}
//3、从Redis中查询出客户剩余的金额
Long balance = ((Integer) cacheClient.hget(CacheConstant.CLIENT_BALANCE + submit.getClientId(), BALANCE)).longValue();
//4、判断金额是否满足当前短信费用\
if(balance >= submit.getFee()){
log.info("【接口模块-校验客户余额】 用户金额充足!!");
return;
}
//5、不满足就抛出异常
log.info("【接口模块-校验客户余额】 客户余额不足");
throw new ApiException(ExceptionEnums.BALANCE_NOT_ENOUGH);
}
}
}

@ -1,8 +1,14 @@
package com.mashibing.api.filter.impl;
import com.alibaba.cloud.commons.lang.StringUtils;
import com.mashibing.api.client.BeaconCacheClient;
import com.mashibing.api.filter.CheckFilter;
import com.mashibing.common.constant.CacheConstant;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import com.mashibing.common.model.StandardSubmit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
/**
@ -13,8 +19,28 @@ import org.springframework.stereotype.Service;
@Service(value = "ip")
@Slf4j
public class IPCheckFilter implements CheckFilter {
@Autowired
private BeaconCacheClient cacheClient;
private final String IP_ADDRESS = "ipAddress";
@Override
public void check(StandardSubmit submit) {
log.info("【接口模块-校验ip】 校验ing…………");
//1. 根据CacheClient根据客户的apikey以及ipAddress去查询客户的IP白名单
String ip = cacheClient.hgetString(CacheConstant.CLIENT_BUSINESS + submit.getApikey(), IP_ADDRESS);
submit.setIp(ip);
//2. 如果IP白名单为null直接放行
if(StringUtils.isEmpty(ip) || ip.contains(submit.getRealIP())){
log.info("【接口模块-校验ip】 客户端请求IP合法");
return;
}
//3. IP白名单不为空并且客户端请求不在IP报名单内
log.info("【接口模块-校验ip】 请求的ip不在白名单内");
throw new ApiException(ExceptionEnums.IP_NOT_WHITE);
}
}
}

@ -1,6 +1,10 @@
package com.mashibing.api.filter.impl;
import com.alibaba.cloud.commons.lang.StringUtils;
import com.mashibing.api.filter.CheckFilter;
import com.mashibing.api.util.PhoneFormatCheckUtil;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import com.mashibing.common.model.StandardSubmit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
@ -18,5 +22,13 @@ public class MobileCheckFilter implements CheckFilter {
@Override
public void check(StandardSubmit submit) {
log.info("【接口模块-校验手机号】 校验ing…………");
String mobile = submit.getMobile();
if(!StringUtils.isEmpty(mobile) && PhoneFormatCheckUtil.isChinaPhone(mobile)){
// 如果校验进来,代表手机号么得问题
log.info("【接口模块-校验手机号】 手机号格式合法 mobile = {}",mobile);
return;
}
log.info("【接口模块-校验手机号】 手机号格式不正确 mobile = {}",mobile);
throw new ApiException(ExceptionEnums.ERROR_MOBILE);
}
}
}

@ -1,10 +1,20 @@
package com.mashibing.api.filter.impl;
import com.alibaba.cloud.commons.lang.StringUtils;
import com.mashibing.api.client.BeaconCacheClient;
import com.mashibing.api.filter.CheckFilter;
import com.mashibing.common.constant.ApiConstant;
import com.mashibing.common.constant.CacheConstant;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import com.mashibing.common.model.StandardSubmit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Map;
import java.util.Set;
/**
* @author dch
* @create 2024-03-18 23:22
@ -14,9 +24,55 @@ import org.springframework.stereotype.Service;
@Slf4j
public class SignCheckFilter implements CheckFilter {
@Autowired
private BeaconCacheClient cacheClient;
/**
*
*/
private final int SIGN_START_INDEX = 1;
/**
*
*/
private final String CLIENT_SIGN_INFO = "signInfo";
private final String SIGN_ID = "id";
@Override
public void check(StandardSubmit submit) {
log.info("【接口模块-校验签名】 校验ing…………");
//1. 判断短信内容是否携带了【】
String text = submit.getText();
if (!text.startsWith(ApiConstant.SIGN_PREFIX) || !text.contains(ApiConstant.SIGN_SUFFIX)) {
log.info("【接口模块-校验签名】 无可用签名 text = {}", text);
throw new ApiException(ExceptionEnums.ERROR_SIGN);
}
//2. 将短信内容中的签名截取出来
String sign = text.substring(SIGN_START_INDEX, text.indexOf(ApiConstant.SIGN_SUFFIX));
if (StringUtils.isEmpty(sign)) {
log.info("【接口模块-校验签名】 无可用签名 text = {}", text);
throw new ApiException(ExceptionEnums.ERROR_SIGN);
}
//3. 从缓存中查询出客户绑定的签名
Set<Map> set = cacheClient.smember(CacheConstant.CLIENT_SIGN + submit.getClientId());
if (set == null || set.size() == 0) {
log.info("【接口模块-校验签名】 无可用签名 text = {}", text);
throw new ApiException(ExceptionEnums.ERROR_SIGN);
}
//4. 判断~
for (Map map : set) {
if (sign.equals(map.get(CLIENT_SIGN_INFO))) {
submit.setSign(sign);
submit.setSignId(Long.parseLong(map.get(SIGN_ID) + ""));
log.info("【接口模块-校验签名】 找到匹配的签名 sign = {}", sign);
return;
}
}
//5. 到这,说明没有匹配的签名
log.info("【接口模块-校验签名】 无可用签名 text = {}", text);
throw new ApiException(ExceptionEnums.ERROR_SIGN);
}
}
}

@ -1,10 +1,19 @@
package com.mashibing.api.filter.impl;
import com.mashibing.api.client.BeaconCacheClient;
import com.mashibing.api.filter.CheckFilter;
import com.mashibing.common.constant.ApiConstant;
import com.mashibing.common.constant.CacheConstant;
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import com.mashibing.common.model.StandardSubmit;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Map;
import java.util.Set;
/**
* @author dch
* @create 2024-03-18 23:22
@ -14,9 +23,58 @@ import org.springframework.stereotype.Service;
@Slf4j
public class TemplateCheckFilter implements CheckFilter {
@Autowired
private BeaconCacheClient cacheClient;
/**
*
*/
private final String TEMPLATE_TEXT = "templateText";
private final String TEMPLATE_PLACEHOLDER = "#";
@Override
public void check(StandardSubmit submit) {
log.info("【接口模块-校验模板】 校验ing…………");
// 1、从submit中获取到短信内容签名信息签名id
String text = submit.getText();
String sign = submit.getSign();
Long signId = submit.getSignId();
// 2、将短信内容中的签名直接去掉获取短信具体内容
text = text.replace(ApiConstant.SIGN_PREFIX + sign + ApiConstant.SIGN_SUFFIX, "");
// 3、从缓存中获取到签名id绑定的所有模板
Set<Map> templates = cacheClient.smember(CacheConstant.CLIENT_TEMPLATE + signId);
// 4、在tempaltes不为null时遍历签名绑定的所有模板信息
if(templates != null && templates.size() > 0) {
for (Map template : templates) {
// 4.1 将模板内容和短信具体内容做匹配-true-匹配成功
String templateText = (String) template.get(TEMPLATE_TEXT);
if(text.equals(templateText)){
// 短信具体内容和模板是匹配的。
log.info("【接口模块-校验模板】 校验模板通过 templateText = {}",templateText);
return;
}
// 4.2 判断模板中是否只包含一个变量,如果是,直接让具体短信内容匹配前缀和后缀
// 例子您的验证码是123434。如非本人操作请忽略本短信
// 例子:您的验证码是#code#。如非本人操作,请忽略本短信
if(templateText != null && templateText.contains(TEMPLATE_PLACEHOLDER)
&& templateText.length() - templateText.replaceAll(TEMPLATE_PLACEHOLDER,"").length() == 2){
// 可以确认模板不为空,并且包含#符号,而且#符号有2个代表是一个占位符变量
// 获取模板撇去占位符之后的前缀和后缀
String templateTextPrefix = templateText.substring(0, templateText.indexOf(TEMPLATE_PLACEHOLDER));
String templateTextSuffix = templateText.substring(templateText.lastIndexOf(TEMPLATE_PLACEHOLDER) + 1);
// 判断短信的具体内容是否匹配前缀和后缀
if(text.startsWith(templateTextPrefix) && text.endsWith(templateTextSuffix)){
// 当前的短信内容匹配短信模板
log.info("【接口模块-校验模板】 校验模板通过 templateText = {}",templateText);
return;
}
}
}
}
// 5、 模板校验失败
log.info("【接口模块-校验模板】 无可用模板 text = {}",text);
throw new ApiException(ExceptionEnums.ERROR_TEMPLATE);
}
}
}

@ -0,0 +1,35 @@
package com.mashibing.api.util;
/**
* @author dch
* @create 2024-03-20 22:25
*/
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
*
*
* @author zjw
* @description
*/
public class PhoneFormatCheckUtil {
/**
*
*/
private final static Pattern CHINA_PATTERN = Pattern.compile("^(13[0-9]|14[01456879]|15[0-35-9]|16[2567]|17[0-8]|18[0-9]|19[0-35-9])\\d{8}$");
/**
*
*
* @param number
* @return
*/
public static boolean isChinaPhone(String number) {
Matcher matcher = CHINA_PATTERN.matcher(number);
return matcher.matches();
}
}

@ -9,9 +9,9 @@ spring:
cloud:
nacos:
discovery:
server-addr: 192.168.1.133:8848
server-addr: 192.168.43.132:8848
# nacos配置中心地址:
config:
server-addr: 192.168.1.133:8848
server-addr: 192.168.43.132:8848
file-extension: yml
# beacon-api-dev.yml

@ -6,6 +6,7 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.Map;
import java.util.Set;
/**
* @author dch
@ -43,4 +44,21 @@ public class CacheController {
return value;
}
@GetMapping("/cache/hget/{key}/{field}")
public Object hget(@PathVariable(value = "key")String key,@PathVariable(value = "field")String field){
log.info("【缓存模块】 hget方法获取key ={}field = {}的数据", key,field);
Object value = redisClient.hGet(key, field);
log.info("【缓存模块】 hget获取key ={}field = {} 的数据 value = {}", key,field,value);
return value;
}
@GetMapping("/cache/smember/{key}")
public Set smember(@PathVariable(value = "key")String key){
log.info("【缓存模块】 smember方法获取key ={}的数据", key);
Set<Object> values = redisClient.sMembers(key);
log.info("【缓存模块】 smember方法获取key ={} 的数据 value = {}", key,values);
return values;
}
}

@ -9,9 +9,9 @@ spring:
cloud:
nacos:
discovery:
server-addr: 192.168.1.133:8848
server-addr: 192.168.43.132:8848
# nacos配置中心地址:
config:
server-addr: 192.168.1.133:8848
server-addr: 192.168.43.132:8848
file-extension: yml
# beacon-cache-dev.yml

@ -21,6 +21,11 @@
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.3.12</version>
</dependency>
</dependencies>
</project>

@ -0,0 +1,14 @@
package com.mashibing.common.constant;
/**
* @author dch
* @create 2024-03-20 20:54
*/
public interface ApiConstant {
String SIGN_PREFIX = "【";
String SIGN_SUFFIX = "】";
Long SINGLE_FEE = 50L;
}

@ -0,0 +1,16 @@
package com.mashibing.common.constant;
/**
* @author dch
* @create 2024-03-21 0:17
* common
* RabbitMQ
* @description
*/
public interface RabbitMQConstants {
/**
*
*/
String SMS_PRE_SEND = "sms_pre_send_topic";
}

@ -16,6 +16,8 @@ public enum ExceptionEnums {
ERROR_MOBILE(-5,"手机号格式不正确"),
BALANCE_NOT_ENOUGH(-6,"手客户余额不足"),
PARAMETER_ERROR(-10, "参数不合法!"),
SNOWFLAKE_OUT_OF_RANGE(-11,"雪花算法的机器id或服务id超出最大范围!"),
SNOWFLAKE_TIME_BACK(-12,"雪花算法的服务器出现时间回拨问题")
;
private Integer code;

@ -4,6 +4,7 @@ import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serializable;
import java.time.LocalDateTime;
/**
@ -15,7 +16,7 @@ import java.time.LocalDateTime;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class StandardSubmit {
public class StandardSubmit implements Serializable {
/**
*
@ -106,4 +107,8 @@ public class StandardSubmit {
0- 1- 3-
*/
private Integer state;
/**签名的id*/
private Long signId;
}

@ -0,0 +1,160 @@
package com.mashibing.common.util;
/**
* @author dch
* @create 2024-03-20 23:24
*/
import com.mashibing.common.enums.ExceptionEnums;
import com.mashibing.common.exception.ApiException;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import javax.annotation.PostConstruct;
/**
* ID
* 64bitlong
* 1bit0.
* 41bit
* 5bitid
* 5bitid
* 12bit
* @author zjw
* @description
*/
@Component
public class SnowFlakeUtil {
/**
* 41bit069.7
* 使19702039
* 2022-11-1141bit使2092~~
*/
private long timeStart = 1668096000000L;
/**
* id
*/
@Value("${snowflake.machineId:0}")
private long machineId;
/**
* id
*/
@Value("${snowflake.serviceId:0}")
private long serviceId;
/**
*
*/
private long sequence;
/**
* idbit
*/
private long machineIdBits = 5L;
/**
* idbit
*/
private long serviceIdBits = 5L;
/**
* bit
*/
private long sequenceBits = 12L;
/**
* id
*/
private long maxMachineId = -1 ^ (-1 << machineIdBits);
/**
* id
*/
private long maxServiceId = -1 ^ (-1 << serviceIdBits);
@PostConstruct
public void init(){
if(machineId > maxMachineId || serviceId > maxServiceId){
System.out.println("机器ID或服务ID超过最大范围值");
throw new ApiException(ExceptionEnums.SNOWFLAKE_OUT_OF_RANGE);
}
}
/**
* id
*/
private long serviceIdShift = sequenceBits;
/**
* id
*/
private long machineIdShift = sequenceBits + serviceIdBits;
/**
*
*/
private long timestampShift = sequenceBits + serviceIdBits + machineIdBits;
/**
*
*/
private long maxSequenceId = -1 ^ (-1 << sequenceBits);
/**
* id
*/
private long lastTimestamp = -1;
/**
*
* @return
*/
private long timeGen(){
return System.currentTimeMillis();
}
public synchronized long nextId(){
//1、 拿到当前系统时间的毫秒值
long timestamp = timeGen();
// 避免时间回拨造成出现重复的id
if(timestamp < lastTimestamp){
// 说明出现了时间回拨
System.out.println("当前服务出现时间回拨!!!");
throw new ApiException(ExceptionEnums.SNOWFLAKE_TIME_BACK);
}
//2、 判断当前生成id的时间和上一次生成的时间
if(timestamp == lastTimestamp){
// 同一毫秒值生成id
sequence = (sequence + 1) & maxSequenceId;
// 0000 10100000 :sequence
// 1111 11111111 :maxSequenceId
if(sequence == 0){
// 进到这个if说明已经超出了sequence序列的最大取值范围
// 需要等到下一个毫秒再做回来生成具体的值
timestamp = timeGen();
while(timestamp <= lastTimestamp){
// 时间还没动。
timestamp = timeGen();
}
}
}else{
// 另一个时间点生成id
sequence = 0;
}
//3、重新给lastTimestamp复制
lastTimestamp = timestamp;
//4、计算id将几位值拼接起来。 41bit位的时间5位的机器5位的服务 12位的序列
return ((timestamp - timeStart) << timestampShift) |
(machineId << machineIdShift) |
(serviceId << serviceIdShift) |
sequence &
Long.MAX_VALUE;
}
}

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.mashibing</groupId>
<artifactId>beacon-cloud</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<artifactId>beacon-strategy</artifactId>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<!-- start-web-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- nacos-dis-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!-- nacos-config-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
<!-- 公共组件common-->
<dependency>
<groupId>com.mashibing</groupId>
<artifactId>beacon-common</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<!-- RabbitMQ依赖-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-amqp</artifactId>
</dependency>
</dependencies>
</project>

@ -0,0 +1,19 @@
package com.mashibing.strategy;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
/**
* @author dch
* @create 2024-03-21 1:19
*/
@SpringBootApplication
@EnableDiscoveryClient
public class StrategyStarterApp {
public static void main(String[] args) {
SpringApplication.run(StrategyStarterApp.class,args);
}
}

@ -0,0 +1,31 @@
package com.mashibing.strategy.mq;
import com.mashibing.common.constant.RabbitMQConstants;
import com.mashibing.common.model.StandardSubmit;
import com.rabbitmq.client.Channel;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.stereotype.Component;
import java.io.IOException;
/**
* @author dch
* @create 2024-03-21 1:45
*/
@Component
@Slf4j
public class PreSendListener {
@RabbitListener(queues = RabbitMQConstants.SMS_PRE_SEND)
public void listen(StandardSubmit submit, Message message, Channel channel) throws IOException {
log.info("【策略模块-接收消息】 接收到接口模块发送的消息 submit = {}",submit);
// 处理业务…………
log.info("【策略模块-消费完毕】手动ack");
channel.basicAck(message.getMessageProperties().getDeliveryTag(),false);
}
}

@ -0,0 +1,17 @@
# 服务名称
spring:
application:
name: beacon-strategy
# 多环境
profiles:
active: dev
# nacos注册中心地址
cloud:
nacos:
discovery:
server-addr: 192.168.43.132:8848
# nacos配置中心地址:
config:
server-addr: 192.168.43.132:8848
file-extension: yml
# beacon-strategy-dev.yml

@ -1,5 +1,6 @@
package com.mashibing.test.mapper;
import com.mashibing.test.entity.ClientBalance;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
@ -8,7 +9,7 @@ import org.apache.ibatis.annotations.Select;
* @create 2024-03-20 1:28
*/
public interface ClientBalanceMapper {
@Select("select balance from client_balance where client_id = #{clientId}")
Long findByClientId(@Param("clientId")Long clientId);
@Select("select * from client_balance where client_id = #{clientId}")
ClientBalance findByClientId(@Param("clientId")Long clientId);
}

@ -6,13 +6,13 @@ spring:
cloud:
nacos:
discovery:
server-addr: 192.168.1.133:8848
server-addr: 192.168.43.132:8848
# datasource
datasource:
driver-class-name: org.gjt.mm.mysql.Driver
url: jdbc:mysql://localhost:3306/beacon_cloud?characterEncoding=utf-8&useSSL=false
username: root
password: 123456
password: 1234
# 端口号
server:
port: 20000

@ -1,12 +1,17 @@
package com.mashibing.test.mapper;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.mashibing.test.client.CacheClient;
import com.mashibing.test.entity.ClientBalance;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
import java.util.Map;
import static org.junit.Assert.*;
/**
@ -24,10 +29,10 @@ public class ClientBalanceMapperTest {
private CacheClient cacheClient;
@Test
public void findByClientId() {
Long balance = mapper.findByClientId(1L);
System.out.println(balance);
cacheClient.set("client_balance:1", balance);
public void findByClientId() throws JsonProcessingException {
ClientBalance clientBalance = mapper.findByClientId(1L);
ObjectMapper objectMapper = new ObjectMapper();
Map map = objectMapper.readValue(objectMapper.writeValueAsString(clientBalance), Map.class);
cacheClient.hmset("client_balance:1",map);
}
}

@ -19,6 +19,7 @@
<module>beacon-common</module>
<module>beacon-cache</module>
<module>beacon-test</module>
<module>beacon-strategy</module>
</modules>
<properties>

Loading…
Cancel
Save