【发布时间】:2020-10-05 06:03:31
【问题描述】:
我正在使用SQLite.swift,我想在类型安全的 API 中表示具有多个动态过滤条件的 SQL 语句。我发现了类似的问题,但没有一个提供任何关于如何实现这一点的见解。
到目前为止,我基本上会像这样构建我的查询(请注意,我的部分或全部 TextFields 可能是空的):
var filters: [String] = ["id != 0"]
if nameFilterTextField.text?.count ?? 0 > 0 {
filters.append("(firstName LIKE '\(nameFilterTextField.text ?? "")' OR lastName LIKE '\(nameFilterTextField.text ?? ""))'")
}
if(dateFromTextField.text?.count ?? 0 > 0 && dateToTextField.text?.count ?? 0 > 0){
let startdate = germanDateFormatter.date(from: dateFromTextField.text ?? "")!
let enddate = germanDateFormatter.date(from: dateToTextField.text ?? "")!
filters.append("savedAt BETWEEN datetime('\(sqlDateFormatter.string(from: startdate))') AND datetime('\(sqlDateFormatter.string(from: enddate))')")
}
if companyFilterTextField.text?.count ?? 0 > 0 {
filters.append("fromCompany LIKE '\(companyFilterTextField.text ?? "")'")
}
if contactPersonFilterTextField.text?.count ?? 0 > 0 {
filters.append("contactPoint LIKE '\(contactPersonFilterTextField.text ?? "")'")
}
if visitedFilterSegmentedControl.selectedSegmentIndex == 1 {
filters.append("visitedCompany = 'company1'")
}
else if visitedFilterSegmentedControl.selectedSegmentIndex == 2{
filters.append("visitedCompany = 'company2'")
}
let filterString = filters.joined(separator: " AND ")
然后我会以某种方式将该字符串附加到我的 SQL 语句中:
public func getData(limit: Int) -> [Visitor]{
var visitors = [Visitor]()
do{
for row in try db.prepare("SELECT * FROM visitors WHERE \(filterString) LIMIT \(limit) ORDER BY id DESC") {
let visitor: Visitor = Visitor(
id: row[id],
firstName: row[firstName],
lastName: row[lastName],
visitedCompany: row[visitedCompany],
savedAt: row[date],
fromCompany: row[fromCompany],
contactPoint: row[contactPoint])
visitors.append(visitor)
}
}
catch {
print("Could not get row: \(error)")
}
return visitors
}
但是上面的例子不起作用(我认为编译器无法键入检查该语句?/ Xcode 冻结...)。
但我仍然不想要使用原始 SQL 方法,而是希望使用 SQLite.swift 提供的类型安全 API,这样我的(不完整的)示例基本上看起来更像这个:
public func getData(limit: Int) -> [Visitor]{
var visitors = [Visitor]()
do{
for row in try db.prepare(visitorsTable.filter(/*what in here?*/).limit(limit, offset: 0).order(id.desc)) {
let visitor: Visitor = Visitor(
id: row[id],
firstName: row[firstName],
lastName: row[lastName],
visitedCompany: row[visitedCompany],
savedAt: row[date],
fromCompany: row[fromCompany],
contactPoint: row[contactPoint])
visitors.append(visitor)
}
}
catch {
print("Could not get row: \(error)")
}
return visitors
}
显然,我之前已经为我的示例定义了所有需要的变量...
【问题讨论】:
标签: ios swift sqlite sqlite.swift