show_for 0.1

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.
data/README.rdoc ADDED
@@ -0,0 +1,150 @@
1
+ == ShowFor
2
+
3
+ ShowFor allows you to quickly show a model information with I18n features.
4
+
5
+ <% show_for @user do |u| %>
6
+ <%= u.attribute :name %>
7
+ <%= u.attribute :confirmed? %>
8
+ <%= u.attribute :created_at, :format => :short %>
9
+ <%= u.attribute :last_sign_in_at, :if_blank => "User did not access yet"
10
+ :wrapper_html => { :id => "sign_in_timestamp" } %>
11
+
12
+ <% u.attribute :photo do
13
+ <%= image_url(@user.photo_url) %>
14
+ end %>
15
+
16
+ <%= u.association :company %>
17
+ <%= u.association :tags, :to_sentence => true %>
18
+ <% end %>
19
+
20
+ == Installation
21
+
22
+ Install the gem:
23
+
24
+ sudo gem install show_for
25
+
26
+ Configure simple_form gem inside your app:
27
+
28
+ config.gem 'show_for'
29
+
30
+ Run the generator:
31
+
32
+ ruby script/generate show_for_install
33
+
34
+ And you're ready to go.
35
+
36
+ == Usage
37
+
38
+ ShowFor allows you to quickly show a model information with I18n features.
39
+
40
+ <% show_for @admin do |a| %>
41
+ <%= a.attribute :name %>
42
+ <%= a.attribute :confirmed? %>
43
+ <%= a.attribute :created_at, :format => :short %>
44
+ <%= a.attribute :last_sign_in_at, :if_blank => "Administrator did not access yet"
45
+ :wrapper_html => { :id => "sign_in_timestamp" } %>
46
+
47
+ <% a.attribute :photo do %>
48
+ <%= image_url(@admin.photo_url) %>
49
+ <% end %>
50
+ <% end %>
51
+
52
+ Will generate something like:
53
+
54
+ <div id="admin_1" class="show_for admin">
55
+ <p class="wrapper admin_name">
56
+ <b class="label">Name</b><br />
57
+ José Valim
58
+ </p>
59
+ <p class="wrapper admin_confirmed">
60
+ <b class="label">Confirmed?</b><br />
61
+ Yes
62
+ </p>
63
+ <p class="wrapper admin_created_at">
64
+ <b class="label">Created at</b><br />
65
+ 13/12/2009 - 19h17
66
+ </p>
67
+ <p id="sign_in_timestamp" class="wrapper admin_last_sign_in_at">
68
+ <b class="label">Last sign in at</b><br />
69
+ Administrator did not access yet
70
+ </p>
71
+ <p class="wrapper admin_photo">
72
+ <b class="label">Photo</b><br />
73
+ <img src="path/to/photo" />
74
+ </p>
75
+ </div>
76
+
77
+ == Value lookup
78
+
79
+ To show the proper value, before retrieving the attribute value, show_for first looks if a
80
+ block without argument was given, otherwise checks if a :"human_#{attribute}" method is defined
81
+ and, if not, only then retrieve the attribute.
82
+
83
+ == Options
84
+
85
+ show_for handles a series of options. Those are:
86
+
87
+ * :escape * - When the attribute should be escaped. True by default.
88
+
89
+ * :format * - Sent to I18n.localize when the attribute is a date/time object.
90
+
91
+ * :if_blank * - An object to be used if the value is blank. Not escaped as well.
92
+
93
+ Besides, all containers (:label, :content and :wrapper) can have their html
94
+ options configured through the :label_html, :content_html and :wrapper_html
95
+ options. Containers can have their tags configured on demand as well through
96
+ :label_tag, :content_tag and :wrapper_tag options.
97
+
98
+ == Label
99
+
100
+ show_for also exposes the label method. In case you want to use the default
101
+ human_attribute_name lookup and the default wrapping:
102
+
103
+ a.label :name #=> <b class="label">Name</b>
104
+ a.label "Name", :id => "my_name" #=> <b class="label" id="my_name">Name</b>
105
+
106
+ == Associations
107
+
108
+ show_for also supports associations.
109
+
110
+ <% show_for @artwork do |a| %>
111
+ <%= a.association :artist %>
112
+ <%= a.association :artist, :method => :name_with_title %>
113
+
114
+ <%= a.association :tags %>
115
+ <%= a.association :tags, :to_sentence => true %>
116
+ <% a.association :tags do
117
+ @artwork.tags.map(&:name).to_sentence
118
+ end %>
119
+
120
+ <% a.association :fans, :collection_tag => :ol do |fan| %>
121
+ <li><%= link_to fan.name, fan %></li>
122
+ <% end %>
123
+ <% end %>
124
+
125
+ The first is a has_one or belongs_to association, which works like an attribute
126
+ to show_for, except it will retrieve the artist association and try to find a
127
+ proper method from ShowFor.association_methods to be used. You can pass
128
+ the option :method to tell (and not guess) which method from the association
129
+ to use.
130
+
131
+ :tags is a has_and_belongs_to_many association which will return a collection.
132
+ show_for can handle collections by default by wrapping them in list (<ul> with
133
+ each item wrapped by an <li>). However, it also allows you to give :to_sentence
134
+ or :join it you want to render them inline.
135
+
136
+ You can also pass a block which expects an argument to association. In such cases,
137
+ a wrapper for the collection is still created and the block just iterates over the
138
+ collection objects.
139
+
140
+ == Contributors
141
+
142
+ * José Valim (http://github.com/josevalim)
143
+
144
+ == Bugs and Feedback
145
+
146
+ If you discover any bugs or want to drop a line, feel free to create an issue on GitHub.
147
+
148
+ http://github.com/plataformatec/show_for/issues
149
+
150
+ MIT License. Copyright 2009 Plataforma Tecnologia. http://blog.plataformatec.com.br
@@ -0,0 +1,3 @@
1
+ To copy a ShowFor initializer to your Rails App, with some configuration values, just do:
2
+
3
+ script/generate show_for_install
@@ -0,0 +1,19 @@
1
+ class ShowForInstallGenerator < Rails::Generator::Base
2
+
3
+ def manifest
4
+ record do |m|
5
+ m.directory 'config/initializers'
6
+ m.template 'show_for.rb', 'config/initializers/show_for.rb'
7
+
8
+ m.directory 'config/locales'
9
+ m.template locale_file, 'config/locales/show_for.en.yml'
10
+ end
11
+ end
12
+
13
+ private
14
+
15
+ def locale_file
16
+ @locale_file ||= '../../../lib/show_for/locale/en.yml'
17
+ end
18
+
19
+ end
@@ -0,0 +1,30 @@
1
+ # Use this setup block to configure all options available in ShowFor.
2
+ ShowFor.setup do |config|
3
+ # The tag which wraps show_for calls.
4
+ # config.show_for_tag = :div
5
+
6
+ # The tag which wraps each attribute/association call. Default is :p.
7
+ # config.wrapper_tag = :dl
8
+
9
+ # The tag used to wrap each label. Default is :strong.
10
+ # config.label_tag = :dt
11
+
12
+ # The tag used to wrap each content (value). Default is nil.
13
+ # config.content_tag = :dd
14
+
15
+ # The separator between label and content. Default is "<br />".
16
+ # config.separator = "<br />"
17
+
18
+ # The tag used to wrap collections. Default is :ul.
19
+ # config.collection_tag = :ul
20
+
21
+ # The default iterator to be used when invoking a collection/association.
22
+ # config.default_collection_proc = lambda { |value| "<li>#{value}</li>" }
23
+
24
+ # The default format to be used in I18n when localizing a Date/Time.
25
+ # config.i18n_format = :default
26
+
27
+ # Whenever a association is given, the first method in association_methods
28
+ # in which the association responds to is used to retrieve the association labels.
29
+ # config.association_methods = [ :name, :title, :to_s ]
30
+ end
data/init.rb ADDED
@@ -0,0 +1 @@
1
+ require 'show_for'
@@ -0,0 +1,98 @@
1
+ require 'show_for/content'
2
+ require 'show_for/label'
3
+
4
+ module ShowFor
5
+ class Builder
6
+ include ShowFor::Content
7
+ include ShowFor::Label
8
+
9
+ attr_reader :object, :template
10
+
11
+ def initialize(object, template)
12
+ @object, @template = object, template
13
+ end
14
+
15
+ def attribute(attribute_name, options={}, &block)
16
+ apply_default_options!(attribute_name, options)
17
+ collection_block, block = block, nil if collection_block?(block)
18
+
19
+ value = if block
20
+ block
21
+ elsif @object.respond_to?(:"human_#{attribute_name}")
22
+ @object.send :"human_#{attribute_name}"
23
+ else
24
+ @object.send(attribute_name)
25
+ end
26
+
27
+ wrap_label_and_content(attribute_name, value, options, &collection_block)
28
+ end
29
+
30
+ def association(association_name, options={}, &block)
31
+ apply_default_options!(association_name, options)
32
+
33
+ # If a block with an iterator was given, no need to calculate the labels
34
+ # since we want the collection to be yielded. Otherwise, calculate the values.
35
+ value = if collection_block?(block)
36
+ collection_block = block
37
+ @object.send(association_name)
38
+ elsif block
39
+ block
40
+ else
41
+ association = @object.send(association_name)
42
+ values = retrieve_values_from_association(association, options)
43
+
44
+ if options.delete(:to_sentence)
45
+ values.to_sentence
46
+ elsif joiner = options.delete(:join)
47
+ values.join(joiner)
48
+ else
49
+ values
50
+ end
51
+ end
52
+
53
+ wrap_label_and_content(association_name, value, options, &collection_block)
54
+ end
55
+
56
+ protected
57
+
58
+ def object_name #:nodoc:
59
+ @object_name ||= @object.class.name.underscore
60
+ end
61
+
62
+ def wrap_label_and_content(name, value, options, &block) #:nodoc:
63
+ wrap_with(:wrapper, label(name, options, false) + ShowFor.separator.to_s +
64
+ content(value, options, false, &block), options, true, value.is_a?(Proc))
65
+ end
66
+
67
+ # Set "#{object_name}_#{attribute_name}" as in the wrapper tag.
68
+ def apply_default_options!(name, options) #:nodoc:
69
+ html_class = "#{object_name}_#{name}".gsub(/\W/, '')
70
+ wrapper_html = options[:wrapper_html] ||= {}
71
+ wrapper_html[:class] = "#{html_class} #{wrapper_html[:class]}".strip
72
+ end
73
+
74
+ # Gets the default tag set in ShowFor module and apply (if defined)
75
+ # around the given content. It also check for html_options in @options
76
+ # hash related to the current type.
77
+ def wrap_with(type, content, options, safe=false, concat=false) #:nodoc:
78
+ tag = options.delete(:"#{type}_tag") || ShowFor.send(:"#{type}_tag")
79
+
80
+ html = if tag
81
+ html_options = options.delete(:"#{type}_html") || {}
82
+ html_options[:class] = "#{type} #{html_options[:class]}".strip
83
+ @template.content_tag(tag, content, html_options)
84
+ else
85
+ content
86
+ end
87
+
88
+ html.html_safe! if safe && html.respond_to?(:html_safe!)
89
+ concat ? @template.concat(html) : html
90
+ end
91
+
92
+ def retrieve_values_from_association(association, options) #:nodoc:
93
+ sample = association.is_a?(Array) ? association.first : association
94
+ method = options[:method] || ShowFor.association_methods.find { |m| sample.respond_to?(m) }
95
+ association.is_a?(Array) ? association.map(&method) : association.try(method)
96
+ end
97
+ end
98
+ end
@@ -0,0 +1,49 @@
1
+ module ShowFor
2
+ module Content
3
+ def content(value, options={}, apply_options=true, &block)
4
+ value = options.delete(:if_blank) if value.blank? && value != false
5
+
6
+ content = case value
7
+ when Date, Time, DateTime
8
+ I18n.l value, :format => options.delete(:format) || ShowFor.i18n_format
9
+ when TrueClass
10
+ I18n.t :"show_for.yes", :default => "Yes"
11
+ when FalseClass
12
+ I18n.t :"show_for.no", :default => "No"
13
+ when Array, Hash
14
+ options[:escape] = false
15
+ collection_handler(value, options, &block)
16
+ when Proc
17
+ options[:escape] = false
18
+ @template.capture(&value)
19
+ when NilClass
20
+ ""
21
+ else
22
+ value
23
+ end
24
+
25
+ content = @template.send(:h, content) unless options.delete(:escape) == false
26
+ options[:content_html] = options.dup if apply_options
27
+ wrap_with(:content, content, options)
28
+ end
29
+
30
+ protected
31
+
32
+ def collection_handler(value, options, &block) #:nodoc:
33
+ iterator = collection_block?(block) ? block : ShowFor.default_collection_proc
34
+ response = ""
35
+
36
+ value.each do |item|
37
+ response << template.capture(item, &iterator)
38
+ end
39
+
40
+ wrap_with(:collection, response, options)
41
+ end
42
+
43
+ # Returns true if the block is supposed to iterate through a collection,
44
+ # i.e. it has arity equals to one.
45
+ def collection_block?(block) #:nodoc:
46
+ block && block.arity == 1
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,25 @@
1
+ module ShowFor
2
+ module Helper
3
+ # Creates a div around the object and yields a builder.
4
+ #
5
+ # Example:
6
+ #
7
+ # show_for @user do |f|
8
+ # f.attribute :name
9
+ # f.attribute :email
10
+ # end
11
+ #
12
+ def show_for(object, html_options={}, &block)
13
+ tag = html_options.delete(:show_for_tag) || ShowFor.show_for_tag
14
+
15
+ html_options[:id] ||= dom_id(object)
16
+ html_options[:class] = "show_for #{dom_class(object)} #{html_options[:class]}".strip
17
+
18
+ concat(content_tag(tag, html_options) do
19
+ yield ShowFor::Builder.new(object, self)
20
+ end)
21
+ end
22
+ end
23
+ end
24
+
25
+ ActionView::Base.send :include, ShowFor::Helper
@@ -0,0 +1,23 @@
1
+ module ShowFor
2
+ module Label
3
+ def label(text_or_attribute, options={}, apply_options=true)
4
+ label = if text_or_attribute.is_a?(String)
5
+ text_or_attribute
6
+ elsif options.key?(:label)
7
+ options.delete(:label)
8
+ else
9
+ human_attribute_name(text_or_attribute)
10
+ end
11
+
12
+ return "" if label == false
13
+ options[:label_html] = options.dup if apply_options
14
+ wrap_with :label, label, options
15
+ end
16
+
17
+ protected
18
+
19
+ def human_attribute_name(attribute) #:nodoc:
20
+ @object.class.human_attribute_name(attribute.to_s)
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,4 @@
1
+ en:
2
+ show_for:
3
+ "yes": 'Yes'
4
+ "no": 'No'
@@ -0,0 +1,3 @@
1
+ module ShowFor
2
+ VERSION = "0.1".freeze
3
+ end
data/lib/show_for.rb ADDED
@@ -0,0 +1,42 @@
1
+ require 'show_for/helper'
2
+
3
+ module ShowFor
4
+ autoload :Builder, 'show_for/builder'
5
+
6
+ mattr_accessor :show_for_tag
7
+ @@show_for_tag = :div
8
+
9
+ mattr_accessor :label_tag
10
+ @@label_tag = :strong
11
+
12
+ mattr_accessor :separator
13
+ @@separator = "<br />"
14
+
15
+ mattr_accessor :content_tag
16
+ @@content_tag = nil
17
+
18
+ mattr_accessor :wrapper_tag
19
+ @@wrapper_tag = :p
20
+
21
+ mattr_accessor :collection_tag
22
+ @@collection_tag = :ul
23
+
24
+ mattr_accessor :default_collection_proc
25
+ @@default_collection_proc = lambda { |value| "<li>#{value}</li>" }
26
+
27
+ mattr_accessor :i18n_format
28
+ @@i18n_format = :default
29
+
30
+ mattr_accessor :association_methods
31
+ @@association_methods = [ :name, :title, :to_s ]
32
+
33
+ # Yield self for configuration block:
34
+ #
35
+ # ShowFor.setup do |config|
36
+ # config.i18n_format = :long
37
+ # end
38
+ #
39
+ def self.setup
40
+ yield self
41
+ end
42
+ end
@@ -0,0 +1,305 @@
1
+ require 'test_helper'
2
+
3
+ class BuilderTest < ActionView::TestCase
4
+
5
+ def with_attribute_for(object, attribute, options={}, &block)
6
+ show_for object do |o|
7
+ concat(o.attribute(attribute, options, &block))
8
+ end
9
+ end
10
+
11
+ def with_association_for(object, association, options={}, &block)
12
+ show_for object do |o|
13
+ concat(o.association(association, options, &block))
14
+ end
15
+ end
16
+
17
+ def with_label_for(object, attribute, options={})
18
+ show_for object do |o|
19
+ concat o.label attribute, options
20
+ end
21
+ end
22
+
23
+ def with_content_for(object, value, options={})
24
+ show_for object do |o|
25
+ concat o.content value, options
26
+ end
27
+ end
28
+
29
+ # WRAPPER
30
+ test "show_for attribute wraps each attribute with a label and content" do
31
+ with_attribute_for @user, :name
32
+ assert_select "div.show_for p.user_name.wrapper"
33
+ assert_select "div.show_for p.wrapper strong.label"
34
+ assert_select "div.show_for p.wrapper"
35
+ end
36
+
37
+ test "show_for allows wrapper tag to be changed by attribute" do
38
+ with_attribute_for @user, :name, :wrapper_tag => :span
39
+ assert_select "div.show_for span.user_name.wrapper"
40
+ end
41
+
42
+ test "show_for allows wrapper html to be configured by attribute" do
43
+ with_attribute_for @user, :name, :wrapper_html => { :id => "thewrapper", :class => "special" }
44
+ assert_select "div.show_for p#thewrapper.user_name.wrapper.special"
45
+ end
46
+
47
+ # SEPARATOR
48
+ test "show_for uses a separator if requested" do
49
+ with_attribute_for @user, :name
50
+ assert_select "div.show_for p.wrapper br"
51
+ end
52
+
53
+ test "show_for does not blow if a separator is not set" do
54
+ swap ShowFor, :separator => nil do
55
+ with_attribute_for @user, :name
56
+ assert_select "div.show_for p.wrapper"
57
+ end
58
+ end
59
+
60
+ # LABEL
61
+ test "show_for shows a label using the humanized attribute name from model" do
62
+ with_attribute_for @user, :name
63
+ assert_select "div.show_for p.wrapper strong.label", "Super User Name!"
64
+ end
65
+
66
+ test "show_for skips label if requested" do
67
+ with_attribute_for @user, :name, :label => false
68
+ assert_no_select "div.show_for p.wrapper strong.label"
69
+ end
70
+
71
+ test "show_for allows label to be configured globally" do
72
+ swap ShowFor, :label_tag => :span do
73
+ with_attribute_for @user, :name
74
+ assert_select "div.show_for p.wrapper span.label"
75
+ end
76
+ end
77
+
78
+ test "show_for allows label to be changed by attribute" do
79
+ with_attribute_for @user, :name, :label_tag => :span
80
+ assert_select "div.show_for p.wrapper span.label"
81
+ end
82
+
83
+ test "show_for allows label html to be configured by attribute" do
84
+ with_attribute_for @user, :name, :label_html => { :id => "thelabel", :class => "special" }
85
+ assert_select "div.show_for p.wrapper strong#thelabel.special.label"
86
+ end
87
+
88
+ test "show_for allows label to be set without lookup" do
89
+ with_attribute_for @user, :name, :label => "Special Label"
90
+ assert_select "div.show_for p.wrapper strong.label", "Special Label"
91
+ end
92
+
93
+ test "show_for#label accepts the text" do
94
+ with_label_for @user, "Special Label"
95
+ assert_select "div.show_for strong.label", "Special Label"
96
+ end
97
+
98
+ test "show_for#label accepts an attribute name" do
99
+ with_label_for @user, :name
100
+ assert_select "div.show_for strong.label", "Super User Name!"
101
+ end
102
+
103
+ test "show_for#label accepts html options" do
104
+ with_label_for @user, :name, :id => "thelabel", :class => "special"
105
+ assert_select "div.show_for strong#thelabel.special.label"
106
+ end
107
+
108
+ # CONTENT
109
+ test "show_for allows content tag to be configured globally" do
110
+ swap ShowFor, :content_tag => :span do
111
+ with_attribute_for @user, :name
112
+ assert_select "div.show_for p.wrapper span.content"
113
+ end
114
+ end
115
+
116
+ test "show_for allows content tag to be changed by attribute" do
117
+ with_attribute_for @user, :name, :content_tag => :span
118
+ assert_select "div.show_for p.wrapper span.content"
119
+ end
120
+
121
+ test "show_for allows content tag html to be configured by attribute" do
122
+ with_attribute_for @user, :name, :content_tag => :span, :content_html => { :id => "thecontent", :class => "special" }
123
+ assert_select "div.show_for p.wrapper span#thecontent.special.content"
124
+ end
125
+
126
+ test "show_for accepts an attribute as string" do
127
+ with_attribute_for @user, :name
128
+ assert_select "div.show_for p.wrapper", /ShowFor/
129
+ end
130
+
131
+ test "show_for accepts an attribute as time" do
132
+ with_attribute_for @user, :created_at
133
+ assert_select "div.show_for p.wrapper", /#{Regexp.escape(I18n.l(@user.created_at))}/
134
+ end
135
+
136
+ test "show_for accepts an attribute as date" do
137
+ with_attribute_for @user, :updated_at
138
+ assert_select "div.show_for p.wrapper", /#{Regexp.escape(I18n.l(@user.updated_at))}/
139
+ end
140
+
141
+ test "show_for accepts an attribute as time with format options" do
142
+ with_attribute_for @user, :created_at, :format => :long
143
+ assert_select "div.show_for p.wrapper", /#{Regexp.escape(I18n.l(@user.created_at, :format => :long))}/
144
+ end
145
+
146
+ test "show_for accepts an attribute as true" do
147
+ with_attribute_for @user, :active
148
+ assert_select "div.show_for p.wrapper", /Yes/
149
+ end
150
+
151
+ test "show_for accepts an attribute as true which can be localized" do
152
+ store_translations(:en, :show_for => { :yes => "Hell yeah!" }) do
153
+ with_attribute_for @user, :active
154
+ assert_select "div.show_for p.wrapper", /Hell yeah!/
155
+ end
156
+ end
157
+
158
+ test "show_for accepts an attribute as false" do
159
+ with_attribute_for @user, :invalid
160
+ assert_select "div.show_for p.wrapper", /No/
161
+ end
162
+
163
+ test "show_for accepts an attribute as false which can be localized" do
164
+ store_translations(:en, :show_for => { :no => "Hell no!" }) do
165
+ with_attribute_for @user, :invalid
166
+ assert_select "div.show_for p.wrapper", /Hell no!/
167
+ end
168
+ end
169
+
170
+ test "show_for accepts nil and or blank attributes" do
171
+ with_attribute_for @user, :description
172
+ assert_select "div.show_for p.wrapper", "Description"
173
+ end
174
+
175
+ test "show_for uses :if_blank if attribute is blank" do
176
+ with_attribute_for @user, :description, :if_blank => "No description provided"
177
+ assert_select "div.show_for p.wrapper", /No description provided/
178
+ end
179
+
180
+ test "show_for accepts a block to supply the content" do
181
+ with_attribute_for @user, :description do
182
+ "This description is not blank"
183
+ end
184
+ assert_select "div.show_for p.wrapper", /This description/
185
+ end
186
+
187
+ test "show_for escapes content by default" do
188
+ @user.name = "<b>hack you!</b>"
189
+ with_attribute_for @user, :name
190
+ assert_no_select "div.show_for p.wrapper b"
191
+ assert_select "div.show_for p.wrapper", /&lt;b&gt;/
192
+ end
193
+
194
+ test "show_for does not escape content if chosen" do
195
+ @user.name = "<b>hack you!</b>"
196
+ with_attribute_for @user, :name, :escape => false
197
+ assert_select "div.show_for p.wrapper b", "hack you!"
198
+ end
199
+
200
+ test "show_for#content accepts any object" do
201
+ with_content_for @user, "Special content"
202
+ assert_select "div.show_for", "Special content"
203
+ end
204
+
205
+ test "show_for#content accepts :if_blank as option" do
206
+ with_content_for @user, "", :if_blank => "Got blank"
207
+ assert_select "div.show_for", "Got blank"
208
+ end
209
+
210
+ test "show_for#content accepts html options" do
211
+ with_content_for @user, "Special content", :content_tag => :b, :id => "thecontent", :class => "special"
212
+ assert_select "div.show_for b#thecontent.special.content", "Special content"
213
+ end
214
+
215
+ # COLLECTIONS
216
+ test "show_for accepts an attribute as a collection" do
217
+ with_attribute_for @user, :scopes
218
+ assert_select "div.show_for p.wrapper ul.collection"
219
+ assert_select "div.show_for p.wrapper ul.collection li", :count => 3
220
+ end
221
+
222
+ test "show_for accepts an attribute as a collection with a block to iterate the collection" do
223
+ with_attribute_for @user, :scopes do |scope|
224
+ content_tag :span, scope
225
+ end
226
+ assert_select "div.show_for p.wrapper ul.collection"
227
+ assert_select "div.show_for p.wrapper ul.collection span", :count => 3
228
+ end
229
+
230
+ test "show_for allows collection tag to be configured globally" do
231
+ swap ShowFor, :collection_tag => :ol do
232
+ with_attribute_for @user, :scopes
233
+ assert_select "div.show_for p.wrapper ol.collection"
234
+ end
235
+ end
236
+
237
+ test "show_for allows collection tag to be changed by attribute" do
238
+ with_attribute_for @user, :scopes, :collection_tag => :ol
239
+ assert_select "div.show_for p.wrapper ol.collection"
240
+ end
241
+
242
+ test "show_for allows collection tag html to be configured by attribute" do
243
+ with_attribute_for @user, :scopes, :collection_html => { :id => "thecollection", :class => "special" }
244
+ assert_select "div.show_for p.wrapper ul#thecollection.special.collection"
245
+ end
246
+
247
+ # ASSOCIATIONS
248
+ test "show_for works with belongs_to/has_one associations" do
249
+ with_association_for @user, :company
250
+ assert_select "div.show_for p.wrapper", /PlataformaTec/
251
+ end
252
+
253
+ test "show_for accepts :method as option to tell how to retrieve association value" do
254
+ with_association_for @user, :company, :method => :alternate_name
255
+ assert_select "div.show_for p.wrapper", /Alternate PlataformaTec/
256
+ end
257
+
258
+ test "show_for works with has_many/has_and_belongs_to_many associations" do
259
+ with_association_for @user, :tags
260
+ assert_select "div.show_for p.wrapper ul.collection"
261
+ assert_select "div.show_for p.wrapper ul.collection li", "Tag 1"
262
+ assert_select "div.show_for p.wrapper ul.collection li", "Tag 2"
263
+ assert_select "div.show_for p.wrapper ul.collection li", "Tag 3"
264
+ end
265
+
266
+ test "show_for accepts :method as option to tell how to retrieve association values" do
267
+ with_association_for @user, :tags, :method => :alternate_name
268
+ assert_select "div.show_for p.wrapper ul.collection"
269
+ assert_select "div.show_for p.wrapper ul.collection li", "Alternate Tag 1"
270
+ assert_select "div.show_for p.wrapper ul.collection li", "Alternate Tag 2"
271
+ assert_select "div.show_for p.wrapper ul.collection li", "Alternate Tag 3"
272
+ end
273
+
274
+ test "show_for accepts :to_sentence as option in collection associations" do
275
+ with_association_for @user, :tags, :to_sentence => true
276
+ assert_no_select "div.show_for p.wrapper ul.collection"
277
+ assert_select "div.show_for p.wrapper", /Tag 1, Tag 2, and Tag 3/
278
+ end
279
+
280
+ test "show_for accepts :join as option in collection associations" do
281
+ with_association_for @user, :tags, :join => ", "
282
+ assert_no_select "div.show_for p.wrapper ul.collection"
283
+ assert_select "div.show_for p.wrapper", /Tag 1, Tag 2, Tag 3/
284
+ end
285
+
286
+ test "show_for accepts a block without argument in collection associations" do
287
+ with_association_for @user, :tags do
288
+ @user.tags.map(&:name).to_sentence
289
+ end
290
+ assert_no_select "div.show_for p.wrapper ul.collection"
291
+ assert_select "div.show_for p.wrapper", /Tag 1, Tag 2, and Tag 3/
292
+ end
293
+
294
+ test "show_for accepts a block with argument in collection associations" do
295
+ with_association_for @user, :tags, :collection_tag => :p do |tag|
296
+ assert_kind_of Tag, tag
297
+ content_tag(:span, tag.name)
298
+ end
299
+ assert_no_select "div.show_for p.wrapper ul.collection"
300
+ assert_select "div.show_for p.wrapper p.collection"
301
+ assert_select "div.show_for p.wrapper p.collection span", "Tag 1"
302
+ assert_select "div.show_for p.wrapper p.collection span", "Tag 2"
303
+ assert_select "div.show_for p.wrapper p.collection span", "Tag 3"
304
+ end
305
+ end
@@ -0,0 +1,31 @@
1
+ require "test_helper"
2
+
3
+ class HelperTest < ActionView::TestCase
4
+ test "show for yields an instance of ShowFor::Builder" do
5
+ show_for @user do |f|
6
+ assert f.instance_of?(ShowFor::Builder)
7
+ end
8
+ end
9
+
10
+ test "show for should add default class to form" do
11
+ show_for @user do |f| end
12
+ assert_select "div.show_for"
13
+ end
14
+
15
+ test "show for should add object class name as css class to form" do
16
+ show_for @user do |f| end
17
+ assert_select "div.show_for.user"
18
+ end
19
+
20
+ test "show for should pass options" do
21
+ show_for @user, :id => "my_div", :class => "common" do |f| end
22
+ assert_select "div#my_div.show_for.user.common"
23
+ end
24
+
25
+ test "show for tag should be configurable" do
26
+ swap ShowFor, :show_for_tag => :p do
27
+ show_for @user do |f| end
28
+ assert_select "p.show_for"
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,29 @@
1
+ module MiscHelpers
2
+ def store_translations(locale, translations, &block)
3
+ begin
4
+ I18n.backend.store_translations locale, translations
5
+ yield
6
+ ensure
7
+ I18n.reload!
8
+ end
9
+ end
10
+
11
+ def assert_no_select(*args)
12
+ assert_raise Test::Unit::AssertionFailedError do
13
+ assert_select(*args)
14
+ end
15
+ end
16
+
17
+ def swap(object, new_values)
18
+ old_values = {}
19
+ new_values.each do |key, value|
20
+ old_values[key] = object.send key
21
+ object.send :"#{key}=", value
22
+ end
23
+ yield
24
+ ensure
25
+ old_values.each do |key, value|
26
+ object.send :"#{key}=", value
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,45 @@
1
+ require 'ostruct'
2
+
3
+ class Company < Struct.new(:id, :name)
4
+ def alternate_name
5
+ "Alternate #{self.name}"
6
+ end
7
+ end
8
+
9
+ class Tag < Struct.new(:id, :name)
10
+ def self.all(options={})
11
+ (1..3).map{ |i| Tag.new(i, "Tag #{i}") }
12
+ end
13
+
14
+ def alternate_name
15
+ "Alternate #{self.name}"
16
+ end
17
+ end
18
+
19
+ class User < OpenStruct
20
+ # Get rid of deprecation warnings
21
+ undef_method :id
22
+
23
+ def tags
24
+ Tag.all
25
+ end
26
+
27
+ def company
28
+ Company.new(1, "PlataformaTec")
29
+ end
30
+
31
+ def self.human_attribute_name(attribute)
32
+ case attribute
33
+ when 'name'
34
+ 'Super User Name!'
35
+ when 'company'
36
+ 'Company Human Name!'
37
+ else
38
+ attribute.humanize
39
+ end
40
+ end
41
+
42
+ def self.human_name
43
+ "User"
44
+ end
45
+ end
@@ -0,0 +1,37 @@
1
+ require 'rubygems'
2
+ require 'test/unit'
3
+
4
+ require 'action_controller'
5
+ require 'action_view/test_case'
6
+
7
+ begin
8
+ require 'ruby-debug'
9
+ rescue LoadError
10
+ end
11
+
12
+ $:.unshift File.join(File.dirname(__FILE__), '..', 'lib', 'show_for')
13
+ require 'show_for'
14
+
15
+ Dir["#{File.dirname(__FILE__)}/support/*.rb"].each { |f| require f }
16
+ I18n.default_locale = :en
17
+
18
+ class ActionView::TestCase
19
+ include MiscHelpers
20
+
21
+ tests ShowFor::Helper
22
+
23
+ setup :setup_new_user
24
+
25
+ def setup_new_user(options={})
26
+ @user = User.new({
27
+ :id => 1,
28
+ :name => 'ShowFor',
29
+ :description => '',
30
+ :active => true,
31
+ :invalid => false,
32
+ :scopes => ["admin", "manager", "visitor"],
33
+ :created_at => Time.now,
34
+ :updated_at => Date.today
35
+ }.merge(options))
36
+ end
37
+ end
metadata ADDED
@@ -0,0 +1,70 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: show_for
3
+ version: !ruby/object:Gem::Version
4
+ version: "0.1"
5
+ platform: ruby
6
+ authors:
7
+ - "Jos\xC3\xA9 Valim"
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2010-01-08 00:00:00 +01:00
13
+ default_executable:
14
+ dependencies: []
15
+
16
+ description: Wrap your objects with a helper to easily show them
17
+ email: contact@plataformatec.com.br
18
+ executables: []
19
+
20
+ extensions: []
21
+
22
+ extra_rdoc_files:
23
+ - README.rdoc
24
+ files:
25
+ - generators/show_for_install/USAGE
26
+ - generators/show_for_install/show_for_install_generator.rb
27
+ - generators/show_for_install/templates/show_for.rb
28
+ - init.rb
29
+ - lib/show_for.rb
30
+ - lib/show_for/builder.rb
31
+ - lib/show_for/content.rb
32
+ - lib/show_for/helper.rb
33
+ - lib/show_for/label.rb
34
+ - lib/show_for/locale/en.yml
35
+ - lib/show_for/version.rb
36
+ - README.rdoc
37
+ has_rdoc: true
38
+ homepage: http://github.com/plataformatec/show_for
39
+ licenses: []
40
+
41
+ post_install_message:
42
+ rdoc_options:
43
+ - --charset=UTF-8
44
+ require_paths:
45
+ - lib
46
+ required_ruby_version: !ruby/object:Gem::Requirement
47
+ requirements:
48
+ - - ">="
49
+ - !ruby/object:Gem::Version
50
+ version: "0"
51
+ version:
52
+ required_rubygems_version: !ruby/object:Gem::Requirement
53
+ requirements:
54
+ - - ">="
55
+ - !ruby/object:Gem::Version
56
+ version: "0"
57
+ version:
58
+ requirements: []
59
+
60
+ rubyforge_project:
61
+ rubygems_version: 1.3.5
62
+ signing_key:
63
+ specification_version: 3
64
+ summary: Wrap your objects with a helper to easily show them
65
+ test_files:
66
+ - test/builder_test.rb
67
+ - test/helper_test.rb
68
+ - test/support/misc_helpers.rb
69
+ - test/support/models.rb
70
+ - test/test_helper.rb