table_cloth 0.1.0 → 0.1.1

Sign up to get free protection for your applications and to get access to all the features.
data/.travis.yml ADDED
@@ -0,0 +1,2 @@
1
+ before_install:
2
+ - gem install nokogiri -- --with-cflags='--std=gnu99'
data/README.md CHANGED
@@ -2,6 +2,8 @@
2
2
 
3
3
  Table Cloth gives you an easy to use DSL for creating and rendering tables in rails.
4
4
 
5
+ [![Build Status](https://travis-ci.org/bobbytables/table_cloth.png)](https://travis-ci.org/bobbytables/table_cloth)
6
+
5
7
  ## Installation
6
8
 
7
9
  Add this line to your application's Gemfile:
@@ -72,6 +74,67 @@ The second approach to making tables with Table Cloth is in the view.
72
74
  <% end %>
73
75
  ```
74
76
 
77
+ ## Columns
78
+
79
+ You can create your own column by making a class that responds to ```.value(object, view)```
80
+
81
+ ```ruby
82
+ class ImageColumn < TableCloth::Column
83
+ def value(object, view)
84
+ view.raw(view.image_tag(object.image_url))
85
+ end
86
+ end
87
+ ```
88
+
89
+ In your table
90
+ ```
91
+ <%= simple_table_for @users do |table| %>
92
+ <% table.column :name %>
93
+ <% table.column :image, using: ImageColumn %>
94
+ <% end %>
95
+ ```
96
+
97
+ ## Actions
98
+
99
+ A lot of tables have an actions column to give you the full CRUD effect. They can be painful but Table Cloth incorporates a way to easily add them to your definition.
100
+
101
+ ```
102
+ class UserTable < TableCloth::Base
103
+ column :name
104
+ action {|object, view| view.link_to 'View', object }
105
+ action(if: :admin?) {|object, view| view.link_to 'Delete', object, method: :delete }
106
+
107
+ def admin?
108
+ view.current_user.admin?
109
+ end
110
+ end
111
+ ```
112
+
113
+
114
+ ## Configuration
115
+
116
+ Create an initializer called ```table_cloth.rb```
117
+
118
+ Configuration looks like this:
119
+
120
+ ```ruby
121
+ TableCloth::Configuration.configure do |config|
122
+ config.table.class = 'table table-bordered'
123
+ config.thead.class = ''
124
+ config.tbody.class = ''
125
+ config.tr.class =''
126
+ config.th.class =''
127
+ config.td.class =''
128
+ end
129
+ ```
130
+
131
+ You can set any value on table element configurations. For example:
132
+
133
+ ```ruby
134
+ config.table.cellpadding = 1
135
+ config.td.valign = 'top'
136
+ ```
137
+
75
138
  ## Contributing
76
139
 
77
140
  1. Fork it
data/Rakefile CHANGED
@@ -1 +1,4 @@
1
- require "bundler/gem_tasks"
1
+ require 'rspec/core/rake_task'
2
+
3
+ RSpec::Core::RakeTask.new(:spec)
4
+ task default: :spec
@@ -5,5 +5,17 @@ module TableCloth
5
5
  def initialize(options)
6
6
  @options = options
7
7
  end
8
+
9
+ def available?(table)
10
+ if options[:if] && options[:if].is_a?(Symbol)
11
+ return !!table.send(options[:if])
12
+ end
13
+
14
+ if options[:unless] && options[:unless].is_a?(Symbol)
15
+ return !table.send(options[:unless])
16
+ end
17
+
18
+ true
19
+ end
8
20
  end
9
21
  end
@@ -39,8 +39,10 @@ module TableCloth
39
39
  options = args.extract_options! || {}
40
40
  options[:proc] = block if block_given?
41
41
 
42
+ column_class = options.delete(:using) || Column
43
+
42
44
  args.each do |name|
43
- add_column name, Column.new(name, options)
45
+ add_column name, column_class.new(name, options)
44
46
  end
45
47
  end
46
48
 
@@ -71,6 +73,7 @@ module TableCloth
71
73
  end
72
74
 
73
75
  columns[:actions].actions << action
76
+ action
74
77
  end
75
78
 
76
79
  def has_actions?
@@ -7,7 +7,7 @@ module TableCloth
7
7
  @options = options
8
8
  end
9
9
 
10
- def value(object, view)
10
+ def value(object, view, table=nil)
11
11
  if options[:proc] && options[:proc].respond_to?(:call)
12
12
  view.capture(object, options, view, &options[:proc])
13
13
  else
@@ -16,7 +16,7 @@ module TableCloth
16
16
  end
17
17
 
18
18
  def human_name
19
- name.to_s.humanize
19
+ options[:label] || name.to_s.humanize
20
20
  end
21
21
 
22
22
  def available?(table)
@@ -1,9 +1,13 @@
1
1
  module TableCloth
2
2
  module Columns
3
3
  class Action < Column
4
- def value(object, view_context)
4
+ def value(object, view_context, table)
5
5
  actions_html = actions.inject('') do |links, action|
6
- links + "\n" + view_context.capture(object, view_context, &action.options[:proc])
6
+ if action.available?(table)
7
+ links + "\n" + view_context.capture(object, view_context, &action.options[:proc])
8
+ else
9
+ links
10
+ end
7
11
  end
8
12
 
9
13
  view_context.raw(actions_html)
@@ -12,6 +16,10 @@ module TableCloth
12
16
  def actions
13
17
  @actions ||= []
14
18
  end
19
+
20
+ def available?(table)
21
+ actions.any? {|a| a.available?(table) }
22
+ end
15
23
  end
16
24
  end
17
25
  end
@@ -33,7 +33,7 @@ module TableCloth
33
33
 
34
34
  def row_values(object)
35
35
  column_values = table.columns.inject([]) do |values, (key, column)|
36
- values << column.value(object, view_context); values
36
+ values << column.value(object, view_context, table); values
37
37
  end
38
38
  end
39
39
 
@@ -1,3 +1,3 @@
1
1
  module TableCloth
2
- VERSION = "0.1.0"
2
+ VERSION = "0.1.1"
3
3
  end
@@ -3,6 +3,13 @@ require 'spec_helper'
3
3
  describe TableCloth::Base do
4
4
  subject { Class.new(TableCloth::Base) }
5
5
  let(:view_context) { ActionView::Base.new }
6
+ let(:dummy_model) do
7
+ DummyModel.new.tap do |d|
8
+ d.id = 1
9
+ d.email = 'robert@example.com'
10
+ d.name = 'robert'
11
+ end
12
+ end
6
13
 
7
14
  context 'columns' do
8
15
  it 'has a column method' do
@@ -19,12 +26,12 @@ describe TableCloth::Base do
19
26
 
20
27
  it '.columns returns all columns' do
21
28
  subject.column :name
22
- subject.columns.size.should == 1
29
+ subject.should have(1).columns
23
30
  end
24
31
 
25
32
  it 'excepts multiple column names' do
26
33
  subject.column :name, :email
27
- subject.columns.size.should == 2
34
+ subject.should have(2).columns
28
35
  end
29
36
 
30
37
  it 'stores a proc if given in options' do
@@ -44,17 +51,52 @@ describe TableCloth::Base do
44
51
  subject.action { '/' }
45
52
  subject.new([], view_context).column_names.should include 'Actions'
46
53
  end
47
- end
48
54
 
49
- context 'conditions' do
50
- let(:dummy_model) do
51
- DummyModel.new.tap do |d|
52
- d.id = 1
53
- d.email = 'robert@example.com'
54
- d.name = 'robert'
55
+ it '.column_names does not include actions if all action conditions fail' do
56
+ subject.action(if: :admin?) { '/' }
57
+ table = subject.new([], view_context)
58
+ def table.admin?
59
+ false
60
+ end
61
+
62
+ table.column_names.should_not include 'Actions'
63
+ end
64
+
65
+ it '.column_names include actions when only partial are available' do
66
+ subject.action(if: :admin?) { '/' }
67
+ subject.action(if: :awesome?) { '/' }
68
+ table = subject.new([], view_context)
69
+ def table.admin?
70
+ false
71
+ end
72
+
73
+ def table.awesome?
74
+ true
75
+ end
76
+
77
+ table.column_names.should include 'Actions'
78
+ end
79
+
80
+ it '.column_names uses a name given to it' do
81
+ subject.column :email, label: 'Email Address'
82
+ subject.new([], view_context).column_names.should include 'Email Address'
83
+ end
84
+
85
+ it '.column can take a custom column' do
86
+ email_column = Class.new(TableCloth::Column) do
87
+ def value(object, view)
88
+ "AN EMAIL!"
89
+ end
55
90
  end
91
+
92
+ subject.column :email, using: email_column
93
+ subject.new([dummy_model], view_context)
94
+
95
+ subject.columns[:email].value(dummy_model, view_context).should == "AN EMAIL!"
56
96
  end
97
+ end
57
98
 
99
+ context 'conditions' do
58
100
  context 'if' do
59
101
  subject { DummyTable.new([dummy_model], view_context) }
60
102
 
@@ -98,7 +140,23 @@ describe TableCloth::Base do
98
140
 
99
141
  it 'it adds an acion' do
100
142
  subject.action { '/' }
101
- subject.columns[:actions].actions.size.should == 1
143
+ subject.columns[:actions].should have(1).actions
144
+ end
145
+
146
+ context 'conditionals' do
147
+ let!(:table_class) { Class.new(DummyTable) }
148
+ subject { table_class.new([dummy_model], view_context) }
149
+
150
+ it 'accepts if condition' do
151
+ action = table_class.action(if: :admin?) { '/conditioned' }
152
+ action.available?(subject).should be_true
153
+ end
154
+
155
+
156
+ it 'accepts unless condition' do
157
+ action = table_class.action(unless: :admin?) { '/conditioned' }
158
+ action.available?(subject).should be_false
159
+ end
102
160
  end
103
161
  end
104
162
  end
@@ -28,4 +28,21 @@ describe TableCloth::Columns::Action do
28
28
  link.should be_present
29
29
  link[:href].should == '1'
30
30
  end
31
+
32
+ it '.value only returns actions that pass' do
33
+ admin_action = dummy_table.action(if: :admin?) { '/admin' }
34
+ moderator_action = dummy_table.action(if: :moderator?) { '/moderator' }
35
+ table = dummy_table.new([], view_context)
36
+
37
+ def table.admin?
38
+ true
39
+ end
40
+
41
+ def table.moderator?
42
+ false
43
+ end
44
+
45
+ dummy_table.columns[:actions].value(dummy_model, view_context, table).should include '/admin'
46
+ dummy_table.columns[:actions].value(dummy_model, view_context, table).should_not include '/moderator'
47
+ end
31
48
  end
data/table_cloth.gemspec CHANGED
@@ -22,6 +22,7 @@ Gem::Specification.new do |gem|
22
22
  gem.add_development_dependency('nokogiri')
23
23
  gem.add_development_dependency('pry')
24
24
  gem.add_development_dependency('guard-rspec')
25
+ gem.add_development_dependency('rake')
25
26
 
26
27
  gem.add_dependency('actionpack', '~> 3.2')
27
28
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: table_cloth
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.1.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-10-02 00:00:00.000000000 Z
12
+ date: 2012-10-04 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rspec
@@ -91,6 +91,22 @@ dependencies:
91
91
  - - ! '>='
92
92
  - !ruby/object:Gem::Version
93
93
  version: '0'
94
+ - !ruby/object:Gem::Dependency
95
+ name: rake
96
+ requirement: !ruby/object:Gem::Requirement
97
+ none: false
98
+ requirements:
99
+ - - ! '>='
100
+ - !ruby/object:Gem::Version
101
+ version: '0'
102
+ type: :development
103
+ prerelease: false
104
+ version_requirements: !ruby/object:Gem::Requirement
105
+ none: false
106
+ requirements:
107
+ - - ! '>='
108
+ - !ruby/object:Gem::Version
109
+ version: '0'
94
110
  - !ruby/object:Gem::Dependency
95
111
  name: actionpack
96
112
  requirement: !ruby/object:Gem::Requirement
@@ -116,6 +132,7 @@ extra_rdoc_files: []
116
132
  files:
117
133
  - .gitignore
118
134
  - .rspec
135
+ - .travis.yml
119
136
  - Gemfile
120
137
  - Guardfile
121
138
  - LICENSE.txt