Searching tags with Ransack
NicWickman opened this issue · 12 comments
I think this would be a common desire, so I'm posting here with my trouble. I'm loving how simple Gutentag is, adding tags is no problem. But I would like to search through them with Ransack.
Whether by adding tag_names
or tags_as_string
as a ransackable_attribute
, I get a undefined method
type' for nil:NilClass` error.
How can I return a proper tag attribute for Ransack to search for? Could you provide instructions for getting Gutentag to work with Ransack?
Hi Nic,
I'm not familiar with Ransack, but from a quick look through its README suggests an attribute like "tags_name" might do the trick? i.e. referring to the underlying association and column. Do let me know if it works :)
Thank you for such a quick reply!
Unfortunately I am getting the same error.
I'm a little short on context here because of not knowing Ransack well. Can you share the code you're using to try this with? i.e. is it in the form? The controller?
I am searching from a view with Ransack's seach_form_for
:
<%= f.text_field :title_or_content_or_tag_names_cont, placeholder: params.dig(:q, :title_or_content_or_tag_names_cont) %>
and in the controller, which throws the error:
@resources = @q.result(distinct: true).paginate(:page => params[:page])
to define ransack's searchable parameters, I add tag_names as a "ransackable parameter" in the model
def self.ransackable_attributes(auth_object = nil)
['title','content','tag_names']
end
I think it needs to be tags_name
- with the pluralisation on the association (tags), not the column (name).
Sorry for the confusion, I've tried that as well. Not sure exactly how useful this is to you since you are not familiar with Ransack (thank you for trying regardless!), the error occurs here:
ransack (1.8.8) lib/ransack/adapters/active_record/context.rb:34:in type_for' ransack (1.8.8) lib/ransack/nodes/attribute.rb:35:in
type'
return ransacker.type
else
context.type_for(self)
end
end
If I search for an attribute which I know exists ("ID", for example) I do not get this error, so I am confident my implementation is not wrong.
PS: It's late in my timezone, I'll check back tomorrow :)
Hmm. What about tags.name
(full stop instead of underscore)? Also, you may want to add includes(:tags)
to your call?
@resources = @q.result(distinct: true).includes(:tags).paginate(:page => params[:page])
No luck. search_form_for won't take tags.name
Sorry, I really should have been more specific. Does putting it in ransackable_attributes
work?
Hi Pat! A kind soul on stackoverflow knew how to make this work, I'll quote him below for yourself and anyone who wanders here.
This happens because there is no column tag_names in your table. Thus you need to define ransackable_attributes for gutentag_tags table, because that is the table whose name column is called under the hood. Create an initializer for gutentag in config/initializers directory, name it however you like. In that initializer put the following:
if ActiveRecord::Base.connection.table_exists? 'gutentag_tags'
model = Object.const_get "Gutentag::Tag"
model.singleton_class.class_eval do
define_method(:ransackable_attributes) do |auth_object|
auth_object = nil
['name']
end
end
end
Ah, great to know you got it figured out, and thanks for sharing the solution!