undercarriage 0.5.5 → 1.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 +4 -4
- data/MIT-LICENSE +1 -1
- data/README.md +30 -19
- data/Rakefile +9 -9
- data/lib/undercarriage/controllers/action_concern.rb +53 -60
- data/lib/undercarriage/controllers/kaminari_concern.rb +21 -10
- data/lib/undercarriage/controllers/locale_concern.rb +28 -12
- data/lib/undercarriage/controllers/restful/actions/base_concern.rb +43 -18
- data/lib/undercarriage/controllers/restful/actions/create_concern.rb +15 -10
- data/lib/undercarriage/controllers/restful/actions/destroy_concern.rb +12 -7
- data/lib/undercarriage/controllers/restful/actions/edit_concern.rb +12 -7
- data/lib/undercarriage/controllers/restful/actions/index_concern.rb +13 -8
- data/lib/undercarriage/controllers/restful/actions/new_concern.rb +13 -8
- data/lib/undercarriage/controllers/restful/actions/show_concern.rb +12 -7
- data/lib/undercarriage/controllers/restful/actions/update_concern.rb +14 -9
- data/lib/undercarriage/controllers/restful/flash_concern.rb +44 -26
- data/lib/undercarriage/controllers/restful/location_after_concern.rb +23 -3
- data/lib/undercarriage/controllers/restful/namespace_concern.rb +6 -6
- data/lib/undercarriage/controllers/restful/permitted_attributes_concern.rb +22 -13
- data/lib/undercarriage/controllers/restful/utility_concern.rb +18 -10
- data/lib/undercarriage/controllers/restful_concern.rb +1 -8
- data/lib/undercarriage/models/published_concern.rb +43 -45
- data/lib/undercarriage/version.rb +1 -2
- data/lib/undercarriage.rb +18 -19
- metadata +5 -7
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 59a96756fb12afc085cd7e915c6c55d4795d354ba3e1206d2f2e4c600366f8ce
|
|
4
|
+
data.tar.gz: 18b7f4c033a3c1e0ec2b15be8a648dd6dd8c44cb77ea3df455a63b7376aa1fc0
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 0b22d67b2f8fddc1b9b5ab58205557e56c2e8ed1e4087092f265252ba573fc111f121c34b403e255556b03abde62dfe8046cb17711662f8c13cb7a9aba762003
|
|
7
|
+
data.tar.gz: b9c0d216a9c6e7455dad762f88dd13c953cc1dc251c4c3be6361b7d7e766882205878a52a923eaa81ace11762a09bd5cd3b670b85c8e3c0e07f4185513314097
|
data/MIT-LICENSE
CHANGED
data/README.md
CHANGED
|
@@ -2,28 +2,24 @@
|
|
|
2
2
|
|
|
3
3
|
**\*Undercarriage is currently under development. It is not ready for production use.\***
|
|
4
4
|
|
|
5
|
-
[](https://circleci.com/gh/dfreerksen/undercarriage)
|
|
6
|
-
[](https://codeclimate.com/github/dfreerksen/undercarriage/maintainability)
|
|
7
|
-
[](https://codeclimate.com/github/dfreerksen/undercarriage/test_coverage)
|
|
8
|
-
|
|
9
5
|
Undercarriage is a set of concerns to add to your application to trim some of the fat from controllers and models.
|
|
10
6
|
|
|
11
7
|
## Requirements
|
|
12
8
|
|
|
13
|
-
* Ruby >=
|
|
9
|
+
* Ruby >= 3.3.0
|
|
14
10
|
* Rails >= 6.0
|
|
15
11
|
|
|
16
12
|
## Installation
|
|
17
13
|
|
|
18
14
|
Add to your application's Gemfile
|
|
19
15
|
|
|
20
|
-
```
|
|
21
|
-
gem 'undercarriage', '~> 0
|
|
16
|
+
```bash
|
|
17
|
+
gem 'undercarriage', '~> 1.0'
|
|
22
18
|
```
|
|
23
19
|
|
|
24
20
|
Run the bundle command
|
|
25
21
|
|
|
26
|
-
```
|
|
22
|
+
```bash
|
|
27
23
|
$ bundle install
|
|
28
24
|
```
|
|
29
25
|
|
|
@@ -31,35 +27,42 @@ $ bundle install
|
|
|
31
27
|
|
|
32
28
|
TODO
|
|
33
29
|
|
|
34
|
-
## TODO
|
|
35
|
-
|
|
36
|
-
* [ ] Allow a way to set locale instead of relying on browser preferred language in `Undercarriage::Controllers::LocaleConcern`
|
|
37
|
-
|
|
38
30
|
## Testing
|
|
39
31
|
|
|
40
32
|
Run tests with one of the following
|
|
41
33
|
|
|
42
|
-
```
|
|
34
|
+
```bash
|
|
43
35
|
$ bundle exec rspec
|
|
44
36
|
$ bundle exec rspec spec
|
|
45
37
|
```
|
|
46
38
|
|
|
47
39
|
### Appraisal
|
|
48
40
|
|
|
49
|
-
Undercarriage uses [Appraisal](https://github.com/thoughtbot/appraisal) to ensure various dependency versions work as expected
|
|
41
|
+
Undercarriage uses [Appraisal2](https://github.com/appraisal-rb/appraisal2) (a maintained fork of [Appraisal](https://github.com/thoughtbot/appraisal), still exposing the `appraisal` executable) to ensure various dependency versions work as expected
|
|
50
42
|
|
|
51
43
|
When dependencies change, run
|
|
52
44
|
|
|
53
|
-
```
|
|
45
|
+
```bash
|
|
54
46
|
$ bundle exec appraisal install
|
|
47
|
+
$ bundle exec appraisal generate-install
|
|
55
48
|
```
|
|
56
49
|
|
|
57
50
|
To run tests with Appraisal, run
|
|
58
51
|
|
|
59
|
-
```
|
|
52
|
+
```bash
|
|
60
53
|
$ bundle exec appraisal rspec
|
|
61
54
|
```
|
|
62
55
|
|
|
56
|
+
```bash
|
|
57
|
+
$ bundle exec appraisal rails-6-0 rspec spec
|
|
58
|
+
$ bundle exec appraisal rails-6-1 rspec spec
|
|
59
|
+
$ bundle exec appraisal rails-7-0 rspec spec
|
|
60
|
+
$ bundle exec appraisal rails-7-1 rspec spec
|
|
61
|
+
$ bundle exec appraisal rails-7-2 rspec spec
|
|
62
|
+
$ bundle exec appraisal rails-8-0 rspec spec
|
|
63
|
+
$ bundle exec appraisal rails-8-1 rspec spec
|
|
64
|
+
```
|
|
65
|
+
|
|
63
66
|
## Code Analysis
|
|
64
67
|
|
|
65
68
|
Various tools are used to ensure code is linted and formatted correctly.
|
|
@@ -68,24 +71,32 @@ Various tools are used to ensure code is linted and formatted correctly.
|
|
|
68
71
|
|
|
69
72
|
[RuboCop](https://github.com/bbatsov/rubocop) is a Ruby static code analyzer.
|
|
70
73
|
|
|
71
|
-
```
|
|
74
|
+
```bash
|
|
72
75
|
$ rubocop
|
|
73
76
|
```
|
|
74
77
|
|
|
78
|
+
### YARD-Lint
|
|
79
|
+
|
|
80
|
+
[YARD-Lint](https://github.com/mensfeld/yard-lint) is a linter for YARD documentation.
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
$ bundle exec yard-lint
|
|
84
|
+
```
|
|
85
|
+
|
|
75
86
|
## Documentation
|
|
76
87
|
|
|
77
88
|
[Yard](https://github.com/lsegal/yard) is used to generate documentation. [Online documentation is available](http://www.rubydoc.info/github/dfreerksen/undercarriage/master)
|
|
78
89
|
|
|
79
90
|
Build the documentation with one of the following
|
|
80
91
|
|
|
81
|
-
```
|
|
92
|
+
```bash
|
|
82
93
|
$ yard
|
|
83
94
|
$ yard doc
|
|
84
95
|
```
|
|
85
96
|
|
|
86
97
|
Build the documentation and list all undocumented objects
|
|
87
98
|
|
|
88
|
-
```
|
|
99
|
+
```bash
|
|
89
100
|
$ yard stats --list-undoc
|
|
90
101
|
```
|
|
91
102
|
|
data/Rakefile
CHANGED
|
@@ -1,19 +1,19 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
begin
|
|
4
|
-
require
|
|
4
|
+
require "bundler/setup"
|
|
5
5
|
rescue LoadError
|
|
6
|
-
puts
|
|
6
|
+
puts "You must `gem install bundler` and `bundle install` to run rake tasks"
|
|
7
7
|
end
|
|
8
8
|
|
|
9
|
-
require
|
|
9
|
+
require "rdoc/task"
|
|
10
10
|
|
|
11
11
|
RDoc::Task.new(:rdoc) do |rdoc|
|
|
12
|
-
rdoc.rdoc_dir =
|
|
13
|
-
rdoc.title =
|
|
14
|
-
rdoc.options <<
|
|
15
|
-
rdoc.rdoc_files.include(
|
|
16
|
-
rdoc.rdoc_files.include(
|
|
12
|
+
rdoc.rdoc_dir = "rdoc"
|
|
13
|
+
rdoc.title = "Undercarriage"
|
|
14
|
+
rdoc.options << "--line-numbers"
|
|
15
|
+
rdoc.rdoc_files.include("README.md")
|
|
16
|
+
rdoc.rdoc_files.include("lib/**/*.rb")
|
|
17
17
|
end
|
|
18
18
|
|
|
19
|
-
require
|
|
19
|
+
require "bundler/gem_tasks"
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
+
# :nodoc:
|
|
3
4
|
module Undercarriage
|
|
4
5
|
# :nodoc:
|
|
5
6
|
module Controllers
|
|
@@ -8,11 +9,10 @@ module Undercarriage
|
|
|
8
9
|
#
|
|
9
10
|
# Helpers for the controller or view to help identify the action
|
|
10
11
|
#
|
|
11
|
-
#
|
|
12
|
+
# @example Controller
|
|
12
13
|
# class ExamplesController < ApplicationController
|
|
13
14
|
# include Undercarriage::Controllers::ActionConcern
|
|
14
15
|
# end
|
|
15
|
-
#
|
|
16
16
|
module ActionConcern
|
|
17
17
|
extend ActiveSupport::Concern
|
|
18
18
|
|
|
@@ -38,14 +38,13 @@ module Undercarriage
|
|
|
38
38
|
#
|
|
39
39
|
# Check if action is a certain action type
|
|
40
40
|
#
|
|
41
|
-
# Usage
|
|
42
|
-
# action?(:show) # true
|
|
43
|
-
# action?('show') # true
|
|
44
|
-
# action?(:index) # false
|
|
45
|
-
#
|
|
46
41
|
# @param action_method [String, Symbol] the action to test
|
|
47
42
|
# @return [Boolean] if action matches
|
|
48
43
|
#
|
|
44
|
+
# @example View
|
|
45
|
+
# action?(:show) # true
|
|
46
|
+
# action?("show") # true
|
|
47
|
+
# action?(:index) # false
|
|
49
48
|
def action?(action_method)
|
|
50
49
|
action == action_method.to_sym
|
|
51
50
|
end
|
|
@@ -55,14 +54,13 @@ module Undercarriage
|
|
|
55
54
|
#
|
|
56
55
|
# Check if action is the index action type. The check will pass if it is an `index` action
|
|
57
56
|
#
|
|
58
|
-
# Usage
|
|
59
|
-
# index_action? # true
|
|
60
|
-
# index_action? # false
|
|
61
|
-
#
|
|
62
57
|
# @return [Boolean] if action is action type
|
|
63
58
|
#
|
|
59
|
+
# @example View
|
|
60
|
+
# index_action? # true
|
|
61
|
+
# index_action? # false
|
|
64
62
|
def index_action?
|
|
65
|
-
action?(
|
|
63
|
+
action?("index")
|
|
66
64
|
end
|
|
67
65
|
|
|
68
66
|
##
|
|
@@ -70,14 +68,13 @@ module Undercarriage
|
|
|
70
68
|
#
|
|
71
69
|
# Check if action is the show action type. The check will pass if it is a `show` action
|
|
72
70
|
#
|
|
73
|
-
# Usage
|
|
74
|
-
# show_action? # true
|
|
75
|
-
# show_action? # false
|
|
76
|
-
#
|
|
77
71
|
# @return [Boolean] if action is action type
|
|
78
72
|
#
|
|
73
|
+
# @example View
|
|
74
|
+
# show_action? # true
|
|
75
|
+
# show_action? # false
|
|
79
76
|
def show_action?
|
|
80
|
-
action?(
|
|
77
|
+
action?("show")
|
|
81
78
|
end
|
|
82
79
|
|
|
83
80
|
##
|
|
@@ -85,14 +82,13 @@ module Undercarriage
|
|
|
85
82
|
#
|
|
86
83
|
# Check if action is the new action type. The check will pass if it is a `new` action
|
|
87
84
|
#
|
|
88
|
-
# Usage
|
|
89
|
-
# new_action? # true
|
|
90
|
-
# new_action? # false
|
|
91
|
-
#
|
|
92
85
|
# @return [Boolean] if action is action type
|
|
93
86
|
#
|
|
87
|
+
# @example View
|
|
88
|
+
# new_action? # true
|
|
89
|
+
# new_action? # false
|
|
94
90
|
def new_action?
|
|
95
|
-
action?(
|
|
91
|
+
action?("new")
|
|
96
92
|
end
|
|
97
93
|
|
|
98
94
|
##
|
|
@@ -100,14 +96,13 @@ module Undercarriage
|
|
|
100
96
|
#
|
|
101
97
|
# Check if action is the create action type. The check will pass if it is a `create` action
|
|
102
98
|
#
|
|
103
|
-
# Usage
|
|
104
|
-
# create_action? # true
|
|
105
|
-
# create_action? # false
|
|
106
|
-
#
|
|
107
99
|
# @return [Boolean] if action is action type
|
|
108
100
|
#
|
|
101
|
+
# @example View
|
|
102
|
+
# create_action? # true
|
|
103
|
+
# create_action? # false
|
|
109
104
|
def create_action?
|
|
110
|
-
action?(
|
|
105
|
+
action?("create")
|
|
111
106
|
end
|
|
112
107
|
|
|
113
108
|
##
|
|
@@ -115,14 +110,13 @@ module Undercarriage
|
|
|
115
110
|
#
|
|
116
111
|
# Check if action is the edit action type. The check will pass if it is an `edit` action
|
|
117
112
|
#
|
|
118
|
-
# Usage
|
|
119
|
-
# edit_action? # true
|
|
120
|
-
# edit_action? # false
|
|
121
|
-
#
|
|
122
113
|
# @return [Boolean] if action is action type
|
|
123
114
|
#
|
|
115
|
+
# @example View
|
|
116
|
+
# edit_action? # true
|
|
117
|
+
# edit_action? # false
|
|
124
118
|
def edit_action?
|
|
125
|
-
action?(
|
|
119
|
+
action?("edit")
|
|
126
120
|
end
|
|
127
121
|
|
|
128
122
|
##
|
|
@@ -130,14 +124,13 @@ module Undercarriage
|
|
|
130
124
|
#
|
|
131
125
|
# Check if action is the update action type. The check will pass if it is an `update` action
|
|
132
126
|
#
|
|
133
|
-
# Usage
|
|
134
|
-
# update_action? # true
|
|
135
|
-
# update_action? # false
|
|
136
|
-
#
|
|
137
127
|
# @return [Boolean] if action is action type
|
|
138
128
|
#
|
|
129
|
+
# @example View
|
|
130
|
+
# update_action? # true
|
|
131
|
+
# update_action? # false
|
|
139
132
|
def update_action?
|
|
140
|
-
action?(
|
|
133
|
+
action?("update")
|
|
141
134
|
end
|
|
142
135
|
|
|
143
136
|
##
|
|
@@ -145,14 +138,13 @@ module Undercarriage
|
|
|
145
138
|
#
|
|
146
139
|
# Check if action is the destroy action type. The check will pass if it is a `destroy` action
|
|
147
140
|
#
|
|
148
|
-
# Usage
|
|
149
|
-
# destroy_action? # true
|
|
150
|
-
# destroy_action? # false
|
|
151
|
-
#
|
|
152
141
|
# @return [Boolean] if action is action type
|
|
153
142
|
#
|
|
143
|
+
# @example View
|
|
144
|
+
# destroy_action? # true
|
|
145
|
+
# destroy_action? # false
|
|
154
146
|
def destroy_action?
|
|
155
|
-
action?(
|
|
147
|
+
action?("destroy")
|
|
156
148
|
end
|
|
157
149
|
|
|
158
150
|
##
|
|
@@ -160,12 +152,11 @@ module Undercarriage
|
|
|
160
152
|
#
|
|
161
153
|
# Check if action is a collection action type. An action is a collection type if it is the `index` action
|
|
162
154
|
#
|
|
163
|
-
# Usage
|
|
164
|
-
# collection_action? # true
|
|
165
|
-
# collection_action? # false
|
|
166
|
-
#
|
|
167
155
|
# @return [Boolean] if action is collection type
|
|
168
156
|
#
|
|
157
|
+
# @example View
|
|
158
|
+
# collection_action? # true
|
|
159
|
+
# collection_action? # false
|
|
169
160
|
def collection_action?
|
|
170
161
|
collection_actions.include?(action)
|
|
171
162
|
end
|
|
@@ -175,15 +166,14 @@ module Undercarriage
|
|
|
175
166
|
#
|
|
176
167
|
# Check if action is a create or new action type. The check will pass if it is a `create` or `new` action
|
|
177
168
|
#
|
|
178
|
-
#
|
|
169
|
+
# @return [Boolean] if action is actions type
|
|
170
|
+
#
|
|
171
|
+
# @example View create
|
|
179
172
|
# create_actions? # true
|
|
180
173
|
# create_actions? # false
|
|
181
|
-
#
|
|
174
|
+
# @example View new
|
|
182
175
|
# new_actions? # true
|
|
183
176
|
# new_actions? # false
|
|
184
|
-
#
|
|
185
|
-
# @return [Boolean] if action is actions type
|
|
186
|
-
#
|
|
187
177
|
def create_actions?
|
|
188
178
|
create_actions.include?(action)
|
|
189
179
|
end
|
|
@@ -195,12 +185,11 @@ module Undercarriage
|
|
|
195
185
|
# Check if action is a member action type. An action is a member type if it is the `edit`, `show`, or `update`
|
|
196
186
|
# action
|
|
197
187
|
#
|
|
198
|
-
# Usage
|
|
199
|
-
# member_action? # true
|
|
200
|
-
# member_action? # false
|
|
201
|
-
#
|
|
202
188
|
# @return [Boolean] if action is member type
|
|
203
189
|
#
|
|
190
|
+
# @example View
|
|
191
|
+
# member_action? # true
|
|
192
|
+
# member_action? # false
|
|
204
193
|
def member_action?
|
|
205
194
|
member_actions.include?(action)
|
|
206
195
|
end
|
|
@@ -210,15 +199,14 @@ module Undercarriage
|
|
|
210
199
|
#
|
|
211
200
|
# Check if action is an edit or update action type. The check will pass if it is an `edit` or `update` action
|
|
212
201
|
#
|
|
213
|
-
#
|
|
202
|
+
# @return [Boolean] if action is actions type
|
|
203
|
+
#
|
|
204
|
+
# @example View update
|
|
214
205
|
# update_actions? # true
|
|
215
206
|
# update_actions? # false
|
|
216
|
-
#
|
|
207
|
+
# @example View edit
|
|
217
208
|
# edit_actions? # true
|
|
218
209
|
# edit_actions? # false
|
|
219
|
-
#
|
|
220
|
-
# @return [Boolean] if action is actions type
|
|
221
|
-
#
|
|
222
210
|
def update_actions?
|
|
223
211
|
update_actions.include?(action)
|
|
224
212
|
end
|
|
@@ -231,6 +219,7 @@ module Undercarriage
|
|
|
231
219
|
#
|
|
232
220
|
# Take `action_name` (string) and turn it into a symbol
|
|
233
221
|
#
|
|
222
|
+
# @return [Symbol] action_name as a symbol
|
|
234
223
|
def action
|
|
235
224
|
action_name.to_sym
|
|
236
225
|
end
|
|
@@ -238,6 +227,7 @@ module Undercarriage
|
|
|
238
227
|
##
|
|
239
228
|
# Collection actions
|
|
240
229
|
#
|
|
230
|
+
# @return [Array] collection actions
|
|
241
231
|
def collection_actions
|
|
242
232
|
%i[index]
|
|
243
233
|
end
|
|
@@ -245,6 +235,7 @@ module Undercarriage
|
|
|
245
235
|
##
|
|
246
236
|
# Member actions
|
|
247
237
|
#
|
|
238
|
+
# @return [Array] member actions
|
|
248
239
|
def member_actions
|
|
249
240
|
%i[edit show update]
|
|
250
241
|
end
|
|
@@ -252,6 +243,7 @@ module Undercarriage
|
|
|
252
243
|
##
|
|
253
244
|
# Create actions
|
|
254
245
|
#
|
|
246
|
+
# @return [Array] create actions
|
|
255
247
|
def create_actions
|
|
256
248
|
%i[create new]
|
|
257
249
|
end
|
|
@@ -259,6 +251,7 @@ module Undercarriage
|
|
|
259
251
|
##
|
|
260
252
|
# Update actions
|
|
261
253
|
#
|
|
254
|
+
# @return [Array] update actions
|
|
262
255
|
def update_actions
|
|
263
256
|
%i[edit update]
|
|
264
257
|
end
|
|
@@ -9,7 +9,7 @@ module Undercarriage
|
|
|
9
9
|
# Helpers for Kaminari style pagination. Note that the Kaminari gem is not loaded with dependency. It must be added
|
|
10
10
|
# to your own Gemfile
|
|
11
11
|
#
|
|
12
|
-
#
|
|
12
|
+
# @example Controller
|
|
13
13
|
# class ExamplesController < ApplicationController
|
|
14
14
|
# include Undercarriage::Controllers::KaminariConcern
|
|
15
15
|
#
|
|
@@ -17,7 +17,6 @@ module Undercarriage
|
|
|
17
17
|
# @examples = Examples.page(page_num).per(per_page)
|
|
18
18
|
# end
|
|
19
19
|
# end
|
|
20
|
-
#
|
|
21
20
|
module KaminariConcern
|
|
22
21
|
extend ActiveSupport::Concern
|
|
23
22
|
|
|
@@ -33,12 +32,11 @@ module Undercarriage
|
|
|
33
32
|
#
|
|
34
33
|
# This is asseccible from the View as `per_page`
|
|
35
34
|
#
|
|
36
|
-
# Usage
|
|
37
|
-
# /examples?per=100 # Return 100 items per page
|
|
38
|
-
# /examples?per=10&page=3 # Return page 3 of items with 10 items per page
|
|
39
|
-
#
|
|
40
35
|
# @return [Integer] the number of items per page
|
|
41
36
|
#
|
|
37
|
+
# @example Request
|
|
38
|
+
# # GET /examples?per=100 # Return 100 items per page
|
|
39
|
+
# # GET /examples?per=10&page=3 # Return page 3 of items with 10 items per page
|
|
42
40
|
def per_page
|
|
43
41
|
params.fetch(per_page_key, per_page_default).to_i
|
|
44
42
|
end
|
|
@@ -50,12 +48,11 @@ module Undercarriage
|
|
|
50
48
|
#
|
|
51
49
|
# This is asseccible from the View as `page_num`
|
|
52
50
|
#
|
|
53
|
-
# Usage
|
|
54
|
-
# /examples?page=5 # Return page 5 of items
|
|
55
|
-
# /examples?per=10&page=3 Return page 3 of items with 10 items per page
|
|
56
|
-
#
|
|
57
51
|
# @return [Integer] the page number
|
|
58
52
|
#
|
|
53
|
+
# @example Request
|
|
54
|
+
# # GET /examples?page=5 # Return page 5 of items
|
|
55
|
+
# # GET /examples?per=10&page=3 # Return page 3 of items with 10 items per page
|
|
59
56
|
def page_num
|
|
60
57
|
params.fetch(page_num_key, page_num_default).to_i
|
|
61
58
|
end
|
|
@@ -67,6 +64,7 @@ module Undercarriage
|
|
|
67
64
|
#
|
|
68
65
|
# Query param to be used to identify count to be returned
|
|
69
66
|
#
|
|
67
|
+
# @return [Integer] per page count
|
|
70
68
|
def per_page_key
|
|
71
69
|
:per
|
|
72
70
|
end
|
|
@@ -76,16 +74,29 @@ module Undercarriage
|
|
|
76
74
|
#
|
|
77
75
|
# Query param to be used to identify page offset
|
|
78
76
|
#
|
|
77
|
+
# @return [String,Symbol] page number key
|
|
79
78
|
def page_num_key
|
|
80
79
|
Kaminari.config.param_name
|
|
81
80
|
end
|
|
82
81
|
|
|
83
82
|
private
|
|
84
83
|
|
|
84
|
+
##
|
|
85
|
+
# Items per page default
|
|
86
|
+
#
|
|
87
|
+
# Fallback used when the `per` query param is absent.
|
|
88
|
+
#
|
|
89
|
+
# @return [Integer] default per page count
|
|
85
90
|
def per_page_default
|
|
86
91
|
Kaminari.config.default_per_page
|
|
87
92
|
end
|
|
88
93
|
|
|
94
|
+
##
|
|
95
|
+
# Page number default
|
|
96
|
+
#
|
|
97
|
+
# Fallback used when the page query param is absent.
|
|
98
|
+
#
|
|
99
|
+
# @return [Integer] default page number
|
|
89
100
|
def page_num_default
|
|
90
101
|
1
|
|
91
102
|
end
|
|
@@ -13,11 +13,10 @@ module Undercarriage
|
|
|
13
13
|
# When preferred language cannot be identified or no translation is available, fall back to `I18n.default_locale`
|
|
14
14
|
# (typically `en`).
|
|
15
15
|
#
|
|
16
|
-
#
|
|
16
|
+
# @example Controller
|
|
17
17
|
# class ExamplesController < ApplicationController
|
|
18
18
|
# include Undercarriage::Controllers::LocaleConcern
|
|
19
19
|
# end
|
|
20
|
-
#
|
|
21
20
|
module LocaleConcern
|
|
22
21
|
extend ActiveSupport::Concern
|
|
23
22
|
|
|
@@ -32,10 +31,11 @@ module Undercarriage
|
|
|
32
31
|
#
|
|
33
32
|
# Helper for Views to return the identified language.
|
|
34
33
|
#
|
|
35
|
-
#
|
|
36
|
-
# <html lang="<%= html_lang %>"> #=> '<html lang="de">'
|
|
37
|
-
# <html lang="<%= html_lang %>"> #=> '<html lang="de-at">'
|
|
34
|
+
# @return [String] locale for html tag lang attribute
|
|
38
35
|
#
|
|
36
|
+
# @example View
|
|
37
|
+
# # <html lang="<%= html_lang %>"> #=> '<html lang="de">'
|
|
38
|
+
# # <html lang="<%= html_lang %>"> #=> '<html lang="de-at">'
|
|
39
39
|
def html_lang
|
|
40
40
|
I18n.locale.to_s
|
|
41
41
|
end
|
|
@@ -54,14 +54,15 @@ module Undercarriage
|
|
|
54
54
|
# * Persian/Farsi
|
|
55
55
|
# * Urdu
|
|
56
56
|
#
|
|
57
|
-
#
|
|
58
|
-
# <html dir="<%= html_dir %>"> #=> <html dir="ltr">
|
|
59
|
-
# <html dir="<%= html_dir %>"> #=> <html dir="rtl">
|
|
57
|
+
# @return [String] direction for html tag dir attribute
|
|
60
58
|
#
|
|
59
|
+
# @example View
|
|
60
|
+
# # <html dir="<%= html_dir %>"> #=> <html dir="ltr">
|
|
61
|
+
# # <html dir="<%= html_dir %>"> #=> <html dir="rtl">
|
|
61
62
|
def html_dir
|
|
62
63
|
rtl_languages = %w[am ar az dv fa he ur]
|
|
63
64
|
|
|
64
|
-
html_lang.start_with?(*rtl_languages) ?
|
|
65
|
+
html_lang.start_with?(*rtl_languages) ? "rtl" : "ltr"
|
|
65
66
|
end
|
|
66
67
|
|
|
67
68
|
protected
|
|
@@ -71,12 +72,20 @@ module Undercarriage
|
|
|
71
72
|
#
|
|
72
73
|
# Set I18n locale for the request
|
|
73
74
|
#
|
|
75
|
+
# @return [String] locale
|
|
74
76
|
def identify_locale(&action)
|
|
75
77
|
I18n.with_locale(first_available_locale, &action)
|
|
76
78
|
end
|
|
77
79
|
|
|
78
80
|
private
|
|
79
81
|
|
|
82
|
+
##
|
|
83
|
+
# First available locale
|
|
84
|
+
#
|
|
85
|
+
# Intersects the request's accepted languages (falling back to `I18n.default_locale`) against
|
|
86
|
+
# `I18n.available_locales`, preferring the request's order.
|
|
87
|
+
#
|
|
88
|
+
# @return [String] locale
|
|
80
89
|
def first_available_locale
|
|
81
90
|
preferred_locales = (accepted_languages_header << I18n.default_locale.to_s).uniq
|
|
82
91
|
available_locales = I18n.available_locales.map(&:to_s)
|
|
@@ -84,11 +93,18 @@ module Undercarriage
|
|
|
84
93
|
(preferred_locales & available_locales).first
|
|
85
94
|
end
|
|
86
95
|
|
|
96
|
+
##
|
|
97
|
+
# Accepted languages header
|
|
98
|
+
#
|
|
99
|
+
# Parses the `HTTP_ACCEPT_LANGUAGE` request header into an ordered list of language tags, stripping any
|
|
100
|
+
# `;q=` quality values.
|
|
101
|
+
#
|
|
102
|
+
# @return [Array<String>] accepted language tags
|
|
87
103
|
def accepted_languages_header
|
|
88
|
-
accepted_languages = request.env[
|
|
104
|
+
accepted_languages = request.env["HTTP_ACCEPT_LANGUAGE"] || ""
|
|
89
105
|
|
|
90
|
-
accepted_languages.gsub(/\s+/,
|
|
91
|
-
lang.split(
|
|
106
|
+
accepted_languages.gsub(/\s+/, "").split(",").map do |lang|
|
|
107
|
+
lang.split(";q=").first
|
|
92
108
|
end
|
|
93
109
|
end
|
|
94
110
|
end
|