[英]Rails how to get an array parameter single quoted and comma seperated in a query.
[英]Rails query with array quoted using the asterisk parameter
我有一個函數,該函數采用*
參數作為傳遞數組的參數。
def has_role?(*role_names)
self.roles.where(:name => role_names).present?
end
我可以這樣稱呼它:
user.has_role?(['super admin', 'member'])
或喜歡
user.has_role?('super admin', 'member')
或喜歡
user.has_role?('member')
當我有兩個參數要傳遞時,如何使用一個列表和一個參數呢?
例如,我有另一個函數將范圍縮小到類似的查詢:
def has_account_role?(role_names, account)
self.account_user_roles.joins(:role).where('roles.name = ? AND account_id = ?', role_names, account.id).present?
end
如果我向has_account_role
這樣添加一個*
,例如has_account_role?(*role_names, account)
並調用user.has_account_role?(['member', 'supervisor'], account)
can't quote Array
收到錯誤消息: can't quote Array
我嘗試從= ?
更改查詢= ?
到IN (?)
但得到相同的問題。 如果我嘗試將查詢更改為...where(:name => role_names)...
我將失去作用域的role.name
提供了對關聯的過濾。
如何將數組傳遞到此查詢中而不使其變得過於完整或效率低下?
最簡單的方法是顛倒參數順序,然后讓splat( *
)吞沒所有不是account
:
def has_account_role?(account, *role_names)
然后,您會說出這樣的話:
user.has_account_role?(account, ['member', 'supervisor'])
user.has_account_role?(account, 'member', 'supervisor')
您還想在方法內部使用where
的哈希形式:
self.account_user_roles
.joins(:role)
.where(roles: { name: role_names }, account_id: account.id)
.present?
使where
可以使用相應的SQL( roles.name = ...
或roles.name in (...)
根據什么role_names
最終看起來像。
BTW,方法簽名中的splat:
def has_role?(*role_names)
#...
end
只需將方法的所有可貼標參數收集到一個數組中(在本例中稱為role_names
),但不會使該數組變平。 這意味着這兩個調用:
user.has_role?(['super admin', 'member'])
user.has_role?('super admin', 'member')
是不同的東西。 在第一個中, role_names
看起來像[['super admin', 'member']]
(即數組中的一個數組),在第二個中, role_names
只是['super admin', 'member']
(即一個簡單的數組)。 方法中的where(:name => role_names)
將使后面的數組變平,但就has_role?
它們仍然有很大不同has_role?
與調用者有關,而不是每個具有has_role?
方法has_role?
電話將扁平化陣列的方式where
呢。
考慮到這一點,您可能想要手動展平ssplats:
def has_role?(*role_names)
role_names = role_names.flatten
# Do whatever needs to be done now that you know that
# `role_names` is a flat array.
# ...
end
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.