pres 1.4.1 → 1.5.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- data/README.md +45 -61
- data/lib/pres.rb +2 -0
- data/lib/pres/presenter.rb +2 -0
- data/lib/pres/presents.rb +13 -3
- data/lib/pres/version.rb +3 -1
- data/lib/pres/view_delegation.rb +8 -6
- metadata +4 -18
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 1c299e16a162674ba826b413ab48bbdc0850af84d8958eb6a3e9f440c7cd4e82
|
4
|
+
data.tar.gz: 40e724787b143aa0ede13a41f2d84e6e2b2297584fb7ab36c2b448826609863d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: '039604e02f82018fff8345492080896501efb7c8b05dab17ed2dfcf7babf9a4873687fac56986ac3b53ed76d4bc048ad4037be350bca4b5985d76c78ad3d0b5c'
|
7
|
+
data.tar.gz: e53da96e07d916ae51ddb499d171ee566f1df5e300ae61d1cc4e2c4e061a6b7614bb546f42d2d8c39a2e0e40f084bff72bc7dbc1fa73a1877fd5fc9bfcfb7371
|
data/README.md
CHANGED
@@ -5,19 +5,28 @@
|
|
5
5
|
|
6
6
|
## What?
|
7
7
|
|
8
|
-
A Presenter is a rendering class.
|
9
|
-
|
8
|
+
A Presenter is a rendering class. The `pres` gem is a lightweight presenter
|
9
|
+
solution with no runtime gem dependencies.
|
10
|
+
|
11
|
+
`Pres` provides the following:
|
12
|
+
|
13
|
+
1. `Pres::Presenter` is a presenter base class.
|
14
|
+
1. `present` is a convenience method to create presenters.
|
15
|
+
1. `Pres::ViewDelegation` is a delegation module, included in the `Presenter` base class.
|
10
16
|
|
11
17
|
## How and Why?
|
12
18
|
|
19
|
+
Presenters are an alternative to an unorganized mass of helper
|
20
|
+
methods in your ruby application.
|
21
|
+
|
13
22
|
Rails' `ViewContext` contains convenience methods for views, such as `link_to`,
|
14
23
|
`url_for`, `truncate`, `number_to_currency`, etc. It's the thing that makes
|
15
24
|
Rails views nice to work with.
|
16
25
|
|
17
26
|
Other presenter libraries mix in all the methods from the Rails `ViewContext` to
|
18
|
-
make it easy to call those methods in the Presenter class. `pres` instead injects
|
19
|
-
the `ViewContext` as a dependency into the Presenter class, and uses `method_missing`
|
20
|
-
to delegate to `ViewContext` methods. `pres` produces small classes that contain and
|
27
|
+
make it easy to call those methods in the Presenter class. `pres` instead injects
|
28
|
+
the `ViewContext` as a dependency into the Presenter class, and uses `method_missing`
|
29
|
+
to delegate to `ViewContext` methods. `pres` produces small classes that contain and
|
21
30
|
delegate to an existing object that handles server-side rendering.
|
22
31
|
|
23
32
|
## Install
|
@@ -28,6 +37,8 @@ Add it to your Gemfile:
|
|
28
37
|
gem "pres"
|
29
38
|
```
|
30
39
|
|
40
|
+
## Setup with Rails
|
41
|
+
|
31
42
|
Include the `Pres::Presents` module:
|
32
43
|
|
33
44
|
```ruby
|
@@ -53,7 +64,7 @@ class DogePresenter < Pres::Presenter
|
|
53
64
|
end
|
54
65
|
|
55
66
|
def name_header
|
56
|
-
# object is the Doge
|
67
|
+
# object is the Doge used to initialize the presenter
|
57
68
|
content_tag(:h1, object.name)
|
58
69
|
end
|
59
70
|
|
@@ -68,30 +79,24 @@ class DogePresenter < Pres::Presenter
|
|
68
79
|
end
|
69
80
|
```
|
70
81
|
|
71
|
-
Wrap your model object in your controller with `present`:
|
82
|
+
Wrap your model object in a presenter in your controller with `present`:
|
72
83
|
|
73
84
|
```ruby
|
74
85
|
class DogesController
|
75
86
|
def show
|
87
|
+
@doge = present(Doge.find(params[:id]))
|
76
88
|
end
|
77
|
-
|
78
|
-
private
|
79
|
-
|
80
|
-
helper_method \
|
81
|
-
def doge
|
82
|
-
@doge ||= present(Doge.find(params[:id]))
|
83
|
-
end
|
84
89
|
end
|
85
90
|
```
|
86
91
|
|
87
92
|
Use the presenter object in `doges/show.haml.html`
|
88
93
|
|
89
94
|
```haml
|
90
|
-
= doge.name_header
|
95
|
+
= @doge.name_header
|
91
96
|
.status
|
92
|
-
You are #{doge.signed_in_status}
|
97
|
+
You are #{@doge.signed_in_status}
|
93
98
|
.links
|
94
|
-
.meme-link= doge.know_your_meme_link
|
99
|
+
.meme-link= @doge.know_your_meme_link
|
95
100
|
```
|
96
101
|
|
97
102
|
#### Collections
|
@@ -104,25 +109,19 @@ class DogePresenter < Pres::Presenter
|
|
104
109
|
end
|
105
110
|
```
|
106
111
|
|
107
|
-
|
112
|
+
Build an array of presenters in your controller with `present`:
|
108
113
|
|
109
114
|
```ruby
|
110
115
|
class DogesController
|
111
116
|
def index
|
117
|
+
@doges = present(Doge.all)
|
112
118
|
end
|
113
|
-
|
114
|
-
private
|
115
|
-
|
116
|
-
helper_method \
|
117
|
-
def doges
|
118
|
-
@doges ||= present(Doge.all)
|
119
|
-
end
|
120
119
|
end
|
121
120
|
```
|
122
121
|
|
123
122
|
Use the presenter objects in `doges/index.haml.html`
|
124
123
|
|
125
|
-
This renders "doges/_doge.html.haml" for each item,
|
124
|
+
This renders "doges/_doge.html.haml" for each item, following rails' usual conventions:
|
126
125
|
|
127
126
|
```haml
|
128
127
|
= render @doges
|
@@ -131,32 +130,34 @@ This renders "doges/_doge.html.haml" for each item, as usual:
|
|
131
130
|
Or use each:
|
132
131
|
|
133
132
|
```haml
|
134
|
-
- doges.each do |doge|
|
133
|
+
- @doges.each do |doge|
|
135
134
|
= doge.name_header
|
136
135
|
```
|
137
136
|
|
138
137
|
#### Present with options
|
139
138
|
|
140
|
-
Pass additional options to a Presenter as a hash
|
139
|
+
Pass additional options to a Presenter as a hash. The presenter class exposes the
|
140
|
+
`options` hash as a method:
|
141
141
|
|
142
142
|
```ruby
|
143
|
-
class UserPresenter < Pres::Presenter
|
144
|
-
def initialize(object, view_context, cool: false)
|
145
|
-
super
|
146
|
-
@cool = cool
|
147
|
-
end
|
148
|
-
end
|
149
|
-
|
150
143
|
user = User.new
|
151
|
-
|
144
|
+
|
145
|
+
# These two lines are the same:
|
146
|
+
# 1. explicit
|
147
|
+
presenter = UserPresenter.new(user, view_context, something: 123)
|
148
|
+
# 2. using #present
|
149
|
+
presenter = present(user, something: 123)
|
152
150
|
=> #<UserPresenter object: #<User> ...>
|
151
|
+
|
152
|
+
presenter.options[:something]
|
153
|
+
=> 123
|
153
154
|
```
|
154
155
|
|
155
|
-
####
|
156
|
+
#### Use a custom presenter class
|
156
157
|
|
157
158
|
By default, a presenter class corresponding to the model class name is
|
158
159
|
constructed in `present`. For example, if you present a `User`, a `UserPresenter`
|
159
|
-
class is constructed. An error is raised if the presenter class does not exist.
|
160
|
+
class is constructed. An error is raised if the presenter class does not exist.
|
160
161
|
To specify a different class, use the `presenter:` key.
|
161
162
|
|
162
163
|
```ruby
|
@@ -178,10 +179,10 @@ present(User.new)
|
|
178
179
|
# => #<MyPresenter object: #<User> ...>
|
179
180
|
```
|
180
181
|
|
181
|
-
####
|
182
|
+
#### Create presenters in views
|
182
183
|
|
183
|
-
|
184
|
-
visible to your views
|
184
|
+
You can create a presenter in your view code. First make the `present` method
|
185
|
+
visible to your views by declaring it a `helper_method`:
|
185
186
|
|
186
187
|
```ruby
|
187
188
|
class ApplicationController
|
@@ -190,29 +191,13 @@ class ApplicationController
|
|
190
191
|
end
|
191
192
|
```
|
192
193
|
|
193
|
-
|
194
|
+
Then you can create presenters inline in a view:
|
194
195
|
|
195
196
|
```haml
|
196
197
|
- present(@doge) do |doge|
|
197
198
|
= doge.name_header
|
198
199
|
```
|
199
200
|
|
200
|
-
### Presenters are objects
|
201
|
-
|
202
|
-
You can mix in common methods.
|
203
|
-
|
204
|
-
```ruby
|
205
|
-
module Shared
|
206
|
-
def truncated_name(length: 40)
|
207
|
-
truncate object.name, length: length
|
208
|
-
end
|
209
|
-
end
|
210
|
-
|
211
|
-
class DogePresenter < Pres::Presenter
|
212
|
-
include Shared
|
213
|
-
end
|
214
|
-
```
|
215
|
-
|
216
201
|
You can override methods as usual:
|
217
202
|
|
218
203
|
```ruby
|
@@ -220,7 +205,7 @@ class DogePresenter < Pres::Presenter
|
|
220
205
|
include Shared
|
221
206
|
|
222
207
|
def truncated_name(length: 60)
|
223
|
-
#
|
208
|
+
# override
|
224
209
|
super(length: length)
|
225
210
|
end
|
226
211
|
end
|
@@ -228,8 +213,7 @@ end
|
|
228
213
|
|
229
214
|
#### Presenters can create other presenters
|
230
215
|
|
231
|
-
|
232
|
-
which can then wrap child objects in presenters of their own.
|
216
|
+
Presenters can wrap child objects in presenters of their own.
|
233
217
|
|
234
218
|
```ruby
|
235
219
|
class DogePresenter < Pres::Presenter
|
data/lib/pres.rb
CHANGED
data/lib/pres/presenter.rb
CHANGED
data/lib/pres/presents.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Pres
|
2
4
|
module Presents
|
3
5
|
private
|
@@ -53,12 +55,20 @@ module Pres
|
|
53
55
|
if object.respond_to?(:to_ary)
|
54
56
|
object.map { |item| present(item, presenter: presenter, **args) }
|
55
57
|
else
|
56
|
-
presenter ||=
|
57
|
-
presenter ||= object.respond_to?(:presenter_class) && object.presenter_class
|
58
|
-
presenter ||= Object.const_get("#{object.class.name}Presenter")
|
58
|
+
presenter ||= presenter_klass(object)
|
59
59
|
wrapper = presenter.new(object, view_context, **args)
|
60
60
|
block_given? ? yield(wrapper) : wrapper
|
61
61
|
end
|
62
62
|
end
|
63
|
+
|
64
|
+
def presenter_klass(object)
|
65
|
+
if object.nil?
|
66
|
+
Presenter
|
67
|
+
elsif object.respond_to?(:presenter_class)
|
68
|
+
object.presenter_class
|
69
|
+
else
|
70
|
+
Object.const_get("#{object.class.name}Presenter")
|
71
|
+
end
|
72
|
+
end
|
63
73
|
end
|
64
74
|
end
|
data/lib/pres/version.rb
CHANGED
data/lib/pres/view_delegation.rb
CHANGED
@@ -1,20 +1,22 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Pres
|
2
4
|
module ViewDelegation
|
3
5
|
def view_context
|
4
6
|
@view_context
|
5
7
|
end
|
6
8
|
|
7
|
-
# Send missing
|
8
|
-
def method_missing(
|
9
|
-
if view_context.respond_to?(
|
10
|
-
view_context.send(
|
9
|
+
# Send missing methods to view_context first
|
10
|
+
def method_missing(method, *args, &block)
|
11
|
+
if view_context.respond_to?(method, true)
|
12
|
+
view_context.send(method, *args, &block)
|
11
13
|
else
|
12
14
|
super
|
13
15
|
end
|
14
16
|
end
|
15
17
|
|
16
|
-
def respond_to_missing?(
|
17
|
-
view_context.respond_to?(
|
18
|
+
def respond_to_missing?(method, _ = false)
|
19
|
+
view_context.respond_to?(method, true) || super
|
18
20
|
end
|
19
21
|
end
|
20
22
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pres
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.5.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tee Parham
|
@@ -9,22 +9,8 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2018-12-09 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
|
-
- !ruby/object:Gem::Dependency
|
15
|
-
name: bundler
|
16
|
-
requirement: !ruby/object:Gem::Requirement
|
17
|
-
requirements:
|
18
|
-
- - "~>"
|
19
|
-
- !ruby/object:Gem::Version
|
20
|
-
version: '1.7'
|
21
|
-
type: :development
|
22
|
-
prerelease: false
|
23
|
-
version_requirements: !ruby/object:Gem::Requirement
|
24
|
-
requirements:
|
25
|
-
- - "~>"
|
26
|
-
- !ruby/object:Gem::Version
|
27
|
-
version: '1.7'
|
28
14
|
- !ruby/object:Gem::Dependency
|
29
15
|
name: minitest
|
30
16
|
requirement: !ruby/object:Gem::Requirement
|
@@ -80,7 +66,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
80
66
|
requirements:
|
81
67
|
- - ">="
|
82
68
|
- !ruby/object:Gem::Version
|
83
|
-
version: 2.
|
69
|
+
version: 2.3.0
|
84
70
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
85
71
|
requirements:
|
86
72
|
- - ">="
|
@@ -88,7 +74,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
88
74
|
version: '0'
|
89
75
|
requirements: []
|
90
76
|
rubyforge_project:
|
91
|
-
rubygems_version: 2.
|
77
|
+
rubygems_version: 2.7.8
|
92
78
|
signing_key:
|
93
79
|
specification_version: 4
|
94
80
|
summary: A Simple Rails Presenter
|