diff --git a/README.md b/README.md
index 986f197..a01a2d4 100644
--- a/README.md
+++ b/README.md
@@ -54,15 +54,14 @@ end
+ `attribute_types`: hash used to specify the filter fields, ex. `{ title: Administrate::Field::String }`
+ `search_path`: the path to use for searching (form URL)
+ `namespace`: the namespace used by Administrate, ex. `:supervisor`
-- For associations (_has many_/_belongs to_) the label used can be customized adding an `admin_label` method to the target model which returns a string while the collection can by filtered with `admin_scope`. Example:
+- For associations (_has many_/_belongs to_) the label used can be customized adding an `display_resource` method to the target dashboard which returns a string. Example:
```rb
-# Sample post model
-class Post < ApplicationRecord
- scope :admin_scope, -> { where(published: true) }
-
- def admin_label
- title.upcase
+class PostDashboard < Administrate::BaseDashboard
+ # Overwrite this method to customize how posts are displayed
+ # across all pages of the admin dashboard.
+ def display_resource(post)
+ "##{post.id} #{post.title&.upcase}"
end
end
```
@@ -139,9 +138,11 @@ end
# In alternative prepare an hash in the dashboard like RANSACK_TYPES = {}
attribute_types = {
title: Administrate::Field::String,
+ title_or_description_cont: Administrate::Field::String,
author: Administrate::Field::BelongsTo,
category: Administrate::Field::Select.with_options(collection: Post.categories.to_a),
- published: Administrate::Field::Boolean
+ published: Administrate::Field::Boolean,
+ updated_at_lteq: Administrate::Field::Date
}
attribute_labels = {
author: 'Written by',
diff --git a/app/views/administrate_ransack/_filters.html.erb b/app/views/administrate_ransack/_filters.html.erb
index ca53b9f..44db5a9 100644
--- a/app/views/administrate_ransack/_filters.html.erb
+++ b/app/views/administrate_ransack/_filters.html.erb
@@ -21,7 +21,7 @@
<% attribute_types.each do |field, type| %>
<% next if field == :id %>
- <% label = attribute_labels.include?(field) ? attribute_labels[field] : field %>
+ <% label = attribute_labels.include?(field) ? attribute_labels[field] : nil %>
<% model = @ransack_results.klass %>
<% input_type = type.is_a?(Administrate::Field::Deferred) ? type.deferred_class.to_s : type.to_s %>
<% component = AdministrateRansack::FILTERS[input_type] || 'field_other' %>
diff --git a/app/views/administrate_ransack/components/_field_belongs_to.html.erb b/app/views/administrate_ransack/components/_field_belongs_to.html.erb
index 0fa4001..df45d0c 100644
--- a/app/views/administrate_ransack/components/_field_belongs_to.html.erb
+++ b/app/views/administrate_ransack/components/_field_belongs_to.html.erb
@@ -1,9 +1,10 @@
<% association = model.reflections[field.to_s] %>
<% if association %>
- <% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_id_eq" %>
- <% desc = association.klass.method_defined?(:admin_label) ? :admin_label : :to_s %>
- <% collection = association.klass.send(association.klass.respond_to?(:admin_scope) ? :admin_scope : :all) %>
+ <% field_key = AdministrateRansack.ransack?(model, {field => "1,2"}) ? field : "#{field}_id_eq" %>
+ <% label ||= AdministrateRansack.ransack?(model, {field => "1,2"}) ? field : "#{field}_id" %>
+ <% resource_field = type.new(field, nil, Administrate::Page::Collection.new(@dashboard), resource: model.new) %>
+ <% collection = resource_field.associated_resource_options %>
<%= form.label(label, class: 'filter-label') %>
- <%= form.collection_select(field_key, collection, :id, desc, include_blank: true) %>
+ <%= form.select("#{field}_id_eq", collection, { include_blank: true }, { class: 'selectize' }) %>
<% end %>
diff --git a/app/views/administrate_ransack/components/_field_boolean.html.erb b/app/views/administrate_ransack/components/_field_boolean.html.erb
index 66c0e66..ee24d29 100644
--- a/app/views/administrate_ransack/components/_field_boolean.html.erb
+++ b/app/views/administrate_ransack/components/_field_boolean.html.erb
@@ -1,5 +1,5 @@
-<% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_eq" %>
+<% field_key = AdministrateRansack.ransack?(model, {field => "true"}) ? field : "#{field}_eq" %>
<% values = [[t('administrate_ransack.filters.no'), false], [t('administrate_ransack.filters.yes'), true]] %>
-<%= form.label(label, class: 'filter-label') %>
+<%= form.label(label || field, class: 'filter-label') %>
<%= form.select(field_key, values, include_blank: true) %>
diff --git a/app/views/administrate_ransack/components/_field_date.html.erb b/app/views/administrate_ransack/components/_field_date.html.erb
index 3a3edef..9e8dd45 100644
--- a/app/views/administrate_ransack/components/_field_date.html.erb
+++ b/app/views/administrate_ransack/components/_field_date.html.erb
@@ -1,5 +1,5 @@
-<%= form.label(label, class: 'filter-label') %>
-<% if model.ransackable_scopes.include?(field) %>
+<%= form.label(label || field, class: 'filter-label') %>
+<% if AdministrateRansack.ransack?(model, {field => Date.today}) %>
<%= form.date_field(field, value: form.object.send(field)) %>
<% else %>
<%= form.date_field("#{field}_gteq") %>
diff --git a/app/views/administrate_ransack/components/_field_datetime.html.erb b/app/views/administrate_ransack/components/_field_datetime.html.erb
index 3966cb3..593d77a 100644
--- a/app/views/administrate_ransack/components/_field_datetime.html.erb
+++ b/app/views/administrate_ransack/components/_field_datetime.html.erb
@@ -1,5 +1,5 @@
-<%= form.label(label, class: 'filter-label') %>
-<% if model.ransackable_scopes.include?(field) %>
+<%= form.label(label || field, class: 'filter-label') %>
+<% if AdministrateRansack.ransack?(model, {field => DateTime.now}) %>
<%= form.datetime_field(field, value: form.object.send(field)) %>
<% else %>
<%= form.datetime_field("#{field}_gteq") %>
diff --git a/app/views/administrate_ransack/components/_field_has_many.html.erb b/app/views/administrate_ransack/components/_field_has_many.html.erb
index a60dc12..d968e3a 100644
--- a/app/views/administrate_ransack/components/_field_has_many.html.erb
+++ b/app/views/administrate_ransack/components/_field_has_many.html.erb
@@ -1,19 +1,17 @@
<% association = model.reflections[field.to_s] %>
<% if association %>
- <% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_id_in" %>
- <% desc = association.klass.method_defined?(:admin_label) ? :admin_label : :to_s %>
- <% collection = association.klass.send(association.klass.respond_to?(:admin_scope) ? :admin_scope : :all) %>
+ <% field_key = AdministrateRansack.ransack?(model, {field => "1,2"}) ? field : "#{field}_id_in" %>
+ <% resource_field = type.new(field, nil, Administrate::Page::Collection.new(@dashboard), resource: model.new) %>
+ <% collection = resource_field.associated_resource_options %>
- <%= form.label(label, class: 'filter-label') %>
+ <%= form.label(label || field_key, class: 'filter-label') %>
<% if options&.include? 'select' %>
- <%= form.select(field_key, nil, {}, multiple: true) do %>
- <%= options_from_collection_for_select(collection, :id, desc) %>
- <% end %>
+ <%= form.select(field_key, collection, {}, multiple: true) %>
<% else %>
- <%= form.collection_check_boxes(field_key, collection, :id, desc) do |b| %>
+ <%= form.collection_check_boxes(field_key, collection, :second, :first) do |b| %>
<%= b.label do %>
<%= b.check_box %>
- <%= b.object.send(desc) %>
+ <%= b.text %>
<% end %>
<% end %>
<% end %>
diff --git a/app/views/administrate_ransack/components/_field_number.html.erb b/app/views/administrate_ransack/components/_field_number.html.erb
index 4a732cd..a6ce474 100644
--- a/app/views/administrate_ransack/components/_field_number.html.erb
+++ b/app/views/administrate_ransack/components/_field_number.html.erb
@@ -1,4 +1,7 @@
-<% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_eq" %>
-
-<%= form.label(label, class: 'filter-label') %>
-<%= form.number_field(field_key) %>
+<%= form.label(label || field, class: 'filter-label') %>
+<% if AdministrateRansack.ransack?(model, {field => "1"}) %>
+ <%= form.number_field "#{field}" %>
+<% else %>
+ <%= form.number_field "#{field}_gteq" %>
+ <%= form.number_field "#{field}_lteq" %>
+<% end %>
diff --git a/app/views/administrate_ransack/components/_field_other.html.erb b/app/views/administrate_ransack/components/_field_other.html.erb
index bac210d..52c3cd8 100644
--- a/app/views/administrate_ransack/components/_field_other.html.erb
+++ b/app/views/administrate_ransack/components/_field_other.html.erb
@@ -1,5 +1,12 @@
-<%= form.label(label, class: 'filter-label') %>
-<%= form.search_field(field) %>
+<% if AdministrateRansack.ransack?(model, {field => "valid"}) %>
+ <%= form.label(label || field, class: 'filter-label') %>
+ <%= form.search_field(field) %>
+<% elsif AdministrateRansack.ransack?(model, {"#{field}_cont" => "valid"}) %>
+ <%= form.label(label || "#{field}_cont", class: 'filter-label') %>
+ <%= form.search_field("#{field}_cont") %>
+<% else %>
+ <%# render nothing %>
+<% end %>
<%# unsupported Field::HasOne %>
<%# unsupported Field::Polymorphic %>
diff --git a/app/views/administrate_ransack/components/_field_select.html.erb b/app/views/administrate_ransack/components/_field_select.html.erb
index 5698415..61ee11e 100644
--- a/app/views/administrate_ransack/components/_field_select.html.erb
+++ b/app/views/administrate_ransack/components/_field_select.html.erb
@@ -1,5 +1,5 @@
<% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_eq" %>
<% collection = (type.respond_to?(:options) ? type.options[:collection] : []) || [] %>
-<%= form.label(label, class: 'filter-label') %>
+<%= form.label(label || field, class: 'filter-label') %>
<%= form.select(field_key, collection, include_blank: true) %>
diff --git a/app/views/administrate_ransack/components/_field_string.html.erb b/app/views/administrate_ransack/components/_field_string.html.erb
index 4630c61..ed5c15d 100644
--- a/app/views/administrate_ransack/components/_field_string.html.erb
+++ b/app/views/administrate_ransack/components/_field_string.html.erb
@@ -1,4 +1,9 @@
-<% field_key = model.ransackable_scopes.include?(field) ? field : "#{field}_cont" %>
-
-<%= form.label(label, class: 'filter-label') %>
-<%= form.search_field(field_key) %>
+<% if AdministrateRansack.ransack?(model, {field => "valid"}) %>
+ <%= form.label(label || field, class: 'filter-label') %>
+ <%= form.search_field(field) %>
+<% elsif AdministrateRansack.ransack?(model, {"#{field}_cont" => "valid"}) %>
+ <%= form.label(label || "#{field}_cont", class: 'filter-label') %>
+ <%= form.search_field("#{field}_cont") %>
+<% else %>
+ <%# render nothing %>
+<% end %>
diff --git a/lib/administrate_ransack.rb b/lib/administrate_ransack.rb
index 093d2fb..bc6962b 100644
--- a/lib/administrate_ransack.rb
+++ b/lib/administrate_ransack.rb
@@ -2,6 +2,7 @@
require 'administrate_ransack/engine'
require 'administrate_ransack/filters'
+require 'administrate_ransack/helpers'
require 'administrate_ransack/searchable'
require 'administrate_ransack/version'
diff --git a/lib/administrate_ransack/helpers.rb b/lib/administrate_ransack/helpers.rb
new file mode 100644
index 0000000..863026c
--- /dev/null
+++ b/lib/administrate_ransack/helpers.rb
@@ -0,0 +1,10 @@
+# frozen_string_literal: true
+
+module AdministrateRansack
+ class << self
+ def ransack?(model, params = {}, options = {})
+ ransack = model.ransack(params, **options)
+ ransack.instance_variable_get(:@scope_args).present? || ransack.base.c.present?
+ end
+ end
+end
diff --git a/spec/dummy/app/controllers/admin/authors_controller.rb b/spec/dummy/app/controllers/admin/authors_controller.rb
index a0a02a8..1c655d0 100644
--- a/spec/dummy/app/controllers/admin/authors_controller.rb
+++ b/spec/dummy/app/controllers/admin/authors_controller.rb
@@ -1,5 +1,7 @@
module Admin
class AuthorsController < Admin::ApplicationController
+ prepend AdministrateRansack::Searchable
+
# Overwrite any of the RESTful controller actions to implement custom behavior
# For example, you may want to send an email after a foo is updated.
#
diff --git a/spec/dummy/app/dashboards/author_dashboard.rb b/spec/dummy/app/dashboards/author_dashboard.rb
index 4f7755d..c94e141 100644
--- a/spec/dummy/app/dashboards/author_dashboard.rb
+++ b/spec/dummy/app/dashboards/author_dashboard.rb
@@ -39,6 +39,16 @@ class AuthorDashboard < Administrate::BaseDashboard
# published_posts
# recent_posts
+ # RANSACK_TYPES
+ RANSACK_TYPES = {
+ posts: Field::HasMany,
+ tags: Field::HasMany,
+ name: Field::String,
+ name_or_email_cont: Field::String,
+ name_not_cont: Field::String,
+ age: Field::Number
+ }.freeze
+
# SHOW_PAGE_ATTRIBUTES
# an array of attributes that will be displayed on the model's show page.
SHOW_PAGE_ATTRIBUTES = %i[
diff --git a/spec/dummy/app/dashboards/tag_dashboard.rb b/spec/dummy/app/dashboards/tag_dashboard.rb
index 1b2af4c..3bbc29d 100644
--- a/spec/dummy/app/dashboards/tag_dashboard.rb
+++ b/spec/dummy/app/dashboards/tag_dashboard.rb
@@ -63,7 +63,7 @@ class TagDashboard < Administrate::BaseDashboard
# Overwrite this method to customize how tags are displayed
# across all pages of the admin dashboard.
#
- # def display_resource(tag)
- # "Tag ##{tag.id}"
- # end
+ def display_resource(tag)
+ "##{tag.id} #{tag.name}"
+ end
end
diff --git a/spec/dummy/app/views/admin/authors/index.html.erb b/spec/dummy/app/views/admin/authors/index.html.erb
new file mode 100644
index 0000000..ea57540
--- /dev/null
+++ b/spec/dummy/app/views/admin/authors/index.html.erb
@@ -0,0 +1,17 @@
+
+ <%= render(
+ "collection",
+ collection_presenter: page,
+ collection_field_name: resource_name,
+ page: page,
+ resources: resources,
+ table_title: "page-title"
+ ) %>
+
+ <%= paginate resources, param_name: '_page' %>
+
+
+<%= render(
+ 'administrate_ransack/filters',
+ attribute_types: @dashboard.class::RANSACK_TYPES
+) %>
diff --git a/spec/dummy/app/views/admin/posts/index.html.erb b/spec/dummy/app/views/admin/posts/index.html.erb
index 7b798a6..2be3f9e 100644
--- a/spec/dummy/app/views/admin/posts/index.html.erb
+++ b/spec/dummy/app/views/admin/posts/index.html.erb
@@ -49,6 +49,7 @@
category: Administrate::Field::Select.with_options(collection: Post.categories.to_a),
published: Administrate::Field::Boolean,
position: Administrate::Field::Number,
+ position_eq: Administrate::Field::Number,
tags: Administrate::Field::HasMany,
dt: Administrate::Field::Date,
created_at: Administrate::Field::DateTime,
diff --git a/spec/rails_helper.rb b/spec/rails_helper.rb
index 11239d2..725cdb8 100644
--- a/spec/rails_helper.rb
+++ b/spec/rails_helper.rb
@@ -42,7 +42,7 @@ def setup_data
author = Author.find_by!(name: 'A test author')
tag = Tag.find_by!(name: 'A test tag')
Post.first.update!(title: 'A post', author: author, category: 'news', published: true, dt: Time.zone.today)
- Post.second.update!(title: 'Another post', author: author, category: 'story', dt: Date.yesterday, tags: [tag])
+ Post.second.update!(title: 'Another post', author: author, category: 'story', position: 123, dt: Date.yesterday, tags: [tag])
Post.third.update!(title: 'Last post', author: author, category: 'news', position: 234, dt: Date.tomorrow)
end
end
diff --git a/spec/system/number_filter_spec.rb b/spec/system/number_filter_spec.rb
index 270255e..a5981fa 100644
--- a/spec/system/number_filter_spec.rb
+++ b/spec/system/number_filter_spec.rb
@@ -2,6 +2,18 @@
RSpec.describe 'Number filter' do
let(:post3) { Post.third }
+ let(:author1) { Author.first }
+
+ it 'filters the authors by age range', :aggregate_failures do
+ visit '/admin/authors'
+
+ fill_in('q[age_lteq]', with: '28')
+ find('input[type="submit"]').click
+
+ expect(page).to have_current_path %r{/admin/authors\?.+q%5Bage_lteq%5D=28.*}
+ expect(page).to have_css('.js-table-row', count: 2)
+ expect(page).to have_css('.js-table-row a.action-show', text: author1.name)
+ end
it 'filters the posts by position', :aggregate_failures do
visit '/admin/posts'
diff --git a/spec/system/string_filter_spec.rb b/spec/system/string_filter_spec.rb
index 75c3a06..a2985b8 100644
--- a/spec/system/string_filter_spec.rb
+++ b/spec/system/string_filter_spec.rb
@@ -2,6 +2,33 @@
RSpec.describe 'String filter' do
let(:post2) { Post.second }
+ let(:author11) { Author.find(11) }
+
+ it 'filters the authors by name or email', :aggregate_failures do
+ visit '/admin/authors'
+
+ fill_in('q[name_or_email_cont]', with: '@bbb')
+ find('input[type="submit"]').click
+
+ expect(page).to have_css('.js-table-row', count: 1)
+ expect(page).to have_css('.js-table-row a.action-show', text: author11.name)
+
+ fill_in('q[name_or_email_cont]', with: 'A test')
+ find('input[type="submit"]').click
+
+ expect(page).to have_css('.js-table-row', count: 1)
+ expect(page).to have_css('.js-table-row a.action-show', text: author11.name)
+ end
+
+ it 'filters the authors by name not contain', :aggregate_failures do
+ visit '/admin/authors'
+
+ fill_in('q[name_not_cont]', with: 'A test')
+ find('input[type="submit"]').click
+
+ expect(page).to have_css('.js-table-row', count: 10)
+ expect(page).not_to have_css('.js-table-row a.action-show', text: author11.name)
+ end
it 'filters the posts by title', :aggregate_failures do
visit '/admin/posts'