garden_variety 2.0 → 4.0.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 +5 -5
- data/README.md +165 -111
- data/Rakefile +1 -27
- data/lib/garden_variety/actions.rb +17 -24
- data/lib/garden_variety/controller.rb +172 -153
- data/lib/garden_variety/railtie.rb +4 -15
- data/lib/garden_variety/talent_scout.rb +28 -0
- data/lib/garden_variety/version.rb +1 -1
- data/lib/garden_variety.rb +13 -0
- data/lib/generators/garden/install/install_generator.rb +3 -1
- data/lib/generators/garden/install/templates/locales/flash.en.yml +11 -0
- data/lib/generators/garden/optimized_generate_action.rb +14 -0
- data/lib/generators/garden/scaffold/scaffold_generator.rb +12 -1
- metadata +17 -46
- data/lib/generators/garden/install/templates/locales/garden_variety.en.yml +0 -10
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
|
-
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: dd6dd125edefcf640a8a2aa1b629510eb3e5526551abfea71738b661c9fe1d83
|
|
4
|
+
data.tar.gz: ec5a4e29f8e1937dd74a88d11fdf087394a95cf67c56ceca177e9ce5fb9ae89e
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: bd41cf0735bfabe753a7bb4b5138d76a5e9c572952d5d4fb344f344dfe44926258c1a64ffe67b66875fcae5b09d9640fb8dfb8ce742a812bcbb0cfcad80b0d21
|
|
7
|
+
data.tar.gz: ba7d049d2952075c9a431dbd76b9ced59abc89918dfdbe589a7e8e183654a769669e6396e6e4546984bddf2057e7164a7f921ee849dacdee59c1f2d1ead39177
|
data/README.md
CHANGED
|
@@ -2,16 +2,15 @@
|
|
|
2
2
|
|
|
3
3
|
Delightfully boring Rails controllers. One of the superb advantages of
|
|
4
4
|
Ruby on Rails is convention over configuration. Opinionated default
|
|
5
|
-
behavior can decrease development time
|
|
5
|
+
behavior can decrease development time and increase application
|
|
6
6
|
robustness (less custom code == less that can go wrong). In service of
|
|
7
7
|
this principle, *garden_variety* provides reasonable default controller
|
|
8
8
|
actions, with care to allow easy override.
|
|
9
9
|
|
|
10
|
-
*garden_variety* also
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
stay DRY and boring.
|
|
10
|
+
*garden_variety* also relies on the [Pundit](https://rubygems.org/gems/pundit)
|
|
11
|
+
gem to isolate authorization concerns. If you're unfamiliar with
|
|
12
|
+
Pundit, see its documentation for an explanation of policy objects and
|
|
13
|
+
how they help controller actions stay DRY and boring.
|
|
15
14
|
|
|
16
15
|
As an example, this controller using `garden_variety`...
|
|
17
16
|
|
|
@@ -27,29 +26,26 @@ end
|
|
|
27
26
|
class PostsController < ApplicationController
|
|
28
27
|
|
|
29
28
|
def index
|
|
30
|
-
authorize(
|
|
31
|
-
self.
|
|
29
|
+
authorize(self.class.model_class)
|
|
30
|
+
self.collection = policy_scope(find_collection)
|
|
32
31
|
end
|
|
33
32
|
|
|
34
33
|
def show
|
|
35
|
-
self.
|
|
36
|
-
authorize(resource)
|
|
34
|
+
self.model = authorize(find_model)
|
|
37
35
|
end
|
|
38
36
|
|
|
39
37
|
def new
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
self.resource = new_resource
|
|
44
|
-
authorize(resource)
|
|
38
|
+
self.model = authorize(new_model)
|
|
39
|
+
if params.key?(self.class.model_class.model_name.param_key)
|
|
40
|
+
assign_attributes(model)
|
|
45
41
|
end
|
|
46
42
|
end
|
|
47
43
|
|
|
48
44
|
def create
|
|
49
|
-
self.
|
|
50
|
-
if
|
|
45
|
+
self.model = assign_attributes(authorize(new_model))
|
|
46
|
+
if model.save
|
|
51
47
|
flash[:success] = flash_message(:success)
|
|
52
|
-
redirect_to
|
|
48
|
+
redirect_to model
|
|
53
49
|
else
|
|
54
50
|
flash.now[:error] = flash_message(:error)
|
|
55
51
|
render :new
|
|
@@ -57,15 +53,14 @@ class PostsController < ApplicationController
|
|
|
57
53
|
end
|
|
58
54
|
|
|
59
55
|
def edit
|
|
60
|
-
self.
|
|
61
|
-
authorize(resource)
|
|
56
|
+
self.model = authorize(find_model)
|
|
62
57
|
end
|
|
63
58
|
|
|
64
59
|
def update
|
|
65
|
-
self.
|
|
66
|
-
if
|
|
60
|
+
self.model = assign_attributes(authorize(find_model))
|
|
61
|
+
if model.save
|
|
67
62
|
flash[:success] = flash_message(:success)
|
|
68
|
-
redirect_to
|
|
63
|
+
redirect_to model
|
|
69
64
|
else
|
|
70
65
|
flash.now[:error] = flash_message(:error)
|
|
71
66
|
render :edit
|
|
@@ -73,9 +68,8 @@ class PostsController < ApplicationController
|
|
|
73
68
|
end
|
|
74
69
|
|
|
75
70
|
def destroy
|
|
76
|
-
self.
|
|
77
|
-
|
|
78
|
-
if resource.destroy
|
|
71
|
+
self.model = authorize(find_model)
|
|
72
|
+
if model.destroy
|
|
79
73
|
flash[:success] = flash_message(:success)
|
|
80
74
|
redirect_to action: :index
|
|
81
75
|
else
|
|
@@ -86,80 +80,82 @@ class PostsController < ApplicationController
|
|
|
86
80
|
|
|
87
81
|
private
|
|
88
82
|
|
|
89
|
-
def
|
|
83
|
+
def self.model_class
|
|
90
84
|
Post
|
|
91
85
|
end
|
|
92
86
|
|
|
93
|
-
def
|
|
87
|
+
def collection
|
|
94
88
|
@posts
|
|
95
89
|
end
|
|
96
90
|
|
|
97
|
-
def
|
|
91
|
+
def collection=(models)
|
|
98
92
|
@posts = models
|
|
99
93
|
end
|
|
100
94
|
|
|
101
|
-
def
|
|
95
|
+
def model
|
|
102
96
|
@post
|
|
103
97
|
end
|
|
104
98
|
|
|
105
|
-
def
|
|
99
|
+
def model=(model)
|
|
106
100
|
@post = model
|
|
107
101
|
end
|
|
108
102
|
|
|
109
|
-
def
|
|
110
|
-
|
|
103
|
+
def find_collection
|
|
104
|
+
self.class.model_class.all
|
|
111
105
|
end
|
|
112
106
|
|
|
113
|
-
def
|
|
114
|
-
|
|
107
|
+
def find_model
|
|
108
|
+
self.class.model_class.find(params[:id])
|
|
115
109
|
end
|
|
116
110
|
|
|
117
|
-
def
|
|
118
|
-
|
|
111
|
+
def new_model
|
|
112
|
+
self.class.model_class.new
|
|
119
113
|
end
|
|
120
114
|
|
|
121
|
-
def
|
|
122
|
-
authorize(model)
|
|
115
|
+
def assign_attributes(model)
|
|
123
116
|
model.assign_attributes(permitted_attributes(model))
|
|
124
117
|
model
|
|
125
118
|
end
|
|
126
119
|
|
|
127
120
|
def flash_options
|
|
128
|
-
{
|
|
121
|
+
{ model_name: "Post" }
|
|
129
122
|
end
|
|
130
123
|
|
|
131
124
|
def flash_message(status)
|
|
132
125
|
keys = [
|
|
133
|
-
:"posts.#{action_name}.#{status}",
|
|
134
|
-
:"posts.#{action_name}.#{status}_html",
|
|
135
|
-
:"
|
|
136
|
-
:"
|
|
137
|
-
:"
|
|
138
|
-
:"
|
|
126
|
+
:"flash.posts.#{action_name}.#{status}",
|
|
127
|
+
:"flash.posts.#{action_name}.#{status}_html",
|
|
128
|
+
:"flash.#{action_name}.#{status}",
|
|
129
|
+
:"flash.#{action_name}.#{status}_html",
|
|
130
|
+
:"flash.#{status}",
|
|
131
|
+
:"flash.#{status}_html",
|
|
139
132
|
]
|
|
140
|
-
helpers.translate(keys.first, default: keys.drop(1), **flash_options)
|
|
133
|
+
helpers.translate(keys.first, { default: keys.drop(1), **flash_options })
|
|
141
134
|
end
|
|
142
135
|
|
|
143
136
|
end
|
|
144
137
|
```
|
|
145
138
|
|
|
146
|
-
The
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
[
|
|
152
|
-
(Note that the
|
|
153
|
-
|
|
139
|
+
The `::model_class` method returns a class corresponding to the
|
|
140
|
+
controller name, by default. That value can be overridden using the
|
|
141
|
+
matching `::model_class=` setter. The `model` / `collection` accessor
|
|
142
|
+
method definitions are dictated by `::model_class`. The rest of the
|
|
143
|
+
methods can be overridden as normal, a la carte. For a detailed
|
|
144
|
+
description of method behavior, see the [API documentation](
|
|
145
|
+
https://www.rubydoc.info/gems/garden_variety/). (Note that the
|
|
146
|
+
`authorize`, `policy_scope`, and `permitted_attributes` methods are
|
|
147
|
+
provided by Pundit.)
|
|
154
148
|
|
|
155
149
|
|
|
156
150
|
## Scaffold generator
|
|
157
151
|
|
|
158
|
-
*garden_variety* includes a scaffold generator similar to the
|
|
159
|
-
scaffold generator:
|
|
152
|
+
*garden_variety* includes a `garden:scaffold` generator similar to the
|
|
153
|
+
Rails `scaffold` generator:
|
|
160
154
|
|
|
161
155
|
```
|
|
162
156
|
$ rails generate garden:scaffold post title:string body:text published:boolean
|
|
157
|
+
exist config/locales
|
|
158
|
+
create config/locales/flash.en.yml
|
|
163
159
|
generate resource
|
|
164
160
|
invoke active_record
|
|
165
161
|
create db/migrate/19991231235959_create_posts.rb
|
|
@@ -176,11 +172,6 @@ $ rails generate garden:scaffold post title:string body:text published:boolean
|
|
|
176
172
|
invoke helper
|
|
177
173
|
create app/helpers/posts_helper.rb
|
|
178
174
|
invoke test_unit
|
|
179
|
-
invoke assets
|
|
180
|
-
invoke coffee
|
|
181
|
-
create app/assets/javascripts/posts.coffee
|
|
182
|
-
invoke scss
|
|
183
|
-
create app/assets/stylesheets/posts.scss
|
|
184
175
|
invoke resource_route
|
|
185
176
|
route resources :posts
|
|
186
177
|
generate erb:scaffold
|
|
@@ -190,6 +181,7 @@ $ rails generate garden:scaffold post title:string body:text published:boolean
|
|
|
190
181
|
create app/views/posts/show.html.erb
|
|
191
182
|
create app/views/posts/new.html.erb
|
|
192
183
|
create app/views/posts/_form.html.erb
|
|
184
|
+
create app/views/posts/_post.html.erb
|
|
193
185
|
insert app/controllers/posts_controller.rb
|
|
194
186
|
generate pundit:policy
|
|
195
187
|
create app/policies/post_policy.rb
|
|
@@ -206,14 +198,23 @@ generator in a few small ways:
|
|
|
206
198
|
* No jbuilder templates. Only HTML templates are generated.
|
|
207
199
|
* `rails generate pundit:policy` is invoked for the specified model.
|
|
208
200
|
|
|
201
|
+
Additionally, if you are using the [talent_scout] gem, the scaffold
|
|
202
|
+
generator will invoke `rails generate talent_scout:search` for the
|
|
203
|
+
specified model. This behavior can be disabled with the
|
|
204
|
+
`--skip-talent-scout` option. For more information about integrating
|
|
205
|
+
with *talent_scout*, see the [Searching with talent_scout](
|
|
206
|
+
#searching-with-talent_scout) section below.
|
|
207
|
+
|
|
208
|
+
[talent_scout]: https://rubygems.org/gems/talent_scout
|
|
209
|
+
|
|
209
210
|
|
|
210
211
|
## Flash messages
|
|
211
212
|
|
|
212
213
|
Flash messages are defined using I18n. The *garden_variety* installer
|
|
213
214
|
(`rails generate garden:install`) will create a
|
|
214
|
-
"config/locales/
|
|
215
|
-
|
|
216
|
-
|
|
215
|
+
"config/locales/flash.en.yml" file containing default "success" and
|
|
216
|
+
"error" messages. You can edit this file to customize those messages,
|
|
217
|
+
or add your own translation files to support other languages.
|
|
217
218
|
|
|
218
219
|
As seen in the `PostsController#flash_message` method in the example
|
|
219
220
|
above, a prioritized list of keys are tried when retrieving a flash
|
|
@@ -226,12 +227,11 @@ Internationalization guide for more information.)
|
|
|
226
227
|
|
|
227
228
|
Interpolation in flash messages is also supported (as described by
|
|
228
229
|
[Passing Variables to Translations]), with interpolation values provided
|
|
229
|
-
by the `flash_options` method. By default, `flash_options` provides
|
|
230
|
-
`
|
|
231
|
-
it to provide your own values.
|
|
230
|
+
by the `flash_options` method. By default, `flash_options` provides a
|
|
231
|
+
`model_name` value, but you can override it to provide your own values.
|
|
232
232
|
|
|
233
|
-
[Safe HTML Translations]:
|
|
234
|
-
[Passing Variables to Translations]:
|
|
233
|
+
[Safe HTML Translations]: https://guides.rubyonrails.org/i18n.html#using-safe-html-translations
|
|
234
|
+
[Passing Variables to Translations]: https://guides.rubyonrails.org/i18n.html#passing-variables-to-translations
|
|
235
235
|
|
|
236
236
|
|
|
237
237
|
## Beyond garden variety behavior
|
|
@@ -240,46 +240,105 @@ it to provide your own values.
|
|
|
240
240
|
written, including in situations where custom code is unavoidable.
|
|
241
241
|
|
|
242
242
|
|
|
243
|
-
###
|
|
243
|
+
### Eliminating N+1 queries
|
|
244
|
+
|
|
245
|
+
With proper Russian doll caching, [N+1 queries can be a feature](
|
|
246
|
+
https://youtu.be/ktZLpjCanvg?t=4m27s). But, if you need to eliminate
|
|
247
|
+
an N+1 query by using eager loading, you can override the
|
|
248
|
+
`find_collection` method:
|
|
249
|
+
|
|
250
|
+
```ruby
|
|
251
|
+
class PostsController < ApplicationController
|
|
252
|
+
garden_variety
|
|
253
|
+
|
|
254
|
+
def find_collection
|
|
255
|
+
super.includes(:author)
|
|
256
|
+
end
|
|
257
|
+
end
|
|
258
|
+
```
|
|
259
|
+
|
|
244
260
|
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
261
|
+
### Pagination
|
|
262
|
+
|
|
263
|
+
You can integrate your favorite pagination gem (*may I suggest
|
|
264
|
+
[moar](https://rubygems.org/gems/moar)?*) by overriding the
|
|
265
|
+
`find_collection` method:
|
|
248
266
|
|
|
249
267
|
```ruby
|
|
250
268
|
class PostsController < ApplicationController
|
|
251
269
|
garden_variety
|
|
252
270
|
|
|
253
|
-
def
|
|
254
|
-
|
|
271
|
+
def find_collection
|
|
272
|
+
moar(super.order(:created_at))
|
|
255
273
|
end
|
|
256
274
|
end
|
|
257
275
|
```
|
|
258
276
|
|
|
259
277
|
|
|
260
|
-
###
|
|
278
|
+
### Searching
|
|
261
279
|
|
|
262
|
-
You can
|
|
263
|
-
|
|
280
|
+
You can provide search functionality by overriding the `find_collection`
|
|
281
|
+
method:
|
|
264
282
|
|
|
265
283
|
```ruby
|
|
266
284
|
class PostsController < ApplicationController
|
|
267
285
|
garden_variety
|
|
268
286
|
|
|
269
|
-
def
|
|
270
|
-
params[:
|
|
287
|
+
def find_collection
|
|
288
|
+
params[:title] ? super.where("title LIKE ?", "%#{params[:title]}%") : super
|
|
271
289
|
end
|
|
272
290
|
end
|
|
273
291
|
```
|
|
274
292
|
|
|
293
|
+
#### Searching with talent_scout
|
|
294
|
+
|
|
295
|
+
If you are using the [talent_scout] gem, the default implementation of
|
|
296
|
+
`find_collection` will automatically instantiate your model search class
|
|
297
|
+
-- no custom code required. For example, if a `PostSearch` class is
|
|
298
|
+
defined, `PostsController#find_collection` will be equivalent to:
|
|
299
|
+
|
|
300
|
+
```ruby
|
|
301
|
+
def find_collection
|
|
302
|
+
@search = PostSearch.new(params[:q])
|
|
303
|
+
@search.results
|
|
304
|
+
end
|
|
305
|
+
```
|
|
306
|
+
|
|
307
|
+
Notice, as a side effect, the `@search` instance variable is set for
|
|
308
|
+
later use in the view.
|
|
275
309
|
|
|
276
|
-
|
|
310
|
+
The model search class will be chosen based on the controller's
|
|
311
|
+
`::model_class`. For example:
|
|
277
312
|
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
313
|
+
```ruby
|
|
314
|
+
class MyPostsController < ApplicationController
|
|
315
|
+
garden_variety
|
|
316
|
+
|
|
317
|
+
self.model_class = Post # find_collection will use PostSearch instead of MyPostSearch
|
|
318
|
+
end
|
|
319
|
+
```
|
|
320
|
+
|
|
321
|
+
If a corresponding model search class is not defined, `find_collection`
|
|
322
|
+
will fall back to its original non-search behavior.
|
|
323
|
+
|
|
324
|
+
Alternatively, you can override the model search class directly:
|
|
325
|
+
|
|
326
|
+
```ruby
|
|
327
|
+
class MyPostsController < ApplicationController
|
|
328
|
+
garden_variety
|
|
329
|
+
|
|
330
|
+
self.model_class = Post
|
|
331
|
+
self.model_search_class = MyPostSearch # find_collection will use MyPostSearch
|
|
332
|
+
end
|
|
333
|
+
```
|
|
334
|
+
|
|
335
|
+
|
|
336
|
+
### Server-generated JavaScript Responses (SJR)
|
|
337
|
+
|
|
338
|
+
SJR controller actions are generally the same as conventional controller
|
|
339
|
+
actions, with one difference: non-GET SJR actions render instead of
|
|
340
|
+
redirect on success. *garden_variety* provides a concise syntax for
|
|
341
|
+
overriding only the on-success behavior of non-GET actions:
|
|
283
342
|
|
|
284
343
|
```ruby
|
|
285
344
|
class PostsController < ApplicationController
|
|
@@ -323,7 +382,7 @@ messages. If a redirect is replaced with a render, the flash message
|
|
|
323
382
|
will be set such that it does not affect the next request.
|
|
324
383
|
|
|
325
384
|
|
|
326
|
-
###
|
|
385
|
+
### Authentication
|
|
327
386
|
|
|
328
387
|
The details of integrating authentication will depend on your chosen
|
|
329
388
|
authentication library. [Devise](https://rubygems.org/gems/devise) is
|
|
@@ -359,7 +418,7 @@ this conflict, add the following line to your Clearance initializer:
|
|
|
359
418
|
```
|
|
360
419
|
|
|
361
420
|
|
|
362
|
-
###
|
|
421
|
+
### Form Objects
|
|
363
422
|
|
|
364
423
|
The Form Object pattern is used to mitigate the complexity of handling
|
|
365
424
|
forms which need special processing logic, such as context-dependent
|
|
@@ -399,10 +458,10 @@ end
|
|
|
399
458
|
In this example, only the `new` and `create` actions are generated by
|
|
400
459
|
the `garden_variety` macro. The on-success behavior of `create` is
|
|
401
460
|
overridden to redirect to `root_path`, using the concise syntax
|
|
402
|
-
discussed in the [
|
|
403
|
-
The *garden_variety* controller helper methods all work as
|
|
404
|
-
because `RegistrationForm` responds to `assign_attributes` and
|
|
405
|
-
and has a default (nullary) constructor.
|
|
461
|
+
discussed in the [Server-generated JavaScript Responses (SJR)](#server-generated-javascript-responses-sjr)
|
|
462
|
+
example. The *garden_variety* controller helper methods all work as
|
|
463
|
+
expected because `RegistrationForm` responds to `assign_attributes` and
|
|
464
|
+
`save`, and has a default (nullary) constructor.
|
|
406
465
|
|
|
407
466
|
|
|
408
467
|
### Non-REST actions
|
|
@@ -430,20 +489,21 @@ end
|
|
|
430
489
|
|
|
431
490
|
```ruby
|
|
432
491
|
class PublishedPostsController < ApplicationController
|
|
433
|
-
|
|
492
|
+
self.model_class = Post
|
|
493
|
+
garden_variety :index
|
|
434
494
|
|
|
435
|
-
def
|
|
495
|
+
def find_collection
|
|
436
496
|
super.where(published: true)
|
|
437
497
|
end
|
|
438
498
|
end
|
|
439
499
|
```
|
|
440
500
|
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
`
|
|
444
|
-
|
|
501
|
+
Notice the call to `::model_class=`. The model class for
|
|
502
|
+
`PublishedPostsController` is overridden as `Post` instead of derived as
|
|
503
|
+
`PublishedPost`. And because of this override, the `@posts` instance
|
|
504
|
+
variable will be used instead of `@published_posts`.
|
|
445
505
|
|
|
446
|
-
This example may be somewhat contrived, but
|
|
506
|
+
This example may be somewhat contrived, but here is an excellent talk
|
|
447
507
|
from RailsConf which delves deeper into the principle:
|
|
448
508
|
[In Relentless Pursuit of REST](https://www.youtube.com/watch?v=HctYHe-YjnE)
|
|
449
509
|
([slides](https://speakerdeck.com/derekprior/in-relentless-pursuit-of-rest)).
|
|
@@ -451,19 +511,13 @@ from RailsConf which delves deeper into the principle:
|
|
|
451
511
|
|
|
452
512
|
## Installation
|
|
453
513
|
|
|
454
|
-
Add
|
|
455
|
-
|
|
456
|
-
```ruby
|
|
457
|
-
gem "garden_variety"
|
|
458
|
-
```
|
|
459
|
-
|
|
460
|
-
Then execute:
|
|
514
|
+
Add the gem to your Gemfile:
|
|
461
515
|
|
|
462
516
|
```bash
|
|
463
|
-
$ bundle
|
|
517
|
+
$ bundle add garden_variety
|
|
464
518
|
```
|
|
465
519
|
|
|
466
|
-
And
|
|
520
|
+
And run the install generator:
|
|
467
521
|
|
|
468
522
|
```bash
|
|
469
523
|
$ rails generate garden:install
|
|
@@ -474,9 +528,9 @@ This will also run the Pundit install generator, if necessary.
|
|
|
474
528
|
|
|
475
529
|
## Contributing
|
|
476
530
|
|
|
477
|
-
Run `
|
|
531
|
+
Run `bin/test` to run the tests.
|
|
478
532
|
|
|
479
533
|
|
|
480
534
|
## License
|
|
481
535
|
|
|
482
|
-
[MIT License](
|
|
536
|
+
[MIT License](MIT-LICENSE)
|
data/Rakefile
CHANGED
|
@@ -1,29 +1,3 @@
|
|
|
1
|
-
|
|
2
|
-
require 'bundler/setup'
|
|
3
|
-
rescue LoadError
|
|
4
|
-
puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
|
|
5
|
-
end
|
|
6
|
-
|
|
7
|
-
require 'yard'
|
|
8
|
-
|
|
9
|
-
YARD::Rake::YardocTask.new(:doc) do |t|
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
1
|
+
require 'bundler/setup'
|
|
17
2
|
|
|
18
3
|
require 'bundler/gem_tasks'
|
|
19
|
-
|
|
20
|
-
require 'rake/testtask'
|
|
21
|
-
|
|
22
|
-
Rake::TestTask.new(:test) do |t|
|
|
23
|
-
t.libs << 'test'
|
|
24
|
-
t.pattern = 'test/**/*_test.rb'
|
|
25
|
-
t.verbose = false
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
task default: :test
|
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
module GardenVariety
|
|
2
2
|
|
|
3
|
-
REDIRECT_CODES = [301, 302, 303, 307, 308]
|
|
3
|
+
REDIRECT_CODES = [301, 302, 303, 307, 308].to_set
|
|
4
4
|
|
|
5
5
|
module IndexAction
|
|
6
6
|
# Garden variety controller +index+ action.
|
|
7
7
|
# @return [void]
|
|
8
8
|
def index
|
|
9
|
-
authorize(
|
|
10
|
-
self.
|
|
9
|
+
authorize(self.class.model_class)
|
|
10
|
+
self.collection = policy_scope(find_collection)
|
|
11
11
|
end
|
|
12
12
|
end
|
|
13
13
|
|
|
@@ -15,8 +15,7 @@ module GardenVariety
|
|
|
15
15
|
# Garden variety controller +show+ action.
|
|
16
16
|
# @return [void]
|
|
17
17
|
def show
|
|
18
|
-
self.
|
|
19
|
-
authorize(resource)
|
|
18
|
+
self.model = authorize(find_model)
|
|
20
19
|
end
|
|
21
20
|
end
|
|
22
21
|
|
|
@@ -24,12 +23,8 @@ module GardenVariety
|
|
|
24
23
|
# Garden variety controller +new+ action.
|
|
25
24
|
# @return [void]
|
|
26
25
|
def new
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
else
|
|
30
|
-
self.resource = new_resource
|
|
31
|
-
authorize(resource)
|
|
32
|
-
end
|
|
26
|
+
self.model = (model = authorize(new_model))
|
|
27
|
+
assign_attributes(model) if params.key?(self.class.model_name.param_key)
|
|
33
28
|
end
|
|
34
29
|
end
|
|
35
30
|
|
|
@@ -40,10 +35,10 @@ module GardenVariety
|
|
|
40
35
|
# @yield on-success callback, replaces default redirect
|
|
41
36
|
# @return [void]
|
|
42
37
|
def create
|
|
43
|
-
self.
|
|
44
|
-
if
|
|
38
|
+
self.model = (model = assign_attributes(authorize(new_model)))
|
|
39
|
+
if model.save
|
|
45
40
|
flash[:success] = flash_message(:success)
|
|
46
|
-
block_given? ? yield : redirect_to(
|
|
41
|
+
block_given? ? yield : redirect_to(model)
|
|
47
42
|
flash.discard(:success) if REDIRECT_CODES.exclude?(response.status)
|
|
48
43
|
else
|
|
49
44
|
flash.now[:error] = flash_message(:error)
|
|
@@ -56,8 +51,7 @@ module GardenVariety
|
|
|
56
51
|
# Garden variety controller +edit+ action.
|
|
57
52
|
# @return [void]
|
|
58
53
|
def edit
|
|
59
|
-
self.
|
|
60
|
-
authorize(resource)
|
|
54
|
+
self.model = authorize(find_model)
|
|
61
55
|
end
|
|
62
56
|
end
|
|
63
57
|
|
|
@@ -68,10 +62,10 @@ module GardenVariety
|
|
|
68
62
|
# @yield on-success callback, replaces default redirect
|
|
69
63
|
# @return [void]
|
|
70
64
|
def update
|
|
71
|
-
self.
|
|
72
|
-
if
|
|
65
|
+
self.model = (model = assign_attributes(authorize(find_model)))
|
|
66
|
+
if model.save
|
|
73
67
|
flash[:success] = flash_message(:success)
|
|
74
|
-
block_given? ? yield : redirect_to(
|
|
68
|
+
block_given? ? yield : redirect_to(model)
|
|
75
69
|
flash.discard(:success) if REDIRECT_CODES.exclude?(response.status)
|
|
76
70
|
else
|
|
77
71
|
flash.now[:error] = flash_message(:error)
|
|
@@ -87,9 +81,8 @@ module GardenVariety
|
|
|
87
81
|
# @yield on-success callback, replaces default redirect
|
|
88
82
|
# @return [void]
|
|
89
83
|
def destroy
|
|
90
|
-
self.
|
|
91
|
-
|
|
92
|
-
if resource.destroy
|
|
84
|
+
self.model = (model = authorize(find_model))
|
|
85
|
+
if model.destroy
|
|
93
86
|
flash[:success] = flash_message(:success)
|
|
94
87
|
block_given? ? yield : redirect_to(action: :index)
|
|
95
88
|
flash.discard(:success) if REDIRECT_CODES.exclude?(response.status)
|
|
@@ -101,8 +94,8 @@ module GardenVariety
|
|
|
101
94
|
end
|
|
102
95
|
|
|
103
96
|
# Map of controller action name to action module. Used by the
|
|
104
|
-
# {GardenVariety::Controller::ClassMethods#garden_variety
|
|
105
|
-
# include desired controller actions.
|
|
97
|
+
# {GardenVariety::Controller::ClassMethods#garden_variety
|
|
98
|
+
# garden_variety} macro to include desired controller actions.
|
|
106
99
|
ACTION_MODULES = {
|
|
107
100
|
index: IndexAction,
|
|
108
101
|
show: ShowAction,
|