Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

是否支持不同字段的or #107

Closed
Cole-Mu opened this issue Sep 11, 2019 · 17 comments
Closed

是否支持不同字段的or #107

Cole-Mu opened this issue Sep 11, 2019 · 17 comments

Comments

@Cole-Mu
Copy link

Cole-Mu commented Sep 11, 2019

例子里是一个字段的or ,但有时需要 (name='xxx' or id=1 ) and status=‘normal’ 这种sql,是否支持呢

@TommyLemon
Copy link
Collaborator

TommyLemon commented Sep 11, 2019

支持,见这个 issue
https://github.com/APIJSON/APIJSON/issues/84

@TommyLemon
Copy link
Collaborator

TommyLemon commented Sep 14, 2019

@wang1784594241 你的评论怎么不见了?我在通知里还看到这个:
"这个我看了啊,只找到这个 "id{}":"<=80000,>90000" 单字段 可是这也不能举一反三就知道怎么写多字段or啊"

@TommyLemon
Copy link
Collaborator

TommyLemon commented Sep 14, 2019

像上面那个例子,不考虑 id 为主键的话,可以

{
    "Table": {  //具体的表名
        "name": "xxx",
        "id": 1,
        "status": "normal",
        "@combine": "name | id"  //或者 "|name,|id",或者 "|name,|id,&status",其中 |  可省略
    }
}

如果 id 是主键,那就不允许和别的字段 OR 了,防止绕过自动化权限控制。
再说这种需求几乎没有,一般都是多条件搜索才会用到不同字段的 OR,
例如通用文档例子里的「搜索name或tag任何一个字段包含字符a的User列表」:

{
    "User[]": {  //查询一个数组,并提取里面的 User
        "User": {
            "name~": "a",  //名称中包含 a
            "tag~": "a",  //标签中包含 a
            "@combine": "name~ | tag~"  //两个条件 OR 连接
        }
    }
}

还可以加上性别为女这个条件:

{
    "User[]": {  //查询一个数组,并提取里面的 User
        "User": {
            "sex": 1,  //性别为女
            "name~": "a",  //名称中包含 a
            "tag~": "a",  //标签中包含 a
            "@combine": "name~ | tag~"  //两个条件 OR 连接
        }
    }
}

可以加上性能分析关键词 @explain

{
    "User[]": {  //查询一个数组,并提取里面的 User
        "User": {
            "sex": 1,  //性别为女
            "name~": "a",  //名称中包含 a
            "tag~": "a",  //标签中包含 a
            "@combine": "name~ | tag~"  //两个条件 OR 连接
        }
    },
    "@explain": true
}

就能直接在 Response 里看到 APIJSON ORM 自动生成的 SQL 语句是:
MySQL( "@database": "MYSQL" ):

SELECT * FROM `sys`.`apijson_user` WHERE ( (`sex` = 1) ) AND ( (`name` REGEXP BINARY 'a') OR (`tag` REGEXP BINARY 'a') ) LIMIT 10 OFFSET 0

PostgreSQL( "@database": "POSTGRESQL" ):

SELECT * FROM "sys"."apijson_user" WHERE ( ("sex" = 1) ) AND ( ("name" ~ 'a') OR ("tag" ~ 'a') ) LIMIT 10 OFFSET 0

@Cole-Mu
Copy link
Author

Cole-Mu commented Sep 17, 2019

感谢,原来文档里也有,只是没这么详细,之前没看明白,这下理解了。

@zhangchunlin
Copy link

zhangchunlin commented Dec 22, 2020

我在 uliweb-apijson里不支持 @combine而是另外支持 @expr 这样一个更灵活的格式,可以支持比较复杂的表达,供参考,例子:

"user":{
    "@column":"id,username,nickname,email",
    "@order":"id-",
    "@role":"ADMIN",
    "@expr":[["username$","|","email$"],"&",["!","nickname$"]],
    "username$":"%b%",
    "email$":"%@example.com",
    "nickname$":"%c%",
}

@TommyLemon
Copy link
Collaborator

我在 uliweb-apijson里不支持 @combine ,而是另外支持 @expr 这样一个更灵活的格式,可以支持比较复杂的表达,供参考,例子:

"user":{
    "@column":"id,username,nickname,email",
    "@order":"id-",
    "@role":"ADMIN",
    "@expr":[["username$","|","email$"],"&",["!","nickname$"]],
    "username$":"%b%",
    "email$":"%@example.com",
    "nickname$":"%c%",
}

可以加个链接方便打开项目查看

@martin-1120
Copy link

这种同一个字段要多次用的呢
(
age = 10
)
or
(
age > 20 and status =1
)

@TommyLemon
Copy link
Collaborator

TommyLemon commented Dec 17, 2023

这种同一个字段要多次用的呢 ( age = 10 ) or ( age > 20 and status =1 )

@martin-1120
https://github.com/Tencent/APIJSON/blob/master/Document.md#3.2

"@combine":"age | (age> & status)", // 任意与或非条件组合
"age":10,
"age>"20,
"status":1

@martin-1120
Copy link

martin-1120 commented Dec 17, 2023 via email

@TommyLemon
Copy link
Collaborator

@martin-1120 你直接在 GitHub 上回复,不要用邮箱回复,现在代码有不少乱码,很难看

@martin-1120
Copy link

@TommyLemon
如果我想这样呢
一:
status=1 | (status=2 & age=20)

二:
status=1 | (status=1 & age=20)

二 我试过会报错 :
报错的意思是:数量不匹配 字段有两个 combine有三个

@TommyLemon
Copy link
Collaborator

@martin-1120

DemoSQLConfig 重写 getMaxCombineRatio ,return 0

@martin-1120
Copy link

@TommyLemon 第一种呢
一:
status=1 | (status=2 & age=20)

@TommyLemon
Copy link
Collaborator

一样。
只不过 JSON 的 key 不支持重名,需要换一种写法:
"status":1,
"status{}":"=2" 或 "status{}":[2]

@martin-1120
Copy link

@TommyLemon 就是重名怎办呢,比如有三个重名?没办法了吗
status=1 | (status=2 & age=20) | (status=3 & age=30)

@martin-1120
Copy link

建议是不是能像这样用冒号增加别名, 这样就很完善了
"status:status1":1,
"status:status2 ":2,
"status:status3 ":3,
"age:age20": 20,
"age:age30": 30,
"@combine":"status1 | (status2 & age20) | (status3 & age30)"

@TommyLemon
Copy link
Collaborator

TommyLemon commented Dec 21, 2023

@martin-1120

还可以
"status&{}": "=1",
"status|{}": "=2"

你举的例子几乎不会实际出现在业务中,一般一个字段最多同时传两个条件,大部分需求一次请求每个字段都只有一个条件,不同的字段各一个条件组合起来,不存在冲突。

真要出现这么极端的情况,可以用 @raw 原始 SQL 片段
#627

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants