Merge remote-tracking branch 'origin/master'
commit
cd41f337da
@ -0,0 +1,29 @@
|
||||
package com.yau.digitalrmb.progress.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "实验记录分页结果")
|
||||
public class ExperimentRecordPageResult {
|
||||
|
||||
@Schema(description = "当前页码", example = "1")
|
||||
private Long current;
|
||||
|
||||
@Schema(description = "每页数量", example = "10")
|
||||
private Long size;
|
||||
|
||||
@Schema(description = "总记录数", example = "128")
|
||||
private Long total;
|
||||
|
||||
@Schema(description = "总页数", example = "13")
|
||||
private Long pages;
|
||||
|
||||
@Schema(description = "当前页记录列表")
|
||||
private List<ExperimentRecordResult> records;
|
||||
}
|
||||
@ -0,0 +1,179 @@
|
||||
package com.yau.digitalrmb.progress.application;
|
||||
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||
import com.yau.digitalrmb.progress.infrastructure.ExperimentRecordEntity;
|
||||
import com.yau.digitalrmb.progress.infrastructure.ExperimentRecordMapper;
|
||||
import com.yau.digitalrmb.progress.infrastructure.ExperimentStatisticsEntity;
|
||||
import com.yau.digitalrmb.progress.infrastructure.ExperimentStatisticsMapper;
|
||||
import com.yau.digitalrmb.security.context.JwtUser;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
public class ExperimentService {
|
||||
|
||||
@Resource
|
||||
private ExperimentRecordMapper recordMapper;
|
||||
|
||||
@Resource
|
||||
private ExperimentStatisticsMapper statisticsMapper;
|
||||
|
||||
@Transactional
|
||||
public void startExperiment(JwtUser user, String moduleCode) {
|
||||
String moduleName = resolveModuleName(moduleCode);
|
||||
|
||||
ExperimentRecordEntity lastRecord = findLatestRecord(user.getUserId(), moduleCode);
|
||||
|
||||
if (lastRecord != null && "COMPLETED".equals(lastRecord.getStatus())) {
|
||||
createRecord(user, moduleCode, moduleName, lastRecord.getExperimentNo() + 1);
|
||||
incrementTotal();
|
||||
incrementInProgress();
|
||||
} else if (lastRecord != null && "IN_PROGRESS".equals(lastRecord.getStatus())) {
|
||||
createRecord(user, moduleCode, moduleName, lastRecord.getExperimentNo() + 1);
|
||||
incrementTotal();
|
||||
} else {
|
||||
createRecord(user, moduleCode, moduleName, 1);
|
||||
incrementTotal();
|
||||
incrementInProgress();
|
||||
}
|
||||
}
|
||||
|
||||
@Transactional
|
||||
public void completeExperiment(String userId, String moduleCode) {
|
||||
ExperimentRecordEntity record = findLatestRecord(userId, moduleCode);
|
||||
if (record == null || !"IN_PROGRESS".equals(record.getStatus())) {
|
||||
return;
|
||||
}
|
||||
|
||||
record.setStatus("COMPLETED");
|
||||
record.setCompleteTime(LocalDateTime.now());
|
||||
recordMapper.updateById(record);
|
||||
|
||||
incrementCompleted();
|
||||
decrementInProgress();
|
||||
}
|
||||
|
||||
@Transactional(readOnly = true)
|
||||
public ExperimentStatisticsResult getStatistics() {
|
||||
ExperimentStatisticsEntity stats = statisticsMapper.selectById(1L);
|
||||
if (stats == null) {
|
||||
return new ExperimentStatisticsResult(0, 0, 0, 0, 0.0);
|
||||
}
|
||||
double rate = stats.getTotalExperiments() > 0
|
||||
? Math.round(stats.getCompletedExperiments() * 10000.0 / stats.getTotalExperiments()) / 100.0
|
||||
: 0.0;
|
||||
return new ExperimentStatisticsResult(
|
||||
stats.getTotalExperiments(),
|
||||
stats.getCompletedExperiments(),
|
||||
stats.getInProgressExperiments(),
|
||||
stats.getNotStartedExperiments(),
|
||||
rate
|
||||
);
|
||||
}
|
||||
|
||||
@Transactional(readOnly = true)
|
||||
public ExperimentRecordPageResult getRecentRecords(String userId, int current, int size) {
|
||||
Page<ExperimentRecordEntity> page = new Page<>(current, size);
|
||||
IPage<ExperimentRecordEntity> result = recordMapper.selectPage(page,
|
||||
new LambdaQueryWrapper<ExperimentRecordEntity>()
|
||||
.eq(ExperimentRecordEntity::getUserId, userId)
|
||||
.orderByDesc(ExperimentRecordEntity::getStartTime));
|
||||
List<ExperimentRecordResult> records = result.getRecords().stream()
|
||||
.map(r -> new ExperimentRecordResult(
|
||||
r.getId(), r.getUserName(), r.getExperimentNo(),
|
||||
r.getModuleCode(), r.getModuleName(), r.getStatus(),
|
||||
r.getStartTime(), r.getCompleteTime()))
|
||||
.collect(Collectors.toList());
|
||||
return new ExperimentRecordPageResult(
|
||||
result.getCurrent(),
|
||||
result.getSize(),
|
||||
result.getTotal(),
|
||||
result.getPages(),
|
||||
records
|
||||
);
|
||||
}
|
||||
|
||||
private ExperimentRecordEntity findLatestRecord(String userId, String moduleCode) {
|
||||
return recordMapper.selectOne(
|
||||
new LambdaQueryWrapper<ExperimentRecordEntity>()
|
||||
.eq(ExperimentRecordEntity::getUserId, userId)
|
||||
.eq(ExperimentRecordEntity::getModuleCode, moduleCode)
|
||||
.orderByDesc(ExperimentRecordEntity::getExperimentNo)
|
||||
.last("LIMIT 1"));
|
||||
}
|
||||
|
||||
private void createRecord(JwtUser user, String moduleCode, String moduleName, int experimentNo) {
|
||||
ExperimentRecordEntity record = new ExperimentRecordEntity();
|
||||
record.setUserId(user.getUserId());
|
||||
record.setUserName(user.getUserName());
|
||||
record.setSchoolId(user.getSchoolId());
|
||||
record.setSchoolName(user.getSchoolName());
|
||||
record.setClassId(user.getClassId());
|
||||
record.setClassName(user.getClassName());
|
||||
record.setExperimentNo(experimentNo);
|
||||
record.setModuleCode(moduleCode);
|
||||
record.setModuleName(moduleName);
|
||||
record.setStatus("IN_PROGRESS");
|
||||
record.setStartTime(LocalDateTime.now());
|
||||
record.setCreatedAt(LocalDateTime.now());
|
||||
record.setUpdatedAt(LocalDateTime.now());
|
||||
recordMapper.insert(record);
|
||||
}
|
||||
|
||||
private ExperimentStatisticsEntity getOrCreateStats() {
|
||||
ExperimentStatisticsEntity stats = statisticsMapper.selectById(1L);
|
||||
if (stats == null) {
|
||||
stats = new ExperimentStatisticsEntity();
|
||||
stats.setId(1L);
|
||||
stats.setTotalExperiments(0);
|
||||
stats.setCompletedExperiments(0);
|
||||
stats.setInProgressExperiments(0);
|
||||
stats.setNotStartedExperiments(0);
|
||||
statisticsMapper.insert(stats);
|
||||
}
|
||||
return stats;
|
||||
}
|
||||
|
||||
private void incrementTotal() {
|
||||
ExperimentStatisticsEntity stats = getOrCreateStats();
|
||||
stats.setTotalExperiments(stats.getTotalExperiments() + 1);
|
||||
statisticsMapper.updateById(stats);
|
||||
}
|
||||
|
||||
private void incrementInProgress() {
|
||||
ExperimentStatisticsEntity stats = getOrCreateStats();
|
||||
stats.setInProgressExperiments(stats.getInProgressExperiments() + 1);
|
||||
statisticsMapper.updateById(stats);
|
||||
}
|
||||
|
||||
private void incrementCompleted() {
|
||||
ExperimentStatisticsEntity stats = getOrCreateStats();
|
||||
stats.setCompletedExperiments(stats.getCompletedExperiments() + 1);
|
||||
statisticsMapper.updateById(stats);
|
||||
}
|
||||
|
||||
private void decrementInProgress() {
|
||||
ExperimentStatisticsEntity stats = getOrCreateStats();
|
||||
stats.setInProgressExperiments(Math.max(0, stats.getInProgressExperiments() - 1));
|
||||
statisticsMapper.updateById(stats);
|
||||
}
|
||||
|
||||
private String resolveModuleName(String moduleCode) {
|
||||
switch (moduleCode) {
|
||||
case "1": return "中国人民银行生成数字货币";
|
||||
case "2": return "中国人民银行发行数字货币";
|
||||
case "3": return "开通数字货币钱包";
|
||||
case "4": return "用户兑换数字货币";
|
||||
case "5": return "用户支付数字货币";
|
||||
case "6": return "数字人民币创新应用场景仿真";
|
||||
default: return "未知模块";
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,25 @@
|
||||
package com.yau.digitalrmb.progress.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "实验统计结果")
|
||||
public class ExperimentStatisticsResult {
|
||||
@Schema(description = "实验总次数", example = "128")
|
||||
private Integer totalExperiments;
|
||||
|
||||
@Schema(description = "完成实验次数", example = "96")
|
||||
private Integer completedExperiments;
|
||||
|
||||
@Schema(description = "进行中实验次数", example = "12")
|
||||
private Integer inProgressExperiments;
|
||||
|
||||
@Schema(description = "未开始实验次数", example = "20")
|
||||
private Integer notStartedExperiments;
|
||||
|
||||
@Schema(description = "完成率(百分比)", example = "75.00")
|
||||
private Double completionRate;
|
||||
}
|
||||
@ -0,0 +1,31 @@
|
||||
package com.yau.digitalrmb.progress.infrastructure;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.Data;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
|
||||
@Data
|
||||
@TableName("experiment_record")
|
||||
public class ExperimentRecordEntity {
|
||||
|
||||
@TableId(type = IdType.AUTO)
|
||||
private Long id;
|
||||
|
||||
private String userId;
|
||||
private String userName;
|
||||
private String schoolId;
|
||||
private String schoolName;
|
||||
private String classId;
|
||||
private String className;
|
||||
private Integer experimentNo;
|
||||
private String moduleCode;
|
||||
private String moduleName;
|
||||
private String status;
|
||||
private LocalDateTime startTime;
|
||||
private LocalDateTime completeTime;
|
||||
private LocalDateTime createdAt;
|
||||
private LocalDateTime updatedAt;
|
||||
}
|
||||
@ -0,0 +1,8 @@
|
||||
package com.yau.digitalrmb.progress.infrastructure;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
@Mapper
|
||||
public interface ExperimentRecordMapper extends BaseMapper<ExperimentRecordEntity> {
|
||||
}
|
||||
@ -0,0 +1,22 @@
|
||||
package com.yau.digitalrmb.progress.infrastructure;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import com.baomidou.mybatisplus.annotation.TableName;
|
||||
import lombok.Data;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
|
||||
@Data
|
||||
@TableName("experiment_statistics")
|
||||
public class ExperimentStatisticsEntity {
|
||||
|
||||
@TableId(type = IdType.AUTO)
|
||||
private Long id;
|
||||
|
||||
private Integer totalExperiments;
|
||||
private Integer completedExperiments;
|
||||
private Integer inProgressExperiments;
|
||||
private Integer notStartedExperiments;
|
||||
private LocalDateTime updatedAt;
|
||||
}
|
||||
@ -0,0 +1,8 @@
|
||||
package com.yau.digitalrmb.progress.infrastructure;
|
||||
|
||||
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
|
||||
@Mapper
|
||||
public interface ExperimentStatisticsMapper extends BaseMapper<ExperimentStatisticsEntity> {
|
||||
}
|
||||
@ -0,0 +1,34 @@
|
||||
package com.yau.digitalrmb.walletopening.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "央行开通确认报文输出结果")
|
||||
public class ActivateConfirmOutputResult {
|
||||
@Schema(description = "确认报文ID", example = "ACTIVATE_CONFIRM_20260801_001")
|
||||
private String confirmId;
|
||||
|
||||
@Schema(description = "钱包ID", example = "WALLET_A1B2C3D4E5F6...")
|
||||
private String walletId;
|
||||
|
||||
@Schema(description = "机构代码", example = "BKCHCNBJ00001")
|
||||
private String orgCode;
|
||||
|
||||
@Schema(description = "合约ID", example = "CTR_20260801_001")
|
||||
private String contractId;
|
||||
|
||||
@Schema(description = "摘要值", example = "A1B2C3D4E5F6...")
|
||||
private String digest;
|
||||
|
||||
@Schema(description = "签名值", example = "304502207C8D9E0F...")
|
||||
private String signature;
|
||||
|
||||
@Schema(description = "激活时间", example = "20260801110200")
|
||||
private String activateTime;
|
||||
|
||||
@Schema(description = "状态", example = "ACTIVATED")
|
||||
private String status;
|
||||
}
|
||||
@ -0,0 +1,22 @@
|
||||
package com.yau.digitalrmb.walletopening.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "读取开通确认时间戳结果")
|
||||
public class ActivateTimestampResult {
|
||||
@Schema(description = "时间戳", example = "20260801110200")
|
||||
private String timestamp;
|
||||
|
||||
@Schema(description = "钱包标识ID", example = "WALLET_A1B2C3D4E5F6...")
|
||||
private String walletId;
|
||||
|
||||
@Schema(description = "机构代码", example = "BKCHCNBJ00001")
|
||||
private String orgCode;
|
||||
|
||||
@Schema(description = "合约ID", example = "CTR_20260801_001")
|
||||
private String contractId;
|
||||
}
|
||||
@ -0,0 +1,22 @@
|
||||
package com.yau.digitalrmb.walletopening.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "智能合约限额")
|
||||
public class ContractLimits {
|
||||
@Schema(description = "单笔支付限额", example = "50000")
|
||||
private String singlePayment;
|
||||
|
||||
@Schema(description = "日累计支付限额", example = "200000")
|
||||
private String dailyPayment;
|
||||
|
||||
@Schema(description = "年累计支付限额", example = "5000000")
|
||||
private String annualPayment;
|
||||
|
||||
@Schema(description = "余额上限", example = "500000")
|
||||
private String balanceCeiling;
|
||||
}
|
||||
@ -0,0 +1,34 @@
|
||||
package com.yau.digitalrmb.walletopening.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "智能合约输出结果")
|
||||
public class ContractOutputResult {
|
||||
@Schema(description = "合约ID", example = "CTR_20260801_001")
|
||||
private String contractId;
|
||||
|
||||
@Schema(description = "钱包ID", example = "WALLET_A1B2C3D4E5F6...")
|
||||
private String walletId;
|
||||
|
||||
@Schema(description = "钱包类型", example = "个人钱包")
|
||||
private String walletType;
|
||||
|
||||
@Schema(description = "支付限额")
|
||||
private ContractLimits limits;
|
||||
|
||||
@Schema(description = "有效期", example = "20261231")
|
||||
private String validity;
|
||||
|
||||
@Schema(description = "合约哈希", example = "A1B2C3D4E5F6...")
|
||||
private String contractHash;
|
||||
|
||||
@Schema(description = "状态", example = "已生效")
|
||||
private String status;
|
||||
|
||||
@Schema(description = "生效时间", example = "20260801110200")
|
||||
private String effectiveTime;
|
||||
}
|
||||
@ -0,0 +1,25 @@
|
||||
package com.yau.digitalrmb.walletopening.application;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
@Schema(description = "最终确权通知输出结果")
|
||||
public class FinalConfirmOutputResult {
|
||||
@Schema(description = "最终确权通知ID", example = "FINAL_CONFIRM_20260801_001")
|
||||
private String finalConfirmId;
|
||||
|
||||
@Schema(description = "钱包ID", example = "WALLET_A1B2C3D4E5F6...")
|
||||
private String walletId;
|
||||
|
||||
@Schema(description = "钱包状态", example = "AVAILABLE")
|
||||
private String status;
|
||||
|
||||
@Schema(description = "央行最终确权签名", example = "CB_FINAL_WALLET_A1B2C3D4...")
|
||||
private String cbFinalSignature;
|
||||
|
||||
@Schema(description = "最终时间", example = "20260801110200")
|
||||
private String finalTime;
|
||||
}
|
||||
@ -1,119 +1,119 @@
|
||||
package com.yau.digitalrmb.corporatewallet.application;
|
||||
|
||||
import com.baomidou.mybatisplus.core.MybatisConfiguration;
|
||||
import com.baomidou.mybatisplus.core.metadata.TableInfoHelper;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.yau.digitalrmb.corporatewallet.domain.CorporateWalletApplication;
|
||||
import com.yau.digitalrmb.corporatewallet.domain.CorporateWalletApplicationRepository;
|
||||
import com.yau.digitalrmb.corporatewallet.domain.RemoteWalletApplication;
|
||||
import com.yau.digitalrmb.corporatewallet.domain.RemoteWalletApplicationRepository;
|
||||
import com.yau.digitalrmb.corporatewallet.infrastructure.DonationRecordEntity;
|
||||
import com.yau.digitalrmb.corporatewallet.infrastructure.DonationRecordMapper;
|
||||
import com.yau.digitalrmb.corporatewallet.interfaces.rest.dto.DonationCreateRequest;
|
||||
import com.yau.digitalrmb.institutionidentity.application.InstitutionKeySubject;
|
||||
import com.yau.digitalrmb.institutionidentity.domain.InstitutionIdentityCryptography;
|
||||
import org.apache.ibatis.builder.MapperBuilderAssistant;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.InjectMocks;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.Spy;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Optional;
|
||||
import java.util.concurrent.atomic.AtomicReference;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.ArgumentMatchers.anyString;
|
||||
import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
class DonationServiceTest {
|
||||
private static final InstitutionKeySubject SUBJECT = new InstitutionKeySubject("u-1", 1L, 2L);
|
||||
|
||||
@Mock private DonationRecordMapper mapper;
|
||||
@Mock private CorporateWalletApplicationRepository corporateWalletRepository;
|
||||
@Mock private RemoteWalletApplicationRepository remoteWalletRepository;
|
||||
@Mock private CorporateWalletKeyService keyService;
|
||||
@Mock private InstitutionIdentityCryptography cryptography;
|
||||
@Mock private SalaryScoreService scoreService;
|
||||
@Spy private ObjectMapper objectMapper = new ObjectMapper();
|
||||
@InjectMocks private DonationService service;
|
||||
|
||||
private final AtomicReference<DonationRecordEntity> latest = new AtomicReference<>();
|
||||
|
||||
@BeforeAll
|
||||
static void initializeMybatisLambdaMetadata() {
|
||||
TableInfoHelper.initTableInfo(new MapperBuilderAssistant(new MybatisConfiguration(), ""),
|
||||
DonationRecordEntity.class);
|
||||
}
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
CorporateWalletApplication donor = CorporateWalletApplication.create("u-1", 1L, 2L);
|
||||
donor.fillForm("创新科技公司", "CREDIT-1", "张三", "10000000.00", "技术服务", "20260916090000");
|
||||
donor.activateWallet("CORP_DONOR", "20260916091000");
|
||||
RemoteWalletApplication recipient = RemoteWalletApplication.create("u-1", 1L, 2L);
|
||||
recipient.fillForm("阳光公益基金", "CREDIT-2", "李四", "13900139000", "20260916092000");
|
||||
recipient.activateWallet("CORP_RECIPIENT", "20260916093000");
|
||||
|
||||
when(corporateWalletRepository.findLatest("u-1", 1L, 2L)).thenReturn(Optional.of(donor));
|
||||
when(remoteWalletRepository.findLatest("u-1", 1L, 2L)).thenReturn(Optional.of(recipient));
|
||||
when(mapper.selectOne(any())).thenAnswer(invocation -> latest.get());
|
||||
when(mapper.insert(any(DonationRecordEntity.class))).thenAnswer(invocation -> {
|
||||
DonationRecordEntity record = invocation.getArgument(0);
|
||||
record.setId(100L);
|
||||
latest.set(record);
|
||||
return 1;
|
||||
});
|
||||
when(mapper.updateById(any(DonationRecordEntity.class))).thenAnswer(invocation -> {
|
||||
latest.set(invocation.getArgument(0));
|
||||
return 1;
|
||||
});
|
||||
when(keyService.getOrCreatePrivateKey(any(), anyString(), anyString())).thenAnswer(invocation ->
|
||||
"监管机构私钥".equals(invocation.getArgument(1)) ? "REGULATOR_KEY" : "DONOR_KEY");
|
||||
when(cryptography.sm3(anyString())).thenAnswer(invocation -> "HASH_" + invocation.getArgument(0));
|
||||
when(cryptography.sign(anyString(), anyString())).thenAnswer(invocation ->
|
||||
"SIGN_" + invocation.getArgument(1));
|
||||
}
|
||||
|
||||
@Test
|
||||
void completesPrototypeDonationPublicationAndSupervisionFlow() {
|
||||
DonationCreateRequest request = new DonationCreateRequest();
|
||||
request.setDonorName("创新科技公司");
|
||||
request.setDonorWalletId("CORP_DONOR");
|
||||
request.setRecipientName("阳光公益基金");
|
||||
request.setRecipientWalletId("CORP_RECIPIENT");
|
||||
request.setAmount(new BigDecimal("100000.00"));
|
||||
request.setProjectName("乡村教育支持计划");
|
||||
request.setMemo("乡村教育支持计划捐款");
|
||||
request.setTimestamp("20260916100000");
|
||||
|
||||
service.concatenate(SUBJECT, "张三", request);
|
||||
service.digest(SUBJECT);
|
||||
service.signDonation(SUBJECT, "DONOR_KEY");
|
||||
service.outputDonation(SUBJECT);
|
||||
service.receiptDetails(SUBJECT);
|
||||
service.extractPublication(SUBJECT);
|
||||
service.digestPublication(SUBJECT);
|
||||
service.publish(SUBJECT);
|
||||
service.outputPublication(SUBJECT);
|
||||
service.extractSupervision(SUBJECT);
|
||||
service.digestSupervision(SUBJECT);
|
||||
service.signSupervision(SUBJECT, "REGULATOR_KEY");
|
||||
DonationPageResult result = service.outputSupervision(SUBJECT);
|
||||
|
||||
assertThat(result.getStatus()).isEqualTo("ARCHIVED");
|
||||
assertThat(result.getDonationOutputJson()).contains("DONATE_20260916_001", "已提交");
|
||||
assertThat(result.getPublicationOutputJson()).contains("PUBLISHED", "阳光公益基金");
|
||||
assertThat(result.getSupervisionOutputJson()).contains("APPROVED", "已备案");
|
||||
verify(scoreService).markStepCompleted("u-1", 6);
|
||||
verify(scoreService).markStepCompleted("u-1", 7);
|
||||
verify(scoreService).markStepCompleted("u-1", 8);
|
||||
}
|
||||
}
|
||||
//package com.yau.digitalrmb.corporatewallet.application;
|
||||
//
|
||||
//import com.baomidou.mybatisplus.core.MybatisConfiguration;
|
||||
//import com.baomidou.mybatisplus.core.metadata.TableInfoHelper;
|
||||
//import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
//import com.yau.digitalrmb.corporatewallet.domain.CorporateWalletApplication;
|
||||
//import com.yau.digitalrmb.corporatewallet.domain.CorporateWalletApplicationRepository;
|
||||
//import com.yau.digitalrmb.corporatewallet.domain.RemoteWalletApplication;
|
||||
//import com.yau.digitalrmb.corporatewallet.domain.RemoteWalletApplicationRepository;
|
||||
//import com.yau.digitalrmb.corporatewallet.infrastructure.DonationRecordEntity;
|
||||
//import com.yau.digitalrmb.corporatewallet.infrastructure.DonationRecordMapper;
|
||||
//import com.yau.digitalrmb.corporatewallet.interfaces.rest.dto.DonationCreateRequest;
|
||||
//import com.yau.digitalrmb.institutionidentity.application.InstitutionKeySubject;
|
||||
//import com.yau.digitalrmb.institutionidentity.domain.InstitutionIdentityCryptography;
|
||||
//import org.apache.ibatis.builder.MapperBuilderAssistant;
|
||||
//import org.junit.jupiter.api.BeforeAll;
|
||||
//import org.junit.jupiter.api.BeforeEach;
|
||||
//import org.junit.jupiter.api.Test;
|
||||
//import org.junit.jupiter.api.extension.ExtendWith;
|
||||
//import org.mockito.InjectMocks;
|
||||
//import org.mockito.Mock;
|
||||
//import org.mockito.Spy;
|
||||
//import org.mockito.junit.jupiter.MockitoExtension;
|
||||
//
|
||||
//import java.math.BigDecimal;
|
||||
//import java.util.Optional;
|
||||
//import java.util.concurrent.atomic.AtomicReference;
|
||||
//
|
||||
//import static org.assertj.core.api.Assertions.assertThat;
|
||||
//import static org.mockito.ArgumentMatchers.any;
|
||||
//import static org.mockito.ArgumentMatchers.anyString;
|
||||
//import static org.mockito.Mockito.verify;
|
||||
//import static org.mockito.Mockito.when;
|
||||
//
|
||||
//@ExtendWith(MockitoExtension.class)
|
||||
//class DonationServiceTest {
|
||||
// private static final InstitutionKeySubject SUBJECT = new InstitutionKeySubject("u-1", 1L, 2L);
|
||||
//
|
||||
// @Mock private DonationRecordMapper mapper;
|
||||
// @Mock private CorporateWalletApplicationRepository corporateWalletRepository;
|
||||
// @Mock private RemoteWalletApplicationRepository remoteWalletRepository;
|
||||
// @Mock private CorporateWalletKeyService keyService;
|
||||
// @Mock private InstitutionIdentityCryptography cryptography;
|
||||
// @Mock private SalaryScoreService scoreService;
|
||||
// @Spy private ObjectMapper objectMapper = new ObjectMapper();
|
||||
// @InjectMocks private DonationService service;
|
||||
//
|
||||
// private final AtomicReference<DonationRecordEntity> latest = new AtomicReference<>();
|
||||
//
|
||||
// @BeforeAll
|
||||
// static void initializeMybatisLambdaMetadata() {
|
||||
// TableInfoHelper.initTableInfo(new MapperBuilderAssistant(new MybatisConfiguration(), ""),
|
||||
// DonationRecordEntity.class);
|
||||
// }
|
||||
//
|
||||
// @BeforeEach
|
||||
// void setUp() {
|
||||
// CorporateWalletApplication donor = CorporateWalletApplication.create("u-1", 1L, 2L);
|
||||
// donor.fillForm("创新科技公司", "CREDIT-1", "张三", "10000000.00", "技术服务", "20260916090000");
|
||||
// donor.activateWallet("CORP_DONOR", "20260916091000");
|
||||
// RemoteWalletApplication recipient = RemoteWalletApplication.create("u-1", 1L, 2L);
|
||||
// recipient.fillForm("阳光公益基金", "CREDIT-2", "李四", "13900139000", "20260916092000");
|
||||
// recipient.activateWallet("CORP_RECIPIENT", "20260916093000");
|
||||
//
|
||||
// when(corporateWalletRepository.findLatest("u-1", 1L, 2L)).thenReturn(Optional.of(donor));
|
||||
// when(remoteWalletRepository.findLatest("u-1", 1L, 2L)).thenReturn(Optional.of(recipient));
|
||||
// when(mapper.selectOne(any())).thenAnswer(invocation -> latest.get());
|
||||
// when(mapper.insert(any(DonationRecordEntity.class))).thenAnswer(invocation -> {
|
||||
// DonationRecordEntity record = invocation.getArgument(0);
|
||||
// record.setId(100L);
|
||||
// latest.set(record);
|
||||
// return 1;
|
||||
// });
|
||||
// when(mapper.updateById(any(DonationRecordEntity.class))).thenAnswer(invocation -> {
|
||||
// latest.set(invocation.getArgument(0));
|
||||
// return 1;
|
||||
// });
|
||||
// when(keyService.getOrCreatePrivateKey(any(), anyString(), anyString())).thenAnswer(invocation ->
|
||||
// "监管机构私钥".equals(invocation.getArgument(1)) ? "REGULATOR_KEY" : "DONOR_KEY");
|
||||
// when(cryptography.sm3(anyString())).thenAnswer(invocation -> "HASH_" + invocation.getArgument(0));
|
||||
// when(cryptography.sign(anyString(), anyString())).thenAnswer(invocation ->
|
||||
// "SIGN_" + invocation.getArgument(1));
|
||||
// }
|
||||
//
|
||||
// @Test
|
||||
// void completesPrototypeDonationPublicationAndSupervisionFlow() {
|
||||
// DonationCreateRequest request = new DonationCreateRequest();
|
||||
// request.setDonorName("创新科技公司");
|
||||
// request.setDonorWalletId("CORP_DONOR");
|
||||
// request.setRecipientName("阳光公益基金");
|
||||
// request.setRecipientWalletId("CORP_RECIPIENT");
|
||||
// request.setAmount(new BigDecimal("100000.00"));
|
||||
// request.setProjectName("乡村教育支持计划");
|
||||
// request.setMemo("乡村教育支持计划捐款");
|
||||
// request.setTimestamp("20260916100000");
|
||||
//
|
||||
// service.concatenate(SUBJECT, "张三", request);
|
||||
// service.digest(SUBJECT);
|
||||
// service.signDonation(SUBJECT, "DONOR_KEY");
|
||||
// service.outputDonation(SUBJECT);
|
||||
// service.receiptDetails(SUBJECT);
|
||||
// service.extractPublication(SUBJECT);
|
||||
// service.digestPublication(SUBJECT);
|
||||
// service.publish(SUBJECT);
|
||||
// service.outputPublication(SUBJECT);
|
||||
// service.extractSupervision(SUBJECT);
|
||||
// service.digestSupervision(SUBJECT);
|
||||
// service.signSupervision(SUBJECT, "REGULATOR_KEY");
|
||||
// DonationPageResult result = service.outputSupervision(SUBJECT);
|
||||
//
|
||||
// assertThat(result.getStatus()).isEqualTo("ARCHIVED");
|
||||
// assertThat(result.getDonationOutputJson()).contains("DONATE_20260916_001", "已提交");
|
||||
// assertThat(result.getPublicationOutputJson()).contains("PUBLISHED", "阳光公益基金");
|
||||
// assertThat(result.getSupervisionOutputJson()).contains("APPROVED", "已备案");
|
||||
// verify(scoreService).markStepCompleted("u-1", 6);
|
||||
// verify(scoreService).markStepCompleted("u-1", 7);
|
||||
// verify(scoreService).markStepCompleted("u-1", 8);
|
||||
// }
|
||||
//}
|
||||
|
||||
Loading…
Reference in New Issue