feat: 统一列表模糊搜索行为
- 统一管理端和用户中心搜索参数及多字段包含匹配 - 修复聊天搜索竞态并优化部门重名路径展示 - 补充部门展开、模型空白词和聊天查询回归测试
This commit is contained in:
@@ -32,6 +32,9 @@ public class Bot extends BotBase {
|
||||
@Column(ignore = true)
|
||||
private String createdByName;
|
||||
|
||||
@Column(ignore = true)
|
||||
private String keyword;
|
||||
|
||||
public boolean isAnonymousEnabled() {
|
||||
Map<String, Object> options = getOptions();
|
||||
if (options == null) {
|
||||
@@ -83,4 +86,22 @@ public class Bot extends BotBase {
|
||||
this.createdByName = createdByName;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取市场列表搜索关键字。
|
||||
*
|
||||
* @return 标题或描述关键字
|
||||
*/
|
||||
public String getKeyword() {
|
||||
return keyword;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置市场列表搜索关键字。
|
||||
*
|
||||
* @param keyword 标题或描述关键字
|
||||
*/
|
||||
public void setKeyword(String keyword) {
|
||||
this.keyword = keyword;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -29,6 +29,9 @@ public class Workflow extends WorkflowBase implements VisibilityResource {
|
||||
@Column(ignore = true)
|
||||
private String createdByName;
|
||||
|
||||
@Column(ignore = true)
|
||||
private String keyword;
|
||||
|
||||
public Tool toFunction(boolean needEnglishName) {
|
||||
return new WorkflowTool(this, needEnglishName);
|
||||
}
|
||||
@@ -78,4 +81,22 @@ public class Workflow extends WorkflowBase implements VisibilityResource {
|
||||
public void setCreatedByName(String createdByName) {
|
||||
this.createdByName = createdByName;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取市场列表搜索关键字。
|
||||
*
|
||||
* @return 标题或描述关键字
|
||||
*/
|
||||
public String getKeyword() {
|
||||
return keyword;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置市场列表搜索关键字。
|
||||
*
|
||||
* @param keyword 标题或描述关键字
|
||||
*/
|
||||
public void setKeyword(String keyword) {
|
||||
this.keyword = keyword;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -27,10 +27,10 @@ public interface PluginService extends IService<Plugin> {
|
||||
* @param pageNumber 页码
|
||||
* @param pageSize 每页数量
|
||||
* @param category 分类 ID
|
||||
* @param name 插件名称关键字
|
||||
* @param keyword 插件名称或描述关键字
|
||||
* @return 插件分页结果
|
||||
*/
|
||||
Result<Page<Plugin>> pageByCategory(Long pageNumber, Long pageSize, int category, String name);
|
||||
Result<Page<Plugin>> pageByCategory(Long pageNumber, Long pageSize, int category, String keyword);
|
||||
|
||||
boolean updatePlugin(Plugin plugin);
|
||||
|
||||
|
||||
@@ -31,6 +31,7 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
import tech.easyflow.ai.config.SearcherFactory;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.ai.documentimport.DocumentImportDtos;
|
||||
import tech.easyflow.ai.documentimport.DocumentImportKeys;
|
||||
import tech.easyflow.ai.documentimport.DocumentImportPreviewService;
|
||||
@@ -183,7 +184,7 @@ public class DocumentServiceImpl extends ServiceImpl<DocumentMapper, Document> i
|
||||
.where(DOCUMENT.COLLECTION_ID.eq(knowledgeId))
|
||||
.orderBy(DOCUMENT.ID, false);
|
||||
if (fileName != null && !fileName.trim().isEmpty()) {
|
||||
queryWrapper.and(DOCUMENT.TITLE.like(fileName));
|
||||
queryWrapper.and(DOCUMENT.TITLE.likeRaw(SearchKeywordUtil.literalContainsPattern(fileName)));
|
||||
}
|
||||
if (documentId != null) {
|
||||
queryWrapper.and(DOCUMENT.ID.eq(documentId));
|
||||
|
||||
@@ -23,6 +23,7 @@ import tech.easyflow.common.domain.Result;
|
||||
import tech.easyflow.common.web.exceptions.BusinessException;
|
||||
import tech.easyflow.common.entity.LoginAccount;
|
||||
import tech.easyflow.common.satoken.util.SaTokenUtil;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.system.entity.vo.RoleCategoryAccessSnapshot;
|
||||
import tech.easyflow.system.service.CategoryPermissionService;
|
||||
|
||||
@@ -138,7 +139,7 @@ public class PluginServiceImpl extends ServiceImpl<PluginMapper, Plugin> impleme
|
||||
}
|
||||
|
||||
@Override
|
||||
public Result<Page<Plugin>> pageByCategory(Long pageNumber, Long pageSize, int category, String name) {
|
||||
public Result<Page<Plugin>> pageByCategory(Long pageNumber, Long pageSize, int category, String keyword) {
|
||||
RoleCategoryAccessSnapshot access = categoryPermissionService.getCurrentAccess("PLUGIN");
|
||||
QueryWrapper queryWrapper = QueryWrapper.create().select(PluginCategoryMapping::getPluginId)
|
||||
.eq(PluginCategoryMapping::getCategoryId, category);
|
||||
@@ -165,7 +166,7 @@ public class PluginServiceImpl extends ServiceImpl<PluginMapper, Plugin> impleme
|
||||
}
|
||||
|
||||
List<Plugin> totalPlugins = preparePluginsForCurrentUser(
|
||||
queryPluginsByIds(visiblePluginIds, name), true, false);
|
||||
queryPluginsByIds(visiblePluginIds, keyword), true, false);
|
||||
int fromIndex = Math.max(0, Math.toIntExact((pageNumber - 1) * pageSize));
|
||||
if (fromIndex >= totalPlugins.size()) {
|
||||
return Result.ok(new Page<>(Collections.emptyList(), pageNumber, pageSize, totalPlugins.size()));
|
||||
@@ -259,19 +260,20 @@ public class PluginServiceImpl extends ServiceImpl<PluginMapper, Plugin> impleme
|
||||
}
|
||||
|
||||
/**
|
||||
* 按给定顺序查询插件,并按名称关键字过滤。
|
||||
* 按给定顺序查询插件,并按名称或描述关键字过滤。
|
||||
*
|
||||
* @param pluginIds 插件 ID 列表
|
||||
* @param name 插件名称关键字
|
||||
* @param keyword 插件名称或描述关键字
|
||||
* @return 保持输入 ID 顺序的插件列表
|
||||
*/
|
||||
private List<Plugin> queryPluginsByIds(List<BigInteger> pluginIds, String name) {
|
||||
private List<Plugin> queryPluginsByIds(List<BigInteger> pluginIds, String keyword) {
|
||||
if (CollectionUtil.isEmpty(pluginIds)) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
QueryWrapper queryPluginWrapper = QueryWrapper.create().select().in(Plugin::getId, pluginIds);
|
||||
if (name != null && !name.isBlank()) {
|
||||
queryPluginWrapper.like(Plugin::getName, name.trim());
|
||||
if (keyword != null && !keyword.isBlank()) {
|
||||
String pattern = SearchKeywordUtil.literalContainsPattern(keyword);
|
||||
queryPluginWrapper.and(PLUGIN.NAME.likeRaw(pattern).or(PLUGIN.DESCRIPTION.likeRaw(pattern)));
|
||||
}
|
||||
List<Plugin> plugins = pluginMapper.selectListWithRelationsByQuery(queryPluginWrapper);
|
||||
Map<BigInteger, Plugin> pluginMap = plugins.stream().collect(Collectors.toMap(
|
||||
|
||||
@@ -19,6 +19,7 @@ import tech.easyflow.approval.mapper.ApprovalTaskAssigneeMapper;
|
||||
import tech.easyflow.approval.mapper.ApprovalTaskMapper;
|
||||
import tech.easyflow.approval.service.ApprovalAssigneeService;
|
||||
import tech.easyflow.common.constant.enums.EnumDataStatus;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.common.web.exceptions.BusinessException;
|
||||
import tech.easyflow.system.entity.SysAccount;
|
||||
import tech.easyflow.system.entity.SysAccountRole;
|
||||
@@ -365,7 +366,7 @@ public class ApprovalAssigneeServiceImpl implements ApprovalAssigneeService {
|
||||
.eq(SysAccount::getStatus, EnumDataStatus.AVAILABLE.getCode())
|
||||
.orderBy("nickname asc, login_name asc, id asc");
|
||||
if (StringUtils.hasText(keyword)) {
|
||||
String likeKeyword = "%" + keyword.trim() + "%";
|
||||
String likeKeyword = SearchKeywordUtil.literalContainsPattern(keyword);
|
||||
queryWrapper.and("(`login_name` like ? or `nickname` like ?)", likeKeyword, likeKeyword);
|
||||
}
|
||||
Page<SysAccount> page = sysAccountService.page(new Page<>(actualPageNumber, actualPageSize), queryWrapper);
|
||||
|
||||
@@ -7,6 +7,7 @@ import com.mybatisflex.spring.service.impl.ServiceImpl;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
import org.springframework.util.StringUtils;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.common.web.exceptions.BusinessException;
|
||||
import tech.easyflow.approval.entity.ApprovalFlow;
|
||||
import tech.easyflow.approval.entity.ApprovalFlowScope;
|
||||
@@ -72,7 +73,7 @@ public class ApprovalFlowServiceImpl extends ServiceImpl<ApprovalFlowMapper, App
|
||||
long actualPageSize = pageSize == null || pageSize < 1 ? 10L : pageSize;
|
||||
QueryWrapper queryWrapper = QueryWrapper.create();
|
||||
if (StringUtils.hasText(name)) {
|
||||
queryWrapper.like(ApprovalFlow::getName, name.trim());
|
||||
queryWrapper.and("name LIKE ?", SearchKeywordUtil.literalContainsPattern(name));
|
||||
}
|
||||
if (StringUtils.hasText(resourceType)) {
|
||||
queryWrapper.eq(ApprovalFlow::getResourceType, ApprovalResourceType.from(resourceType).getCode());
|
||||
|
||||
@@ -7,6 +7,7 @@ import org.springframework.stereotype.Service;
|
||||
import org.springframework.util.StringUtils;
|
||||
import tech.easyflow.common.entity.LoginAccount;
|
||||
import tech.easyflow.common.satoken.util.SaTokenUtil;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.common.web.exceptions.BusinessException;
|
||||
import tech.easyflow.approval.entity.ApprovalFlowStep;
|
||||
import tech.easyflow.approval.entity.ApprovalInstance;
|
||||
@@ -310,7 +311,7 @@ public class ApprovalQueryServiceImpl implements ApprovalQueryService {
|
||||
queryWrapper.eq(ApprovalInstance::getActionType, ApprovalActionType.from(actionType).getCode());
|
||||
}
|
||||
if (StringUtils.hasText(keyword)) {
|
||||
queryWrapper.like(ApprovalInstance::getSummary, keyword.trim());
|
||||
queryWrapper.and("summary LIKE ?", SearchKeywordUtil.literalContainsPattern(keyword));
|
||||
}
|
||||
return queryWrapper;
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ public class ChatPageQuery implements Serializable {
|
||||
|
||||
private long pageNumber = 1;
|
||||
private long pageSize = 20;
|
||||
private String keyword;
|
||||
|
||||
public long getPageNumber() {
|
||||
return pageNumber;
|
||||
@@ -26,4 +27,22 @@ public class ChatPageQuery implements Serializable {
|
||||
public long getOffset() {
|
||||
return (pageNumber - 1) * pageSize;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取会话搜索关键字。
|
||||
*
|
||||
* @return 会话标题、最近消息或助手名称关键字
|
||||
*/
|
||||
public String getKeyword() {
|
||||
return keyword;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置会话搜索关键字。
|
||||
*
|
||||
* @param keyword 会话标题、最近消息或助手名称关键字
|
||||
*/
|
||||
public void setKeyword(String keyword) {
|
||||
this.keyword = keyword == null ? null : keyword.trim();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ import tech.easyflow.common.analyticaldb.core.AnalyticalDBOperations;
|
||||
import tech.easyflow.common.analyticaldb.page.AnalyticalDBPageRequest;
|
||||
import tech.easyflow.common.analyticaldb.page.AnalyticalDBPageResult;
|
||||
import tech.easyflow.common.analyticaldb.support.AnalyticalDBHealthSupport;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
|
||||
import java.math.BigInteger;
|
||||
import java.sql.Timestamp;
|
||||
@@ -746,7 +747,7 @@ public class ChatAnalyticalDBRepository {
|
||||
}
|
||||
if (query.getUserAccount() != null && !query.getUserAccount().isBlank()) {
|
||||
sql.append(" AND user_account LIKE ?");
|
||||
args.add("%" + query.getUserAccount().trim() + "%");
|
||||
args.add(SearchKeywordUtil.literalContainsPattern(query.getUserAccount()));
|
||||
}
|
||||
if (query.getStartTime() != null) {
|
||||
String startTime = formatDateTime(query.getStartTime());
|
||||
|
||||
@@ -10,6 +10,7 @@ import tech.easyflow.chatlog.domain.event.payload.ChatSessionDeletePayload;
|
||||
import tech.easyflow.chatlog.domain.event.payload.ChatSessionRenamePayload;
|
||||
import tech.easyflow.chatlog.domain.query.ChatPageQuery;
|
||||
import tech.easyflow.chatlog.support.ChatTableRouter;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
|
||||
import java.math.BigInteger;
|
||||
import java.sql.ResultSet;
|
||||
@@ -122,6 +123,7 @@ public class MySqlChatSessionRepository {
|
||||
sql.append(" AND assistant_code=?");
|
||||
params.add(assistantCode);
|
||||
}
|
||||
appendKeywordCondition(sql, params, query);
|
||||
sql.append(" ORDER BY last_message_at DESC, id DESC LIMIT ? OFFSET ?");
|
||||
params.add(query.getPageSize());
|
||||
params.add(query.getOffset());
|
||||
@@ -133,6 +135,20 @@ public class MySqlChatSessionRepository {
|
||||
}
|
||||
|
||||
public long countSessions(BigInteger userId, BigInteger assistantId, String assistantCode) {
|
||||
return countSessions(userId, assistantId, assistantCode, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* 按用户、助手和关键字统计会话数量。
|
||||
*
|
||||
* @param userId 用户 ID
|
||||
* @param assistantId 助手 ID,可为空
|
||||
* @param assistantCode 助手编码,可为空
|
||||
* @param query 分页与关键字条件,可为空
|
||||
* @return 符合条件的会话数量
|
||||
*/
|
||||
public long countSessions(BigInteger userId, BigInteger assistantId,
|
||||
String assistantCode, ChatPageQuery query) {
|
||||
String table = tableRouter.resolveSessionTable();
|
||||
List<Object> params = new ArrayList<>();
|
||||
StringBuilder sql = new StringBuilder("SELECT COUNT(1) FROM `").append(table)
|
||||
@@ -146,10 +162,31 @@ public class MySqlChatSessionRepository {
|
||||
sql.append(" AND assistant_code=?");
|
||||
params.add(assistantCode);
|
||||
}
|
||||
appendKeywordCondition(sql, params, query);
|
||||
Long count = jdbcTemplate.queryForObject(sql.toString(), Long.class, params.toArray());
|
||||
return count == null ? 0L : count;
|
||||
}
|
||||
|
||||
/**
|
||||
* 向会话 SQL 追加标题、最近消息和助手名称的普通文本包含匹配。
|
||||
*
|
||||
* @param sql SQL 构造器
|
||||
* @param params SQL 参数
|
||||
* @param query 查询条件
|
||||
*/
|
||||
private void appendKeywordCondition(StringBuilder sql, List<Object> params, ChatPageQuery query) {
|
||||
String keyword = query == null ? null : query.getKeyword();
|
||||
if (keyword == null || keyword.isBlank()) {
|
||||
return;
|
||||
}
|
||||
String pattern = SearchKeywordUtil.literalContainsPattern(keyword);
|
||||
sql.append(" AND (title LIKE ? ESCAPE '\\\\' OR last_message_preview LIKE ? ESCAPE '\\\\'"
|
||||
+ " OR assistant_name LIKE ? ESCAPE '\\\\')");
|
||||
params.add(pattern);
|
||||
params.add(pattern);
|
||||
params.add(pattern);
|
||||
}
|
||||
|
||||
public ChatSessionSummary findBySessionIdAndUserId(BigInteger sessionId, BigInteger userId) {
|
||||
String table = tableRouter.resolveSessionTable();
|
||||
List<ChatSessionSummary> list = jdbcTemplate.query(
|
||||
|
||||
@@ -64,7 +64,7 @@ public class ChatSessionQueryServiceImpl implements ChatSessionQueryService {
|
||||
page.setPageNumber(query.getPageNumber());
|
||||
page.setPageSize(query.getPageSize());
|
||||
|
||||
page.setTotal(sessionRepository.countSessions(userId, assistantId, assistantCode));
|
||||
page.setTotal(sessionRepository.countSessions(userId, assistantId, assistantCode, query));
|
||||
page.setRecords(listSessions(userId, assistantId, assistantCode, query));
|
||||
return page;
|
||||
}
|
||||
|
||||
@@ -69,6 +69,27 @@ public class ChatSessionQueryServiceImplTest {
|
||||
Assert.assertEquals("AGENT", sessionRepository.capturedCountAssistantCode);
|
||||
}
|
||||
|
||||
/**
|
||||
* 会话关键词必须同时下推到列表和计数查询,保证分页总数一致。
|
||||
*/
|
||||
@Test
|
||||
public void pageSessionsShouldPassKeywordToListAndCountQueries() {
|
||||
FakeSessionRepository sessionRepository = new FakeSessionRepository();
|
||||
ChatSessionQueryServiceImpl service = new ChatSessionQueryServiceImpl(
|
||||
sessionRepository,
|
||||
new FakeLogRepository(),
|
||||
new FakeTableManager(List.of()),
|
||||
new FakeHotStateService()
|
||||
);
|
||||
ChatPageQuery query = new ChatPageQuery();
|
||||
query.setKeyword("最近消息");
|
||||
|
||||
service.pageSessions(BigInteger.valueOf(7), null, query);
|
||||
|
||||
Assert.assertSame(query, sessionRepository.capturedListQuery);
|
||||
Assert.assertSame(query, sessionRepository.capturedCountQuery);
|
||||
}
|
||||
|
||||
/**
|
||||
* 工作台消息分页必须走 MySQL 热表主线查询,并保持分页参数语义。
|
||||
*/
|
||||
@@ -147,6 +168,8 @@ public class ChatSessionQueryServiceImplTest {
|
||||
private int listSessionsCalls;
|
||||
private String capturedListAssistantCode;
|
||||
private String capturedCountAssistantCode;
|
||||
private ChatPageQuery capturedListQuery;
|
||||
private ChatPageQuery capturedCountQuery;
|
||||
private ChatSessionSummary summary;
|
||||
private List<ChatSessionSummary> sessions = new ArrayList<>();
|
||||
|
||||
@@ -163,6 +186,7 @@ public class ChatSessionQueryServiceImplTest {
|
||||
public List<ChatSessionSummary> listSessions(BigInteger userId, BigInteger assistantId, String assistantCode, ChatPageQuery query) {
|
||||
listSessionsCalls += 1;
|
||||
capturedListAssistantCode = assistantCode;
|
||||
capturedListQuery = query;
|
||||
return sessions;
|
||||
}
|
||||
|
||||
@@ -173,8 +197,15 @@ public class ChatSessionQueryServiceImplTest {
|
||||
|
||||
@Override
|
||||
public long countSessions(BigInteger userId, BigInteger assistantId, String assistantCode) {
|
||||
return countSessions(userId, assistantId, assistantCode, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public long countSessions(BigInteger userId, BigInteger assistantId,
|
||||
String assistantCode, ChatPageQuery query) {
|
||||
countSessionsCalls += 1;
|
||||
capturedCountAssistantCode = assistantCode;
|
||||
capturedCountQuery = query;
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
@@ -19,6 +19,7 @@ import tech.easyflow.ai.service.PluginVisibilityService;
|
||||
import tech.easyflow.ai.service.WorkflowService;
|
||||
import tech.easyflow.common.entity.LoginAccount;
|
||||
import tech.easyflow.common.satoken.util.SaTokenUtil;
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.common.web.exceptions.BusinessException;
|
||||
import tech.easyflow.skill.entity.SkillCapabilityBinding;
|
||||
import tech.easyflow.skill.enums.SkillCapabilityType;
|
||||
@@ -502,7 +503,7 @@ public class SkillCapabilityTargetAccessServiceImpl implements SkillCapabilityTa
|
||||
if (keyword == null || keyword.isBlank() || columns.length == 0) {
|
||||
return;
|
||||
}
|
||||
String pattern = "%" + keyword.toLowerCase(Locale.ROOT) + "%";
|
||||
String pattern = SearchKeywordUtil.literalContainsPattern(keyword.toLowerCase(Locale.ROOT));
|
||||
StringBuilder condition = new StringBuilder("(");
|
||||
Object[] arguments = new Object[columns.length];
|
||||
for (int index = 0; index < columns.length; index++) {
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
package tech.easyflow.system.entity;
|
||||
|
||||
import com.mybatisflex.annotation.Column;
|
||||
import tech.easyflow.system.entity.base.SysDeptBase;
|
||||
import com.mybatisflex.annotation.Table;
|
||||
|
||||
@@ -12,4 +13,25 @@ import com.mybatisflex.annotation.Table;
|
||||
|
||||
@Table(value = "tb_sys_dept", comment = "部门表")
|
||||
public class SysDept extends SysDeptBase {
|
||||
|
||||
@Column(ignore = true)
|
||||
private String keyword;
|
||||
|
||||
/**
|
||||
* 获取部门列表搜索关键字。
|
||||
*
|
||||
* @return 部门名称或编码关键字
|
||||
*/
|
||||
public String getKeyword() {
|
||||
return keyword;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置部门列表搜索关键字。
|
||||
*
|
||||
* @param keyword 部门名称或编码关键字
|
||||
*/
|
||||
public void setKeyword(String keyword) {
|
||||
this.keyword = keyword;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
package tech.easyflow.system.entity;
|
||||
|
||||
import tech.easyflow.common.util.SearchKeywordUtil;
|
||||
import tech.easyflow.common.util.SpringContextUtil;
|
||||
import tech.easyflow.common.dict.Dict;
|
||||
import tech.easyflow.common.dict.DictItem;
|
||||
@@ -81,7 +82,7 @@ public class SysDict extends SysDictBase {
|
||||
QueryWrapper qw = QueryWrapper.create()
|
||||
.eq(SysDictItem::getDictId, this.dictId)
|
||||
.eq(SysDictItem::getStatus, 0)
|
||||
.like(SysDictItem::getText, keyword);
|
||||
.and("`text` LIKE ?", SearchKeywordUtil.literalContainsPattern(keyword));
|
||||
List<SysDictItem> sysDictItems = itemService.list(qw);
|
||||
|
||||
Dict dict = new Dict();
|
||||
|
||||
Reference in New Issue
Block a user