Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
Y
yd-csf
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
xingmin
yd-csf
Commits
4efcf911
Commit
4efcf911
authored
May 14, 2026
by
zhangxingmin
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
push
parent
72070e82
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
68 additions
and
20 deletions
+68
-20
yd-csf-service/src/main/java/com/yd/csf/service/service/impl/FortuneAccountServiceImpl.java
+53
-7
yd-csf-service/src/main/java/com/yd/csf/service/utils/BusinessNoUtils.java
+15
-13
No files found.
yd-csf-service/src/main/java/com/yd/csf/service/service/impl/FortuneAccountServiceImpl.java
View file @
4efcf911
...
...
@@ -125,16 +125,19 @@ public class FortuneAccountServiceImpl extends ServiceImpl<FortuneAccountMapper,
String
billingYearMonth
=
actualPayoutDate
!=
null
?
actualPayoutDate
.
format
(
java
.
time
.
format
.
DateTimeFormatter
.
ofPattern
(
"yyyyMM"
))
:
""
;
// 本地缓存,key=prefix, value=当前已分配给该prefix的最大流水号数值
Map
<
String
,
Integer
>
prefixSerialCache
=
new
HashMap
<>();
for
(
FortuneAccountExportDTO
accountExportDTO
:
accountExportDTOList
)
{
FortuneAccount
fortuneAccount
=
new
FortuneAccount
();
fortuneAccount
.
setFortuneAccountBizId
(
RandomStringGenerator
.
generateBizId16
(
"fortune_account"
));
String
internalCode
=
map
.
get
(
accountExportDTO
.
getBrokerBizId
());
// LocalDate payoutDate = accountExportDTO.getActualPayoutDate();
// String billingYearMonth = payoutDate != null
// ? actualPayoutDate.format(java.time.format.DateTimeFormatter.ofPattern("yyyyMM"))
// : "";
String
businessNo
=
BusinessNoUtils
.
generate
(
billingYearMonth
,
internalCode
);
//出账业务编号(出账年月 + 转介人内部编号(后6位)(如无,用0补齐)+流水号(6位))
String
prefix
=
BusinessNoUtils
.
getPrefix
(
billingYearMonth
,
internalCode
);
// 业务编号生成
String
businessNo
=
generateBusinessNoWithCache
(
prefix
,
billingYearMonth
,
internalCode
,
prefixSerialCache
);
fortuneAccount
.
setBusinessNo
(
businessNo
);
fortuneAccount
.
setBroker
(
accountExportDTO
.
getBroker
());
fortuneAccount
.
setBrokerBizId
(
accountExportDTO
.
getBrokerBizId
());
...
...
@@ -143,7 +146,6 @@ public class FortuneAccountServiceImpl extends ServiceImpl<FortuneAccountMapper,
fortuneAccount
.
setCurrency
(
accountExportDTO
.
getCurrency
());
fortuneAccount
.
setHkdAmount
(
accountExportDTO
.
getAmount
());
fortuneAccount
.
setFortuneAccountDate
(
this
.
getActualPayoutDate
(
actualPayoutDate
));
// 出账状态默认待出账
fortuneAccount
.
setStatus
(
FortuneStatusEnum
.
CHECKED
.
getItemValue
());
// 转换为List<Map<String, Object>>
...
...
@@ -219,6 +221,50 @@ public class FortuneAccountServiceImpl extends ServiceImpl<FortuneAccountMapper,
}
/**
* 带本地缓存的业务编号生成(解决同一批次内相同 prefix 的流水号重复问题)
* @param prefix 业务编号前缀(出账年月 + 转介人内部编号后6位)
* @param billingYearMonth 出账年月
* @param internalCode 转介人内部编号
* @param prefixSerialCache 本地缓存(Map<prefix, 当前已使用的最大流水号数值>)
* @return 完整的业务编号
*/
private
String
generateBusinessNoWithCache
(
String
prefix
,
String
billingYearMonth
,
String
internalCode
,
Map
<
String
,
Integer
>
prefixSerialCache
)
{
// 从缓存中获取当前 prefix 已分配的最大流水号,若不存在则查询数据库
Integer
currentMaxSerial
=
prefixSerialCache
.
get
(
prefix
);
if
(
currentMaxSerial
==
null
)
{
String
maxSerialFromDb
=
getMaxSerialNoByPrefix
(
prefix
);
// 返回如 "000000"
currentMaxSerial
=
Integer
.
parseInt
(
maxSerialFromDb
);
}
int
nextSerial
=
currentMaxSerial
+
1
;
String
serialPart
=
String
.
format
(
"%06d"
,
nextSerial
);
String
businessNo
=
BusinessNoUtils
.
generate
(
billingYearMonth
,
internalCode
,
serialPart
);
// 更新缓存
prefixSerialCache
.
put
(
prefix
,
nextSerial
);
return
businessNo
;
}
/**
* 根据前缀查询当前最大流水号(后6位)
* @param prefix 业务编号前缀(出账年月+转介人内部编号后6位,共12位)
* @return 最大流水号(6位字符串),如果没有记录则返回 "000000"
*/
private
String
getMaxSerialNoByPrefix
(
String
prefix
)
{
// 查询 business_no 以指定前缀开头的记录,按业务编号降序取第一条
LambdaQueryWrapper
<
FortuneAccount
>
wrapper
=
new
LambdaQueryWrapper
<>();
wrapper
.
likeRight
(
FortuneAccount:
:
getBusinessNo
,
prefix
)
.
orderByDesc
(
FortuneAccount:
:
getBusinessNo
)
.
last
(
"limit 1"
);
FortuneAccount
account
=
this
.
getOne
(
wrapper
,
false
);
if
(
account
==
null
)
{
return
"000000"
;
}
String
businessNo
=
account
.
getBusinessNo
();
// 取最后6位作为流水号
return
businessNo
.
substring
(
businessNo
.
length
()
-
6
);
}
private
Date
getActualPayoutDate
(
LocalDate
actualPayoutDate
)
{
if
(
actualPayoutDate
==
null
)
{
return
null
;
...
...
yd-csf-service/src/main/java/com/yd/csf/service/utils/BusinessNoUtils.java
View file @
4efcf911
package
com
.
yd
.
csf
.
service
.
utils
;
import
java.util.concurrent.ThreadLocalRandom
;
/**
* 业务编号生成工具类
*
<p>格式:出账年月 + 转介人内部编号后6位(无则补0) + 6位随机数字</p>
*
格式:出账年月(6) + 转介人内部编号后6位 + 6位流水号(从000001开始递增)
*/
public
class
BusinessNoUtils
{
/**
* 生成业务编号
*
* 生成业务编号(流水号由调用方传入)
* @param billingYearMonth 出账年月,如 "202604"
* @param referrerInnerNo 转介人内部编号,可为 null 或空字符串
* @return 完整的业务编号字符串
* @param referrerInnerNo 转介人内部编号,可为null或空
* @param serialPart 6位流水号(如 "000001")
* @return 完整业务编号
*/
public
static
String
generate
(
String
billingYearMonth
,
String
referrerInnerNo
)
{
public
static
String
generate
(
String
billingYearMonth
,
String
referrerInnerNo
,
String
serialPart
)
{
String
referrerPart
=
formatReferrerInnerNo
(
referrerInnerNo
);
String
serialPart
=
generateRandomSerial
();
return
billingYearMonth
+
referrerPart
+
serialPart
;
}
...
...
@@ -33,9 +30,13 @@ public class BusinessNoUtils {
return
String
.
format
(
"%6s"
,
no
).
replace
(
' '
,
'0'
);
}
// 生成6位随机数字(000000~999999)
private
static
String
generateRandomSerial
()
{
int
random
=
ThreadLocalRandom
.
current
().
nextInt
(
1000000
);
return
String
.
format
(
"%06d"
,
random
);
/**
* 获取业务编号中的前缀部分(用于数据库查询)
* @param billingYearMonth 出账年月
* @param referrerInnerNo 转介人内部编号
* @return 前缀字符串(12位)
*/
public
static
String
getPrefix
(
String
billingYearMonth
,
String
referrerInnerNo
)
{
return
billingYearMonth
+
formatReferrerInnerNo
(
referrerInnerNo
);
}
}
\ No newline at end of file
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
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 comment