我已經在這樣的實體,使用GORM存儲在數據庫(I省略不相關的字段):GORM - 變化3個查詢到1(或至少2)
class Payment {
static hasMany = [paymentEntries: PaymentEntry]
}
class PaymentEntry {
static hasOne = [category: PaymentCategory]
static belongsTo = [payment: Payment]
static constraints = {
category(nullable: true)
}
}
class PaymentCategory {
static hasMany = [payments: PaymentEntry, rules: PaymentRule]
String name
}
因此,我們必須在頂部付款,從而可以有許多PaymentEntry,並且每個PaymentEntry可以屬於一個PaymentCategory。
我需要選擇Payments,它符合一些條件,但只有那些也具有屬於特定類別的PaymentEntries的Payments。目前,我這樣做是在3個查詢:
選擇類別,其適合的類別名稱的一部分,或者只是省略類別查詢(在我們希望無論他們的作品類別的所有付款這種情況下):
private static List<PaymentCategory> getCategories(String category) { def result = null if (category != null && category.length() > 0) { def c = PaymentCategory.createCriteria() result = c { ilike("name", "%${category}%") } } result }
選擇PaymentEntries IDS,基於PaymentCategory:
private static List<Long> paymentEntryIds(String category) { def categories = getCategories(category) def c = PaymentEntry.createCriteria() def result = new ArrayList() // If category is selected, but there is no matching category, return empty list if (!categorySelectedButNoMatch(category, categories)) { result = c { if (category == null) { isNull("category") } else if (categories != null && categories.size() > 0) { inList("category", categories) } projections { property("id") } } } result }
最後選擇付款,僅限於包含特定Paymen的那些tEntries:
def paymentEntriesIds = paymentEntryIds(selectedCategory) def c = Payment.createCriteria() def result = new ArrayList() // If there are no payment entries matching category criteria, we return empty list anyway, so there // is no need querying payments. if (paymentEntriesIds.size() > 0) { result = c { paymentEntries { inList("id", paymentEntriesIds) } if (importEntryId != null) { eq("importEntry.id", importEntryId) } if (query != null) { ilike("description", query) } // Omitted ordering and paging } } result
這工作,但它運行3個數據庫查詢。我很確定這個代碼可以更清晰,並且可以在更少的查詢中完成。歡迎所有關於如何改進它的想法。
想一想使用連接。在付款標準 – user3718614