I'm trying to access a model method in a Ruby on Rails rabl template but I'm having trouble figuring out how to pass in an argument to the function. Here's the model code -
class Conversation < ActiveRecord::Base
has_many :messages, dependent: :destroy
belongs_to :sender, foreign_key: :sender_id, class_name: User
belongs_to :recipient, foreign_key: :recipient_id, class_name: User
def opposed_user(user)
user == recipient ? sender : recipient
end
end
And here's my rabl template file -
collection @conversations, object_root: false
attributes :id, :sender_id, :recipient_id
node :otheruser do |c|
c.opposed_user(current_user)
end
Specifically it's the opposed_user
that I'm trying to return but the error I'm getting with the above is wrong number of arguments (0 for 1)
. current_user
is returning the correct user ok so is this is simple thing or am I going about it in the wrong way?
Update
If I use c.opposed_user(current_user).to_json
it works however the json is returning an escaped string rather than the actual json object. I think maybe I need to use child instead of node but not sure.
It sounds like you were fairly close to solving this. You can use as_json
instead of to_json
to fix the RABL template you already have.
The final template would look like this:
collection @conversations, object_root: false
attributes :id, :sender_id, :recipient_id
node :otheruser do |c|
c.opposed_user(current_user).as_json
end
With RABL, there are a number of different ways to handle things. When you use node
, it will simply add one key if you provide a string. Since to_json
returns a string, you end up with something like { otheruser: "whatever string you provided" }
.
However, if you use as_json
, you'll end up providing a hash which node
can also handle. For example, like this:
node :otheruser do |c|
{ id: 1, name: 'Bob' }
end
You'll end up with JSON that looks like: { otheruser: { id: 1, name: 'Bob' } }
. Here's a link to the documentation on node in RABL.