假設有一組資料,類似下面
選擇搜尋條件時,可能不選(不設條件代表全部)或多選
| id | user | state | 
|---|---|---|
| 1 | test1 | done | 
| 2 | test1 | done | 
| 3 | test2 | undone | 
| 4 | test2 | done | 
| 5 | test3 | undone | 
搜尋條件
user = [] or ["test1"] or ["test1", "test2"] or ...
state = [] or ["done"] or ["done", "undone"]
問題:
使用 SQlalchemy 或是其他方式(SQL 或是 Javascript)
可能在一種語句下去滿足這些可能嗎?不然就要用判斷式寫不同的語句了
例如 ? 依狀況代入
WHERE user = ? and state IN ?
各 1
user = ["test1"]
state = ["done"]
WHERE user = "test1" and state = "done"
結果
1 | test1 | done
2 | test1 | done
不選
user = []
state = ["undone"]
WHERE state = "done" # 省略 and
結果
3 | test2 | undone
5 | test3 | undone
多選
user = ["test1", "test2"]
state = ["done"]
WHERE user IN ("test1", "test2") and state = "done"
結果
1 | test1 | done
2 | test1 | done
4 | test2 | done
目前研究大概知道前面 2 種可以用 **kwargs 代入來避開 and
但列表要改用 in 時是否適用呢
query = {
    "user": "test1"
}
filter(**query) # 不行
filter_by(**query) # 可以
filter(user == "test1").filter(state ==??) # 不行
備註:補充,以 SQLAlchemy 來說
filter_by 才可以使用 **kwargs 代入
但語法只有簡單的相等比較,無法滿足較複雜的搜尋
參考 data
data = [
    {
    "id":1,
    "user":"test1",
    "state": "done"
    },
    {
    "id":2,
    "user":"test1",
    "state": "done"
    },
    {
    "id":3,
    "user":"test2",
    "state": "undone"
    },
    {
    "id":4,
    "user":"test2",
    "state": "done"
    },
    {
    "id":5,
    "user":"test3",
    "state": "undone"
    },
]
query = {
    "user": ["test1"],
    "state":["done", "undone"]
}
當使用 SQLAlchemy 進行查詢時,你可以使用 filter 方法來設定查詢條件。在這個例子中,我們將演示如何使用 in 和普通的相等條件,以及如何使用 **kwargs 傳入條件。
假設你有一個 SQLAlchemy 的模型叫做 User,並且這個模型有兩個屬性:id 和 status。下面是一個查詢的範例:
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
from your_module import User  # 假設 User 是你的模型
# 建立資料庫連線
engine = create_engine('sqlite:///my_database.db')
Session = sessionmaker(bind=engine)
session = Session()
# 假設這是你從 **kwargs 中獲得的條件
query_conditions = {
    'id': [1, 2, 3],  # 用於 in 條件
    'status': 'active'  # 用於相等條件
}
# 建立查詢
query = session.query(User)
# 加入條件
if 'id' in query_conditions:
    query = query.filter(User.id.in_(query_conditions['id']))
if 'status' in query_conditions:
    query = query.filter(User.status == query_conditions['status'])
# 執行查詢並獲取結果
results = query.all()
# 輸出結果
for user in results:
    print(f"User ID: {user.id}, Status: {user.status}")
在這個範例中,我們使用了 filter 方法來添加查詢條件。如果 id 在 query_conditions 中存在,我們使用 User.id.in_() 來設定 in 條件;如果 status 在 query_conditions 中存在,我們使用 User.status == 來設定相等條件。
這樣你就可以根據不同的查詢條件進行動態的查詢,並使用 **kwargs 來方便地傳入條件。
query = {
    "user": ["test1"],
    "state":["done", "undone"]
}
query["user"] = User.id.in_(query["user"])
query["state"] = User.state.in_(query["state"])
filter(**query)
這樣不就好了...
題外話,django的orm就只要在前端的key改成 user_id__in,就可以直接用。