feat:修复代码
parent
6b571dfddc
commit
97572f5712
|
@ -4,14 +4,10 @@ server:
|
|||
|
||||
# nacos线上地址
|
||||
nacos:
|
||||
addr: 106.54.193.225:8848
|
||||
addr: 47.116.173.119:8848
|
||||
user-name: nacos
|
||||
password: nacos
|
||||
|
||||
namespace: one-saas
|
||||
|
||||
namespace: one
|
||||
|
||||
# Spring
|
||||
spring:
|
||||
application:
|
||||
|
@ -26,33 +22,26 @@ spring:
|
|||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
# username: ${nacos.user-name}
|
||||
# # nacos密码
|
||||
# password: ${nacos.password}
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
config:
|
||||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
# username: ${nacos.user-name}
|
||||
# # nacos密码
|
||||
# password: ${nacos.password}
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
# 配置文件格式
|
||||
file-extension: yml
|
||||
# 共享配置
|
||||
shared-configs:
|
||||
|
||||
# 系统环境Config共享配置
|
||||
- application-config-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
# 系统共享配置
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
# 系统共享配置
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
# 系统环境Config共享配置
|
||||
- application-config-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
|
||||
|
|
|
@ -5,23 +5,26 @@
|
|||
<modelVersion>4.0.0</modelVersion>
|
||||
<parent>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-breakdown</artifactId>
|
||||
<artifactId>cloud-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-breakdown-client</artifactId>
|
||||
|
||||
<artifactId>cloud-common-cache</artifactId>
|
||||
<description>
|
||||
cloud-common-cache 缓存基准
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<!-- 基础缓存模块 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-breakdown-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
<artifactId>cloud-common-redis</artifactId>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
</project>
|
|
@ -0,0 +1,37 @@
|
|||
package com.muyu.common.cache;
|
||||
|
||||
import com.muyu.common.cache.decoration.DecorationKey;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: 原子序列缓存基准
|
||||
* @Date 2024-4-1 下午 08:07
|
||||
*/
|
||||
public interface AtomicSequenceCache<K> extends DecorationKey<K> {
|
||||
|
||||
/**
|
||||
* 获取存储的值
|
||||
* @param key 键
|
||||
* @return 值
|
||||
*/
|
||||
public Long get(K key);
|
||||
|
||||
/**
|
||||
* 自增
|
||||
*/
|
||||
public Long increment(K key);
|
||||
/**
|
||||
* 自减
|
||||
*/
|
||||
public Long decrement(K key);
|
||||
|
||||
/**
|
||||
* 增加数值
|
||||
*/
|
||||
public Long increment(K key, Long number);
|
||||
|
||||
/**
|
||||
* 减少数值
|
||||
*/
|
||||
public Long decrement(K key, Long number);
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
package com.muyu.common.cache;
|
||||
|
||||
/**
|
||||
* 数据转换接口
|
||||
* @param <K> 数据键
|
||||
* @param <V> 数据值
|
||||
*/
|
||||
public interface BasicCacheData <K,V>{
|
||||
|
||||
public V apply(K key);
|
||||
}
|
|
@ -0,0 +1,43 @@
|
|||
package com.muyu.common.cache;
|
||||
|
||||
import com.muyu.common.cache.decoration.DecorationKey;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: 缓存接口基类
|
||||
* @Date 2024-3-26 下午 03:25
|
||||
*/
|
||||
public interface Cache <K, V> extends DecorationKey<K> {
|
||||
|
||||
/**
|
||||
* 通过Key获取value值
|
||||
* @param key 键
|
||||
* @return 值
|
||||
*/
|
||||
public V get(K key);
|
||||
|
||||
/**
|
||||
* 缓存添加/修改
|
||||
* @param key 键
|
||||
* @param value 值
|
||||
*/
|
||||
public void put(K key, V value);
|
||||
|
||||
/**
|
||||
* 通过键删除
|
||||
* @param key 键
|
||||
*/
|
||||
public void remove(K key);
|
||||
|
||||
/**
|
||||
* 刷新缓存时间
|
||||
* @param key 键
|
||||
*/
|
||||
public void refreshTime (K key);
|
||||
|
||||
/**
|
||||
* 刷新缓存数据
|
||||
* @param key 键
|
||||
*/
|
||||
public void refreshData (K key);
|
||||
}
|
|
@ -0,0 +1,104 @@
|
|||
package com.muyu.common.cache;
|
||||
|
||||
import com.muyu.common.cache.decoration.DecorationKey;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.function.Function;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: Hash缓存基准
|
||||
* @Date 2024-3-29 下午 03:16
|
||||
*/
|
||||
public interface HashCache <K, HK, HV> extends DecorationKey<K> {
|
||||
|
||||
|
||||
/**
|
||||
* 编码
|
||||
* @param hashKey ID
|
||||
* @return 键
|
||||
*/
|
||||
public String encodeHashKey(HK hashKey);
|
||||
|
||||
/**
|
||||
* 解码
|
||||
* @param redisHashKey 数据库键
|
||||
* @return ID
|
||||
*/
|
||||
public HK decodeHashKey(String redisHashKey);
|
||||
|
||||
/**
|
||||
* 通过Key获取所有的map
|
||||
* @param key 数据库键
|
||||
* @return 所有集合Map
|
||||
*/
|
||||
public Map<HK, HV> get(K key);
|
||||
|
||||
/**
|
||||
* 通过键和hashKey获取数据库hashValue
|
||||
* @param key 键
|
||||
* @param hashKey hash键
|
||||
* @return hash值
|
||||
*/
|
||||
public HV get(K key, HK hashKey);
|
||||
|
||||
/**
|
||||
* 通过键和hashKey获取数据库hashValue
|
||||
* @param key 键
|
||||
* @param hashKeyList hash键集合
|
||||
* @return hash值
|
||||
*/
|
||||
public List<HV> get(K key, HK... hashKeyList);
|
||||
|
||||
/**
|
||||
* 获取hash值集合
|
||||
* @param key 键
|
||||
* @return hash值集合
|
||||
*/
|
||||
public List<HV> getToList(K key);
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
* @param key redis键
|
||||
* @param map hashMap集合
|
||||
*/
|
||||
public void put(K key, Map<HK, HV> map);
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
* @param key redis键
|
||||
* @param dataList 数据值
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
public void put(K key, List<HV> dataList, Function<HV, HK> hashKey);
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
* @param hashValue hash值
|
||||
*/
|
||||
public void put(K key, HK hashKey, HV hashValue);
|
||||
|
||||
/**
|
||||
* 通过redis键删除
|
||||
* @param key hash键
|
||||
*/
|
||||
public void remove(K key);
|
||||
|
||||
/**
|
||||
* 通过redis键和hash键删除
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
public void remove(K key, HK hashKey);
|
||||
|
||||
/**
|
||||
* 判断redis中hashKey是否存在
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
public boolean hasKey(K key, HK hashKey);
|
||||
|
||||
}
|
|
@ -0,0 +1,99 @@
|
|||
package com.muyu.common.cache.abs;
|
||||
|
||||
import com.muyu.common.cache.AtomicSequenceCache;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: 原子序列缓存抽象类
|
||||
* @Date 2024-4-1 下午 08:33
|
||||
*/
|
||||
public abstract class AtomicSequenceCacheAbs<K> implements AtomicSequenceCache<K> {
|
||||
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
|
||||
/**
|
||||
* 获取存储的值
|
||||
* @param key 键
|
||||
* @return 值
|
||||
*/
|
||||
@Override
|
||||
public Long get (K key) {
|
||||
Long cacheValue = this.redisService.getCacheObject(encode(key));
|
||||
if (cacheValue == null){
|
||||
Long data = getData(key);
|
||||
cacheValue = data == null ? 0L : data;
|
||||
this.redisService.setCacheObject(encode(key), cacheValue);
|
||||
}
|
||||
return cacheValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* 自增
|
||||
* @param key
|
||||
*/
|
||||
@Override
|
||||
public Long increment (K key) {
|
||||
return this.increment(key, 1L);
|
||||
}
|
||||
|
||||
/**
|
||||
* 自减
|
||||
*
|
||||
* @param key
|
||||
*/
|
||||
@Override
|
||||
public Long decrement (K key) {
|
||||
return this.decrement(key, 1L);
|
||||
}
|
||||
|
||||
/**
|
||||
* 增加数值
|
||||
*
|
||||
* @param key
|
||||
* @param number
|
||||
*/
|
||||
@Override
|
||||
public Long increment (K key, Long number) {
|
||||
Long numberValue = redisService.getCacheObject(encode(key));
|
||||
if (numberValue == null){
|
||||
Long data = getData(key);
|
||||
data = data == null ? 0L : data;
|
||||
redisService.setCacheObject(encode(key), data);
|
||||
}
|
||||
return redisService.increment(encode(key), number);
|
||||
}
|
||||
|
||||
/**
|
||||
* 减少数值
|
||||
*
|
||||
* @param key
|
||||
* @param number
|
||||
*/
|
||||
@Override
|
||||
public Long decrement (K key, Long number) {
|
||||
Long numberValue = redisService.getCacheObject(encode(key));
|
||||
if (numberValue == null){
|
||||
Long data = getData(key);
|
||||
data = data == null ? 0L : data;
|
||||
redisService.setCacheObject(encode(key), data);
|
||||
}
|
||||
return redisService.decrement(encode(key), number);
|
||||
}
|
||||
|
||||
/**
|
||||
* 编码
|
||||
*
|
||||
* @param key ID
|
||||
*
|
||||
* @return 键
|
||||
*/
|
||||
@Override
|
||||
public String encode (K key) {
|
||||
return keyPre() + key;
|
||||
}
|
||||
|
||||
public abstract Long getData(K key);
|
||||
}
|
|
@ -0,0 +1,96 @@
|
|||
package com.muyu.common.cache.abs;
|
||||
|
||||
import com.muyu.common.cache.Cache;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: 缓存抽象类
|
||||
* @Date 2024-3-27 下午 03:10
|
||||
*/
|
||||
public abstract class CacheAbs<K, V> implements Cache<K, V> {
|
||||
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
|
||||
/**
|
||||
* 编码
|
||||
* @param key ID
|
||||
* @return 键
|
||||
*/
|
||||
@Override
|
||||
public String encode (K key) {
|
||||
return keyPre() + key;
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过Key获取value值
|
||||
* @param key 键
|
||||
* @return 值
|
||||
*/
|
||||
@Override
|
||||
public V get (K key) {
|
||||
V value = redisService.getCacheObject(encode(key));
|
||||
if (value == null){
|
||||
value = getData(key);
|
||||
if (value == null){
|
||||
value = defaultValue();
|
||||
}
|
||||
}
|
||||
this.put(key, value);
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* 缓存添加/修改
|
||||
* @param key 键
|
||||
* @param value 值
|
||||
*/
|
||||
@Override
|
||||
public void put (K key, V value) {
|
||||
this.redisService.setCacheObject(encode(key), value);
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过键删除
|
||||
* @param key 键
|
||||
*/
|
||||
@Override
|
||||
public void remove (K key) {
|
||||
this.redisService.deleteObject(encode(key));
|
||||
}
|
||||
|
||||
/**
|
||||
* 刷新缓存
|
||||
* @param key 键
|
||||
*/
|
||||
@Override
|
||||
public void refreshTime (K key) {
|
||||
this.redisService.expire(encode(key), 60, TimeUnit.SECONDS);
|
||||
}
|
||||
|
||||
/**
|
||||
* 刷新缓存数据
|
||||
*
|
||||
* @param key 键
|
||||
*/
|
||||
@Override
|
||||
public void refreshData (K key) {
|
||||
this.put(key, getData(key));
|
||||
}
|
||||
|
||||
/**
|
||||
* 从数据库获取数据
|
||||
* @param key ID
|
||||
* @return 缓存对象
|
||||
*/
|
||||
public abstract V getData(K key);
|
||||
|
||||
/**
|
||||
* 默认值
|
||||
*/
|
||||
public abstract V defaultValue();
|
||||
}
|
|
@ -0,0 +1,223 @@
|
|||
package com.muyu.common.cache.abs;
|
||||
|
||||
import com.muyu.common.cache.HashCache;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.function.Function;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: hash缓存抽象类
|
||||
* @Date 2024-3-29 下午 07:40
|
||||
*/
|
||||
public abstract class HashCacheAbs<K, HK, HV> implements HashCache<K, HK, HV> {
|
||||
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
|
||||
/**
|
||||
* 编码
|
||||
*
|
||||
* @param key ID
|
||||
*
|
||||
* @return 键
|
||||
*/
|
||||
@Override
|
||||
public String encode (K key) {
|
||||
return keyPre() + key;
|
||||
}
|
||||
|
||||
/**
|
||||
* 编码
|
||||
* @param hashKey ID
|
||||
* @return 键
|
||||
*/
|
||||
@Override
|
||||
public String encodeHashKey (HK hashKey) {
|
||||
return hashKey.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过Key获取所有的map
|
||||
* @param key 数据库键
|
||||
* @return 所有集合Map
|
||||
*/
|
||||
@Override
|
||||
public Map<HK, HV> get (K key) {
|
||||
// 获取为null的情况
|
||||
Map<String, HV> cacheMap = redisService.getCacheMap(encode(key));
|
||||
if (cacheMap == null || cacheMap.isEmpty()){
|
||||
Map<HK, HV> dataMap = getData(key);
|
||||
if (dataMap != null && !dataMap.isEmpty()){
|
||||
cacheMap = encodeMap(dataMap);
|
||||
}else {
|
||||
cacheMap = encodeMap(defaultValue());
|
||||
}
|
||||
redisService.setCacheMap(encode(key), cacheMap);
|
||||
}
|
||||
return decodeMap(cacheMap);
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过键和hashKey获取数据库hashValue
|
||||
*
|
||||
* @param key 键
|
||||
* @param hashKey hash键
|
||||
*
|
||||
* @return hash值
|
||||
*/
|
||||
@Override
|
||||
public HV get (K key, HK hashKey) {
|
||||
HV hashValue = redisService.getCacheMapValue(encode(key), encodeHashKey(hashKey));
|
||||
if (hashValue == null){
|
||||
HV dataValue = getData(key, hashKey);
|
||||
hashValue = dataValue != null ? dataValue : defaultHashValue();
|
||||
put(key, hashKey, hashValue);
|
||||
}
|
||||
return hashValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过键和hashKey获取数据库hashValue
|
||||
*
|
||||
* @param key 键
|
||||
* @param hashKeyList hash键集合
|
||||
*
|
||||
* @return hash值
|
||||
*/
|
||||
@Override
|
||||
public List<HV> get (K key, HK... hashKeyList) {
|
||||
List<String> encodeHashKeyList = Arrays.stream(hashKeyList).map(this::encodeHashKey).toList();
|
||||
return redisService.getMultiCacheMapValue(encode(key), encodeHashKeyList);
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取hash值集合
|
||||
*
|
||||
* @param key 键
|
||||
*
|
||||
* @return hash值集合
|
||||
*/
|
||||
@Override
|
||||
public List<HV> getToList (K key) {
|
||||
Map<HK, HV> hkhvMap = get(key);
|
||||
return hkhvMap.values().stream().toList();
|
||||
}
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
*
|
||||
* @param key redis键
|
||||
* @param map hashMap集合
|
||||
*/
|
||||
@Override
|
||||
public void put (K key, Map<HK, HV> map) {
|
||||
redisService.setCacheMap(encode(key), encodeMap(map));
|
||||
}
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
*
|
||||
* @param key redis键
|
||||
* @param dataList 数据值
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
@Override
|
||||
public void put (K key, List<HV> dataList, Function<HV, HK> hashKey) {
|
||||
Map<HK, HV> dataMap = new HashMap<>();
|
||||
dataList.forEach((data) -> dataMap.put(hashKey.apply(data), data));
|
||||
redisService.setCacheMap(encode(key), encodeMap(dataMap));
|
||||
}
|
||||
|
||||
/**
|
||||
* 存储数据
|
||||
*
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
* @param hashValue hash值
|
||||
*/
|
||||
@Override
|
||||
public void put (K key, HK hashKey, HV hashValue) {
|
||||
redisService.setCacheMapValue(encode(key), encodeHashKey(hashKey), hashValue);
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过redis键删除
|
||||
*
|
||||
* @param key hash键
|
||||
*/
|
||||
@Override
|
||||
public void remove (K key) {
|
||||
redisService.deleteObject(encode(key));
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过redis键和hash键删除
|
||||
*
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
@Override
|
||||
public void remove (K key, HK hashKey) {
|
||||
redisService.deleteCacheMapValue(encode(key), encodeHashKey(hashKey));
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断redis中hashKey是否存在
|
||||
*
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
@Override
|
||||
public boolean hasKey (K key, HK hashKey) {
|
||||
return redisService.hashKey(encode(key), encodeHashKey(hashKey));
|
||||
}
|
||||
|
||||
/**
|
||||
* 原始数据转编码数据
|
||||
* @param dataMap 原始数据
|
||||
* @return 编码数据
|
||||
*/
|
||||
private Map<String, HV> encodeMap(Map<HK, HV> dataMap){
|
||||
Map<String, HV> encodeDataMap = new HashMap<>();
|
||||
dataMap.forEach((hashKey, HashValue) -> encodeDataMap.put(encodeHashKey(hashKey), HashValue));
|
||||
return encodeDataMap;
|
||||
}
|
||||
|
||||
/**
|
||||
* 编码数据转原始数据
|
||||
* @param encodeDataMap 编码数据
|
||||
* @return 原始数据
|
||||
*/
|
||||
private Map<HK, HV> decodeMap(Map<String, HV> encodeDataMap){
|
||||
Map<HK, HV> dataMap = new HashMap<>();
|
||||
encodeDataMap.forEach((hashKey, hashValue) -> dataMap.put(decodeHashKey(hashKey), hashValue));
|
||||
return dataMap;
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过键获取所有的hash数据
|
||||
* @param key 键
|
||||
* @return
|
||||
*/
|
||||
public abstract Map<HK, HV> getData(K key);
|
||||
|
||||
/**
|
||||
* 通过缓存键和hash键获取hash值
|
||||
* @param key 缓存键
|
||||
* @param hashKey hash键
|
||||
* @return hash值
|
||||
*/
|
||||
public abstract HV getData(K key, HK hashKey);
|
||||
|
||||
/**
|
||||
* 默认值
|
||||
*/
|
||||
public abstract Map<HK, HV> defaultValue();
|
||||
public abstract HV defaultHashValue();
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
package com.muyu.common.cache.decoration;
|
||||
|
||||
/**
|
||||
* @author DongZl
|
||||
* @description: 装饰Key
|
||||
* @Date 2024-3-29 下午 03:19
|
||||
*/
|
||||
public interface DecorationKey <K>{
|
||||
|
||||
/**
|
||||
* key前缀
|
||||
* @return key前缀
|
||||
*/
|
||||
public String keyPre();
|
||||
|
||||
|
||||
/**
|
||||
* 编码
|
||||
* @param key ID
|
||||
* @return 键
|
||||
*/
|
||||
public String encode(K key);
|
||||
|
||||
/**
|
||||
* 解码
|
||||
* @param redisKey 数据库键
|
||||
* @return ID
|
||||
*/
|
||||
public K decode(String redisKey);
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
com.muyu.common.kafka.config.KafkaConsumerConfig
|
||||
com.muyu.common.kafka.config.KafkaProviderConfig
|
|
@ -5,23 +5,31 @@
|
|||
<modelVersion>4.0.0</modelVersion>
|
||||
<parent>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-modules</artifactId>
|
||||
<artifactId>cloud-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-breakdown</artifactId>
|
||||
<packaging>pom</packaging>
|
||||
<modules>
|
||||
<module>cloud-breakdown-common</module>
|
||||
<module>cloud-breakdown-server</module>
|
||||
<module>cloud-breakdown-remote</module>
|
||||
<module>cloud-breakdown-client</module>
|
||||
</modules>
|
||||
|
||||
<artifactId>cloud-common-caffeine</artifactId>
|
||||
<description>
|
||||
cloud-common-caffeine caffeine缓存模块
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-redis</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.github.ben-manes.caffeine</groupId>
|
||||
<artifactId>caffeine</artifactId>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
</project>
|
|
@ -0,0 +1,49 @@
|
|||
package com.muyu.common.caffeine.bean;
|
||||
|
||||
|
||||
import com.muyu.common.caffeine.enums.CacheNameEnums;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import com.github.benmanes.caffeine.cache.Caffeine;
|
||||
import org.springframework.cache.CacheManager;
|
||||
import org.springframework.cache.caffeine.CaffeineCache;
|
||||
import org.springframework.cache.support.SimpleCacheManager;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
|
||||
/**
|
||||
* Caffeine管理器
|
||||
* @Author: 胡杨
|
||||
* @Name: CaffeineCacheConfig
|
||||
* @Description: Caffeine管理器
|
||||
* @CreatedDate: 2024/9/26 上午11:52
|
||||
* @FilePath: com.muyu.common.caffeine.config
|
||||
*/
|
||||
|
||||
@Slf4j
|
||||
@Configuration
|
||||
public class CaffeineManager {
|
||||
|
||||
/**
|
||||
* 创建缓存管理器
|
||||
* @return 缓存管理器实例
|
||||
*/
|
||||
@Bean
|
||||
public CacheManager cacheManager() {
|
||||
SimpleCacheManager cacheManager = new SimpleCacheManager();
|
||||
List<String> cacheNames = CacheNameEnums.getCodes();
|
||||
cacheManager.setCaches(cacheNames.stream()
|
||||
.map(name -> new CaffeineCache(
|
||||
name,
|
||||
Caffeine.newBuilder()
|
||||
.recordStats()
|
||||
.build()))
|
||||
.toList());
|
||||
log.info("缓存管理器初始化完成,缓存分区:{}", cacheNames);
|
||||
return cacheManager;
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,17 @@
|
|||
package com.muyu.common.caffeine.constents;
|
||||
|
||||
/**
|
||||
* Caffeine常量
|
||||
* @Author: 胡杨
|
||||
* @Name: CaffeineContent
|
||||
* @Description: Caffeine常量
|
||||
* @CreatedDate: 2024/9/26 下午12:06
|
||||
* @FilePath: com.muyu.common.caffeine.constents
|
||||
*/
|
||||
|
||||
public class CaffeineContent {
|
||||
|
||||
public static final String CAR_VIN_KEY = "car:vin";
|
||||
|
||||
public static final String VIN = "vin";
|
||||
}
|
|
@ -0,0 +1,68 @@
|
|||
package com.muyu.common.caffeine.enums;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 缓存分区枚举
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: CacheNameEnums
|
||||
* @Description: 缓存分区枚举
|
||||
* @CreatedDate: 2024/10/2 上午9:17
|
||||
* @FilePath: com.muyu.common.caffeine.enums
|
||||
*/
|
||||
|
||||
@Getter
|
||||
public enum CacheNameEnums {
|
||||
STORAGE("storage", "持久化"),
|
||||
FAULT("fault", "故障"),
|
||||
FENCE("fence", "围栏"),
|
||||
WARMING("warming", "预警"),
|
||||
REALTIME("realTime", "实时信息");
|
||||
|
||||
private final String code;
|
||||
private final String info;
|
||||
|
||||
CacheNameEnums(String code, String info) {
|
||||
this.code = code;
|
||||
this.info = info;
|
||||
}
|
||||
|
||||
/**
|
||||
* 鉴别参数是否是枚举的值
|
||||
*
|
||||
* @param code 需鉴别参数
|
||||
* @return 如果存在返回结果turn, 否则返回false
|
||||
*/
|
||||
public static boolean isCode(String code) {
|
||||
return Arrays.stream(values())
|
||||
.map(CacheNameEnums::getCode)
|
||||
.anyMatch(c -> c.equals(code));
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取枚举Value
|
||||
* @param code 编码
|
||||
* @return Value
|
||||
*/
|
||||
public static String getInfo(String code) {
|
||||
return Arrays.stream(values())
|
||||
.filter(c -> c.getCode().equals(code))
|
||||
.map(CacheNameEnums::getInfo)
|
||||
.findFirst()
|
||||
.orElse("");
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取所有code
|
||||
* @return code集合
|
||||
*/
|
||||
public static List<String> getCodes() {
|
||||
return Arrays.stream(values())
|
||||
.map(CacheNameEnums::getCode)
|
||||
.toList();
|
||||
}
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
com.muyu.common.caffeine.bean.CaffeineManager
|
|
@ -22,6 +22,7 @@
|
|||
<artifactId>mybatis-plus-join-boot-starter</artifactId>
|
||||
<version>1.4.11</version>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Openfeign -->
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
|
|
|
@ -21,132 +21,132 @@ public @interface Excel {
|
|||
/**
|
||||
* 导出时在excel中排序
|
||||
*/
|
||||
public int sort () default Integer.MAX_VALUE;
|
||||
public int sort() default Integer.MAX_VALUE;
|
||||
|
||||
/**
|
||||
* 导出到Excel中的名字.
|
||||
*/
|
||||
public String name () default "";
|
||||
public String name() default "";
|
||||
|
||||
/**
|
||||
* 日期格式, 如: yyyy-MM-dd
|
||||
*/
|
||||
public String dateFormat () default "";
|
||||
public String dateFormat() default "";
|
||||
|
||||
/**
|
||||
* 读取内容转表达式 (如: 0=男,1=女,2=未知)
|
||||
*/
|
||||
public String readConverterExp () default "";
|
||||
public String readConverterExp() default "";
|
||||
|
||||
/**
|
||||
* 分隔符,读取字符串组内容
|
||||
*/
|
||||
public String separator () default ",";
|
||||
public String separator() default ",";
|
||||
|
||||
/**
|
||||
* BigDecimal 精度 默认:-1(默认不开启BigDecimal格式化)
|
||||
*/
|
||||
public int scale () default -1;
|
||||
public int scale() default -1;
|
||||
|
||||
/**
|
||||
* BigDecimal 舍入规则 默认:BigDecimal.ROUND_HALF_EVEN
|
||||
*/
|
||||
public int roundingMode () default BigDecimal.ROUND_HALF_EVEN;
|
||||
public int roundingMode() default BigDecimal.ROUND_HALF_EVEN;
|
||||
|
||||
/**
|
||||
* 导出时在excel中每个列的高度
|
||||
*/
|
||||
public double height () default 14;
|
||||
public double height() default 14;
|
||||
|
||||
/**
|
||||
* 导出时在excel中每个列的宽度
|
||||
*/
|
||||
public double width () default 16;
|
||||
public double width() default 16;
|
||||
|
||||
/**
|
||||
* 文字后缀,如% 90 变成90%
|
||||
*/
|
||||
public String suffix () default "";
|
||||
public String suffix() default "";
|
||||
|
||||
/**
|
||||
* 当值为空时,字段的默认值
|
||||
*/
|
||||
public String defaultValue () default "";
|
||||
public String defaultValue() default "";
|
||||
|
||||
/**
|
||||
* 提示信息
|
||||
*/
|
||||
public String prompt () default "";
|
||||
public String prompt() default "";
|
||||
|
||||
/**
|
||||
* 设置只能选择不能输入的列内容.
|
||||
*/
|
||||
public String[] combo () default {};
|
||||
public String[] combo() default {};
|
||||
|
||||
/**
|
||||
* 是否需要纵向合并单元格,应对需求:含有list集合单元格)
|
||||
*/
|
||||
public boolean needMerge () default false;
|
||||
public boolean needMerge() default false;
|
||||
|
||||
/**
|
||||
* 是否导出数据,应对需求:有时我们需要导出一份模板,这是标题需要但内容需要用户手工填写.
|
||||
*/
|
||||
public boolean isExport () default true;
|
||||
public boolean isExport() default true;
|
||||
|
||||
/**
|
||||
* 另一个类中的属性名称,支持多级获取,以小数点隔开
|
||||
*/
|
||||
public String targetAttr () default "";
|
||||
public String targetAttr() default "";
|
||||
|
||||
/**
|
||||
* 是否自动统计数据,在最后追加一行统计数据总和
|
||||
*/
|
||||
public boolean isStatistics () default false;
|
||||
public boolean isStatistics() default false;
|
||||
|
||||
/**
|
||||
* 导出类型(0数字 1字符串)
|
||||
*/
|
||||
public ColumnType cellType () default ColumnType.STRING;
|
||||
public ColumnType cellType() default ColumnType.STRING;
|
||||
|
||||
/**
|
||||
* 导出列头背景颜色
|
||||
*/
|
||||
public IndexedColors headerBackgroundColor () default IndexedColors.GREY_50_PERCENT;
|
||||
public IndexedColors headerBackgroundColor() default IndexedColors.GREY_50_PERCENT;
|
||||
|
||||
/**
|
||||
* 导出列头字体颜色
|
||||
*/
|
||||
public IndexedColors headerColor () default IndexedColors.WHITE;
|
||||
public IndexedColors headerColor() default IndexedColors.WHITE;
|
||||
|
||||
/**
|
||||
* 导出单元格背景颜色
|
||||
*/
|
||||
public IndexedColors backgroundColor () default IndexedColors.WHITE;
|
||||
public IndexedColors backgroundColor() default IndexedColors.WHITE;
|
||||
|
||||
/**
|
||||
* 导出单元格字体颜色
|
||||
*/
|
||||
public IndexedColors color () default IndexedColors.BLACK;
|
||||
public IndexedColors color() default IndexedColors.BLACK;
|
||||
|
||||
/**
|
||||
* 导出字段对齐方式
|
||||
*/
|
||||
public HorizontalAlignment align () default HorizontalAlignment.CENTER;
|
||||
public HorizontalAlignment align() default HorizontalAlignment.CENTER;
|
||||
|
||||
/**
|
||||
* 自定义数据处理器
|
||||
*/
|
||||
public Class<?> handler () default ExcelHandlerAdapter.class;
|
||||
public Class<?> handler() default ExcelHandlerAdapter.class;
|
||||
|
||||
/**
|
||||
* 自定义数据处理器参数
|
||||
*/
|
||||
public String[] args () default {};
|
||||
public String[] args() default {};
|
||||
|
||||
/**
|
||||
* 字段类型(0:导出导入;1:仅导出;2:仅导入)
|
||||
*/
|
||||
Type type () default Type.ALL;
|
||||
Type type() default Type.ALL;
|
||||
|
||||
public enum Type {
|
||||
ALL(0), EXPORT(1), IMPORT(2);
|
||||
|
|
|
@ -13,5 +13,5 @@ import java.lang.annotation.Target;
|
|||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Excels {
|
||||
Excel[] value ();
|
||||
Excel[] value();
|
||||
}
|
||||
|
|
|
@ -21,6 +21,8 @@ public class ServiceNameConstants {
|
|||
*/
|
||||
public static final String FILE_SERVICE = "cloud-file";
|
||||
|
||||
public static final String CAR_SERVICE = "cloud-car";
|
||||
|
||||
/**
|
||||
* 智能车联服务
|
||||
*/
|
||||
|
|
|
@ -0,0 +1,63 @@
|
|||
package com.muyu.common.core.enums;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* 类型枚举
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: ClassType
|
||||
* @Description: 类型枚举
|
||||
* @CreatedDate: 2024/9/29 上午9:28
|
||||
* @FilePath: com.muyu.common.core.enums
|
||||
*/
|
||||
|
||||
@Getter
|
||||
public enum ClassType {
|
||||
BYTE("byte", byte.class),
|
||||
SHORT("short", short.class),
|
||||
INT("int", int.class),
|
||||
LONG("long", long.class),
|
||||
FLOAT("float", float.class),
|
||||
DOUBLE("double", double.class),
|
||||
BOOLEAN("boolean", boolean.class),
|
||||
CHAR("char", char.class),
|
||||
STRING("String", String.class),
|
||||
SET("Set", Set.class),
|
||||
MAP("Map", Map.class),
|
||||
LIST("List", List.class);
|
||||
|
||||
private final String code;
|
||||
private final Class<?> info;
|
||||
|
||||
ClassType(String code, Class<?> info) {
|
||||
this.code = code;
|
||||
this.info = info;
|
||||
}
|
||||
|
||||
/**
|
||||
* 鉴别参数是否是枚举的值
|
||||
*
|
||||
* @param code 需鉴别参数
|
||||
* @return 如果存在返回结果turn, 否则返回false
|
||||
*/
|
||||
public static boolean isCode(String code) {
|
||||
return Arrays.stream(values())
|
||||
.map(ClassType::getCode)
|
||||
.anyMatch(c -> c.equals(code));
|
||||
}
|
||||
|
||||
|
||||
public static Class<?> getInfo(String code) {
|
||||
return Arrays.stream(values())
|
||||
.filter(c -> c.getCode().equals(code))
|
||||
.findFirst()
|
||||
.map(ClassType::getInfo)
|
||||
.orElse(null);
|
||||
}
|
||||
}
|
|
@ -26,7 +26,7 @@ public final class SpringUtils implements BeanFactoryPostProcessor {
|
|||
*
|
||||
* @return Object 一个以所给名字注册的bean的实例
|
||||
*
|
||||
* @throws org.springframework.beans.BeansException
|
||||
* @throws BeansException
|
||||
*/
|
||||
@SuppressWarnings("unchecked")
|
||||
public static <T> T getBean (String name) throws BeansException {
|
||||
|
@ -40,7 +40,7 @@ public final class SpringUtils implements BeanFactoryPostProcessor {
|
|||
*
|
||||
* @return
|
||||
*
|
||||
* @throws org.springframework.beans.BeansException
|
||||
* @throws BeansException
|
||||
*/
|
||||
public static <T> T getBean (Class<T> clz) throws BeansException {
|
||||
T result = (T) beanFactory.getBean(clz);
|
||||
|
@ -65,7 +65,7 @@ public final class SpringUtils implements BeanFactoryPostProcessor {
|
|||
*
|
||||
* @return boolean
|
||||
*
|
||||
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
|
||||
* @throws NoSuchBeanDefinitionException
|
||||
*/
|
||||
public static boolean isSingleton (String name) throws NoSuchBeanDefinitionException {
|
||||
return beanFactory.isSingleton(name);
|
||||
|
@ -76,7 +76,7 @@ public final class SpringUtils implements BeanFactoryPostProcessor {
|
|||
*
|
||||
* @return Class 注册对象的类型
|
||||
*
|
||||
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
|
||||
* @throws NoSuchBeanDefinitionException
|
||||
*/
|
||||
public static Class<?> getType (String name) throws NoSuchBeanDefinitionException {
|
||||
return beanFactory.getType(name);
|
||||
|
@ -89,7 +89,7 @@ public final class SpringUtils implements BeanFactoryPostProcessor {
|
|||
*
|
||||
* @return
|
||||
*
|
||||
* @throws org.springframework.beans.factory.NoSuchBeanDefinitionException
|
||||
* @throws NoSuchBeanDefinitionException
|
||||
*/
|
||||
public static String[] getAliases (String name) throws NoSuchBeanDefinitionException {
|
||||
return beanFactory.getAliases(name);
|
||||
|
|
|
@ -17,11 +17,11 @@ import java.lang.annotation.Target;
|
|||
@Target(value = {ElementType.METHOD, ElementType.FIELD, ElementType.CONSTRUCTOR, ElementType.PARAMETER})
|
||||
@Constraint(validatedBy = {XssValidator.class})
|
||||
public @interface Xss {
|
||||
String message ()
|
||||
String message()
|
||||
|
||||
default "不允许任何脚本运行";
|
||||
|
||||
Class<?>[] groups () default {};
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload () default {};
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
|
|
|
@ -14,15 +14,15 @@ public @interface DataScope {
|
|||
/**
|
||||
* 部门表的别名
|
||||
*/
|
||||
public String deptAlias () default "";
|
||||
public String deptAlias() default "";
|
||||
|
||||
/**
|
||||
* 用户表的别名
|
||||
*/
|
||||
public String userAlias () default "";
|
||||
public String userAlias() default "";
|
||||
|
||||
/**
|
||||
* 权限字符(用于多个角色匹配符合要求的权限)默认根据权限注解@RequiresPermissions获取,多个权限用逗号分隔开来
|
||||
*/
|
||||
public String permission () default "";
|
||||
public String permission() default "";
|
||||
}
|
||||
|
|
|
@ -5,22 +5,32 @@
|
|||
<modelVersion>4.0.0</modelVersion>
|
||||
<parent>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-breakdown</artifactId>
|
||||
<artifactId>cloud-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-breakdown-common</artifactId>
|
||||
|
||||
<artifactId>cloud-common-iotdb</artifactId>
|
||||
<description>
|
||||
cloud-common-iotdb 时序数据库模块
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-core</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.iotdb</groupId>
|
||||
<artifactId>iotdb-session</artifactId>
|
||||
<version>1.3.2</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
</project>
|
|
@ -0,0 +1,53 @@
|
|||
package com.muyu.common.iotdb.config;
|
||||
|
||||
import org.apache.iotdb.rpc.IoTDBConnectionException;
|
||||
import org.apache.iotdb.rpc.StatementExecutionException;
|
||||
import org.apache.iotdb.session.Session;
|
||||
import org.apache.iotdb.session.pool.SessionPool;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
/**
|
||||
* 时序数据库配置
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: IotDBConfig
|
||||
* @Description: 时序数据库配置
|
||||
* @CreatedDate: 2024/9/29 下午9:30
|
||||
* @FilePath: com.muyu.data.processing.config
|
||||
*/
|
||||
|
||||
@Configuration
|
||||
public class IotDBSessionConfig {
|
||||
|
||||
@Value("${spring.iotdb.ip}")
|
||||
private String ip;
|
||||
|
||||
@Value("${spring.iotdb.port}")
|
||||
private int port;
|
||||
|
||||
@Value("${spring.iotdb.user}")
|
||||
private String user;
|
||||
|
||||
@Value("${spring.iotdb.password}")
|
||||
private String password;
|
||||
|
||||
@Value("${spring.iotdb.fetchSize}")
|
||||
private int fetchSize;
|
||||
|
||||
private static SessionPool sessionPool;
|
||||
@Bean
|
||||
public SessionPool getSessionPool(){
|
||||
if (sessionPool == null) {
|
||||
sessionPool = new SessionPool(ip, port, user, password, fetchSize);
|
||||
try {
|
||||
sessionPool.setTimeZone("+08:00");
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
return sessionPool;
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1 @@
|
|||
com.muyu.common.iotdb.config.IotDBSessionConfig
|
|
@ -0,0 +1,37 @@
|
|||
<?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.muyu</groupId>
|
||||
<artifactId>cloud-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-common-kafka</artifactId>
|
||||
<description>
|
||||
cloud-common-kafka kafka中间件模块
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-redis</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.kafka</groupId>
|
||||
<artifactId>kafka-clients</artifactId>
|
||||
<version>3.0.0</version>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
</project>
|
|
@ -0,0 +1,54 @@
|
|||
package com.muyu.common.kafka.config;
|
||||
|
||||
import com.muyu.common.kafka.constants.KafkaConstants;
|
||||
import org.apache.kafka.clients.consumer.KafkaConsumer;
|
||||
import org.apache.kafka.common.serialization.Deserializer;
|
||||
import org.apache.kafka.common.serialization.StringDeserializer;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* kafka 消息的消费者 配置类
|
||||
*/
|
||||
@Configuration
|
||||
public class KafkaConsumerConfig {
|
||||
|
||||
@Bean
|
||||
public KafkaConsumer kafkaConsumer() {
|
||||
Map<String, Object> configs = new HashMap<>();
|
||||
//kafka服务端的IP和端口,格式:(ip:port)
|
||||
configs.put("bootstrap.servers", "47.116.173.119:9092");
|
||||
//开启consumer的偏移量(offset)自动提交到Kafka
|
||||
configs.put("enable.auto.commit", true);
|
||||
//consumer的偏移量(offset) 自动提交的时间间隔,单位毫秒
|
||||
configs.put("auto.commit.interval", 5000);
|
||||
//在Kafka中没有初始化偏移量或者当前偏移量不存在情况
|
||||
//earliest, 在偏移量无效的情况下, 自动重置为最早的偏移量
|
||||
//latest, 在偏移量无效的情况下, 自动重置为最新的偏移量
|
||||
//none, 在偏移量无效的情况下, 抛出异常.
|
||||
configs.put("auto.offset.reset", "latest");
|
||||
//请求阻塞的最大时间(毫秒)
|
||||
configs.put("fetch.max.wait", 500);
|
||||
//请求应答的最小字节数
|
||||
configs.put("fetch.min.size", 1);
|
||||
//心跳间隔时间(毫秒)
|
||||
configs.put("heartbeat-interval", 3000);
|
||||
//一次调用poll返回的最大记录条数
|
||||
configs.put("max.poll.records", 500);
|
||||
//指定消费组
|
||||
configs.put("group.id", KafkaConstants.KafkaGrop);
|
||||
//指定key使用的反序列化类
|
||||
Deserializer keyDeserializer = new StringDeserializer();
|
||||
//指定value使用的反序列化类
|
||||
Deserializer valueDeserializer = new StringDeserializer();
|
||||
//创建Kafka消费者
|
||||
KafkaConsumer kafkaConsumer = new KafkaConsumer(configs, keyDeserializer, valueDeserializer);
|
||||
return kafkaConsumer;
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
package com.muyu.common.kafka.config;
|
||||
|
||||
import org.apache.kafka.clients.producer.KafkaProducer;
|
||||
import org.apache.kafka.common.serialization.Serializer;
|
||||
import org.apache.kafka.common.serialization.StringSerializer;
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* kafka 消息的生产者 配置类
|
||||
*/
|
||||
@Configuration
|
||||
public class KafkaProviderConfig {
|
||||
|
||||
@Bean
|
||||
public KafkaProducer kafkaProducer() {
|
||||
Map<String, Object> configs = new HashMap<>();
|
||||
//#kafka服务端的IP和端口,格式:(ip:port)
|
||||
configs.put("bootstrap.servers", "47.116.173.119:9092");
|
||||
//客户端发送服务端失败的重试次数
|
||||
configs.put("retries", 2);
|
||||
//多个记录被发送到同一个分区时,生产者将尝试将记录一起批处理成更少的请求.
|
||||
//此设置有助于提高客户端和服务器的性能,配置控制默认批量大小(以字节为单位)
|
||||
configs.put("batch.size", 16384);
|
||||
//生产者可用于缓冲等待发送到服务器的记录的总内存字节数(以字节为单位)
|
||||
configs.put("buffer-memory", 33554432);
|
||||
//生产者producer要求leader节点在考虑完成请求之前收到的确认数,用于控制发送记录在服务端的持久化
|
||||
//acks=0,设置为0,则生产者producer将不会等待来自服务器的任何确认.该记录将立即添加到套接字(socket)缓冲区并视为已发送.在这种情况下,无法保证服务器已收到记录,并且重试配置(retries)将不会生效(因为客户端通常不会知道任何故障),每条记录返回的偏移量始终设置为-1.
|
||||
//acks=1,设置为1,leader节点会把记录写入本地日志,不需要等待所有follower节点完全确认就会立即应答producer.在这种情况下,在follower节点复制前,leader节点确认记录后立即失败的话,记录将会丢失.
|
||||
//acks=all,acks=-1,leader节点将等待所有同步复制副本完成再确认记录,这保证了只要至少有一个同步复制副本存活,记录就不会丢失.
|
||||
configs.put("acks", "-1");
|
||||
//指定key使用的序列化类
|
||||
Serializer keySerializer = new StringSerializer();
|
||||
//指定value使用的序列化类
|
||||
Serializer valueSerializer = new StringSerializer();
|
||||
//创建Kafka生产者
|
||||
KafkaProducer kafkaProducer = new KafkaProducer(configs, keySerializer, valueSerializer);
|
||||
return kafkaProducer;
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,14 @@
|
|||
package com.muyu.common.kafka.constants;
|
||||
|
||||
/**
|
||||
* @Author: 胡杨
|
||||
* @date: 2024/7/10
|
||||
* @Description: kafka常量
|
||||
* @Version 1.0.0
|
||||
*/
|
||||
public class KafkaConstants {
|
||||
|
||||
public final static String KafkaTopic = "kafka_topic";
|
||||
|
||||
public final static String KafkaGrop = "kafka_grop";
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
com.muyu.common.kafka.config.KafkaConsumerConfig
|
||||
com.muyu.common.kafka.config.KafkaProviderConfig
|
|
@ -17,30 +17,30 @@ public @interface Log {
|
|||
/**
|
||||
* 模块
|
||||
*/
|
||||
public String title () default "";
|
||||
public String title() default "";
|
||||
|
||||
/**
|
||||
* 功能
|
||||
*/
|
||||
public BusinessType businessType () default BusinessType.OTHER;
|
||||
public BusinessType businessType() default BusinessType.OTHER;
|
||||
|
||||
/**
|
||||
* 操作人类别
|
||||
*/
|
||||
public OperatorType operatorType () default OperatorType.MANAGE;
|
||||
public OperatorType operatorType() default OperatorType.MANAGE;
|
||||
|
||||
/**
|
||||
* 是否保存请求的参数
|
||||
*/
|
||||
public boolean isSaveRequestData () default true;
|
||||
public boolean isSaveRequestData() default true;
|
||||
|
||||
/**
|
||||
* 是否保存响应的参数
|
||||
*/
|
||||
public boolean isSaveResponseData () default true;
|
||||
public boolean isSaveResponseData() default true;
|
||||
|
||||
/**
|
||||
* 排除指定的请求参数
|
||||
*/
|
||||
public String[] excludeParamNames () default {};
|
||||
public String[] excludeParamNames() default {};
|
||||
}
|
||||
|
|
|
@ -10,7 +10,9 @@
|
|||
</parent>
|
||||
|
||||
<artifactId>cloud-common-rabbit</artifactId>
|
||||
|
||||
<description>
|
||||
cloud-common-rabbit rabbit中间件模块
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
|
@ -32,7 +34,4 @@
|
|||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
|
||||
</project>
|
||||
|
||||
|
||||
|
|
|
@ -1,41 +0,0 @@
|
|||
package com.muyu.common.rabbit;
|
||||
|
||||
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
|
||||
import org.springframework.amqp.rabbit.listener.RabbitListenerEndpointRegistrar;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.messaging.converter.MappingJackson2MessageConverter;
|
||||
import org.springframework.messaging.handler.annotation.support.DefaultMessageHandlerMethodFactory;
|
||||
|
||||
@Configuration
|
||||
public class RabbitListenerConfigurer implements org.springframework.amqp.rabbit.annotation.RabbitListenerConfigurer {
|
||||
|
||||
static {
|
||||
System.setProperty("spring.amqp.deserialization.trust.all", "true");
|
||||
}
|
||||
|
||||
//以下配置RabbitMQ消息服务
|
||||
@Autowired
|
||||
public ConnectionFactory connectionFactory;
|
||||
|
||||
|
||||
/**
|
||||
* 处理器方法工厂
|
||||
* @return
|
||||
*/
|
||||
@Bean
|
||||
public DefaultMessageHandlerMethodFactory handlerMethodFactory() {
|
||||
DefaultMessageHandlerMethodFactory factory = new DefaultMessageHandlerMethodFactory();
|
||||
// 这里的转换器设置实现了 通过 @Payload 注解 自动反序列化message body
|
||||
factory.setMessageConverter(new MappingJackson2MessageConverter());
|
||||
return factory;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void configureRabbitListeners(RabbitListenerEndpointRegistrar rabbitListenerEndpointRegistrar) {
|
||||
rabbitListenerEndpointRegistrar.setMessageHandlerMethodFactory(handlerMethodFactory());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
package com.muyu.common.rabbit.constants;
|
||||
|
||||
/**
|
||||
* rabbit常量
|
||||
* @Author: 胡杨
|
||||
* @date: 2024/7/10
|
||||
* @Description: rabbit常量
|
||||
* @Version 1.0.0
|
||||
*/
|
||||
public class RabbitConstants {
|
||||
|
||||
public final static String GO_ONLINE_QUEUE= "GoOnline";
|
||||
|
||||
public final static String DOWNLINE_QUEUE= "Downline";
|
||||
}
|
|
@ -1,7 +1,3 @@
|
|||
|
||||
com.muyu.common.rabbit.config.RabbitListenerConfig
|
||||
com.muyu.common.rabbit.config.RabbitAdminConfig
|
||||
com.muyu.common.rabbit.config.RabbitMQMessageConverterConfig
|
||||
|
||||
com.muyu.common.rabbit.RabbitListenerConfigurer
|
||||
|
||||
|
|
|
@ -235,7 +235,7 @@ public class RedisService {
|
|||
*
|
||||
* @return Hash对象集合
|
||||
*/
|
||||
public <T> List<T> getMultiCacheMapValue (final String key, final Collection<Object> hKeys) {
|
||||
public <T> List<T> getMultiCacheMapValue (final String key, final Collection<String> hKeys) {
|
||||
return redisTemplate.opsForHash().multiGet(key, hKeys);
|
||||
}
|
||||
|
||||
|
@ -261,4 +261,33 @@ public class RedisService {
|
|||
public Collection<String> keys (final String pattern) {
|
||||
return redisTemplate.keys(pattern);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 判断redis中hashKey是否存在
|
||||
* @param key redis键
|
||||
* @param hashKey hash键
|
||||
*/
|
||||
public boolean hashKey(final String key, final String hashKey){
|
||||
return this.redisTemplate.opsForHash().hasKey(key, hashKey);
|
||||
}
|
||||
|
||||
/**
|
||||
* 减少序列值
|
||||
* @param key key
|
||||
* @param number 值
|
||||
* @return 操作后的值
|
||||
*/
|
||||
public Long decrement (final String key, Long number) {
|
||||
return redisTemplate.opsForValue().decrement(key,number);
|
||||
}
|
||||
/**
|
||||
* 增加序列值
|
||||
* @param key key
|
||||
* @param number 值
|
||||
* @return 操作后的值
|
||||
*/
|
||||
public Long increment (final String key, Long number) {
|
||||
return redisTemplate.opsForValue().increment(key,number);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,7 +10,9 @@
|
|||
</parent>
|
||||
|
||||
<artifactId>cloud-common-saas</artifactId>
|
||||
|
||||
<description>
|
||||
cloud-common-saas saas数据源切换模块
|
||||
</description>
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
|
|
|
@ -71,8 +71,10 @@ public class ManyDataSource implements ApplicationRunner{
|
|||
Objects.requireNonNull(dataSourceInfoList())
|
||||
.stream()
|
||||
.map(DataSourceInfo::hostAndPortBuild)
|
||||
.forEach(dataSourceInfo -> {
|
||||
dataSourceMap.put(dataSourceInfo.getKey(), druidDataSourceFactory.create(dataSourceInfo));
|
||||
.map(druidDataSourceFactory::create)
|
||||
.filter(Objects::nonNull)
|
||||
.forEach( druidDataSource -> {
|
||||
dataSourceMap.put(druidDataSource.getName(), druidDataSource);
|
||||
});
|
||||
//设置动态数据源
|
||||
DynamicDataSource dynamicDataSource = new DynamicDataSource();
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package com.muyu.cloud.common.many.datasource.factory;
|
||||
|
||||
import com.alibaba.druid.pool.DruidDataSource;
|
||||
import com.alibaba.druid.pool.DruidPooledConnection;
|
||||
import com.muyu.cloud.common.many.datasource.domain.model.DataSourceInfo;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
@ -23,15 +24,18 @@ public class DruidDataSourceFactory {
|
|||
*/
|
||||
public DruidDataSource create(DataSourceInfo dataSourceInfo) {
|
||||
DruidDataSource druidDataSource = new DruidDataSource();
|
||||
druidDataSource.setName(dataSourceInfo.getKey());
|
||||
druidDataSource.setUrl(dataSourceInfo.getUrl());
|
||||
druidDataSource.setConnectTimeout(10000);
|
||||
druidDataSource.setMaxWait(60000);
|
||||
druidDataSource.setUsername(dataSourceInfo.getUserName());
|
||||
druidDataSource.setPassword(dataSourceInfo.getPassword());
|
||||
druidDataSource.setBreakAfterAcquireFailure(true);
|
||||
druidDataSource.setConnectionErrorRetryAttempts(0);
|
||||
try {
|
||||
druidDataSource.getConnection(2000);
|
||||
DruidPooledConnection connection = druidDataSource.getConnection(2000);
|
||||
log.info("{} -> 数据源连接成功", dataSourceInfo.getKey());
|
||||
connection.close();
|
||||
return druidDataSource;
|
||||
} catch (SQLException throwables) {
|
||||
log.error("数据源 {} 连接失败,用户名:{},密码 {}, 原因:{}",dataSourceInfo.getUrl(),dataSourceInfo.getUserName(),dataSourceInfo.getPassword(), throwables);
|
||||
|
|
|
@ -15,13 +15,13 @@ import java.lang.annotation.*;
|
|||
@Documented
|
||||
@EnableFeignClients
|
||||
public @interface EnableMyFeignClients {
|
||||
String[] value () default {};
|
||||
String[] value() default {};
|
||||
|
||||
String[] basePackages () default {"com.muyu"};
|
||||
String[] basePackages() default {"com.muyu"};
|
||||
|
||||
Class<?>[] basePackageClasses () default {};
|
||||
Class<?>[] basePackageClasses() default {};
|
||||
|
||||
Class<?>[] defaultConfiguration () default {};
|
||||
Class<?>[] defaultConfiguration() default {};
|
||||
|
||||
Class<?>[] clients () default {};
|
||||
Class<?>[] clients() default {};
|
||||
}
|
||||
|
|
|
@ -14,5 +14,5 @@ public @interface InnerAuth {
|
|||
/**
|
||||
* 是否校验用户信息
|
||||
*/
|
||||
boolean isUser () default false;
|
||||
boolean isUser() default false;
|
||||
}
|
||||
|
|
|
@ -16,10 +16,10 @@ public @interface RequiresPermissions {
|
|||
/**
|
||||
* 需要校验的权限码
|
||||
*/
|
||||
String[] value () default {};
|
||||
String[] value() default {};
|
||||
|
||||
/**
|
||||
* 验证模式:AND | OR,默认AND
|
||||
*/
|
||||
Logical logical () default Logical.AND;
|
||||
Logical logical() default Logical.AND;
|
||||
}
|
||||
|
|
|
@ -16,10 +16,10 @@ public @interface RequiresRoles {
|
|||
/**
|
||||
* 需要校验的角色标识
|
||||
*/
|
||||
String[] value () default {};
|
||||
String[] value() default {};
|
||||
|
||||
/**
|
||||
* 验证逻辑:AND | OR,默认AND
|
||||
*/
|
||||
Logical logical () default Logical.AND;
|
||||
Logical logical() default Logical.AND;
|
||||
}
|
||||
|
|
|
@ -34,4 +34,5 @@ public class SysEnt {
|
|||
private String userName;
|
||||
|
||||
private String password;
|
||||
|
||||
}
|
||||
|
|
|
@ -22,4 +22,5 @@ public class SysFirmUser extends SysUser {
|
|||
* 用户数据库
|
||||
*/
|
||||
private String databaseName;
|
||||
|
||||
}
|
||||
|
|
|
@ -0,0 +1,31 @@
|
|||
package com.muyu.common.system.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import com.muyu.common.core.annotation.Excel;
|
||||
import lombok.*;
|
||||
import lombok.experimental.SuperBuilder;
|
||||
|
||||
/**
|
||||
* 会员表(SysMember)实体类
|
||||
*
|
||||
*/
|
||||
@Data
|
||||
@Setter
|
||||
@Getter
|
||||
@SuperBuilder
|
||||
@NoArgsConstructor
|
||||
@AllArgsConstructor
|
||||
@TableName("sys_member")
|
||||
public class SysMember {
|
||||
@TableId(type = IdType.AUTO)
|
||||
private Long memberId;
|
||||
@Excel(name = "会员等级")
|
||||
private String memberName;
|
||||
@Excel(name = "可添加车辆数量")
|
||||
private Integer memberCarNum;
|
||||
@Excel(name = "可添加报文模板数量")
|
||||
private Integer memberCarType;
|
||||
}
|
||||
|
|
@ -21,6 +21,10 @@
|
|||
<module>cloud-common-xxl</module>
|
||||
<module>cloud-common-rabbit</module>
|
||||
<module>cloud-common-saas</module>
|
||||
<module>cloud-common-cache</module>
|
||||
<module>cloud-common-caffeine</module>
|
||||
<module>cloud-common-iotdb</module>
|
||||
<module>cloud-common-kafka</module>
|
||||
</modules>
|
||||
|
||||
<artifactId>cloud-common</artifactId>
|
||||
|
|
|
@ -1,18 +1,14 @@
|
|||
# Tomcat
|
||||
server:
|
||||
port: 8080
|
||||
port: 8081
|
||||
|
||||
# nacos线上地址
|
||||
nacos:
|
||||
addr: 106.54.193.225:8848
|
||||
addr: 47.116.173.119:8848
|
||||
user-name: nacos
|
||||
password: nacos
|
||||
|
||||
namespace: one-saas
|
||||
|
||||
namespace: one
|
||||
|
||||
|
||||
# Spring
|
||||
spring:
|
||||
application:
|
||||
|
@ -26,60 +22,35 @@ spring:
|
|||
discovery:
|
||||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
|
||||
# # nacos用户名
|
||||
# username: ${nacos.user-name}
|
||||
# # nacos密码
|
||||
# password: ${nacos.password}
|
||||
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
config:
|
||||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
|
||||
# # nacos用户名
|
||||
# username: ${nacos.user-name}
|
||||
# # nacos密码
|
||||
# password: ${nacos.password}
|
||||
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
# 配置文件格式
|
||||
file-extension: yml
|
||||
# 共享配置
|
||||
shared-configs:
|
||||
|
||||
# 系统环境Config共享配置
|
||||
- application-config-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
# 系统共享配置
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
# 系统共享配置
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
# 系统环境Config共享配置
|
||||
- application-config-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
sentinel:
|
||||
# 取消控制台懒加载
|
||||
eager: true
|
||||
transport:
|
||||
# 控制台地址
|
||||
|
||||
dashboard: 106.54.193.225:8718
|
||||
|
||||
dashboard: 127.0.0.1:8718
|
||||
|
||||
# nacos配置持久化
|
||||
datasource:
|
||||
ds1:
|
||||
|
|
|
@ -1,93 +0,0 @@
|
|||
//package com.muyu.breakdown.DTO;
|
||||
//
|
||||
//
|
||||
//import com.muyu.breakdown.domain.Messages;
|
||||
//import org.springframework.beans.factory.annotation.Autowired;
|
||||
//import org.springframework.stereotype.Component;
|
||||
//
|
||||
//import java.sql.*;
|
||||
//import java.util.*;
|
||||
//
|
||||
///**
|
||||
// * @ Tool:IntelliJ IDEA
|
||||
// * @ Author:CHX
|
||||
// * @ Date:2024-09-18-15:00
|
||||
// * @ Version:1.0
|
||||
// * @ Description:数据库连接层
|
||||
// * @author Lenovo
|
||||
// */
|
||||
//@Component
|
||||
//public class MessageDTO {
|
||||
// private static final String DB_URL = "jdbc:mysql://106.54.193.225:3306/one";
|
||||
// private static final String USER = "root";
|
||||
// private static final String PASSWORD = "bawei2112A";
|
||||
//
|
||||
// // 2. 建立数据库连接
|
||||
// Connection connection;
|
||||
// // 构造函数,初始化数据库连接
|
||||
// // 保存消息到数据库
|
||||
// public void saveMessage(Messages message) {
|
||||
// String sql = "INSERT INTO sys_messages (sender_id, receiver_id, content) VALUES (?, ?, ?)";
|
||||
// try {
|
||||
// Class.forName("com.mysql.cj.jdbc.Driver");
|
||||
// } catch (ClassNotFoundException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// try {
|
||||
// connection = DriverManager.getConnection(DB_URL, USER, PASSWORD);
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// try (PreparedStatement preparedStatement = connection.prepareStatement(sql)) {
|
||||
// preparedStatement.setInt(1, message.getSenderId());
|
||||
// preparedStatement.setInt(2, message.getReceiverId());
|
||||
// preparedStatement.setString(3, message.getContent());
|
||||
// // 执行添加操作
|
||||
// preparedStatement.executeUpdate();
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// try {
|
||||
// connection.close();
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// // 获取所有消息
|
||||
// public List<Messages> getAllMessages(int receiverId){
|
||||
// String sql = "SELECT * FROM sys_messages WHERE receiver_id = ?";
|
||||
// try {
|
||||
// Class.forName("com.mysql.cj.jdbc.Driver");
|
||||
// } catch (ClassNotFoundException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// List<Messages> messages = new ArrayList<>();
|
||||
// try {
|
||||
// connection = DriverManager.getConnection(DB_URL, USER, PASSWORD);
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// try (PreparedStatement preparedStatement = connection.prepareStatement(sql)) {
|
||||
// preparedStatement.setInt(1, receiverId);
|
||||
// // 执行查询操作
|
||||
// ResultSet rs = preparedStatement.executeQuery();
|
||||
// while (rs.next()) {
|
||||
// Messages message = new Messages(rs.getInt("sender_id"), receiverId, rs.getString("content"));
|
||||
//
|
||||
// // 添加到消息列表
|
||||
// messages.add(message);
|
||||
// }
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// try {
|
||||
// connection.close();
|
||||
// } catch (SQLException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// // 返回消息列表
|
||||
// return messages;
|
||||
// }
|
||||
//
|
||||
//}
|
|
@ -1,43 +0,0 @@
|
|||
package com.muyu.breakdown.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.experimental.SuperBuilder;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-20-15:35
|
||||
* @ Version:1.0
|
||||
* @ Description:报文
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
@SuperBuilder
|
||||
@TableName("sys_car_message")
|
||||
public class SysCarMessage {
|
||||
/**
|
||||
* id
|
||||
*/
|
||||
private Integer id;
|
||||
/**
|
||||
* 车辆型号编码
|
||||
*/
|
||||
private String modelCode;
|
||||
/**
|
||||
* 车辆报文类型编码
|
||||
*/
|
||||
private String messageTypeCode;
|
||||
/**
|
||||
* 开始位下标
|
||||
*/
|
||||
private String messageStartIndex;
|
||||
/**
|
||||
* 结束位下标
|
||||
*/
|
||||
private String messageEndIndex;
|
||||
}
|
|
@ -1 +0,0 @@
|
|||
|
|
@ -1,92 +0,0 @@
|
|||
<?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.muyu</groupId>
|
||||
<artifactId>cloud-breakdown</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-breakdown-server</artifactId>
|
||||
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
<dependencies>
|
||||
<!-- SpringCloud Alibaba Nacos -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Alibaba Nacos Config -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Alibaba Sentinel -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringBoot Actuator -->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- Mysql Connector -->
|
||||
<dependency>
|
||||
<groupId>com.mysql</groupId>
|
||||
<artifactId>mysql-connector-j</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataSource -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datasource</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataScope -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datascope</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common Log -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-log</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- 接口模块 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-api-doc</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- XllJob定时任务 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-xxl</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-rabbit</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-breakdown-common</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
</project>
|
|
@ -1,23 +0,0 @@
|
|||
package com.muyu;
|
||||
|
||||
import com.muyu.common.security.annotation.EnableCustomConfig;
|
||||
import com.muyu.common.security.annotation.EnableMyFeignClients;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-17-15:00
|
||||
* @ Version:1.0
|
||||
* @ Description:故障启动类
|
||||
* @author Lenovo
|
||||
*/
|
||||
@EnableCustomConfig
|
||||
@EnableMyFeignClients
|
||||
@SpringBootApplication
|
||||
public class BreakDownApplication {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(BreakDownApplication.class, args);
|
||||
}
|
||||
}
|
|
@ -1,20 +0,0 @@
|
|||
package com.muyu.breakdown.controller;
|
||||
|
||||
import com.muyu.breakdown.service.SysCarMessageService;
|
||||
import com.muyu.common.core.web.controller.BaseController;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-20-15:41
|
||||
* @ Version:1.0
|
||||
* @ Description:报文模版控制层
|
||||
* @author Lenovo
|
||||
*/
|
||||
@RestController
|
||||
public class SysCarMessageController extends BaseController {
|
||||
@Autowired
|
||||
private SysCarMessageService sysCarMessageService;
|
||||
}
|
|
@ -1,15 +0,0 @@
|
|||
package com.muyu.breakdown.service;
|
||||
|
||||
import com.baomidou.mybatisplus.extension.service.IService;
|
||||
import com.muyu.breakdown.domain.SysCarMessage;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-20-15:42
|
||||
* @ Version:1.0
|
||||
* @ Description:
|
||||
* @author Lenovo
|
||||
*/
|
||||
public interface SysCarMessageService extends IService<SysCarMessage> {
|
||||
}
|
|
@ -1,19 +0,0 @@
|
|||
package com.muyu.breakdown.service.impl;
|
||||
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.muyu.breakdown.domain.SysCarMessage;
|
||||
import com.muyu.breakdown.mapper.SysCarMessageMapper;
|
||||
import com.muyu.breakdown.service.SysCarMessageService;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-20-15:42
|
||||
* @ Version:1.0
|
||||
* @ Description:
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Service
|
||||
public class SysCarMessageServiceImpl extends ServiceImpl<SysCarMessageMapper, SysCarMessage> implements SysCarMessageService {
|
||||
}
|
|
@ -1,74 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<configuration scan="true" scanPeriod="60 seconds" debug="false">
|
||||
<!-- 日志存放路径 -->
|
||||
<property name="log.path" value="logs/cloud-breakdown"/>
|
||||
<!-- 日志输出格式 -->
|
||||
<property name="log.pattern" value="%d{HH:mm:ss.SSS} [%thread] %-5level %logger{20} - [%method,%line] - %msg%n"/>
|
||||
|
||||
<!-- 控制台输出 -->
|
||||
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
|
||||
<encoder>
|
||||
<pattern>${log.pattern}</pattern>
|
||||
</encoder>
|
||||
</appender>
|
||||
|
||||
<!-- 系统日志输出 -->
|
||||
<appender name="file_info" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||
<file>${log.path}/info.log</file>
|
||||
<!-- 循环政策:基于时间创建日志文件 -->
|
||||
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||
<!-- 日志文件名格式 -->
|
||||
<fileNamePattern>${log.path}/info.%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||
<!-- 日志最大的历史 60天 -->
|
||||
<maxHistory>60</maxHistory>
|
||||
</rollingPolicy>
|
||||
<encoder>
|
||||
<pattern>${log.pattern}</pattern>
|
||||
</encoder>
|
||||
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||
<!-- 过滤的级别 -->
|
||||
<level>INFO</level>
|
||||
<!-- 匹配时的操作:接收(记录) -->
|
||||
<onMatch>ACCEPT</onMatch>
|
||||
<!-- 不匹配时的操作:拒绝(不记录) -->
|
||||
<onMismatch>DENY</onMismatch>
|
||||
</filter>
|
||||
</appender>
|
||||
|
||||
<appender name="file_error" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||
<file>${log.path}/error.log</file>
|
||||
<!-- 循环政策:基于时间创建日志文件 -->
|
||||
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||
<!-- 日志文件名格式 -->
|
||||
<fileNamePattern>${log.path}/error.%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||
<!-- 日志最大的历史 60天 -->
|
||||
<maxHistory>60</maxHistory>
|
||||
</rollingPolicy>
|
||||
<encoder>
|
||||
<pattern>${log.pattern}</pattern>
|
||||
</encoder>
|
||||
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||
<!-- 过滤的级别 -->
|
||||
<level>ERROR</level>
|
||||
<!-- 匹配时的操作:接收(记录) -->
|
||||
<onMatch>ACCEPT</onMatch>
|
||||
<!-- 不匹配时的操作:拒绝(不记录) -->
|
||||
<onMismatch>DENY</onMismatch>
|
||||
</filter>
|
||||
</appender>
|
||||
|
||||
<!-- 系统模块日志级别控制 -->
|
||||
<logger name="com.muyu" level="info"/>
|
||||
<!-- Spring日志级别控制 -->
|
||||
<logger name="org.springframework" level="warn"/>
|
||||
|
||||
<root level="info">
|
||||
<appender-ref ref="console"/>
|
||||
</root>
|
||||
|
||||
<!--系统操作日志-->
|
||||
<root level="info">
|
||||
<appender-ref ref="file_info"/>
|
||||
<appender-ref ref="file_error"/>
|
||||
</root>
|
||||
</configuration>
|
|
@ -1,81 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<configuration scan="true" scanPeriod="60 seconds" debug="false">
|
||||
<!-- 日志存放路径 -->
|
||||
<property name="log.path" value="logs/cloud-breakdown"/>
|
||||
<!-- 日志输出格式 -->
|
||||
<property name="log.pattern" value="%d{HH:mm:ss.SSS} [%thread] %-5level %logger{20} - [%method,%line] - %msg%n"/>
|
||||
<property name="log.sky.pattern" value="%d{HH:mm:ss.SSS} %yellow([%tid]) [%thread] %-5level %logger{20} - [%method,%line] - %msg%n"/>
|
||||
|
||||
<!-- 控制台输出 -->
|
||||
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
|
||||
<encoder>
|
||||
<pattern>${log.sky.pattern}</pattern>
|
||||
</encoder>
|
||||
</appender>
|
||||
|
||||
<!-- 系统日志输出 -->
|
||||
<appender name="file_info" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||
<file>${log.path}/info.log</file>
|
||||
<!-- 循环政策:基于时间创建日志文件 -->
|
||||
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||
<!-- 日志文件名格式 -->
|
||||
<fileNamePattern>${log.path}/info.%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||
<!-- 日志最大的历史 60天 -->
|
||||
<maxHistory>60</maxHistory>
|
||||
</rollingPolicy>
|
||||
|
||||
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||
<!-- 过滤的级别 -->
|
||||
<level>INFO</level>
|
||||
<!-- 匹配时的操作:接收(记录) -->
|
||||
<onMatch>ACCEPT</onMatch>
|
||||
<!-- 不匹配时的操作:拒绝(不记录) -->
|
||||
<onMismatch>DENY</onMismatch>
|
||||
</filter>
|
||||
</appender>
|
||||
|
||||
<appender name="file_error" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||
<file>${log.path}/error.log</file>
|
||||
<!-- 循环政策:基于时间创建日志文件 -->
|
||||
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||
<!-- 日志文件名格式 -->
|
||||
<fileNamePattern>${log.path}/error.%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||
<!-- 日志最大的历史 60天 -->
|
||||
<maxHistory>60</maxHistory>
|
||||
</rollingPolicy>
|
||||
|
||||
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||
<!-- 过滤的级别 -->
|
||||
<level>ERROR</level>
|
||||
<!-- 匹配时的操作:接收(记录) -->
|
||||
<onMatch>ACCEPT</onMatch>
|
||||
<!-- 不匹配时的操作:拒绝(不记录) -->
|
||||
<onMismatch>DENY</onMismatch>
|
||||
</filter>
|
||||
</appender>
|
||||
|
||||
<!-- 使用gRpc将日志发送到skywalking服务端 -->
|
||||
<appender name="GRPC_LOG" class="org.apache.skywalking.apm.toolkit.log.logback.v1.x.log.GRPCLogClientAppender">
|
||||
<encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
|
||||
<layout class="org.apache.skywalking.apm.toolkit.log.logback.v1.x.TraceIdPatternLogbackLayout">
|
||||
<Pattern>${log.sky.pattern}</Pattern>
|
||||
</layout>
|
||||
</encoder>
|
||||
</appender>
|
||||
|
||||
<!-- 系统模块日志级别控制 -->
|
||||
<logger name="com.muyu" level="info"/>
|
||||
<!-- Spring日志级别控制 -->
|
||||
<logger name="org.springframework" level="warn"/>
|
||||
|
||||
<root level="info">
|
||||
<appender-ref ref="GRPC_LOG"/>
|
||||
<appender-ref ref="console"/>
|
||||
</root>
|
||||
|
||||
<!--系统操作日志-->
|
||||
<root level="info">
|
||||
<appender-ref ref="file_info"/>
|
||||
<appender-ref ref="file_error"/>
|
||||
</root>
|
||||
</configuration>
|
|
@ -1,147 +0,0 @@
|
|||
package com.muyu.car.gateway.service.Impl;
|
||||
|
||||
import com.muyu.car.gateway.domain.VehicleConnection;
|
||||
import com.muyu.car.gateway.domain.VinIp;
|
||||
import com.muyu.car.gateway.domain.model.MqttServerModel;
|
||||
import com.muyu.car.gateway.domain.properties.MqttProperties;
|
||||
import com.muyu.car.gateway.domain.req.VehicleConnectionReq;
|
||||
import com.muyu.car.gateway.mapper.CarOneClickOperationMapper;
|
||||
import com.muyu.car.gateway.service.CarOneClickOperationService;
|
||||
import com.muyu.common.core.domain.Result;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.amqp.rabbit.core.RabbitTemplate;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.redis.core.HashOperations;
|
||||
import org.springframework.data.redis.core.StringRedisTemplate;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static com.muyu.car.gateway.config.RabbitmqConfig.EXCHANGE_TOPICS_INFORM;
|
||||
import static com.muyu.car.gateway.config.RabbitmqConfig.ROUTINGKEY_SMS;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-26-20:16
|
||||
* @ Version:1.0
|
||||
* @ Description:车辆一键操作业务实现层
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Log4j2
|
||||
@Service
|
||||
public class CarOneClickOperationServiceImpl implements CarOneClickOperationService {
|
||||
|
||||
@Autowired
|
||||
private CarOneClickOperationMapper carOneClickOperationMapper;
|
||||
@Autowired
|
||||
private RabbitTemplate rabbitTemplate;
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
@Autowired
|
||||
private StringRedisTemplate redisTemplate;
|
||||
|
||||
/**
|
||||
* 获取连接信息
|
||||
* @param vehicleConnectionReq 车辆连接请求参数
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Result<MqttServerModel> getConnect(VehicleConnectionReq vehicleConnectionReq) {
|
||||
log.info("车辆连接请求:{}",vehicleConnectionReq.toString());
|
||||
|
||||
// // 使用交换机发送消息 给事件系统发
|
||||
// rabbitTemplate.convertAndSend("exchange_topics_inform","inform.#.email.#",vehicleConnectionReq.getVehicleVin());
|
||||
// log.info("发送消息成功:{}",vehicleConnectionReq.getVehicleVin());
|
||||
|
||||
VehicleConnection vehicleConnection = new VehicleConnection();
|
||||
//车辆vin
|
||||
vehicleConnection.setVehicleVin(vehicleConnectionReq.getVehicleVin());
|
||||
//用户名
|
||||
vehicleConnection.setUsername(vehicleConnectionReq.getUsername());
|
||||
//密码(vin+时间戳+随机数)
|
||||
vehicleConnection.setPassword(vehicleConnectionReq.getVehicleVin()+vehicleConnectionReq.getTimestamp()+vehicleConnectionReq.getNonce());
|
||||
//查询有没有这辆车的vin码
|
||||
List<String> selectVehicle = carOneClickOperationMapper.selectByVehicleVin(vehicleConnectionReq.getVehicleVin());
|
||||
|
||||
if(selectVehicle.isEmpty()){
|
||||
//添加连接信息
|
||||
carOneClickOperationMapper.addConnect(vehicleConnection);
|
||||
log.info("车辆上线成功");
|
||||
}else {
|
||||
throw new RuntimeException("车辆无法重复上线");
|
||||
|
||||
}
|
||||
//先判断vin码
|
||||
HashOperations<String, String, String> hashOps = redisTemplate.opsForHash();
|
||||
String vinIp = hashOps.get("oneVinIp", vehicleConnectionReq.getVehicleVin());
|
||||
if(vinIp!=null){
|
||||
throw new RuntimeException("车辆绑定ip失败,已经存在");
|
||||
}
|
||||
MqttProperties mqttProperties = new MqttProperties();
|
||||
List<VehicleConnection> vehicleVin = selectByVehicleVin(vehicleConnectionReq.getVehicleVin());
|
||||
for (VehicleConnection connection : vehicleVin) {
|
||||
mqttProperties.setClientId(connection.getVehicleVin());
|
||||
mqttProperties.setUserName(connection.getUsername());
|
||||
mqttProperties.setPassword(connection.getPassword());
|
||||
}
|
||||
mqttProperties.setTopic("vehicle");
|
||||
mqttProperties.setQos(0);
|
||||
//判断redis有没有count键
|
||||
if(redisTemplate.hasKey("oneCount")){
|
||||
//取出count
|
||||
Integer count = Integer.valueOf(redisTemplate.opsForValue().get("oneCount"));
|
||||
if(count == 1){
|
||||
redisTemplate.opsForValue().set("oneCount",String.valueOf(0));
|
||||
}else {
|
||||
redisTemplate.opsForValue().set("oneCount",String.valueOf(count+1));
|
||||
}
|
||||
//根据游标count获取服务IP
|
||||
// String ip = redisTemplate.opsForList().index("ipList", count);
|
||||
Object ipList = redisService.redisTemplate.opsForList().index("oneIpList", count);
|
||||
|
||||
log.info("=========================oneIpList:"+ipList);
|
||||
//关联车辆和服务
|
||||
this.addIpAddress(new VinIp(vehicleConnectionReq.getVehicleVin(),ipList.toString()));
|
||||
//响应信息
|
||||
log.info("车辆:{}",vehicleConnectionReq.getVehicleVin()+"绑定成功:{}",ipList);
|
||||
mqttProperties.setBroker("tcp://"+ipList+":1883");
|
||||
// 使用交换机发送消息
|
||||
rabbitTemplate.convertAndSend(EXCHANGE_TOPICS_INFORM,ROUTINGKEY_SMS,mqttProperties);
|
||||
log.info("============================发送消息成功:{}",mqttProperties);
|
||||
return Result.success(new MqttServerModel("tcp://"+ipList+":1883","vehicle"));
|
||||
}else {
|
||||
redisTemplate.opsForValue().set("oneCount",String.valueOf(0));
|
||||
//根据游标count获取服务器Ip
|
||||
Object ipList = redisService.redisTemplate.opsForList().index("oneIpList", 0);
|
||||
//关联车辆和服务
|
||||
this.addIpAddress(new VinIp(vehicleConnectionReq.getVehicleVin(),ipList.toString()));
|
||||
//响应信息
|
||||
log.info("车辆:{}",vehicleConnectionReq.getVehicleVin(),"与:{}绑定成功",ipList);
|
||||
mqttProperties.setBroker("tcp://"+ipList+":1883");
|
||||
// 使用交换机发送消息
|
||||
rabbitTemplate.convertAndSend(EXCHANGE_TOPICS_INFORM,ROUTINGKEY_SMS,mqttProperties);
|
||||
log.info("============================发送消息成功:{}",mqttProperties);
|
||||
return Result.success(new MqttServerModel("tcp://"+ipList+":1883","vehicle"));
|
||||
}
|
||||
}
|
||||
/**
|
||||
* 添加车辆绑定IP地址存入redis中
|
||||
*/
|
||||
public void addIpAddress(VinIp vinIp) {
|
||||
if (vinIp == null || vinIp.getVin() == null || vinIp.getVin().isEmpty() || vinIp.getIp() == null || vinIp.getIp().isEmpty()) {
|
||||
throw new IllegalArgumentException("vin 或 ip 不能为空或无效");
|
||||
}
|
||||
redisTemplate.opsForHash().put("oneVinIp", vinIp.getVin(), vinIp.getIp());
|
||||
}
|
||||
|
||||
/**
|
||||
* 查询车辆绑定的服务器信息
|
||||
* @param vehicleVin 车辆vin码集合
|
||||
* @return
|
||||
*/
|
||||
public List<VehicleConnection> selectByVehicleVin(String vehicleVin) {
|
||||
return carOneClickOperationMapper.getMqttServerModel(vehicleVin);
|
||||
}
|
||||
}
|
|
@ -1,8 +1,8 @@
|
|||
package com.muyu.car.gateway.Aliyun;
|
||||
package com.muyu.cargateway.Aliyun;
|
||||
|
||||
import com.aliyun.ecs20140526.Client;
|
||||
import com.aliyun.teaopenapi.models.Config;
|
||||
import com.muyu.car.gateway.config.AliProperties;
|
||||
import com.muyu.cargateway.config.AliProperties;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
|
@ -1,11 +1,11 @@
|
|||
package com.muyu.car.gateway.Aliyun.service;
|
||||
package com.muyu.cargateway.Aliyun.service;
|
||||
|
||||
import com.aliyun.ecs20140526.Client;
|
||||
import com.aliyun.ecs20140526.models.*;
|
||||
import com.aliyun.tea.TeaException;
|
||||
import com.aliyun.teautil.models.RuntimeOptions;
|
||||
import com.muyu.car.gateway.domain.AliInstance;
|
||||
import com.muyu.car.gateway.config.AliProperties;
|
||||
import com.muyu.cargateway.config.AliProperties;
|
||||
import com.muyu.cargateway.domain.AliInstance;
|
||||
import com.muyu.common.core.exception.ServiceException;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
|
@ -49,9 +49,8 @@ public class AliYunEcsService {
|
|||
* @return 实例id集合
|
||||
*/
|
||||
public List<String> generateInstance(Integer amount) {
|
||||
redisService.deleteObject("oneIpList");
|
||||
redisService.deleteObject("oneCount");
|
||||
redisService.deleteObject("oneVinIp");
|
||||
redisService.deleteObject("instanceIds");
|
||||
redisService.deleteObject("instanceList");
|
||||
// 检查生成实例的数量是否有效
|
||||
if (amount == null || amount <= 0) {
|
||||
throw new ServiceException("生成数量不能小于1");
|
||||
|
@ -126,7 +125,6 @@ public class AliYunEcsService {
|
|||
// 创建运行时选项对象,用于配置请求的额外参数
|
||||
RuntimeOptions runtimeOptions = new RuntimeOptions();
|
||||
List<AliInstance> aliInstances = new ArrayList<>();
|
||||
List<String> stringArrayList = new ArrayList<>();
|
||||
try {
|
||||
// 发送请求并获取响应对象
|
||||
DescribeInstancesResponse describeInstancesResponse = client.describeInstancesWithOptions(request, runtimeOptions);
|
||||
|
@ -138,25 +136,16 @@ public class AliYunEcsService {
|
|||
for (DescribeInstancesResponseBody.DescribeInstancesResponseBodyInstancesInstance bodyInstance : instance) {
|
||||
// 实例id
|
||||
String instanceId = bodyInstance.getInstanceId();
|
||||
log.info("实例id为:{}", instanceId);
|
||||
// ip地址
|
||||
String ipAddress = bodyInstance.getPublicIpAddress().getIpAddress().get(0);
|
||||
log.info("实例ip为:{}", ipAddress);
|
||||
// 实例状态
|
||||
String status = bodyInstance.getStatus();
|
||||
|
||||
log.info("=======================实例id为:{}", instanceId);
|
||||
log.info("=======================实例ip为:{}", ipAddress);
|
||||
log.info("=======================实例状态为:{}", status);
|
||||
|
||||
|
||||
stringArrayList.add(ipAddress);
|
||||
log.info("实例状态为:{}", status);
|
||||
AliInstance aliInstance = new AliInstance(instanceId, ipAddress, status);
|
||||
aliInstances.add(aliInstance);
|
||||
redisService.setCacheList(instanceId, aliInstances);
|
||||
aliInstances.remove(aliInstance);
|
||||
|
||||
}
|
||||
log.info("======================ipList:{}", stringArrayList);
|
||||
redisService.setCacheList("oneIpList", stringArrayList);
|
||||
log.info("查询成功");
|
||||
} catch (Exception e) {
|
||||
log.error("查询服务器实例错误:[{}]", e.getMessage(), e);
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway;
|
||||
package com.muyu.cargateway;
|
||||
|
||||
import com.muyu.common.security.annotation.EnableCustomConfig;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
|
@ -18,8 +18,8 @@ import org.springframework.cloud.openfeign.EnableFeignClients;
|
|||
@EnableCustomConfig
|
||||
@EnableFeignClients
|
||||
@SpringBootApplication
|
||||
public class CarGatewayApplication {
|
||||
public class CloudVehicleGatewayApplication {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(CarGatewayApplication.class, args);
|
||||
SpringApplication.run(CloudVehicleGatewayApplication.class, args);
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.config;
|
||||
package com.muyu.cargateway.config;
|
||||
|
||||
import lombok.Data;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.config;
|
||||
package com.muyu.cargateway.config;
|
||||
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.slf4j.Logger;
|
|
@ -1,8 +1,8 @@
|
|||
package com.muyu.car.gateway.controller;
|
||||
package com.muyu.cargateway.controller;
|
||||
|
||||
import com.muyu.car.gateway.domain.req.VehicleConnectionReq;
|
||||
import com.muyu.car.gateway.service.CarOneClickOperationService;
|
||||
import com.muyu.car.gateway.domain.model.MqttServerModel;
|
||||
import com.muyu.cargateway.domain.model.MqttServerModel;
|
||||
import com.muyu.cargateway.domain.req.VehicleConnectionReq;
|
||||
import com.muyu.cargateway.service.CarOneClickOperationService;
|
||||
import com.muyu.common.core.domain.Result;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
|
@ -36,7 +36,7 @@ public class CarOneClickOperationController {
|
|||
@PostMapping("/receiveMsg/connect")
|
||||
public Result<MqttServerModel> receiveMsg(@RequestBody VehicleConnectionReq vehicleConnectionReq){
|
||||
log.info(">"+vehicleConnectionReq);
|
||||
return carOneClickOperationService.getConnect(vehicleConnectionReq);
|
||||
|
||||
MqttServerModel mqttServerModel =carOneClickOperationService.getConnect(vehicleConnectionReq);
|
||||
return Result.success(mqttServerModel);
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Builder;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
/**
|
||||
* 返回状态码
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain;
|
||||
package com.muyu.cargateway.domain;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
@ -19,9 +19,9 @@ public class VinIp {
|
|||
/**
|
||||
* 车辆的vin
|
||||
*/
|
||||
String vin;
|
||||
String vehicleVin;
|
||||
/**
|
||||
* 车辆的ip
|
||||
*/
|
||||
String ip;
|
||||
String ipAddress;
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain.model;
|
||||
package com.muyu.cargateway.domain.model;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Builder;
|
||||
|
@ -26,6 +26,4 @@ public class MqttServerModel {
|
|||
* MQTT订阅主题
|
||||
*/
|
||||
private String topic;
|
||||
|
||||
|
||||
}
|
|
@ -0,0 +1,87 @@
|
|||
package com.muyu.cargateway.domain.model;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Builder;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.LinkedBlockingDeque;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-26-20:23
|
||||
* @ Version:1.0
|
||||
* @ Description:任务执行模型
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Data
|
||||
@Log4j2
|
||||
@Builder
|
||||
@AllArgsConstructor
|
||||
@NoArgsConstructor
|
||||
public class TaskModel {
|
||||
/**
|
||||
* 任务状态 默认为false状态
|
||||
* true为执行中,false为未执行
|
||||
*/
|
||||
private final AtomicBoolean status =new AtomicBoolean(Boolean.FALSE);
|
||||
/**
|
||||
* 堵塞计数器
|
||||
*/
|
||||
private CountDownLatch countDownLatch;
|
||||
/**
|
||||
* 任务执行堵塞队列
|
||||
*/
|
||||
private LinkedBlockingDeque<String> carQueue =new LinkedBlockingDeque<>();
|
||||
/**
|
||||
* 任务是否执行
|
||||
* true 执行中
|
||||
* false 未执行
|
||||
* @return 是否有任务执行
|
||||
*/
|
||||
private boolean isExecution(){
|
||||
return !status.get();
|
||||
}
|
||||
/**
|
||||
* 任务名称
|
||||
*/
|
||||
private String taskName;
|
||||
/**
|
||||
* 任务执行次数
|
||||
*/
|
||||
private Integer taskExecutionCount=0;
|
||||
/**
|
||||
* 任务开始时间
|
||||
*/
|
||||
private Long taskStartTime;
|
||||
/**
|
||||
* 任务成功执行次数
|
||||
*/
|
||||
private AtomicInteger taskSuccessSum=new AtomicInteger();
|
||||
/**
|
||||
* 任务执行失败次数
|
||||
*/
|
||||
private AtomicInteger taskErrorSum=new AtomicInteger();
|
||||
|
||||
/**
|
||||
* 判断是否有任务
|
||||
* @return true 有任务
|
||||
*/
|
||||
public boolean hashNext(){
|
||||
return !carQueue.isEmpty();
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取下一个任务节点
|
||||
* @return 任务VIN
|
||||
*/
|
||||
public String next(){
|
||||
return carQueue.poll();
|
||||
}
|
||||
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain.properties;
|
||||
package com.muyu.cargateway.domain.properties;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Builder;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain.req;
|
||||
package com.muyu.cargateway.domain.req;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Builder;
|
|
@ -1,4 +1,4 @@
|
|||
package com.muyu.car.gateway.domain.resp;
|
||||
package com.muyu.cargateway.domain.resp;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
|
@ -1,6 +1,6 @@
|
|||
package com.muyu.car.gateway.Aliyun.instance;
|
||||
package com.muyu.cargateway.instance;
|
||||
|
||||
import com.muyu.car.gateway.Aliyun.service.AliYunEcsService;
|
||||
import com.muyu.cargateway.Aliyun.service.AliYunEcsService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.DisposableBean;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
|
@ -1,8 +1,9 @@
|
|||
package com.muyu.car.gateway.Aliyun.instance;
|
||||
package com.muyu.cargateway.instance;
|
||||
|
||||
import com.muyu.car.gateway.Aliyun.service.AliYunEcsService;
|
||||
import com.muyu.car.gateway.config.AliProperties;
|
||||
import com.muyu.car.gateway.domain.AliInstance;
|
||||
import com.muyu.cargateway.Aliyun.service.AliYunEcsService;
|
||||
import com.muyu.cargateway.config.AliProperties;
|
||||
import com.muyu.cargateway.domain.AliInstance;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.ApplicationArguments;
|
||||
|
@ -27,6 +28,8 @@ public class Sample implements ApplicationRunner{
|
|||
private AliYunEcsService aliYunEcsService;
|
||||
@Autowired
|
||||
private AliProperties aliProperties;
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
|
||||
@Override
|
||||
public void run(ApplicationArguments args) throws Exception {
|
||||
|
@ -39,14 +42,17 @@ public class Sample implements ApplicationRunner{
|
|||
throw new RuntimeException(e);
|
||||
}
|
||||
log.info("创建实例成功");
|
||||
// redisService.setCacheList("instanceIds", list);
|
||||
redisService.setCacheList("instanceIds", list);
|
||||
try {
|
||||
Thread.sleep(9000);
|
||||
Thread.sleep(6000);
|
||||
} catch (InterruptedException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
List<AliInstance> aliInstances = aliYunEcsService.selectInstance(list);
|
||||
log.info("================查询实例信息成功:{}",aliInstances);
|
||||
log.info("查询实例信息成功:{}",aliInstances);
|
||||
// 将查询到的实例信息列表存储到Redis中
|
||||
redisService.setCacheList("instanceList", aliInstances);
|
||||
log.info("redis存储成功:{}", aliInstances);
|
||||
}
|
||||
|
||||
// @Override
|
|
@ -1,6 +1,6 @@
|
|||
package com.muyu.car.gateway.mapper;
|
||||
package com.muyu.cargateway.mapper;
|
||||
|
||||
import com.muyu.car.gateway.domain.VehicleConnection;
|
||||
import com.muyu.cargateway.domain.VehicleConnection;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
import java.util.List;
|
||||
|
@ -18,9 +18,4 @@ public interface CarOneClickOperationMapper {
|
|||
void addConnect(VehicleConnection vehicleConnection);
|
||||
|
||||
List<String> selectByVehicleVin(String vehicleVin);
|
||||
|
||||
|
||||
List<VehicleConnection> getMqttServerModel(String vehicleVin);
|
||||
|
||||
|
||||
}
|
|
@ -1,8 +1,7 @@
|
|||
package com.muyu.car.gateway.service;
|
||||
package com.muyu.cargateway.service;
|
||||
|
||||
import com.muyu.car.gateway.domain.model.MqttServerModel;
|
||||
import com.muyu.car.gateway.domain.req.VehicleConnectionReq;
|
||||
import com.muyu.common.core.domain.Result;
|
||||
import com.muyu.cargateway.domain.model.MqttServerModel;
|
||||
import com.muyu.cargateway.domain.req.VehicleConnectionReq;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
|
@ -19,5 +18,5 @@ public interface CarOneClickOperationService {
|
|||
* @param vehicleConnectionReq 车辆连接请求参数
|
||||
* @return
|
||||
*/
|
||||
Result<MqttServerModel> getConnect(VehicleConnectionReq vehicleConnectionReq);
|
||||
MqttServerModel getConnect(VehicleConnectionReq vehicleConnectionReq);
|
||||
}
|
|
@ -0,0 +1,79 @@
|
|||
package com.muyu.cargateway.service.Impl;
|
||||
|
||||
import com.muyu.cargateway.config.RabbitmqConfig;
|
||||
import com.muyu.cargateway.domain.VehicleConnection;
|
||||
import com.muyu.cargateway.domain.VinIp;
|
||||
import com.muyu.cargateway.domain.model.MqttServerModel;
|
||||
import com.muyu.cargateway.domain.req.VehicleConnectionReq;
|
||||
import com.muyu.cargateway.mapper.CarOneClickOperationMapper;
|
||||
import com.muyu.cargateway.service.CarOneClickOperationService;
|
||||
import com.muyu.common.redis.service.RedisService;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.amqp.rabbit.core.RabbitTemplate;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-09-26-20:16
|
||||
* @ Version:1.0
|
||||
* @ Description:车辆一键操作业务实现层
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Log4j2
|
||||
@Service
|
||||
public class CarOneClickOperationServiceImpl implements CarOneClickOperationService {
|
||||
|
||||
@Autowired
|
||||
private CarOneClickOperationMapper carOneClickOperationMapper;
|
||||
|
||||
@Autowired
|
||||
private RabbitTemplate rabbitTemplate;
|
||||
@Autowired
|
||||
private RedisService redisService;
|
||||
|
||||
/**
|
||||
* 获取连接信息
|
||||
* @param vehicleConnectionReq 车辆连接请求参数
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public MqttServerModel getConnect(VehicleConnectionReq vehicleConnectionReq) {
|
||||
log.info("车辆连接请求:{}",vehicleConnectionReq.toString());
|
||||
|
||||
// 使用交换机发送消息
|
||||
rabbitTemplate.convertAndSend(RabbitmqConfig.EXCHANGE_TOPICS_INFORM,RabbitmqConfig.ROUTINGKEY_EMAIL,vehicleConnectionReq.getVehicleVin());
|
||||
log.info("发送消息成功:{}",vehicleConnectionReq.getVehicleVin());
|
||||
|
||||
|
||||
VehicleConnection vehicleConnection = new VehicleConnection();
|
||||
//车辆vin
|
||||
vehicleConnection.setVehicleVin(vehicleConnectionReq.getVehicleVin());
|
||||
//用户名
|
||||
vehicleConnection.setUsername(vehicleConnectionReq.getUsername());
|
||||
//密码(vin+时间戳+随机数)
|
||||
vehicleConnection.setPassword(vehicleConnectionReq.getVehicleVin()+vehicleConnectionReq.getTimestamp()+vehicleConnectionReq.getNonce());
|
||||
//查询车辆vin集合
|
||||
List<String> vehicleConnections =carOneClickOperationMapper.selectByVehicleVin(vehicleConnectionReq.getVehicleVin());
|
||||
if(vehicleConnections.isEmpty()){
|
||||
//添加
|
||||
carOneClickOperationMapper.addConnect(vehicleConnection);
|
||||
}
|
||||
log.info("该车辆已存在,不能重复预上线");
|
||||
//TODO 返回连接信息 做轮询操作
|
||||
|
||||
|
||||
return new MqttServerModel("tcp://"+"106.15.136.7"+":1883","vehicle");
|
||||
|
||||
}
|
||||
/**
|
||||
* 添加车辆绑定IP地址存入redis中
|
||||
*/
|
||||
public void addIpAddress(VinIp vinIp){
|
||||
redisService.setCacheObject("vehicle_ip_address:"+vinIp.getVehicleVin(),vinIp.getIpAddress());
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,135 @@
|
|||
package com.muyu.cargateway.utils;
|
||||
|
||||
import com.aliyun.ecs20140526.Client;
|
||||
import com.aliyun.ecs20140526.models.DeleteInstanceRequest;
|
||||
import com.aliyun.ecs20140526.models.DescribeInstancesRequest;
|
||||
import com.aliyun.ecs20140526.models.DescribeInstancesResponse;
|
||||
import com.aliyun.ecs20140526.models.RunInstancesRequest;
|
||||
import com.aliyun.tea.TeaException;
|
||||
import com.aliyun.teaopenapi.models.Config;
|
||||
import com.aliyun.teautil.Common;
|
||||
import com.aliyun.teautil.models.RuntimeOptions;
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-10-02-16:04
|
||||
* @ Version:1.0
|
||||
* @ Description:ecs实例工具类
|
||||
* @author Lenovo
|
||||
*/
|
||||
@Log4j2
|
||||
public class ECSTool {
|
||||
|
||||
public static final String ACCESS_KEY_ID = "LTAI5tDH3FyRx4PRr6anx2TL";
|
||||
public static final String ACCESS_KEY_SECRET = "xdQnX2tDattY50raNkUWmHzE2tondP";
|
||||
|
||||
public static Client createClient() throws Exception {
|
||||
// 工程代码泄露可能会导致 AccessKey 泄露,并威胁账号下所有资源的安全性。以下代码示例仅供参考。
|
||||
Config config = new Config()
|
||||
// 必填,请确保代码运行环境设置了环境变量 ALIBABA_CLOUD_ACCESS_KEY_ID。
|
||||
.setAccessKeyId(ACCESS_KEY_ID)
|
||||
// 必填,请确保代码运行环境设置了环境变量 ALIBABA_CLOUD_ACCESS_KEY_SECRET。
|
||||
.setAccessKeySecret(ACCESS_KEY_SECRET);
|
||||
// Endpoint 请参考 https://api.aliyun.com/product/Ecs
|
||||
config.endpoint = "ecs-cn-hangzhou.aliyuncs.com";
|
||||
return new Client(config);
|
||||
}
|
||||
public static void runEcsInstance(String regionId, String launchTemplateId) throws Exception {
|
||||
Client client = ECSTool.createClient();
|
||||
RunInstancesRequest request = new RunInstancesRequest();
|
||||
request.setRegionId(regionId)
|
||||
.setLaunchTemplateId(launchTemplateId);
|
||||
RuntimeOptions runtimeOptions = new RuntimeOptions();
|
||||
try{
|
||||
client.runInstancesWithOptions(request, runtimeOptions);
|
||||
}catch (Exception error){
|
||||
// 处理API调用过程中出现的异常
|
||||
System.out.println(error.getMessage());
|
||||
if (error instanceof TeaException) {
|
||||
// 处理特定类型的异常,如TeaException
|
||||
TeaException teaError = (TeaException) error;
|
||||
// 打印诊断推荐链接
|
||||
System.out.println(teaError.getData().get("Recommend"));
|
||||
// 断言错误信息
|
||||
Common.assertAsString(teaError.getMessage());
|
||||
} else {
|
||||
// 处理其他类型的异常
|
||||
System.out.println(error.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
*销毁实例
|
||||
*/
|
||||
public static void runEcsRemove(String instanceId) throws Exception {
|
||||
Client client = ECSTool.createClient();
|
||||
DeleteInstanceRequest deleteInstancesRequest = new DeleteInstanceRequest();
|
||||
deleteInstancesRequest.setInstanceId(instanceId);
|
||||
RuntimeOptions runtimeOptions = new RuntimeOptions();
|
||||
|
||||
try {
|
||||
// 复制代码运行请自行打印 API 的返回值
|
||||
client.deleteInstanceWithOptions(deleteInstancesRequest, runtimeOptions);
|
||||
} catch (TeaException error) {
|
||||
// 此处仅做打印展示,请谨慎对待异常处理,在工程项目中切勿直接忽略异常。
|
||||
// 错误 message
|
||||
System.out.println(error.getMessage());
|
||||
// 诊断地址
|
||||
System.out.println(error.getData().get("Recommend"));
|
||||
Common.assertAsString(error.message);
|
||||
} catch (Exception _error) {
|
||||
TeaException error = new TeaException(_error.getMessage(), _error);
|
||||
// 此处仅做打印展示,请谨慎对待异常处理,在工程项目中切勿直接忽略异常。
|
||||
// 错误 message
|
||||
System.out.println(error.getMessage());
|
||||
// 诊断地址
|
||||
System.out.println(error.getData().get("Recommend"));
|
||||
Common.assertAsString(error.message);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 查询实例列表
|
||||
* @param regionId 地域ID
|
||||
*/
|
||||
public static List<String> findInstance(String regionId) throws Exception {
|
||||
Client client = ECSTool.createClient();
|
||||
DescribeInstancesRequest describeInstancesRequest = new DescribeInstancesRequest();
|
||||
describeInstancesRequest.setRegionId(regionId);
|
||||
RuntimeOptions runtimeOptions = new RuntimeOptions();
|
||||
List<String> stringArrayList = new ArrayList<>();
|
||||
try {
|
||||
DescribeInstancesResponse response = client.describeInstancesWithOptions(describeInstancesRequest, runtimeOptions);
|
||||
List<List<String>> ipListList = response.getBody().instances.getInstance().stream().map(instance -> instance.publicIpAddress.ipAddress).collect(Collectors.toList());
|
||||
for (List<String> strings : ipListList) {
|
||||
for (String ip : strings) {
|
||||
stringArrayList.add(ip);
|
||||
}
|
||||
return stringArrayList;
|
||||
}
|
||||
} catch (TeaException error) {
|
||||
// 此处仅做打印展示,请谨慎对待异常处理,在工程项目中切勿直接忽略异常。
|
||||
// 错误 message
|
||||
System.out.println(error.getMessage());
|
||||
// 诊断地址
|
||||
System.out.println(error.getData().get("Recommend"));
|
||||
Common.assertAsString(error.message);
|
||||
} catch (Exception _error) {
|
||||
TeaException error = new TeaException(_error.getMessage(), _error);
|
||||
// 此处仅做打印展示,请谨慎对待异常处理,在工程项目中切勿直接忽略异常。
|
||||
// 错误 message
|
||||
System.out.println(error.getMessage());
|
||||
// 诊断地址
|
||||
System.out.println(error.getData().get("Recommend"));
|
||||
Common.assertAsString(error.message);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
|
@ -7,7 +7,7 @@ nacos:
|
|||
addr: 47.116.173.119:8848
|
||||
user-name: nacos
|
||||
password: nacos
|
||||
namespace: one
|
||||
namespace: one-saas
|
||||
# SPRING_AMQP_DESERIALIZATION_TRUST_ALL=true spring.amqp.deserialization.trust.all
|
||||
# Spring
|
||||
spring:
|
||||
|
@ -82,4 +82,4 @@ aliyun:
|
|||
instance-type: ecs.t6-c1m1.large
|
||||
security-group-id: sg-uf642d5u4ja5gsiitx8y
|
||||
switch-id: vsw-uf66lifrkhxqc94xi06v3
|
||||
amount: 2
|
||||
amount: 1
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
<!DOCTYPE mapper
|
||||
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
|
||||
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
|
||||
<mapper namespace="com.muyu.car.gateway.mapper.CarOneClickOperationMapper">
|
||||
<mapper namespace="com.muyu.cargateway.mapper.CarOneClickOperationMapper">
|
||||
|
||||
|
||||
<insert id="addConnect">
|
||||
|
@ -14,14 +14,6 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
|
|||
<select id="selectByVehicleVin" resultType="java.lang.String">
|
||||
select vehicle_vin from car_one_click_operation where vehicle_vin = #{vehicleVin}
|
||||
</select>
|
||||
<select id="getMqttServerModel" resultType="com.muyu.car.gateway.domain.VehicleConnection">
|
||||
select
|
||||
vehicle_vin,user_name,password
|
||||
from
|
||||
car_one_click_operation
|
||||
where
|
||||
vehicle_vin = #{vehicleVin}
|
||||
</select>
|
||||
|
||||
|
||||
</mapper>
|
||||
|
|
|
@ -1,95 +0,0 @@
|
|||
<?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.muyu</groupId>
|
||||
<artifactId>cloud-modules</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-modules-car</artifactId>
|
||||
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<!-- SpringCloud Alibaba Nacos -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Alibaba Nacos Config -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Alibaba Sentinel -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
<artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringBoot Actuator -->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- Mysql Connector -->
|
||||
<dependency>
|
||||
<groupId>com.mysql</groupId>
|
||||
<artifactId>mysql-connector-j</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataSource -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datasource</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataScope -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datascope</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-core</artifactId>
|
||||
</dependency>
|
||||
<!-- 接口模块 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-api-doc</artifactId>
|
||||
</dependency>
|
||||
|
||||
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<finalName>${project.artifactId}</finalName>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>repackage</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
|
||||
</project>
|
|
@ -1,23 +0,0 @@
|
|||
package com.muyu.carrail;
|
||||
|
||||
import com.muyu.common.security.annotation.EnableCustomConfig;
|
||||
import com.muyu.common.security.annotation.EnableMyFeignClients;
|
||||
import org.mybatis.spring.annotation.MapperScan;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
|
||||
|
||||
@EnableCustomConfig
|
||||
@EnableMyFeignClients
|
||||
@MapperScan("com.muyu.carrail.mapper")
|
||||
@SpringBootApplication
|
||||
public class CloudCarRailApplication {
|
||||
public static void main(String[] args) {
|
||||
// try {
|
||||
//
|
||||
// } catch (Exception e) {
|
||||
// e.printStackTrace();
|
||||
// }
|
||||
SpringApplication.run(CloudCarRailApplication.class, args);
|
||||
}
|
||||
}
|
|
@ -1,58 +0,0 @@
|
|||
# Tomcat
|
||||
server:
|
||||
port: 10011
|
||||
|
||||
# nacos线上地址
|
||||
nacos:
|
||||
addr: 47.116.173.119:8848
|
||||
user-name: nacos
|
||||
password: nacos
|
||||
namespace: public
|
||||
# SPRING_AMQP_DESERIALIZATION_TRUST_ALL=true spring.amqp.deserialization.trust.all
|
||||
# Spring
|
||||
spring:
|
||||
amqp:
|
||||
deserialization:
|
||||
trust:
|
||||
all: true
|
||||
main:
|
||||
allow-bean-definition-overriding: true
|
||||
application:
|
||||
# 应用名称
|
||||
name: cloud-car
|
||||
profiles:
|
||||
# 环境配置
|
||||
active: dev
|
||||
cloud:
|
||||
nacos:
|
||||
discovery:
|
||||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
config:
|
||||
# 服务注册地址
|
||||
server-addr: ${nacos.addr}
|
||||
# nacos用户名
|
||||
username: ${nacos.user-name}
|
||||
# nacos密码
|
||||
password: ${nacos.password}
|
||||
# 命名空间
|
||||
namespace: ${nacos.namespace}
|
||||
# 配置文件格式
|
||||
file-extension: yml
|
||||
# 共享配置
|
||||
shared-configs:
|
||||
# 系统共享配置
|
||||
- application-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
# 系统环境Config共享配置
|
||||
- application-config-${spring.profiles.active}.${spring.cloud.nacos.config.file-extension}
|
||||
|
||||
logging:
|
||||
level:
|
||||
com.muyu.carrail.mapper: DEBUG
|
||||
|
|
@ -1,21 +0,0 @@
|
|||
package com.muyu.car;
|
||||
|
||||
import com.muyu.common.security.annotation.EnableCustomConfig;
|
||||
import com.muyu.common.security.annotation.EnableMyFeignClients;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
|
||||
/**
|
||||
* 系统模块
|
||||
*
|
||||
* @author muyu
|
||||
*/
|
||||
@EnableCustomConfig
|
||||
//@EnableCustomSwagger2
|
||||
@EnableMyFeignClients
|
||||
@SpringBootApplication
|
||||
public class CloudCarApplication {
|
||||
public static void main (String[] args) {
|
||||
SpringApplication.run(CloudCarApplication.class, args);
|
||||
}
|
||||
}
|
|
@ -1,157 +0,0 @@
|
|||
package com.muyu.car.redis;
|
||||
|
||||
import com.alibaba.fastjson2.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
|
||||
import com.muyu.car.constant.RedisConstant;
|
||||
import com.muyu.car.domain.VehicleMessage;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
@Component
|
||||
public class RedisInitialize {
|
||||
|
||||
|
||||
@Autowired
|
||||
private RedisTemplate<String,String>redisTemplate;
|
||||
|
||||
@PostConstruct
|
||||
public void a() {
|
||||
|
||||
new Thread(()->{
|
||||
try {
|
||||
Thread.sleep(1000);
|
||||
}catch (Exception exception){
|
||||
throw new RuntimeException(exception);
|
||||
}
|
||||
});
|
||||
VehicleMessage message1 = new VehicleMessage();
|
||||
message1.setStartTime(System.currentTimeMillis());
|
||||
message1.setSpeed("50");
|
||||
message1.setLongitude("126.397428");
|
||||
message1.setLatitude("37.90923");
|
||||
message1.setTotalMileage("1010");
|
||||
message1.setTotalVoltage("22.5");
|
||||
message1.setAcceleratorPedalTravelValue("1.5");
|
||||
message1.setBrakePedalTravelValue("1.2");
|
||||
message1.setSpecificFuelConsumption("1.8");
|
||||
message1.setMotorControllerTemperature("59");
|
||||
message1.setMotorSpeed("850");
|
||||
message1.setMotorTorque("110");
|
||||
message1.setMotorTemperature("53");
|
||||
message1.setMotorVoltage("12.5");
|
||||
message1.setMotorCurrent("1.1");
|
||||
message1.setPowerBatteryRemainingSOC("88");
|
||||
message1.setMaximumPower("999");
|
||||
message1.setMaximumDischargePower("950");
|
||||
message1.setDcdc("2");
|
||||
message1.setChg("2");
|
||||
message1.setBMSSelfCheckCounter("2");
|
||||
message1.setElectricCurrent("2.3");
|
||||
message1.setTotalVoltageV3("13.1");
|
||||
message1.setSingleMaximumVoltage("14.1");
|
||||
message1.setMinimumVoltageOfABattery("12.2");
|
||||
message1.setMaximumBatteryTemperature("85");
|
||||
message1.setMinimumBatteryTemperature("51");
|
||||
message1.setPowerBatteryAvailableCapacity("560");
|
||||
message1.setCombinedCurrent("1.1");
|
||||
message1.setRunningState("2");
|
||||
message1.setWorkStatus("2");
|
||||
message1.setDriveMotorCondition("1");
|
||||
message1.setVehicleStatus("1");
|
||||
message1.setChargingState("1");
|
||||
message1.setHeatingState("1");
|
||||
message1.setCarVin("1HGCM826X3A004352");
|
||||
|
||||
redisTemplate.opsForValue().set(RedisConstant.VEHICLE_ENTERPRISE + message1.getCarVin(), JSON.toJSONString(message1));
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
public void initialize() {
|
||||
|
||||
|
||||
//
|
||||
// new Thread(() -> {
|
||||
// try {
|
||||
// Thread.sleep(500);
|
||||
// } catch (InterruptedException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
// List<VehicleMessageMiddle> vehicleMessageMiddleList = vehicleMessageMiddleService.list();
|
||||
// vehicleMessageMiddleList.forEach(vehicleMessageMiddle -> {
|
||||
// List<MessageDetail> messageDetailList = messageDetailService.list(new LambdaQueryWrapper<>() {{
|
||||
// in(MessageDetail::getId, Arrays.asList(vehicleMessageMiddle.getMessageIds().split(",")));
|
||||
// }});
|
||||
// String jsonString = JSON.toJSONString(messageDetailList);
|
||||
// redisTemplate.opsForHash().put(RedisConstant.MESSAGE_DETAIL, vehicleMessageMiddle.getCarVin(), jsonString);
|
||||
// });
|
||||
// });
|
||||
|
||||
// MessageDetail messageDetail = new MessageDetail();
|
||||
// messageDetail.setKeyCode("1");
|
||||
// messageDetail.setLabel("测试");
|
||||
// messageDetail.setStartBit(0);
|
||||
// messageDetail.setStopBit(8);
|
||||
// messageDetail.setType("1");
|
||||
|
||||
// List<VehicleMessageMiddle> list = vehicleMessageMiddleService.list();
|
||||
// list.forEach(vehicleMessageMiddle -> {
|
||||
// List<MessageDetail> messageDetailList = messageDetailService.list(new LambdaQueryWrapper<>() {{
|
||||
// in(MessageDetail::getId, Arrays.asList(vehicleMessageMiddle.getMessageIds().split(",")));
|
||||
// });
|
||||
// String jsonString = JSON.toJSONString(messageDetailList);
|
||||
// redisTemplate.opsForHash().put(RedisConstant.VEHICLE_ENTERPRISE, message1.getCarVin(), String.valueOf(jsonString));
|
||||
|
||||
new Thread(()->{
|
||||
try {
|
||||
Thread.sleep(500);
|
||||
}catch (Exception exception){
|
||||
throw new RuntimeException(exception);
|
||||
}
|
||||
});
|
||||
VehicleMessage message1 = new VehicleMessage();
|
||||
message1.setStartTime(System.currentTimeMillis());
|
||||
message1.setSpeed("50");
|
||||
message1.setLongitude("116.397428");
|
||||
message1.setLatitude("39.90923");
|
||||
message1.setTotalMileage("1000");
|
||||
message1.setTotalVoltage("12.5");
|
||||
message1.setAcceleratorPedalTravelValue("0.5");
|
||||
message1.setBrakePedalTravelValue("0.2");
|
||||
message1.setSpecificFuelConsumption("0.8");
|
||||
message1.setMotorControllerTemperature("60");
|
||||
message1.setMotorSpeed("800");
|
||||
message1.setMotorTorque("100");
|
||||
message1.setMotorTemperature("70");
|
||||
message1.setMotorVoltage("12.6");
|
||||
message1.setMotorCurrent("1.2");
|
||||
message1.setPowerBatteryRemainingSOC("80");
|
||||
message1.setMaximumPower("1000");
|
||||
message1.setMaximumDischargePower("900");
|
||||
message1.setDcdc("1");
|
||||
message1.setChg("1");
|
||||
message1.setBMSSelfCheckCounter("1");
|
||||
message1.setElectricCurrent("2.5");
|
||||
message1.setTotalVoltageV3("13.5");
|
||||
message1.setSingleMaximumVoltage("14.5");
|
||||
message1.setMinimumVoltageOfABattery("12.0");
|
||||
message1.setMaximumBatteryTemperature("80");
|
||||
message1.setMinimumBatteryTemperature("50");
|
||||
message1.setPowerBatteryAvailableCapacity("800");
|
||||
message1.setCombinedCurrent("1.5");
|
||||
message1.setRunningState("1");
|
||||
message1.setWorkStatus("1");
|
||||
message1.setDriveMotorCondition("1");
|
||||
message1.setVehicleStatus("1");
|
||||
message1.setChargingState("1");
|
||||
message1.setHeatingState("1");
|
||||
message1.setCarVin("1HGCM826X3A004352");
|
||||
|
||||
redisTemplate.opsForValue().set(RedisConstant.VEHICLE_ENTERPRISE + message1.getCarVin(), JSON.toJSONString(message1));
|
||||
}
|
||||
}
|
|
@ -1,75 +0,0 @@
|
|||
package com.muyu.car.util;
|
||||
|
||||
import org.bouncycastle.jce.provider.BouncyCastleProvider;
|
||||
import org.bouncycastle.openssl.PEMKeyPair;
|
||||
import org.bouncycastle.openssl.PEMParser;
|
||||
import org.bouncycastle.openssl.jcajce.JcaPEMKeyConverter;
|
||||
|
||||
import javax.net.ssl.KeyManagerFactory;
|
||||
import javax.net.ssl.SSLContext;
|
||||
import javax.net.ssl.SSLSocketFactory;
|
||||
import javax.net.ssl.TrustManagerFactory;
|
||||
import java.io.BufferedInputStream;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileReader;
|
||||
import java.security.KeyPair;
|
||||
import java.security.KeyStore;
|
||||
import java.security.Security;
|
||||
import java.security.cert.CertificateFactory;
|
||||
import java.security.cert.X509Certificate;
|
||||
|
||||
public class SSLUtils {
|
||||
public static SSLSocketFactory getSocketFactory(final String caCrtFile,
|
||||
final String crtFile, final String keyFile, final String password)
|
||||
throws Exception {
|
||||
Security.addProvider(new BouncyCastleProvider());
|
||||
|
||||
// load CA certificate
|
||||
X509Certificate caCert = null;
|
||||
|
||||
FileInputStream fis = new FileInputStream(caCrtFile);
|
||||
BufferedInputStream bis = new BufferedInputStream(fis);
|
||||
CertificateFactory cf = CertificateFactory.getInstance("X.509");
|
||||
|
||||
while (bis.available() > 0) {
|
||||
caCert = (X509Certificate) cf.generateCertificate(bis);
|
||||
}
|
||||
|
||||
// load client certificate
|
||||
bis = new BufferedInputStream(new FileInputStream(crtFile));
|
||||
X509Certificate cert = null;
|
||||
while (bis.available() > 0) {
|
||||
cert = (X509Certificate) cf.generateCertificate(bis);
|
||||
}
|
||||
|
||||
// load client private key
|
||||
PEMParser pemParser = new PEMParser(new FileReader(keyFile));
|
||||
Object object = pemParser.readObject();
|
||||
JcaPEMKeyConverter converter = new JcaPEMKeyConverter().setProvider("BC");
|
||||
KeyPair key = converter.getKeyPair((PEMKeyPair) object);
|
||||
pemParser.close();
|
||||
|
||||
// CA certificate is used to authenticate server
|
||||
KeyStore caKs = KeyStore.getInstance(KeyStore.getDefaultType());
|
||||
caKs.load(null, null);
|
||||
caKs.setCertificateEntry("ca-certificate", caCert);
|
||||
TrustManagerFactory tmf = TrustManagerFactory.getInstance("X509");
|
||||
tmf.init(caKs);
|
||||
|
||||
// client key and certificates are sent to server so it can authenticate
|
||||
KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
|
||||
ks.load(null, null);
|
||||
ks.setCertificateEntry("certificate", cert);
|
||||
ks.setKeyEntry("private-key", key.getPrivate(), password.toCharArray(),
|
||||
new java.security.cert.Certificate[]{cert});
|
||||
KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory
|
||||
.getDefaultAlgorithm());
|
||||
kmf.init(ks, password.toCharArray());
|
||||
|
||||
// finally, create SSL socket factory
|
||||
SSLContext context = SSLContext.getInstance("TLSv1.2");
|
||||
context.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);
|
||||
|
||||
return context.getSocketFactory();
|
||||
}
|
||||
}
|
|
@ -9,16 +9,42 @@
|
|||
<version>3.6.3</version>
|
||||
</parent>
|
||||
|
||||
<artifactId>cloud-modules-carmanage</artifactId>
|
||||
<artifactId>cloud-modules-data-processing</artifactId>
|
||||
|
||||
<description>
|
||||
cloud-data-processing 数据处理模块
|
||||
</description>
|
||||
|
||||
<properties>
|
||||
<maven.compiler.source>17</maven.compiler.source>
|
||||
<maven.compiler.target>17</maven.compiler.target>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-kafka</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-caffeine</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-rabbit</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-iotdb</artifactId>
|
||||
<version>3.6.3</version>
|
||||
</dependency>
|
||||
|
||||
<!-- SpringCloud Alibaba Nacos -->
|
||||
<dependency>
|
||||
<groupId>com.alibaba.cloud</groupId>
|
||||
|
@ -43,51 +69,26 @@
|
|||
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-tomcat</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- Mysql Connector -->
|
||||
<dependency>
|
||||
<groupId>com.mysql</groupId>
|
||||
<artifactId>mysql-connector-j</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataSource -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datasource</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common DataScope -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-datascope</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- MuYu Common Log -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-log</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- 接口模块 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-api-doc</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- XllJob定时任务 -->
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-xxl</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.muyu</groupId>
|
||||
<artifactId>cloud-common-rabbit</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.bouncycastle</groupId>
|
||||
<artifactId>bcpkix-jdk15on</artifactId>
|
||||
<version>1.70</version>
|
||||
<artifactId>cloud-common-datasource</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
package com.muyu.data.processing;
|
||||
|
||||
import com.muyu.common.security.annotation.EnableCustomConfig;
|
||||
import com.muyu.common.security.annotation.EnableMyFeignClients;
|
||||
import org.springframework.amqp.rabbit.annotation.EnableRabbit;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.context.annotation.ComponentScan;
|
||||
|
||||
/**
|
||||
* 数据处理模块启动器
|
||||
* @Author: 胡杨
|
||||
* @Name: MyData
|
||||
* @Description: 数据处理模块启动器
|
||||
* @CreatedDate: 2024/9/26 下午7:31
|
||||
* @FilePath: com.muyu.data.processing
|
||||
*/
|
||||
@EnableRabbit
|
||||
@EnableCustomConfig
|
||||
@EnableMyFeignClients
|
||||
@ComponentScan(basePackages = {"com.muyu"})
|
||||
@SpringBootApplication
|
||||
public class CloudVehicleEventApplication {
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(CloudVehicleEventApplication.class, args);
|
||||
|
||||
System.out.println("MyData 模块启动成功!");
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,100 @@
|
|||
package com.muyu.data.processing.config;
|
||||
|
||||
import lombok.extern.log4j.Log4j2;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.amqp.core.*;
|
||||
import org.springframework.beans.factory.annotation.Qualifier;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
/**
|
||||
* @author Lenovo
|
||||
* @ Tool:IntelliJ IDEA
|
||||
* @ Author:CHX
|
||||
* @ Date:2024-10-04-15:13
|
||||
* @ Version:1.0
|
||||
* @ Description:rabbitmq配置类
|
||||
*/
|
||||
@Log4j2
|
||||
@Configuration
|
||||
public class RabbitmqConfig {
|
||||
// 日志
|
||||
private static final Logger logger = LoggerFactory.getLogger(RabbitmqConfig.class);
|
||||
|
||||
/**
|
||||
* 队列
|
||||
*/
|
||||
public static final String QUEUE_INFORM_EMAIL = "queue_inform_email";
|
||||
/**
|
||||
* 队列
|
||||
*/
|
||||
public static final String QUEUE_INFORM_SMS = "queue_inform_sms";
|
||||
/**
|
||||
* 交换机
|
||||
*/
|
||||
public static final String EXCHANGE_TOPICS_INFORM = "exchange_topics_inform";
|
||||
/**
|
||||
* 路由key
|
||||
*/
|
||||
public static final String ROUTINGKEY_EMAIL = "inform.#.email.#";
|
||||
/**
|
||||
* 路由key
|
||||
*/
|
||||
public static final String ROUTINGKEY_SMS = "inform.#.sms.#";
|
||||
|
||||
/**
|
||||
* 声明交换机,做持久化
|
||||
*/
|
||||
@Bean(EXCHANGE_TOPICS_INFORM)
|
||||
public Exchange exchangeTopicsInform() {
|
||||
try {
|
||||
Exchange exchange = ExchangeBuilder.topicExchange(EXCHANGE_TOPICS_INFORM).durable(true).build();
|
||||
log.info("创建的交换机为: {}", EXCHANGE_TOPICS_INFORM);
|
||||
return exchange;
|
||||
} catch (Exception e) {
|
||||
log.error("创建该: {} 交换机失败", EXCHANGE_TOPICS_INFORM, e);
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
// 声明QUEUE_INFORM_EMAIL队列
|
||||
@Bean(QUEUE_INFORM_EMAIL)
|
||||
public Queue queueInformEmail() {
|
||||
try {
|
||||
Queue queue = new Queue(QUEUE_INFORM_EMAIL);
|
||||
log.info("创建的队列为: {}", QUEUE_INFORM_EMAIL);
|
||||
return queue;
|
||||
} catch (Exception e) {
|
||||
log.error("创建该: {} 队列失败", QUEUE_INFORM_EMAIL, e);
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
// 声明QUEUE_INFORM_SMS队列
|
||||
@Bean(QUEUE_INFORM_SMS)
|
||||
public Queue queueInformSms() {
|
||||
try {
|
||||
Queue queue = new Queue(QUEUE_INFORM_SMS);
|
||||
log.info("创建的队列为: {}", QUEUE_INFORM_SMS);
|
||||
return queue;
|
||||
} catch (Exception e) {
|
||||
log.error("创建该: {} 队列失败", QUEUE_INFORM_SMS, e);
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
//ROUTINGKEY_EMAIL队列绑定交换机,指定routingKey
|
||||
@Bean
|
||||
public Binding bindingQueueInformEmail(@Qualifier(QUEUE_INFORM_EMAIL) Queue queue,
|
||||
@Qualifier(EXCHANGE_TOPICS_INFORM) Exchange exchange) {
|
||||
return BindingBuilder.bind(queue).to(exchange).with(ROUTINGKEY_EMAIL).noargs();
|
||||
}
|
||||
|
||||
//ROUTINGKEY_SMS队列绑定交换机,指定routingKey
|
||||
@Bean
|
||||
public Binding bindingRoutingKeySms(@Qualifier(QUEUE_INFORM_SMS) Queue queue,
|
||||
@Qualifier(EXCHANGE_TOPICS_INFORM) Exchange exchange) {
|
||||
return BindingBuilder.bind(queue).to(exchange).with(ROUTINGKEY_SMS).noargs();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,37 @@
|
|||
package com.muyu.data.processing.controller;
|
||||
|
||||
import com.muyu.data.processing.config.RabbitmqConfig;
|
||||
import com.muyu.data.processing.service.DataProcessingService;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
import org.springframework.amqp.core.Message;
|
||||
import org.springframework.amqp.rabbit.core.RabbitTemplate;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
/**
|
||||
* 数据处理控制层
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: DataProcessing
|
||||
* @Description: 数据处理控制层
|
||||
* @CreatedDate: 2024/9/28 下午3:53
|
||||
* @FilePath: com.muyu.data.processing.controller
|
||||
*/
|
||||
|
||||
@Slf4j
|
||||
@RestController
|
||||
@RequestMapping("/DataProcessing")
|
||||
public class DataProcessingController {
|
||||
@Resource
|
||||
private DataProcessingService service;
|
||||
@Resource
|
||||
private RabbitTemplate rabbitTemplate;
|
||||
|
||||
@GetMapping("/goOnline")
|
||||
public void goOnline(@RequestParam("vin") String vin) {
|
||||
rabbitTemplate.convertAndSend(RabbitmqConfig.EXCHANGE_TOPICS_INFORM, "inform.email", vin);
|
||||
log.info("发送消息成功:{}",vin);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
package com.muyu.data.processing.domain;
|
||||
|
||||
import lombok.*;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* 报文信息 时序实体类
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: DataProcessing
|
||||
* @Description: 报文信息 时序实体类
|
||||
* @CreatedDate: 2024/9/28 下午3:48
|
||||
* @FilePath: com.muyu.data.processing.domain
|
||||
*/
|
||||
|
||||
@Data
|
||||
@ToString
|
||||
@Builder
|
||||
@NoArgsConstructor
|
||||
@AllArgsConstructor
|
||||
public class BasicData implements Serializable {
|
||||
|
||||
private String key;
|
||||
private String label;
|
||||
private String value;
|
||||
private String type;
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
package com.muyu.data.processing.domain;
|
||||
|
||||
import lombok.*;
|
||||
|
||||
/**
|
||||
* 车辆信息
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: CarData
|
||||
* @Description: 车辆信息
|
||||
* @CreatedDate: 2024/10/2 下午2:34
|
||||
* @FilePath: com.muyu.data.processing.domain
|
||||
*/
|
||||
|
||||
@Data
|
||||
@Builder
|
||||
@ToString
|
||||
@NoArgsConstructor
|
||||
@AllArgsConstructor
|
||||
public class CarData {
|
||||
private String vin;
|
||||
private long timestamp;
|
||||
private String latitude;
|
||||
private String longitude;
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
package com.muyu.data.processing.domain;
|
||||
|
||||
import com.muyu.common.core.web.domain.BaseEntity;
|
||||
import lombok.*;
|
||||
import lombok.experimental.SuperBuilder;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* 报文信息 时序实体类
|
||||
*
|
||||
* @Author: 胡杨
|
||||
* @Name: DataProcessing
|
||||
* @Description: 报文信息 时序实体类
|
||||
* @CreatedDate: 2024/9/28 下午3:48
|
||||
* @FilePath: com.muyu.data.processing.domain
|
||||
*/
|
||||
|
||||
@EqualsAndHashCode(callSuper = true)
|
||||
@Data
|
||||
@ToString
|
||||
@SuperBuilder
|
||||
@NoArgsConstructor
|
||||
@AllArgsConstructor
|
||||
public class IotDbData extends BaseEntity {
|
||||
private long timestamp;
|
||||
|
||||
private String vin;
|
||||
|
||||
private String latitude;
|
||||
private String longitude;
|
||||
|
||||
|
||||
}
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue