Skip to content
Toggle navigation
Projects
Groups
Snippets
Help
yangxiujun
/
paidan_demo
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Snippets
Settings
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit 35bbd68c
authored
Nov 16, 2023
by
Ren Ping
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
feat:自动任务增加redis锁
1 parent
f8d4ef2f
Show whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
175 additions
and
9 deletions
project-dispatch/pom.xml
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedisConfig.java
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedissonConfig.java
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedissonUtil.java
project-dispatch/src/main/java/com/dituhui/pea/dispatch/service/impl/SchedulerServiceImpl.java
project-dispatch/src/main/resources/application-dev.yaml
project-dispatch/src/main/resources/application.yaml
project-dispatch/pom.xml
View file @
35bbd68
...
...
@@ -17,6 +17,7 @@
<druid.version>
1.1.10
</druid.version>
<version.org.optaplanner>
9.38.0.Final
</version.org.optaplanner>
<mysql.version>
8.0.28
</mysql.version>
<redisson.version>
3.19.0
</redisson.version>
</properties>
<dependencies>
...
...
@@ -163,6 +164,18 @@
<version>
5.8.22
</version>
</dependency>
<!-- Redis -->
<dependency>
<groupId>
org.springframework.boot
</groupId>
<artifactId>
spring-boot-starter-data-redis
</artifactId>
</dependency>
<dependency>
<groupId>
org.redisson
</groupId>
<artifactId>
redisson
</artifactId>
<version>
${redisson.version}
</version>
</dependency>
</dependencies>
<build>
<plugins>
...
...
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedisConfig.java
0 → 100644
View file @
35bbd68
package
com
.
dituhui
.
pea
.
dispatch
.
common
;
import
org.springframework.context.annotation.Bean
;
import
org.springframework.context.annotation.Configuration
;
import
org.springframework.data.redis.connection.RedisConnectionFactory
;
import
org.springframework.data.redis.core.RedisTemplate
;
import
org.springframework.data.redis.serializer.StringRedisSerializer
;
@Configuration
public
class
RedisConfig
{
@Bean
public
RedisTemplate
<
String
,
String
>
redisTemplate
(
RedisConnectionFactory
connectionFactory
)
{
// ObjectMapper objectMapper = new ObjectMapper();
// objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
// objectMapper.activateDefaultTyping(objectMapper.getPolymorphicTypeValidator(),
// ObjectMapper.DefaultTyping.EVERYTHING, JsonTypeInfo.As.PROPERTY);
RedisTemplate
<
String
,
String
>
redisTemplate
=
new
RedisTemplate
<>();
redisTemplate
.
setConnectionFactory
(
connectionFactory
);
redisTemplate
.
setKeySerializer
(
new
StringRedisSerializer
());
redisTemplate
.
setValueSerializer
(
new
StringRedisSerializer
());
return
redisTemplate
;
}
}
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedissonConfig.java
0 → 100644
View file @
35bbd68
package
com
.
dituhui
.
pea
.
dispatch
.
common
;
import
org.redisson.Redisson
;
import
org.redisson.api.RedissonClient
;
import
org.redisson.config.Config
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.boot.autoconfigure.data.redis.RedisProperties
;
import
org.springframework.context.annotation.Bean
;
import
org.springframework.context.annotation.Configuration
;
import
java.util.Objects
;
/**
* jedis配置类
*/
@Configuration
public
class
RedissonConfig
{
@Autowired
private
RedisProperties
redisProperties
;
@Bean
public
RedissonClient
redissonClient
()
{
Config
config
=
new
Config
();
if
(
Objects
.
isNull
(
redisProperties
.
getCluster
())
||
Objects
.
isNull
(
redisProperties
.
getCluster
().
getNodes
()))
{
//单机配置
config
.
useSingleServer
()
.
setPassword
(
redisProperties
.
getPassword
())
.
setAddress
(
"redis://"
+
redisProperties
.
getHost
()
+
":"
+
redisProperties
.
getPort
())
//连接池大小:默认值:64
.
setConnectionPoolSize
(
64
);
//连接池大小:默认值:64
}
else
{
String
[]
nodes
=
redisProperties
.
getCluster
().
getNodes
().
toArray
(
new
String
[
0
]);
String
[]
result
=
new
String
[
nodes
.
length
];
for
(
int
i
=
0
;
i
<
nodes
.
length
;
i
++)
{
String
nodePart
=
"redis://"
+
nodes
[
i
];
result
[
i
]
=
nodePart
;
}
//集群配置
config
.
useClusterServers
()
.
setPassword
(
redisProperties
.
getPassword
())
.
setScanInterval
(
10000
)
.
addNodeAddress
(
result
);
}
return
Redisson
.
create
(
config
);
}
}
\ No newline at end of file
project-dispatch/src/main/java/com/dituhui/pea/dispatch/common/RedissonUtil.java
0 → 100644
View file @
35bbd68
package
com
.
dituhui
.
pea
.
dispatch
.
common
;
import
cn.hutool.extra.spring.SpringUtil
;
import
lombok.extern.slf4j.Slf4j
;
import
org.redisson.api.*
;
import
org.springframework.data.redis.connection.RedisConnectionFactory
;
import
org.springframework.stereotype.Service
;
import
javax.annotation.PostConstruct
;
import
java.util.concurrent.TimeUnit
;
/**
* TODO redisson 工具类
*
* @Author RenPing
* @Date 2022/1/7 11:04
*/
@Slf4j
@Service
public
class
RedissonUtil
{
private
static
RedissonClient
redissonClient
;
private
static
RedisConnectionFactory
redisConnectionFactory
;
@PostConstruct
public
void
init
()
{
redissonClient
=
SpringUtil
.
getBean
(
RedissonClient
.
class
);
redisConnectionFactory
=
SpringUtil
.
getBean
(
RedisConnectionFactory
.
class
);
}
/**
* 单个加锁操作,示例:lockKey="operate_object_key_1"
*
* @param lockKey
* @param operation
*/
public
static
void
lockOperation
(
String
lockKey
,
Runnable
operation
)
{
RedissonClient
redissonClient
=
SpringUtil
.
getBean
(
RedissonClient
.
class
);
RLock
lock
=
redissonClient
.
getLock
(
lockKey
);
try
{
while
(
true
)
{
//第一个参数:尝试获取锁的最大等待时间,超过这个值,则获取失败
//第二个参数:锁的持有时间,超过这个时间锁会自动失效
boolean
res
=
lock
.
tryLock
(
60
,
60
,
TimeUnit
.
MINUTES
);
if
(
res
)
{
log
.
info
(
">>> "
+
Thread
.
currentThread
()
+
" 获取 redis lock"
);
//成功获得锁,在这里处理业务
operation
.
run
();
break
;
}
}
}
catch
(
InterruptedException
e
)
{
log
.
error
(
e
.
getMessage
(),
e
);
throw
new
RuntimeException
(
"获取 redis lock 失败"
);
}
catch
(
Exception
e
)
{
throw
e
;
}
finally
{
if
(
lock
.
isLocked
()
&&
lock
.
isHeldByCurrentThread
())
{
log
.
info
(
">>> "
+
Thread
.
currentThread
()
+
" 释放 redis lock"
);
lock
.
unlock
();
}
}
}
}
project-dispatch/src/main/java/com/dituhui/pea/dispatch/service/impl/SchedulerServiceImpl.java
View file @
35bbd68
...
...
@@ -3,6 +3,7 @@ package com.dituhui.pea.dispatch.service.impl;
import
cn.hutool.core.date.DateUtil
;
import
cn.hutool.core.util.ObjectUtil
;
import
cn.hutool.core.util.StrUtil
;
import
com.dituhui.pea.dispatch.common.RedissonUtil
;
import
com.dituhui.pea.dispatch.dao.DispatchBatchRepository
;
import
com.dituhui.pea.dispatch.dao.OrgGroupRepository
;
import
com.dituhui.pea.dispatch.dao.OrgTeamDao
;
...
...
@@ -10,6 +11,7 @@ import com.dituhui.pea.dispatch.entity.DispatchBatch;
import
com.dituhui.pea.dispatch.entity.OrgGroup
;
import
com.dituhui.pea.dispatch.entity.OrgTeamEntity
;
import
com.dituhui.pea.dispatch.pojo.DispatchSolution
;
import
com.dituhui.pea.dispatch.quartz.dispatch.AutoDispatchJob
;
import
com.dituhui.pea.dispatch.service.BatchService
;
import
com.dituhui.pea.dispatch.service.ExtractService
;
import
com.dituhui.pea.dispatch.service.SchedulerService
;
...
...
@@ -22,8 +24,6 @@ import org.optaplanner.persistence.jackson.impl.domain.solution.JacksonSolutionF
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Value
;
import
org.springframework.stereotype.Service
;
import
org.springframework.transaction.annotation.Isolation
;
import
org.springframework.transaction.annotation.Transactional
;
import
javax.annotation.Resource
;
import
java.io.File
;
...
...
@@ -113,13 +113,21 @@ public class SchedulerServiceImpl implements SchedulerService {
for
(
int
i
=
1
;
i
<=
nextDaysLimit
;
i
++)
{
String
currDay
=
LocalDate
.
now
().
plusDays
(
i
).
format
(
DateTimeFormatter
.
ISO_LOCAL_DATE
);
boolean
finalCutOff
=
cutOff
;
RedissonUtil
.
lockOperation
(
AutoDispatchJob
.
TEAM_JOB_PREFIX
+
teamId
,
()
->
{
dispatchRun2OneDay
(
teamId
,
currDay
,
today
,
finalCutOff
);
});
}
}
private
void
dispatchRun2OneDay
(
String
teamId
,
String
currDay
,
String
today
,
boolean
cutOff
)
{
Optional
<
DispatchBatch
>
optional
=
dispatchBatchRepository
.
findByTeamIdAndBatchDate
(
teamId
,
currDay
);
if
(
optional
.
isPresent
()
&&
Objects
.
nonNull
(
optional
.
get
().
getCutoffedTime
())
&&
today
.
equals
(
DateUtil
.
format
(
optional
.
get
().
getCutoffedTime
(),
"yyyy-MM-dd"
)
))
{
&&
DateUtil
.
format
(
optional
.
get
().
getCutoffedTime
(),
"yyyy-MM-dd"
).
equals
(
today
))
{
//自动任务截止
log
.
error
(
">>> teamId:{}, day:{} 自动任务已截止"
,
teamId
,
currDay
);
continue
;
return
;
}
try
{
...
...
@@ -133,7 +141,7 @@ public class SchedulerServiceImpl implements SchedulerService {
if
(
problem
.
getCustomerList
().
size
()
<=
0
)
{
log
.
info
(
"dispatchRun 当前批次没有待指派工单 , teamId:{}, day:{}, batch:{}, problemId:{}, order-size:{}"
,
teamId
,
currDay
,
batchNo
,
problemId
,
problem
.
getCustomerList
().
size
());
continue
;
return
;
}
log
.
info
(
"dispatchRun prepare done, teamId:{}, day:{}, batch:{}, problemId:{}"
,
teamId
,
currDay
,
batchNo
,
problemId
);
Solver
<
DispatchSolution
>
solver
=
solverFactory
.
buildSolver
();
...
...
@@ -150,8 +158,7 @@ public class SchedulerServiceImpl implements SchedulerService {
//log.info("dispatchRun group:{}, team:{} done", groupId, teamId);
}
catch
(
Exception
e
)
{
log
.
error
(
">>> (teamId:{}, day:{})自动排班失败:{}"
,
teamId
,
currDay
,
e
.
getMessage
(),
e
);
throw
e
;
}
//throw e;
}
}
}
\ No newline at end of file
project-dispatch/src/main/resources/application-dev.yaml
View file @
35bbd68
...
...
@@ -3,9 +3,8 @@ server:
dispatch
:
cron
:
expr
:
0
25
8-23 * * ?
expr
:
0
*/3
8-23 * * ?
next-day-limit
:
20
# expr: 0 */10 8-18 * * ?
scheduler
:
init-engineer-capacity
:
...
...
project-dispatch/src/main/resources/application.yaml
View file @
35bbd68
...
...
@@ -45,6 +45,9 @@ spring:
import-check
:
# no config file
enabled
:
false
config
:
import
:
-
nacos:redis-config.yaml?group=project&refreshEnabled=true
datasource
:
driver-class-name
:
com.mysql.cj.jdbc.Driver
url
:
jdbc:mysql://10.10.0.116:32306/saas_aftersale_test?serverTimezone=Asia/Shanghai
...
...
Write
Preview
Markdown
is supported
Attach a file
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to post a comment