Class: Plutonium::Resource::QueryObject
- Inherits:
-
Object
- Object
- Plutonium::Resource::QueryObject
- Defined in:
- lib/plutonium/resource/query_object.rb
Instance Attribute Summary collapse
-
#default_scope_name ⇒ Object
Returns the value of attribute default_scope_name.
-
#default_sort_config ⇒ Object
Returns the value of attribute default_sort_config.
-
#search_filter ⇒ Object
readonly
Returns the value of attribute search_filter.
-
#search_query ⇒ Object
readonly
Returns the value of attribute search_query.
Instance Method Summary collapse
-
#active_filter_descriptions ⇒ Object
Returns an array of hashes describing each currently active filter.
-
#all_scope_selected? ⇒ Boolean
Returns true if user explicitly selected “All” scope (no filtering).
-
#apply(scope, params, context: nil) ⇒ Object
Applies the defined filters and sorts to the given scope.
-
#build_url(**options) ⇒ String
Builds a URL with the given options for search and sorting.
-
#define_filter(name, body) ⇒ Object
Defines a filter with the given name and body.
-
#define_scope(name, body = nil) ⇒ Object
Defines a scope with the given name and body.
-
#define_search(body) ⇒ Object
Defines a search filter with the given body.
-
#define_sorter(name, body = nil, using: nil) ⇒ Object
Defines a sort with the given name and body.
- #filter_definitions ⇒ Object
-
#initialize(resource_class, params, request_path) {|_self| ... } ⇒ QueryObject
constructor
Initializes a QueryObject with the given resource_class and parameters.
- #scope_definitions ⇒ Object
-
#selected_scope ⇒ Object
Returns the currently selected scope (may be default if none explicitly selected).
- #sort_definitions ⇒ Object
-
#sort_params_for(name) ⇒ Hash?
Provides sorting parameters for the given field name.
Constructor Details
#initialize(resource_class, params, request_path) {|_self| ... } ⇒ QueryObject
Initializes a QueryObject with the given resource_class and parameters.
11 12 13 14 15 16 17 18 19 20 |
# File 'lib/plutonium/resource/query_object.rb', line 11 def initialize(resource_class, params, request_path, &) @resource_class = resource_class @params = params @request_path = request_path define_standard_queries yield self if block_given? extract_filter_params extract_sort_params end |
Instance Attribute Details
#default_scope_name ⇒ Object
Returns the value of attribute default_scope_name.
5 6 7 |
# File 'lib/plutonium/resource/query_object.rb', line 5 def default_scope_name @default_scope_name end |
#default_sort_config ⇒ Object
Returns the value of attribute default_sort_config.
5 6 7 |
# File 'lib/plutonium/resource/query_object.rb', line 5 def default_sort_config @default_sort_config end |
#search_filter ⇒ Object (readonly)
Returns the value of attribute search_filter.
4 5 6 |
# File 'lib/plutonium/resource/query_object.rb', line 4 def search_filter @search_filter end |
#search_query ⇒ Object (readonly)
Returns the value of attribute search_query.
4 5 6 |
# File 'lib/plutonium/resource/query_object.rb', line 4 def search_query @search_query end |
Instance Method Details
#active_filter_descriptions ⇒ Object
Returns an array of hashes describing each currently active filter. Each hash has: name, label, value_label, clear_url
133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 |
# File 'lib/plutonium/resource/query_object.rb', line 133 def active_filter_descriptions filter_definitions.filter_map do |name, filter| name = name.to_sym filter_params = params[name] next unless filter_params.present? value_label = case filter_params when Hash, ActionController::Parameters entries = filter_params.to_h.reject { |_, v| v.blank? } next if entries.empty? # Single-input filters defer to the filter's `humanize_value` # (e.g. Association resolves ids to labels, Boolean translates # "true" -> "Yes"). Multi-input filters keep input-name # qualifiers (e.g. "from 2024, to 2025"). if entries.size == 1 humanized = filter.humanize_value(entries.values.first) next if humanized.blank? humanized else entries.map { |k, v| "#{k.to_s.humanize.downcase} #{v}" }.join(", ") end when Array entries = filter_params.reject(&:blank?) next if entries.empty? humanized = filter.humanize_value(entries) next if humanized.blank? humanized else next if filter_params.to_s.blank? humanized = filter.humanize_value(filter_params) next if humanized.blank? humanized end { name: name, label: name.to_s.humanize, value_label: value_label, clear_url: build_url(name => nil) } end end |
#all_scope_selected? ⇒ Boolean
Returns true if user explicitly selected “All” scope (no filtering)
122 |
# File 'lib/plutonium/resource/query_object.rb', line 122 def all_scope_selected? = @all_scope_selected |
#apply(scope, params, context: nil) ⇒ Object
Applies the defined filters and sorts to the given scope.
109 110 111 112 113 114 115 116 117 |
# File 'lib/plutonium/resource/query_object.rb', line 109 def apply(scope, params, context: nil) params = deep_compact(params.with_indifferent_access) scope = search_filter.apply(scope, search: params[:search]) if search_filter && params[:search] # Use selected_scope which includes the default when no explicit selection effective_scope = @selected_scope_filter scope = scope_definitions[effective_scope].apply(scope, context:) if effective_scope && scope_definitions[effective_scope] scope = apply_sorts(scope, params) apply_filters(scope, params) end |
#build_url(**options) ⇒ String
Builds a URL with the given options for search and sorting.
68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 |
# File 'lib/plutonium/resource/query_object.rb', line 68 def build_url(**) q = {} q[:search] = .key?(:search) ? [:search].presence : search_query q[:scope] = if .key?(:scope) [:scope].presence else selected_scope_filter end if .delete(:replace) q[:sort_directions] = {} q[:sort_fields] = [] else q[:sort_directions] = selected_sort_directions.dup q[:sort_fields] = selected_sort_fields.dup end (q, ) filter_keys = filter_definitions.keys.map(&:to_sym) filter_overrides = .slice(*filter_keys).stringify_keys q.merge! params.with_indifferent_access.slice(*filter_definitions.keys) q.merge!(filter_overrides) compacted = deep_compact({q: q}) # Preserve explicit "All" selection (scope: nil in options means show all) if .key?(:scope) && [:scope].nil? compacted[:q] ||= {} compacted[:q][:scope] = "" end query_params = compacted.to_param "#{@request_path}?#{query_params}" end |
#define_filter(name, body) ⇒ Object
Defines a filter with the given name and body.
26 27 28 |
# File 'lib/plutonium/resource/query_object.rb', line 26 def define_filter(name, body, &) filter_definitions[name] = build_query(body, &) end |
#define_scope(name, body = nil) ⇒ Object
Defines a scope with the given name and body.
34 35 36 37 |
# File 'lib/plutonium/resource/query_object.rb', line 34 def define_scope(name, body = nil, **) body ||= name scope_definitions[name] = build_query(body) end |
#define_search(body) ⇒ Object
Defines a search filter with the given body.
57 58 59 60 61 |
# File 'lib/plutonium/resource/query_object.rb', line 57 def define_search(body) @search_filter = build_query(body) do |query| query.input :search end end |
#define_sorter(name, body = nil, using: nil) ⇒ Object
Defines a sort with the given name and body.
43 44 45 46 47 48 49 50 51 52 |
# File 'lib/plutonium/resource/query_object.rb', line 43 def define_sorter(name, body = nil, using: nil) if body.nil? sort_field = using || determine_sort_field(name) body = ->(scope, direction:) { scope.order(sort_field => direction) } end sort_definitions[name] = build_query(body) do |query| query.input :direction end end |
#filter_definitions ⇒ Object
127 |
# File 'lib/plutonium/resource/query_object.rb', line 127 def filter_definitions = @filter_definitions ||= {}.with_indifferent_access |
#scope_definitions ⇒ Object
119 |
# File 'lib/plutonium/resource/query_object.rb', line 119 def scope_definitions = @scope_definitions ||= {}.with_indifferent_access |
#selected_scope ⇒ Object
Returns the currently selected scope (may be default if none explicitly selected)
125 |
# File 'lib/plutonium/resource/query_object.rb', line 125 def selected_scope = @selected_scope_filter |
#sort_definitions ⇒ Object
129 |
# File 'lib/plutonium/resource/query_object.rb', line 129 def sort_definitions = @sort_definitions ||= {}.with_indifferent_access |
#sort_params_for(name) ⇒ Hash?
Provides sorting parameters for the given field name.
180 181 182 183 184 185 186 187 188 189 190 191 192 193 |
# File 'lib/plutonium/resource/query_object.rb', line 180 def sort_params_for(name) return unless sort_definitions[name] multi = selected_sort_fields.size > 1 && selected_sort_fields.include?(name.to_s) { url: build_url(sort: name, replace: true), multi_url: build_url(sort: name), reset_url: build_url(sort: name, reset: true), position: selected_sort_fields.index(name.to_s), direction: selected_sort_directions[name], multi: multi } end |