ADVANCED_QUERY_USAGE.md 11 KB

高级查询使用说明

概述

高级查询模块提供了类似 Navicat 数据筛选的灵活查询条件构建能力,支持复杂的条件组合和嵌套。

核心概念

1. 查询操作符 (QueryOperator)

操作符 常量 说明 示例
等于 OperatorEqual 字段值等于指定值 name = "测试"
不等于 OperatorNotEqual 字段值不等于指定值 status != "deleted"
大于 OperatorGreaterThan 字段值大于指定值 quantity > 10
大于等于 OperatorGreaterEqual 字段值大于等于指定值 price >= 100
小于 OperatorLessThan 字段值小于指定值 stock < 50
小于等于 OperatorLessEqual 字段值小于等于指定值 age <= 18
包含 OperatorLike 字段值包含指定字符串 name LIKE "%测试%"
不包含 OperatorNotLike 字段值不包含指定字符串 name NOT LIKE "%测试%"
开头是 OperatorStartsWith 字段值以指定字符串开头 code LIKE "ABC%"
结尾是 OperatorEndsWith 字段值以指定字符串结尾 email LIKE "%@qq.com"
为空 OperatorIsNull 字段值为 NULL deleted_at IS NULL
不为空 OperatorIsNotNull 字段值不为 NULL email IS NOT NULL
在列表中 OperatorIn 字段值在指定列表中 status IN ('active', 'pending')
不在列表中 OperatorNotIn 字段值不在指定列表中 status NOT IN ('deleted', 'archived')

2. 逻辑操作符 (LogicOperator)

操作符 常量 说明
LogicAnd 所有条件都必须满足
LogicOr 满足任意一个条件即可

3. 数据结构

// 单个查询条件
type QueryCondition struct {
    Field    string        // 字段名
    Operator QueryOperator // 操作符
    Value    any           // 比较值(可选)
}

// 条件项(可以是单个条件或嵌套的条件组)
type ConditionItem struct {
    Condition       *ConditionGroup // 嵌套条件组
    SingleCondition *QueryCondition // 单个条件
}

// 条件组
type ConditionGroup struct {
    Conditions []ConditionItem // 条件列表
    Logic      LogicOperator   // 组内逻辑关系
}

// 高级查询参数
type AdvancedQueryParams struct {
    ConditionGroups []ConditionGroup // 条件组列表
    GroupLogic      LogicOperator    // 组间逻辑关系
}

快捷函数

单条件快捷函数

// 等于
Equal("name", "测试资源")

// 不等于
NotEqual("status", "deleted")

// 大于
GreaterThan("quantity", 10)

// 大于等于
GreaterEqual("price", 100)

// 小于
LessThan("stock", 50)

// 小于等于
LessEqual("age", 18)

// 包含(模糊匹配)
Like("name", "测试")

// 不包含
NotLike("name", "测试")

// 开头是
StartsWith("code", "ABC")

// 结尾是
EndsWith("email", "@qq.com")

// 为空
IsNull("deleted_at")

// 不为空
IsNotNull("email")

// 在列表中
In("category", []any{"设备", "耗材", "工具"})

// 不在列表中
NotIn("status", []any{"deleted", "archived"})

条件组快捷函数

// AND 条件组(所有条件都必须满足)
AndGroup(
    Equal("name", "测试"),
    GreaterThan("quantity", 10),
    IsNotNull("code"),
)

// OR 条件组(满足任意一个条件即可)
OrGroup(
    Equal("category", "设备"),
    Equal("category", "耗材"),
    Like("name", "测试"),
)

完整查询快捷函数

// AND 查询(所有条件组都必须满足)
AndQuery(
    AndGroup(Equal("name", "测试"), GreaterThan("quantity", 10)),
    OrGroup(Equal("category", "设备"), Equal("category", "耗材")),
)

// OR 查询(满足任意一个条件组即可)
OrQuery(
    AndGroup(Equal("status", "active"), GreaterThan("quantity", 0)),
    AndGroup(Equal("status", "pending"), IsNotNull("approved_by")),
)

使用示例

示例 1:简单条件查询

查询名称包含"测试"且数量大于 10 的资源:

params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: &managesdk.AdvancedQueryParams{
        ConditionGroups: []managesdk.ConditionGroup{
            managesdk.AndGroup(
                managesdk.Like("name", "测试"),
                managesdk.GreaterThan("quantity", 10),
            ),
        },
        GroupLogic: managesdk.LogicAnd,
    },
    BaseQueryParams: managesdk.BaseQueryParams{
        PageNo:   1,
        PageSize: 10,
    },
}

result, err := client.Manage().Query(params)

等价于 SQL:

WHERE (name LIKE '%测试%' AND quantity > 10)

示例 2:OR 条件查询

查询分类为"设备"或"耗材"的资源:

params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: &managesdk.AdvancedQueryParams{
        ConditionGroups: []managesdk.ConditionGroup{
            managesdk.OrGroup(
                managesdk.Equal("category", "设备"),
                managesdk.Equal("category", "耗材"),
            ),
        },
        GroupLogic: managesdk.LogicAnd,
    },
    PageNo:   1,
    PageSize: 10,
}

等价于 SQL:

WHERE (category = '设备' OR category = '耗材')

示例 3:使用 IN 操作符

查询多个分类的资源:

params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: &managesdk.AdvancedQueryParams{
        ConditionGroups: []managesdk.ConditionGroup{
            {
                Conditions: []managesdk.ConditionItem{
                    managesdk.In("category", []any{"设备", "耗材", "工具"}),
                },
                Logic: managesdk.LogicAnd,
            },
        },
        GroupLogic: managesdk.LogicAnd,
    },
    PageNo:   1,
    PageSize: 10,
}

等价于 SQL:

WHERE category IN ('设备', '耗材', '工具')

示例 4:复杂嵌套查询

查询满足以下条件的资源:

  • (名称包含"测试" AND 数量 > 10) OR (分类是"设备" AND 状态不为空)

    params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: managesdk.OrQuery(
        managesdk.AndGroup(
            managesdk.Like("name", "测试"),
            managesdk.GreaterThan("quantity", 10),
        ),
        managesdk.AndGroup(
            managesdk.Equal("category", "设备"),
            managesdk.IsNotNull("status"),
        ),
    ),
    PageNo:   1,
    PageSize: 10,
    }
    

等价于 SQL:

WHERE ((name LIKE '%测试%' AND quantity > 10) OR (category = '设备' AND status IS NOT NULL))

示例 5:多条件组组合

查询满足以下条件的资源:

  • (名称包含"测试" AND 数量 > 10)
  • AND (分类是"设备" OR 分类是"耗材")
  • AND (状态不为空)

    params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: managesdk.AndQuery(
        // 条件组1:名称和数量
        managesdk.AndGroup(
            managesdk.Like("name", "测试"),
            managesdk.GreaterThan("quantity", 10),
        ),
        // 条件组2:分类
        managesdk.OrGroup(
            managesdk.Equal("category", "设备"),
            managesdk.Equal("category", "耗材"),
        ),
        // 条件组3:状态
        managesdk.AndGroup(
            managesdk.IsNotNull("status"),
        ),
    ),
    PageNo:   1,
    PageSize: 10,
    }
    

等价于 SQL:

WHERE ((name LIKE '%测试%' AND quantity > 10) 
       AND (category = '设备' OR category = '耗材') 
       AND (status IS NOT NULL))

示例 6:深层嵌套查询

查询满足以下条件的资源:

  • ((名称包含"A" OR 名称包含"B") AND 数量 > 0) OR ((分类是"设备" AND 状态是"可用"))

    params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: managesdk.OrQuery(
        // 条件组1
        managesdk.AndGroup(
            // 嵌套的 OR 条件
            managesdk.NewNestedConditionGroup(
                managesdk.OrGroup(
                    managesdk.Like("name", "A"),
                    managesdk.Like("name", "B"),
                ),
            ),
            managesdk.GreaterThan("quantity", 0),
        ),
        // 条件组2
        managesdk.AndGroup(
            managesdk.Equal("category", "设备"),
            managesdk.Equal("status", "available"),
        ),
    ),
    PageNo:   1,
    PageSize: 10,
    }
    

等价于 SQL:

WHERE (((name LIKE '%A%' OR name LIKE '%B%') AND quantity > 0) 
       OR (category = '设备' AND status = 'available'))

示例 7:范围查询

查询数量在 10 到 100 之间的资源:

params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: &managesdk.AdvancedQueryParams{
        ConditionGroups: []managesdk.ConditionGroup{
            managesdk.AndGroup(
                managesdk.GreaterEqual("quantity", 10),
                managesdk.LessEqual("quantity", 100),
            ),
        },
        GroupLogic: managesdk.LogicAnd,
    },
    PageNo:   1,
    PageSize: 10,
}

等价于 SQL:

WHERE (quantity >= 10 AND quantity <= 100)

示例 8:空值判断

查询未删除的资源(deleted_at 为空):

params := managesdk.QueryResourcesParams{
    TenantID: "tenant123",
    AdvancedQuery: &managesdk.AdvancedQueryParams{
        ConditionGroups: []managesdk.ConditionGroup{
            managesdk.AndGroup(
                managesdk.IsNull("deleted_at"),
            ),
        },
        GroupLogic: managesdk.LogicAnd,
    },
    PageNo:   1,
    PageSize: 10,
}

等价于 SQL:

WHERE deleted_at IS NULL

与传统查询参数配合使用

高级查询可以与传统查询参数配合使用:

params := managesdk.QueryResourcesParams{
    TenantID:     "tenant123",
    Name:         "测试",           // 传统参数:名称筛选
    BusinessType: "mbrms",         // 传统参数:业务类型
    AdvancedQuery: managesdk.AndQuery(  // 高级查询:额外条件
        managesdk.GreaterThan("quantity", 10),
        managesdk.IsNotNull("code"),
    ),
    PageNo:   1,
    PageSize: 10,
}

传统参数会先应用,然后再应用高级查询条件。

最佳实践

1. 性能优化

  • 对于大表查询,优先使用 EqualIn 等精确匹配操作符
  • 避免在大文本字段上使用 Like 操作符
  • 合理使用索引字段进行查询

2. 条件组织

  • 将选择性高的条件放在前面
  • 合理分组,避免过深的嵌套层级
  • 使用语义化的条件组命名(通过代码注释)

3. 安全性

  • 字段名应该使用白名单验证
  • 避免直接拼接用户输入到查询条件

注意事项

  1. 字段名映射:确保使用的字段名与数据库字段名一致
  2. 类型匹配:比较值的类型应与字段类型匹配
  3. NULL 处理IsNullIsNotNull 不需要 Value 参数
  4. 数组参数InNotIn 的 Value 应该是 []any 类型