activeadmin-searchable_select 1.3.0 → 1.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6a0f1ed4c7ca3f0b20a9a1844aa46ecf2693b5b91f447874cbfbc013d5a84e31
4
- data.tar.gz: cdca70eae83da1caf578f39957b66fe30cec69a76c67f7f06d2a45bb3c680f7d
3
+ metadata.gz: 86f2b11107d464955292c9d5a51629757ff3fb213aafdeb9302b948f421796ee
4
+ data.tar.gz: 961efac5444a994afac0b8a13437bbd96ec8effedbbc6356b606a9d23bc80849
5
5
  SHA512:
6
- metadata.gz: b509e473b24b32cad8c401f197413c7b01c7de196aaf0a2a4a735f7f6bd40d4ea76ed7733f9b00f87ecf23e6d3aba0bceee599f85c4e39fb1a17639b4234d94f
7
- data.tar.gz: f224c6cc6fe60af0373b1d82c9d57a43282c3f327bf5c3c295d2b1d17ce5f9aace56aa0d4320405f40783a270fedaa8137496712091fc167712b9b1e1364a029
6
+ metadata.gz: 79b204c1f6af56e2d39c4ee658cfde5af5ca31733ed3d2eb657ab78a8de66511b9e7387dd5fa64a457768095c67858e64f3fd598058ef1458fceba0575880522
7
+ data.tar.gz: 9bcbd53a3504788a0c18ce8f701efefcc2f0495625eedf277a30c738c5083d4b3a4602fdd95c05ca904ad8b0034e551ea1706a46f077805c5b0146f0121ee2fc
@@ -1,5 +1,9 @@
1
1
  name: tests
2
- on: [push, pull_request]
2
+ on:
3
+ push:
4
+ pull_request:
5
+ schedule:
6
+ - cron: '45 2 * * *'
3
7
 
4
8
  jobs:
5
9
  rspec:
@@ -31,4 +35,4 @@ jobs:
31
35
  ruby-version: ${{ matrix.ruby-version }}
32
36
  bundler-cache: true
33
37
  - name: Run tests
34
- run: bundle exec rspec
38
+ run: bundle exec rspec
data/.rubocop.yml CHANGED
@@ -1,5 +1,7 @@
1
1
  AllCops:
2
2
  TargetRubyVersion: 2.3
3
+ Exclude:
4
+ - 'bin/**/*'
3
5
 
4
6
  # The default of 80 characters is a little to narrow.
5
7
  Metrics/LineLength:
data/CHANGELOG.md CHANGED
@@ -1,20 +1,14 @@
1
1
  # CHANGELOG
2
2
 
3
- ### Version 1.3.0
3
+ ### Version 1.6.0
4
4
 
5
- 2021-02-03
5
+ 2022-04-05
6
6
 
7
- [Compare changes](https://github.com/codevise/activeadmin-searchable_select/compare/1-2-stable...v1.3.0)
7
+ [Compare changes](https://github.com/codevise/activeadmin-searchable_select/compare/1-5-stable...v1.6.0)
8
8
 
9
- - Add support for Ruby 3
10
- ([#26](https://github.com/codevise/activeadmin-searchable_select/pull/26))
11
- - Add a small description of how to pass options to Select2
12
- ([#27](https://github.com/codevise/activeadmin-searchable_select/pull/27))
13
- - Update CI Setup
14
- ([#25](https://github.com/codevise/activeadmin-searchable_select/pull/25))
15
- - Allow Bundler 2 in development dependencies
16
- ([#18](https://github.com/codevise/activeadmin-searchable_select/pull/18))
9
+ - Add option to pass path params for nested resource fetching
10
+ ([#39](https://github.com/codevise/activeadmin-searchable_select/pull/39))
17
11
 
18
12
  See
19
- [1-2-stable branch](https://github.com/codevise/activeadmin-searchable_select/blob/1-2-stable/CHANGELOG.md)
13
+ [1-5-stable branch](https://github.com/codevise/activeadmin-searchable_select/blob/1-5-stable/CHANGELOG.md)
20
14
  for previous changes.
data/README.md CHANGED
@@ -193,6 +193,25 @@ build your query in a way that it can query multiple attributes at once.
193
193
 
194
194
  In this example, the `all` scope will query `email OR username`.
195
195
 
196
+ You can add the additional payload as dsl option:
197
+
198
+ ```ruby
199
+ ActiveAdmin.register Category do
200
+ searchable_select_options(scope: Category.all,
201
+ text_attribute: :name,
202
+ additional_payload: ->(record) { { foo: record.bar } } )
203
+ end
204
+ ```
205
+
206
+ response example which uses additional_payload:
207
+
208
+ ```json
209
+ {
210
+ "results": [{ "id": "1", "text": "Bicycles", "foo": "Bar" }],
211
+ "pagination": { "more": "false" }
212
+ }
213
+ ```
214
+
196
215
  #### Passing Parameters
197
216
 
198
217
  You can pass additional parameters to the options endpoint:
@@ -223,6 +242,67 @@ argument:
223
242
  end
224
243
  ```
225
244
 
245
+ #### Path options for nested resources
246
+
247
+ Example for the following setup:
248
+
249
+ ```ruby
250
+ # Models
251
+ class OptionType < ActiveRecord::Base; end
252
+
253
+ class OptionValue < ActiveRecord::Base
254
+ belongs_to :option_type
255
+ end
256
+
257
+ class Product < ActiveRecord::Base
258
+ belongs_to :option_type
259
+ has_many :variants
260
+ end
261
+
262
+ class Variant < ActiveRecord::Base
263
+ belongs_to :product
264
+ belongs_to :option_value
265
+ end
266
+
267
+ # ActiveAdmin
268
+ ActiveAdmin.register(OptionType)
269
+
270
+ ActiveAdmin.register(Product)
271
+
272
+ ActiveAdmin.register(OptionValue) do
273
+ belongs_to :option_type
274
+ searchable_select_options(scope: lambda do |params|
275
+ OptionValue.where(
276
+ option_type_id: params[:option_type_id]
277
+ )
278
+ end,
279
+ text_attribute: :value)
280
+ end
281
+ ```
282
+
283
+ It is possible to pass path parameters for correctly generating URLs for nested resources fetching via `path_params`
284
+
285
+ ```ruby
286
+ ActiveAdmin.register(Variant) do
287
+ belongs_to :product
288
+
289
+ form do |f|
290
+ ...
291
+ f.input(:option_value,
292
+ as: :searchable_select,
293
+ ajax: {
294
+ resource: OptionValue,
295
+ path_params: {
296
+ option_type_id: f.object.product.option_type_id
297
+ }
298
+ })
299
+ ...
300
+ end
301
+ end
302
+ ```
303
+
304
+ This will generate the path for fetching as `all_options_admin_option_type_option_values(option_type_id: f.object.product.option_type_id)` (e.g. `/admin/option_types/2/option_values/all_options`)
305
+
226
306
  #### Inlining Ajax Options in Feature Tests
227
307
 
228
308
  When writing UI driven feature specs (i.e. with Capybara),
@@ -238,7 +318,7 @@ for feature specs:
238
318
  ```ruby
239
319
  RSpec.configure do |config|
240
320
  config.before(:each) do |example|
241
- ActiveAdmin::Select2.inline_ajax_options = (example.metadata[:type] == :feature)
321
+ ActiveAdmin::SearchableSelect.inline_ajax_options = (example.metadata[:type] == :feature)
242
322
  end
243
323
  end
244
324
 
@@ -246,7 +326,7 @@ for feature specs:
246
326
 
247
327
  ### Passing options to Select2
248
328
 
249
- It is possible to pass and define configuration options to Select2
329
+ It is possible to pass and define configuration options to Select2
250
330
  via `data-attributes` using nested (subkey) options.
251
331
 
252
332
  Attributes need to be added to the `input_html` option in the form input.
@@ -8,6 +8,7 @@ module ActiveAdmin
8
8
  @display_text = extract_display_text_option(options)
9
9
  @filter = extract_filter_option(options)
10
10
  @per_page = options.fetch(:per_page, 10)
11
+ @additional_payload = options.fetch(:additional_payload, {})
11
12
  end
12
13
 
13
14
  def scope(template, params)
@@ -38,7 +39,7 @@ module ActiveAdmin
38
39
  {
39
40
  id: record.id,
40
41
  text: display_text(record)
41
- }
42
+ }.merge(hash_of_additional_payload(record) || {})
42
43
  end
43
44
 
44
45
  { results: results, pagination: { more: more } }
@@ -98,6 +99,21 @@ module ActiveAdmin
98
99
  ->(term, scope) { scope.ransack("#{text_attribute}_cont" => term).result }
99
100
  end
100
101
  end
102
+
103
+ def build_additional_payload(record)
104
+ case @additional_payload
105
+ when Proc
106
+ @additional_payload.call(record).to_h
107
+ else
108
+ {}
109
+ end
110
+ end
111
+
112
+ def hash_of_additional_payload(record)
113
+ return nil if @additional_payload.nil? && @additional_payload.empty?
114
+
115
+ build_additional_payload(record)
116
+ end
101
117
  end
102
118
  end
103
119
  end
@@ -26,6 +26,23 @@ module ActiveAdmin
26
26
  #
27
27
  # @param name [Symbol] Optional collection name if helper is
28
28
  # used multiple times within one resource.
29
+ #
30
+ # @param additional_payload [Proc]
31
+ # Adds additional attributes to the results array
32
+ # @example
33
+ #
34
+ # ActiveAdmin.register Tag do
35
+ # searchable_select_options(
36
+ # scope: Color,
37
+ # text_attributes: :title,
38
+ # additional_payload: lambda { |record| { color: record.color } }
39
+ # )
40
+ # end
41
+ # @json
42
+ # {
43
+ # "results": [{ "id": "1", "text": "Red", "color": "#FFF" }],
44
+ # "pagination": { "more": "false" }
45
+ # }
29
46
  def searchable_select_options(name: :all, **options)
30
47
  option_collection = OptionCollection.new(name, options)
31
48
  config.searchable_select_option_collections[name] = option_collection
@@ -20,6 +20,10 @@ module ActiveAdmin
20
20
  # - `params`: Hash of query parameters that shall be passed to the
21
21
  # options endpoint.
22
22
  #
23
+ # - `path_params`: Hash of parameters, which would be passed to the
24
+ # dynamic collection path generation for the resource.
25
+ # e.g `admin_articles_path(path_params)`
26
+ #
23
27
  # If the `ajax` option is present, the `collection` option is
24
28
  # ignored.
25
29
  module SelectInputExtension
@@ -45,9 +49,11 @@ module ActiveAdmin
45
49
 
46
50
  def ajax_url
47
51
  return unless options[:ajax]
48
- template.polymorphic_path([template.active_admin_namespace.route_prefix, ajax_resource_class],
49
- action: option_collection.collection_action_name,
50
- **ajax_params)
52
+ [ajax_resource.route_collection_path(path_params),
53
+ '/',
54
+ option_collection.collection_action_name,
55
+ '?',
56
+ ajax_params.to_query].join
51
57
  end
52
58
 
53
59
  def all_options_collection
@@ -122,6 +128,10 @@ module ActiveAdmin
122
128
  ajax_options.fetch(:params, {})
123
129
  end
124
130
 
131
+ def path_params
132
+ ajax_options.fetch(:path_params, {})
133
+ end
134
+
125
135
  def ajax_options
126
136
  options[:ajax] == true ? {} : options[:ajax]
127
137
  end
@@ -1,5 +1,5 @@
1
1
  module ActiveAdmin
2
2
  module SearchableSelect
3
- VERSION = '1.3.0'.freeze
3
+ VERSION = '1.6.0'.freeze
4
4
  end
5
5
  end
@@ -5,60 +5,180 @@ require 'support/capybara'
5
5
  require 'support/active_admin_helpers'
6
6
 
7
7
  RSpec.describe 'end to end', type: :feature, js: true do
8
- before(:each) do
9
- ActiveAdminHelpers.setup do
10
- ActiveAdmin.register(Category) do
11
- searchable_select_options(scope: Category, text_attribute: :name)
12
- end
8
+ context 'class name without namespaces' do
9
+ before(:each) do
10
+ ActiveAdminHelpers.setup do
11
+ ActiveAdmin.register(Category) do
12
+ searchable_select_options(scope: Category, text_attribute: :name)
13
+ end
13
14
 
14
- ActiveAdmin.register(Post) do
15
- filter(:category, as: :searchable_select, ajax: true)
15
+ ActiveAdmin.register(Post) do
16
+ filter(:category, as: :searchable_select, ajax: true)
16
17
 
17
- form do |f|
18
- f.input(:category, as: :searchable_select, ajax: true)
18
+ form do |f|
19
+ f.input(:category, as: :searchable_select, ajax: true)
20
+ end
19
21
  end
22
+
23
+ ActiveAdmin.setup {}
20
24
  end
25
+ end
26
+
27
+ describe 'index page with searchable select filter' do
28
+ it 'loads filter input options' do
29
+ Category.create(name: 'Music')
30
+ Category.create(name: 'Travel')
31
+
32
+ visit '/admin/posts'
33
+
34
+ expand_select_box
35
+ wait_for_ajax
36
+
37
+ expect(select_box_items).to eq(%w(Music Travel))
38
+ end
39
+
40
+ it 'allows filtering options by term' do
41
+ Category.create(name: 'Music')
42
+ Category.create(name: 'Travel')
43
+
44
+ visit '/admin/posts'
21
45
 
22
- ActiveAdmin.setup {}
46
+ expand_select_box
47
+ enter_search_term('T')
48
+ wait_for_ajax
49
+
50
+ expect(select_box_items).to eq(%w(Travel))
51
+ end
52
+
53
+ it 'loads more items when scrolling down' do
54
+ 15.times { |i| Category.create(name: "Category #{i}") }
55
+ visit '/admin/posts'
56
+
57
+ expand_select_box
58
+ wait_for_ajax
59
+ scroll_select_box_list
60
+ wait_for_ajax
61
+
62
+ expect(select_box_items.size).to eq(15)
63
+ end
23
64
  end
24
65
  end
25
66
 
26
- describe 'index page with searchable select filter' do
27
- it 'loads filter input options' do
28
- Category.create(name: 'Music')
29
- Category.create(name: 'Travel')
30
-
31
- visit '/admin/posts'
67
+ context 'class name with namespace' do
68
+ before(:each) do
69
+ ActiveAdminHelpers.setup do
70
+ ActiveAdmin.register RGB::Color, as: 'color' do
71
+ searchable_select_options scope: RGB::Color, text_attribute: :code
72
+ end
32
73
 
33
- expand_select_box
34
- wait_for_ajax
74
+ ActiveAdmin.register Internal::TagName, as: 'Tag Name' do
75
+ filter :color, as: :searchable_select, ajax: { resource: RGB::Color }
76
+ end
35
77
 
36
- expect(select_box_items).to eq(%w(Music Travel))
78
+ ActiveAdmin.setup {}
79
+ end
37
80
  end
38
81
 
39
- it 'allows filtering options by term' do
40
- Category.create(name: 'Music')
41
- Category.create(name: 'Travel')
82
+ describe 'index page with searchable select filter' do
83
+ it 'loads filter input options' do
84
+ RGB::Color.create(code: '#eac112', description: 'Orange')
85
+ RGB::Color.create(code: '#19bf25', description: 'Green')
42
86
 
43
- visit '/admin/posts'
87
+ visit '/admin/tag_names'
44
88
 
45
- expand_select_box
46
- enter_search_term('T')
47
- wait_for_ajax
89
+ expand_select_box
90
+ wait_for_ajax
48
91
 
49
- expect(select_box_items).to eq(%w(Travel))
92
+ expect(select_box_items).to eq(%w(#eac112 #19bf25))
93
+ end
50
94
  end
95
+ end
51
96
 
52
- it 'loads more items when scrolling down' do
53
- 15.times { |i| Category.create(name: "Category #{i}") }
54
- visit '/admin/posts'
97
+ context 'class with nested belongs_to association' do
98
+ before(:all) do
99
+ ActiveAdminHelpers.setup do
100
+ ActiveAdmin.register(OptionType)
101
+
102
+ ActiveAdmin.register(Product)
103
+
104
+ ActiveAdmin.register(OptionValue) do
105
+ belongs_to :option_type
106
+ searchable_select_options(scope: lambda do |params|
107
+ OptionValue.where(
108
+ option_type_id: params[:option_type_id]
109
+ )
110
+ end,
111
+ text_attribute: :value)
112
+ end
55
113
 
56
- expand_select_box
57
- wait_for_ajax
58
- scroll_select_box_list
59
- wait_for_ajax
114
+ ActiveAdmin.register(Variant) do
115
+ belongs_to :product
116
+
117
+ form do |f|
118
+ input :price
119
+ input(:option_value,
120
+ as: :searchable_select,
121
+ ajax: {
122
+ resource: OptionValue,
123
+ path_params: {
124
+ option_type_id: f.object.product.option_type_id
125
+ }
126
+ })
127
+ end
128
+ end
60
129
 
61
- expect(select_box_items.size).to eq(15)
130
+ ActiveAdmin.setup {}
131
+ end
132
+ end
133
+
134
+ describe 'new page with searchable select filter' do
135
+ it 'loads filter input options' do
136
+ option_type = OptionType.create(name: 'Color')
137
+ ot = OptionType.create(name: 'Size')
138
+ OptionValue.create(value: 'Black', option_type: option_type)
139
+ OptionValue.create(value: 'Orange', option_type: option_type)
140
+ OptionValue.create(value: 'M', option_type: ot)
141
+ product = Product.create(name: 'Cap', option_type: option_type)
142
+
143
+ visit "/admin/products/#{product.id}/variants/new"
144
+
145
+ expand_select_box
146
+ wait_for_ajax
147
+
148
+ expect(select_box_items).to eq(%w(Black Orange))
149
+ end
150
+
151
+ it 'allows filtering options by term' do
152
+ option_type = OptionType.create(name: 'Color')
153
+ ot = OptionType.create(name: 'Size')
154
+ OptionValue.create(value: 'Black', option_type: option_type)
155
+ OptionValue.create(value: 'Orange', option_type: option_type)
156
+ OptionValue.create(value: 'M', option_type: ot)
157
+ product = Product.create(name: 'Cap', option_type: option_type)
158
+
159
+ visit "/admin/products/#{product.id}/variants/new"
160
+
161
+ expand_select_box
162
+ enter_search_term('O')
163
+ wait_for_ajax
164
+
165
+ expect(select_box_items).to eq(%w(Orange))
166
+ end
167
+
168
+ it 'loads more items when scrolling down' do
169
+ option_type = OptionType.create(name: 'Color')
170
+ 15.times { |i| OptionValue.create(value: "Black #{i}", option_type: option_type) }
171
+ product = Product.create(name: 'Cap', option_type: option_type)
172
+
173
+ visit "/admin/products/#{product.id}/variants/new"
174
+
175
+ expand_select_box
176
+ wait_for_ajax
177
+ scroll_select_box_list
178
+ wait_for_ajax
179
+
180
+ expect(select_box_items.size).to eq(15)
181
+ end
62
182
  end
63
183
  end
64
184
 
@@ -140,6 +140,60 @@ RSpec.describe 'searchable_select_options dsl', type: :request do
140
140
  end
141
141
  end
142
142
 
143
+ describe 'with additional_payload' do
144
+ context 'as lambda' do
145
+ before(:each) do
146
+ ActiveAdminHelpers.setup do
147
+ ActiveAdmin.register(Post) do
148
+ searchable_select_options(
149
+ scope: Post,
150
+ text_attribute: :title,
151
+ additional_payload: lambda do |record|
152
+ { published: record.published }
153
+ end
154
+ )
155
+ end
156
+ end
157
+ end
158
+ let!(:post) { Post.create!(title: 'A post', published: false) }
159
+
160
+ subject { get '/admin/posts/all_options' }
161
+
162
+ it 'returns options with our additional attribute' do
163
+ subject
164
+ expect(json_response).to match(
165
+ results: [{ text: 'A post', id: post.id, published: false }],
166
+ pagination: { more: false }
167
+ )
168
+ end
169
+ end
170
+
171
+ context 'as Proc' do
172
+ before(:each) do
173
+ ActiveAdminHelpers.setup do
174
+ ActiveAdmin.register(Post) do
175
+ searchable_select_options(
176
+ scope: Post,
177
+ text_attribute: :title,
178
+ additional_payload: proc { |record| { published: record.published } }
179
+ )
180
+ end
181
+ end
182
+ end
183
+ let!(:post) { Post.create!(title: 'A post', published: false) }
184
+
185
+ subject { get '/admin/posts/all_options' }
186
+
187
+ it 'returns options with our additional attribute' do
188
+ subject
189
+ expect(json_response).to match(
190
+ results: [{ text: 'A post', id: post.id, published: false }],
191
+ pagination: { more: false }
192
+ )
193
+ end
194
+ end
195
+ end
196
+
143
197
  it 'allows passing lambda as scope' do
144
198
  ActiveAdminHelpers.setup do
145
199
  ActiveAdmin.register(Post) do
@@ -20,6 +20,37 @@ ActiveRecord::Schema.define do
20
20
  t.boolean :published
21
21
  end
22
22
 
23
+ create_table(:rgb_colors, force: true) do |t|
24
+ t.string :code
25
+ t.text :description
26
+ end
27
+
28
+ create_table(:internal_tag_names, force: true) do |t|
29
+ t.string :name
30
+ t.text :description
31
+ t.integer :color_id
32
+ end
33
+
34
+ create_table(:option_types, force: true) do |t|
35
+ t.string :name
36
+ end
37
+
38
+ create_table(:option_values, force: true) do |t|
39
+ t.string :value
40
+ t.belongs_to :option_type
41
+ end
42
+
43
+ create_table(:products, force: true) do |t|
44
+ t.string :name
45
+ t.belongs_to :option_type
46
+ end
47
+
48
+ create_table(:variants, force: true) do |t|
49
+ t.integer :price
50
+ t.belongs_to :product
51
+ t.belongs_to :option_value
52
+ end
53
+
23
54
  create_table(:users, force: true) do |t|
24
55
  t.string :name
25
56
  end
@@ -1,9 +1,13 @@
1
1
  module ActiveAdminHelpers
2
2
  module_function
3
3
 
4
+ def reload_routes!
5
+ Rails.application.reload_routes!
6
+ end
7
+
4
8
  def setup
5
9
  ActiveAdmin.application = nil
6
10
  yield
7
- Rails.application.reload_routes!
11
+ reload_routes!
8
12
  end
9
13
  end
@@ -13,6 +13,36 @@ class Post < ActiveRecord::Base
13
13
  scope(:published, -> { where(published: true) })
14
14
  end
15
15
 
16
+ module RGB
17
+ class Color < ActiveRecord::Base
18
+ self.table_name = :rgb_colors
19
+ has_many :tags, class_name: 'Internal::TagName'
20
+ end
21
+ end
22
+
23
+ module Internal
24
+ class TagName < ActiveRecord::Base
25
+ self.table_name = :internal_tag_names
26
+ belongs_to :color, class_name: 'RGB::Color', foreign_key: :color_id
27
+ end
28
+ end
29
+
30
+ class OptionType < ActiveRecord::Base; end
31
+
32
+ class OptionValue < ActiveRecord::Base
33
+ belongs_to :option_type
34
+ end
35
+
36
+ class Product < ActiveRecord::Base
37
+ belongs_to :option_type
38
+ has_many :variants
39
+ end
40
+
41
+ class Variant < ActiveRecord::Base
42
+ belongs_to :product
43
+ belongs_to :option_value
44
+ end
45
+
16
46
  RSpec.configure do |config|
17
47
  config.after do
18
48
  DatabaseCleaner.strategy = :truncation
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: activeadmin-searchable_select
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.0
4
+ version: 1.6.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Codevise Solutions Ltd
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-02-03 00:00:00.000000000 Z
11
+ date: 2022-04-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -375,7 +375,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
375
375
  - !ruby/object:Gem::Version
376
376
  version: '0'
377
377
  requirements: []
378
- rubygems_version: 3.2.3
378
+ rubygems_version: 3.0.8
379
379
  signing_key:
380
380
  specification_version: 4
381
381
  summary: Use searchable selects based on Select2 in Active Admin forms and filters.