This is an automated email from the ASF dual-hosted git repository.
lizhimins pushed a commit to branch rocketmq-studio
in repository https://gitbox.apache.org/repos/asf/rocketmq-dashboard.git
The following commit(s) were added to refs/heads/rocketmq-studio by this push:
new cd88faf15 fix(common): consolidate backend numeric and input
sanitization fixes (#2656)
cd88faf15 is described below
commit cd88faf1531b53d4a15c8068d76b790b18e6ff8a
Author: yyqdbngt <[email protected]>
AuthorDate: Mon Aug 31 19:26:14 2026 +0800
fix(common): consolidate backend numeric and input sanitization fixes
(#2656)
* fix(dashboard): ignore invalid broker TPS
* fix(cluster): normalize broker disk ratio percentage
* fix(ai): bound Claude CLI stderr buffering
* fix(acl): normalize user search with root locale
* fix(dlq): reject blank selected message IDs
* fix(credentials): trim paged search terms
* fix(common): isolate page result items
---------
Co-authored-by: Yue Wang <[email protected]>
---
.../rocketmq/studio/common/domain/PageResult.java | 5 ++++-
.../instance/acl/MybatisPlusAclRepository.java | 3 ++-
.../instance/dlq/DLQResendSelectedRequestDTO.java | 2 +-
.../studio/ops/ai/ClaudeCodeAgentProvider.java | 8 +++++++-
.../provider/apache/RocketMQClusterProvider.java | 4 +++-
.../provider/apache/RocketMQDashboardProvider.java | 12 ++++++++++--
.../MybatisPlusCloudCredentialRepository.java | 14 +++++++++++---
.../studio/common/domain/PageResultTest.java | 16 ++++++++++++++++
.../instance/acl/MybatisPlusAclRepositoryTest.java | 21 +++++++++++++++++++++
.../studio/instance/dlq/DLQControllerTest.java | 18 ++++++++++++++++++
.../studio/ops/ai/ClaudeCodeAgentProviderTest.java | 12 ++++++++++++
.../apache/RocketMQClusterProviderTest.java | 16 ++++++++++++++++
.../apache/RocketMQDashboardProviderTest.java | 20 ++++++++++++++++++++
.../MybatisPlusCloudCredentialRepositoryTest.java | 20 ++++++++++++++++++++
14 files changed, 161 insertions(+), 10 deletions(-)
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/common/domain/PageResult.java
b/server/src/main/java/org/apache/rocketmq/studio/common/domain/PageResult.java
index 34fa1f578..cba427495 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/common/domain/PageResult.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/common/domain/PageResult.java
@@ -17,6 +17,7 @@
package org.apache.rocketmq.studio.common.domain;
import lombok.Getter;
+import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
@@ -31,7 +32,9 @@ public class PageResult<T> {
public static <T> PageResult<T> of(List<T> items, long total, int page,
int size) {
PageResult<T> result = new PageResult<>();
- result.items = items == null ? Collections.emptyList() : items;
+ result.items = items == null
+ ? Collections.emptyList()
+ : Collections.unmodifiableList(new ArrayList<>(items));
result.total = total;
result.page = page;
result.size = size;
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepository.java
b/server/src/main/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepository.java
index 5f463c9ed..442fa7b7c 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepository.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepository.java
@@ -37,6 +37,7 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashSet;
import java.util.List;
+import java.util.Locale;
import java.util.Optional;
import java.util.Set;
import java.util.stream.Collectors;
@@ -105,7 +106,7 @@ public class MybatisPlusAclRepository implements
AclRepository {
@Override
public PageResult<AclUserVO> findUserPage(String keyword, int page, int
pageSize) {
- String search = StringUtils.hasText(keyword) ?
keyword.trim().toLowerCase() : null;
+ String search = StringUtils.hasText(keyword) ?
keyword.trim().toLowerCase(Locale.ROOT) : null;
QueryWrapper<RmqAclUser> query = new QueryWrapper<RmqAclUser>()
.and(search != null, w -> w
.like("username", search)
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/instance/dlq/DLQResendSelectedRequestDTO.java
b/server/src/main/java/org/apache/rocketmq/studio/instance/dlq/DLQResendSelectedRequestDTO.java
index 73c20c266..1ee31b5a9 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/instance/dlq/DLQResendSelectedRequestDTO.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/instance/dlq/DLQResendSelectedRequestDTO.java
@@ -39,7 +39,7 @@ public class DLQResendSelectedRequestDTO {
@NotEmpty(message = "At least one msgId is required")
@Size(max = 100, message = "At most 100 msgIds are allowed per resend")
- private List<String> msgIds;
+ private List<@NotBlank(message = "msgId must not be blank") String> msgIds;
private String targetTopic;
}
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProvider.java
b/server/src/main/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProvider.java
index c7038dd80..aeb0c639c 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProvider.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProvider.java
@@ -52,6 +52,8 @@ public class ClaudeCodeAgentProvider extends CliAgentProvider
{
private static final String ANTHROPIC_APP_SUFFIX = "/apps/anthropic";
private static final long STREAM_TIMEOUT_SECONDS = 300;
private static final long OUTPUT_DRAIN_TIMEOUT_SECONDS = 10;
+ private static final int MAX_STDERR_BYTES = 64 * 1024;
+ private static final String STDERR_TRUNCATED_SUFFIX = "\n...[stderr
truncated]";
private final LlmProperties llmProperties;
private final ObjectMapper objectMapper = new ObjectMapper();
@@ -179,7 +181,11 @@ public class ClaudeCodeAgentProvider extends
CliAgentProvider {
CompletableFuture<String> result = new CompletableFuture<>();
Thread.ofVirtual().start(() -> {
try (stream) {
- result.complete(new String(stream.readAllBytes(),
StandardCharsets.UTF_8));
+ byte[] bytes = stream.readNBytes(MAX_STDERR_BYTES + 1);
+ boolean truncated = bytes.length > MAX_STDERR_BYTES;
+ int length = Math.min(bytes.length, MAX_STDERR_BYTES);
+ String output = new String(bytes, 0, length,
StandardCharsets.UTF_8);
+ result.complete(truncated ? output + STDERR_TRUNCATED_SUFFIX :
output);
} catch (Exception exception) {
result.completeExceptionally(exception);
}
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProvider.java
b/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProvider.java
index 8cd304741..8deca28eb 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProvider.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProvider.java
@@ -276,7 +276,9 @@ public class RocketMQClusterProvider implements
ClusterProvider {
try {
double parsedRatio = Double.parseDouble(diskRatio);
if (Double.isFinite(parsedRatio) && parsedRatio >= 0) {
- builder.diskUsage(parsedRatio);
+ // RocketMQ exposes commitLogDiskRatio as a fraction
in [0, 1],
+ // while BrokerVO and the web progress bars use
percentage points.
+ builder.diskUsage(parsedRatio * 100D);
}
} catch (NumberFormatException ignored) {
// keep default
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProvider.java
b/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProvider.java
index 6fbe18459..7299fb0d0 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProvider.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProvider.java
@@ -489,9 +489,9 @@ public class RocketMQDashboardProvider implements
DashboardProvider {
try {
String[] parts = tpsStr.trim().split("\\s+");
if (parts.length >= 2) {
- return (long) Double.parseDouble(parts[1]);
+ return parseTpsValue(parts[1]);
} else if (parts.length == 1) {
- return (long) Double.parseDouble(parts[0]);
+ return parseTpsValue(parts[0]);
}
} catch (NumberFormatException e) {
log.debug("Failed to parse TPS value: {}", tpsStr);
@@ -499,6 +499,14 @@ public class RocketMQDashboardProvider implements
DashboardProvider {
return 0;
}
+ private long parseTpsValue(String value) {
+ double parsed = Double.parseDouble(value);
+ if (!Double.isFinite(parsed) || parsed < 0 || parsed > Long.MAX_VALUE)
{
+ return 0;
+ }
+ return (long) parsed;
+ }
+
private long parseMessagesToday(Map<String, String> runtimeStats) {
String morningValue = runtimeStats.get("msgPutTotalTodayMorning");
String currentValue = runtimeStats.get("msgPutTotalTodayNow");
diff --git
a/server/src/main/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepository.java
b/server/src/main/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepository.java
index f60e42251..f9676ffc8 100644
---
a/server/src/main/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepository.java
+++
b/server/src/main/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepository.java
@@ -49,10 +49,18 @@ public class MybatisPlusCloudCredentialRepository
implements CloudCredentialRepo
.map(MybatisPlusCloudCredentialRepository::toVO)
.collect(Collectors.toList());
}
- @Override public PageResult<CloudCredentialVO> findPage(InstanceVendor
vendor, String search, int page, int pageSize) {
- QueryWrapper<RmqCloudCredential> q = new
QueryWrapper<RmqCloudCredential>().eq(vendor != null, "vendor", vendor == null
? null : vendor.name()).like(search != null && !search.isBlank(), "name",
search).orderByDesc("gmt_modified", "id");
+ @Override
+ public PageResult<CloudCredentialVO> findPage(InstanceVendor vendor,
String search, int page, int pageSize) {
+ String normalizedSearch = search == null || search.isBlank() ? null :
search.trim();
+ QueryWrapper<RmqCloudCredential> q = new
QueryWrapper<RmqCloudCredential>()
+ .eq(vendor != null, "vendor", vendor == null ? null :
vendor.name())
+ .like(normalizedSearch != null, "name", normalizedSearch)
+ .orderByDesc("gmt_modified", "id");
Page<RmqCloudCredential> result = credentialMapper.selectPage(new
Page<>(page, pageSize), q);
- return
PageResult.of(result.getRecords().stream().map(MybatisPlusCloudCredentialRepository::toVO).toList(),
result.getTotal(), page, pageSize);
+ return PageResult.of(result.getRecords().stream()
+ .map(MybatisPlusCloudCredentialRepository::toVO)
+ .toList(),
+ result.getTotal(), page, pageSize);
}
@Override
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/common/domain/PageResultTest.java
b/server/src/test/java/org/apache/rocketmq/studio/common/domain/PageResultTest.java
index 7bcb3dadb..586aac76f 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/common/domain/PageResultTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/common/domain/PageResultTest.java
@@ -18,7 +18,11 @@ package org.apache.rocketmq.studio.common.domain;
import org.junit.jupiter.api.Test;
+import java.util.ArrayList;
+import java.util.List;
+
import static org.assertj.core.api.Assertions.assertThat;
+import static org.assertj.core.api.Assertions.assertThatThrownBy;
class PageResultTest {
@@ -28,4 +32,16 @@ class PageResultTest {
assertThat(result.getItems()).isNotNull().isEmpty();
}
+
+ @Test
+ void ofShouldIsolateItemsFromTheSourceList() {
+ List<String> source = new ArrayList<>(List.of("first"));
+
+ PageResult<String> result = PageResult.of(source, 1, 1, 20);
+ source.add("later");
+
+ assertThat(result.getItems()).containsExactly("first");
+ assertThatThrownBy(() -> result.getItems().add("mutated"))
+ .isInstanceOf(UnsupportedOperationException.class);
+ }
}
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepositoryTest.java
b/server/src/test/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepositoryTest.java
index 0e7e075f3..a8604ba4e 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepositoryTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/instance/acl/MybatisPlusAclRepositoryTest.java
@@ -40,6 +40,7 @@ import org.mockito.junit.jupiter.MockitoExtension;
import java.time.LocalDateTime;
import java.util.Arrays;
import java.util.List;
+import java.util.Locale;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
@@ -152,6 +153,26 @@ class MybatisPlusAclRepositoryTest {
verify(userMapper, never()).selectList(any(QueryWrapper.class));
}
+ @Test
+ void findUserPageShouldNormalizeSearchWithRootLocale() {
+ Page<RmqAclUser> mapperPage = new Page<RmqAclUser>(1, 20)
+ .setRecords(List.of())
+ .setTotal(0);
+ when(userMapper.selectPage(any(IPage.class),
any(Wrapper.class))).thenReturn(mapperPage);
+ Locale previous = Locale.getDefault();
+ try {
+ Locale.setDefault(Locale.forLanguageTag("tr-TR"));
+ repository.findUserPage(" INSTANCE ", 1, 20);
+ } finally {
+ Locale.setDefault(previous);
+ }
+ ArgumentCaptor<Wrapper<RmqAclUser>> queryCaptor =
ArgumentCaptor.forClass(Wrapper.class);
+ verify(userMapper).selectPage(any(IPage.class), queryCaptor.capture());
+ QueryWrapper<RmqAclUser> query = (QueryWrapper<RmqAclUser>)
queryCaptor.getValue();
+ assertThat(query.getSqlSegment()).contains("username", "access_key");
+ assertThat(query.getParamNameValuePairs()).containsValue("%instance%");
+ }
+
@Test
void replaceRuleShouldReturnEmptyWhenConcurrentDeleteWins() {
RmqAclRule existing = new RmqAclRule();
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/instance/dlq/DLQControllerTest.java
b/server/src/test/java/org/apache/rocketmq/studio/instance/dlq/DLQControllerTest.java
index 748913621..e2f54c15d 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/instance/dlq/DLQControllerTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/instance/dlq/DLQControllerTest.java
@@ -426,6 +426,24 @@ class DLQControllerTest {
verifyNoInteractions(dlqService);
}
+ @Test
+ void resendSelectedMessagesShouldRejectBlankMsgIdsTest() throws Exception {
+ Map<String, Object> body = Map.of(
+ "instanceId", "instance-1",
+ "groupName", "test-group",
+ "msgIds", List.of("msg-1", " ")
+ );
+
+ mockMvc.perform(post("/api/dlq/resend-selected")
+ .contentType(MediaType.APPLICATION_JSON)
+ .content(objectMapper.writeValueAsString(body)))
+ .andExpect(status().isBadRequest())
+ .andExpect(jsonPath("$.code").value(400))
+ .andExpect(jsonPath("$.message").value("msgId must not be
blank"));
+
+ verifyNoInteractions(dlqService);
+ }
+
@Test
void resendSelectedMessagesShouldRejectMoreThanHundredMsgIdsTest() throws
Exception {
List<String> msgIds = new java.util.ArrayList<>();
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProviderTest.java
b/server/src/test/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProviderTest.java
index 7786839ce..f9093a867 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProviderTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/ops/ai/ClaudeCodeAgentProviderTest.java
@@ -50,6 +50,18 @@ class ClaudeCodeAgentProviderTest {
assertThat(tokens).containsExactly("done");
}
+ @Test
+ void streamShouldBoundStderrIncludedInFailuresTest() {
+ TestClaudeCodeAgentProvider provider = new TestClaudeCodeAgentProvider(
+ List.of("sh", "-c", "yes failure | head -c 131072 >&2; exit
1"), 5);
+
+ assertThatThrownBy(() -> provider.stream(
+ LlmConfigVO.builder().build(), "prompt", null, ignored -> { }))
+ .isInstanceOf(LlmGatewayException.class)
+ .hasMessageContaining("[stderr truncated]")
+ .satisfies(exception ->
assertThat(exception.getMessage().length()).isLessThan(70_000));
+ }
+
@Test
void streamShouldEnforceTimeoutBeforeWaitingForStdoutTest() {
TestClaudeCodeAgentProvider provider = new TestClaudeCodeAgentProvider(
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProviderTest.java
b/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProviderTest.java
index 5ba2fb094..89ea41124 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProviderTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQClusterProviderTest.java
@@ -73,6 +73,22 @@ class RocketMQClusterProviderTest {
assertThat(clusters.get(0).getStatus()).isEqualTo(ClusterStatus.healthy);
}
+ @Test
+ void discoverClustersShouldConvertDiskRatioToPercentage() throws Exception
{
+ DefaultMQAdminExt adminExt = mock(DefaultMQAdminExt.class);
+ RocketMQClusterProvider provider = newProvider(adminExt);
+ when(adminExt.examineBrokerClusterInfo()).thenReturn(clusterInfo());
+ KVTable runtime = runtimeStats();
+ runtime.getTable().put("commitLogDiskRatio", "0.625");
+
when(adminExt.fetchBrokerRuntimeStats("10.0.0.11:10911")).thenReturn(runtime);
+
+ ClusterVO cluster = provider.discoverClusters().get(0);
+
+ assertThat(cluster.getBrokers()).singleElement()
+ .extracting(broker -> broker.getDiskUsage())
+ .isEqualTo(62.5D);
+ }
+
@Test
void discoverClustersShouldPopulateSafeDefaults() throws Exception {
DefaultMQAdminExt adminExt = mock(DefaultMQAdminExt.class);
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProviderTest.java
b/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProviderTest.java
index 46172fa7b..04c625f01 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProviderTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/provider/apache/RocketMQDashboardProviderTest.java
@@ -484,6 +484,26 @@ class RocketMQDashboardProviderTest {
});
}
+ @Test
+ void dashboardShouldIgnoreNonFiniteNegativeAndOverflowingTps() throws
Exception {
+ DefaultMQAdminExt adminExt = mock(DefaultMQAdminExt.class);
+
when(adminExt.examineBrokerClusterInfo()).thenReturn(clusterInfoWithTwoMasters());
+ when(adminExt.fetchAllTopicList()).thenReturn(topicList());
+ when(adminExt.fetchBrokerRuntimeStats("10.0.0.11:10911"))
+ .thenReturn(runtimeStats("NaN", "Infinity"));
+ when(adminExt.fetchBrokerRuntimeStats("10.0.0.12:10911"))
+ .thenReturn(runtimeStats("-1", "1e300"));
+
+ DashboardDataVO dashboard = newProvider(adminExt).getDashboardData();
+
+ assertThat(dashboard.getStats().getTpsIn()).isZero();
+ assertThat(dashboard.getStats().getTpsOut()).isZero();
+ assertThat(dashboard.getClusters()).allSatisfy(cluster -> {
+ assertThat(cluster.getTpsIn()).isZero();
+ assertThat(cluster.getTpsOut()).isZero();
+ });
+ }
+
@Test
void dashboardShouldReportMessagesProducedSinceTodayMorning() throws
Exception {
DefaultMQAdminExt adminExt = mock(DefaultMQAdminExt.class);
diff --git
a/server/src/test/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepositoryTest.java
b/server/src/test/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepositoryTest.java
index d31cd29a2..7ee62d058 100644
---
a/server/src/test/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepositoryTest.java
+++
b/server/src/test/java/org/apache/rocketmq/studio/provider/credential/MybatisPlusCloudCredentialRepositoryTest.java
@@ -17,12 +17,17 @@
package org.apache.rocketmq.studio.provider.credential;
+import com.baomidou.mybatisplus.core.conditions.Wrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import org.apache.rocketmq.studio.common.domain.enums.InstanceVendor;
import org.apache.rocketmq.studio.common.exception.BusinessException;
import org.apache.rocketmq.studio.persistence.entity.RmqCloudCredential;
import org.apache.rocketmq.studio.persistence.mapper.RmqCloudCredentialMapper;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
+import org.mockito.ArgumentCaptor;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
@@ -32,6 +37,7 @@ import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@ExtendWith(MockitoExtension.class)
@@ -77,6 +83,20 @@ class MybatisPlusCloudCredentialRepositoryTest {
.hasMessageContaining("3");
}
+ @Test
+ void findPageShouldTrimTheSearchTerm() {
+ when(credentialMapper.selectPage(any(IPage.class), any(Wrapper.class)))
+ .thenReturn(new Page<RmqCloudCredential>(1, 20));
+
+ repository.findPage(null, " credential ", 1, 20);
+
+ ArgumentCaptor<Wrapper<RmqCloudCredential>> queryCaptor =
ArgumentCaptor.forClass(Wrapper.class);
+ verify(credentialMapper).selectPage(any(IPage.class),
queryCaptor.capture());
+ QueryWrapper<RmqCloudCredential> query =
(QueryWrapper<RmqCloudCredential>) queryCaptor.getValue();
+ query.getCustomSqlSegment();
+
assertThat(query.getParamNameValuePairs()).containsValue("%credential%");
+ }
+
private RmqCloudCredential entity(Long id, String name, String vendor) {
RmqCloudCredential entity = new RmqCloudCredential();
entity.setId(id);