brentano 0.0.1 → 0.0.2

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/Gemfile CHANGED
@@ -1,4 +1,4 @@
1
1
  source "http://rubygems.org"
2
2
 
3
3
  # Specify your gem's dependencies in brentano.gemspec
4
- gemspec
4
+ gemspec
@@ -0,0 +1,94 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ brentano (0.0.1)
5
+ activerecord (~> 3)
6
+ activesupport (~> 3)
7
+ hashie (>= 0.4)
8
+ railties (~> 3)
9
+
10
+ GEM
11
+ remote: http://rubygems.org/
12
+ specs:
13
+ abstract (1.0.0)
14
+ actionmailer (3.0.7)
15
+ actionpack (= 3.0.7)
16
+ mail (~> 2.2.15)
17
+ actionpack (3.0.7)
18
+ activemodel (= 3.0.7)
19
+ activesupport (= 3.0.7)
20
+ builder (~> 2.1.2)
21
+ erubis (~> 2.6.6)
22
+ i18n (~> 0.5.0)
23
+ rack (~> 1.2.1)
24
+ rack-mount (~> 0.6.14)
25
+ rack-test (~> 0.5.7)
26
+ tzinfo (~> 0.3.23)
27
+ activemodel (3.0.7)
28
+ activesupport (= 3.0.7)
29
+ builder (~> 2.1.2)
30
+ i18n (~> 0.5.0)
31
+ activerecord (3.0.7)
32
+ activemodel (= 3.0.7)
33
+ activesupport (= 3.0.7)
34
+ arel (~> 2.0.2)
35
+ tzinfo (~> 0.3.23)
36
+ activeresource (3.0.7)
37
+ activemodel (= 3.0.7)
38
+ activesupport (= 3.0.7)
39
+ activesupport (3.0.7)
40
+ arel (2.0.9)
41
+ builder (2.1.2)
42
+ diff-lcs (1.1.2)
43
+ erubis (2.6.6)
44
+ abstract (>= 1.0.0)
45
+ hashie (1.0.0)
46
+ i18n (0.5.0)
47
+ mail (2.2.19)
48
+ activesupport (>= 2.3.6)
49
+ i18n (>= 0.4.0)
50
+ mime-types (~> 1.16)
51
+ treetop (~> 1.4.8)
52
+ mime-types (1.16)
53
+ polyglot (0.3.1)
54
+ rack (1.2.2)
55
+ rack-mount (0.6.14)
56
+ rack (>= 1.0.0)
57
+ rack-test (0.5.7)
58
+ rack (>= 1.0)
59
+ rails (3.0.7)
60
+ actionmailer (= 3.0.7)
61
+ actionpack (= 3.0.7)
62
+ activerecord (= 3.0.7)
63
+ activeresource (= 3.0.7)
64
+ activesupport (= 3.0.7)
65
+ bundler (~> 1.0)
66
+ railties (= 3.0.7)
67
+ railties (3.0.7)
68
+ actionpack (= 3.0.7)
69
+ activesupport (= 3.0.7)
70
+ rake (>= 0.8.7)
71
+ thor (~> 0.14.4)
72
+ rake (0.8.7)
73
+ rspec (2.6.0)
74
+ rspec-core (~> 2.6.0)
75
+ rspec-expectations (~> 2.6.0)
76
+ rspec-mocks (~> 2.6.0)
77
+ rspec-core (2.6.0)
78
+ rspec-expectations (2.6.0)
79
+ diff-lcs (~> 1.1.2)
80
+ rspec-mocks (2.6.0)
81
+ sqlite3 (1.3.3)
82
+ thor (0.14.6)
83
+ treetop (1.4.9)
84
+ polyglot (>= 0.3.1)
85
+ tzinfo (0.3.27)
86
+
87
+ PLATFORMS
88
+ ruby
89
+
90
+ DEPENDENCIES
91
+ brentano!
92
+ rails (= 3.0.7)
93
+ rspec (~> 2)
94
+ sqlite3 (~> 1.3.3)
@@ -12,12 +12,16 @@ Gem::Specification.new do |s|
12
12
  s.summary = %q{Classy presenters for Rails 3}
13
13
  s.description = %q{Brentano helps you present ActiveRecord collections to your controllers and avoid repetitive ORM logic}
14
14
 
15
- s.rubyforge_project = "brentano"
16
-
17
- s.add_dependency "activesupport", "~> 3.0"
18
- s.add_dependency "activerecord", "~> 3.0"
19
- s.add_dependency "actionpack", "~> 3.0"
20
- s.add_dependency "hashie", "~> 0.4"
15
+ s.rubyforge_project = "Brentano"
16
+
17
+ s.add_dependency "activesupport", "~> 3"
18
+ s.add_dependency "activerecord", "~> 3"
19
+ s.add_dependency "railties", "~> 3"
20
+ s.add_dependency "hashie", ">= 0.4"
21
+
22
+ s.add_development_dependency "rails", '3.0.7'
23
+ s.add_development_dependency "sqlite3", "~> 1.3.3"
24
+ s.add_development_dependency "rspec", "~> 2"
21
25
 
22
26
  s.files = `git ls-files`.split("\n")
23
27
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
@@ -1,21 +1,21 @@
1
- require 'brentano/rails'
1
+ require 'brentano/railtie'
2
2
 
3
3
  module Brentano
4
-
4
+
5
5
  autoload :Presenter, 'brentano/presenter'
6
6
  autoload :Query, 'brentano/query'
7
-
7
+
8
8
  mattr_accessor :query_limit
9
9
  @@query_limit = 20
10
-
10
+
11
11
  mattr_accessor :qualifier_key
12
12
  @@qualifier_key = :options
13
-
13
+
14
14
  mattr_accessor :presenter_module
15
- @@presenter_module = "Presenters"
16
-
15
+ @@presenter_module = "Presenters"
16
+
17
17
  def config
18
18
  yield self
19
19
  end
20
-
21
- end
20
+
21
+ end
@@ -1,13 +1,15 @@
1
+ require 'hashie'
2
+
1
3
  module Brentano
2
4
  class Presenter
3
-
5
+
4
6
  class_attribute :sizes
5
7
 
6
8
  attr_reader :subject, :options, :collection, :maximum_size
7
9
 
8
10
  alias_method :proxy_respond_to?, :respond_to?
9
11
 
10
- def initialize(subject, options, &blk)
12
+ def initialize(subject, options = {}, &blk)
11
13
  @subject = subject
12
14
  @options = Hashie::Mash.new(options)
13
15
  yield self if block_given?
@@ -22,7 +24,7 @@ module Brentano
22
24
  @maximum_size = if size.is_a? Fixnum
23
25
  size
24
26
  else
25
- sizes[size]
27
+ sizes[size]
26
28
  end
27
29
  options.limit = @maximum_size
28
30
  end
@@ -53,6 +55,6 @@ module Brentano
53
55
  def to_sql
54
56
  @collection.to_sql
55
57
  end
56
-
58
+
57
59
  end
58
60
  end
@@ -3,38 +3,38 @@
3
3
  # queries from request params
4
4
  module Brentano
5
5
  class Query
6
-
6
+
7
7
  attr_accessor_with_default :allowed_methods, [:limit, :offset].freeze
8
8
  attr_accessor_with_default :allowed_scopes, [].freeze
9
9
  attr_accessor_with_default :absolute_limit, Brentano.query_limit
10
-
10
+
11
11
  def self.finish(relation, options)
12
- obj = new relation
12
+ obj = self.new relation
13
13
  yield obj if block_given?
14
14
  obj.apply options
15
15
  end
16
-
17
- def apply(options)
16
+
17
+ def apply(options)
18
18
  supplied_scopes = Array.wrap(options[:scopes] || options[:scope])
19
19
  supplied_scopes << "by_#{options[:by]}" if options[:by].present?
20
20
  supplied_scopes.map!(&:to_sym)
21
21
  scopes = allowed_scopes & supplied_scopes
22
- scoped_relation = scopes.inject(@relation) { |r, s| r.send(s) }
22
+ scoped_relation = scopes.inject(@relation) { |r, s| r.send(s) }
23
23
  if absolute_limit.present?
24
24
  options[:limit] ||= absolute_limit
25
25
  options[:limit] = [ options[:limit].to_i, absolute_limit ].min
26
26
  end
27
27
  options[:offset] &&= options[:offset].to_i
28
28
  options[:limit] &&= options[:limit].to_i
29
- allowed_methods.inject(scoped_relation) do |r, m|
29
+ allowed_methods.inject(scoped_relation) do |r, m|
30
30
  r = r.send(m, options[m]) if options[m].present?
31
31
  r
32
32
  end
33
33
  end
34
-
34
+
35
35
  def initialize(relation)
36
36
  @relation = relation
37
37
  end
38
-
38
+
39
39
  end
40
40
  end
@@ -1,14 +1,13 @@
1
- require 'brentano/rails/helpers'
1
+ require File.join(File.dirname(__FILE__), '..', '..', 'rails', 'helpers')
2
2
 
3
3
  module Brentano
4
4
  class Railtie < ::Rails::Railtie
5
-
6
- initializer 'brentano.extend_action_contrller' do
5
+
6
+ initializer 'brentano.extend_action_controller' do
7
7
  ActiveSupport.on_load(:action_controller) do
8
8
  self.send :include, Brentano::Helpers
9
9
  end
10
10
  end
11
-
12
- end
13
- end
14
11
 
12
+ end
13
+ end
@@ -1,3 +1,3 @@
1
1
  module Brentano
2
- VERSION = "0.0.1"
2
+ VERSION = "0.0.2"
3
3
  end
@@ -1,10 +1,10 @@
1
1
  module Brentano
2
2
  module Helpers
3
-
4
- def presenter(klass_name, subject, options = params[Brentano.qualifier_key], &blk)
3
+
4
+ def presenter(klass_name, subject, options = params[Brentano.qualifier_key], &blk)
5
5
  klass = "#{Brentano.presenter_module}::#{klass_name.to_s.camelcase}".constantize
6
6
  klass.new subject, options, &blk
7
7
  end
8
-
8
+
9
9
  end
10
10
  end
@@ -0,0 +1,164 @@
1
+ require File.join(File.dirname(__FILE__), 'spec_helper')
2
+
3
+ describe TestPresenter do
4
+
5
+ before { @subject = Post.first }
6
+
7
+ describe ".new" do
8
+
9
+ it "sets the subject instance variable" do
10
+ presenter = TestPresenter.new @subject
11
+ presenter.subject.should == @subject
12
+ end
13
+
14
+ context "when options are passed" do
15
+ before do
16
+ @options = { :limit => 10 }
17
+ @presenter = TestPresenter.new @subject, @options
18
+ end
19
+
20
+ it "sets the options instance variable" do
21
+ @presenter.options.with_indifferent_access.should == @options.with_indifferent_access
22
+ end
23
+
24
+ it "makes the options into a Hashie Mash" do
25
+ @presenter.options.should be_a(Hashie::Mash)
26
+ end
27
+
28
+ end
29
+
30
+ it "calls #finish" do
31
+ TestPresenter.any_instance.should_receive(:finish)
32
+ TestPresenter.new @subject
33
+ end
34
+
35
+ context "when a block is given" do
36
+ out = nil
37
+ it "yields self to the block" do
38
+ presenter = TestPresenter.new @subject do |obj|
39
+ out = obj
40
+ end
41
+ presenter.should equal(out)
42
+ end
43
+ end
44
+ end
45
+
46
+ describe "#finish" do
47
+ before { @presenter = TestPresenter.new @subject }
48
+ specify { @presenter.collection.should be }
49
+ end
50
+
51
+ describe "#maximum_size=" do
52
+ before { @presenter = TestPresenter.new @subject }
53
+
54
+ context "when the size is a Fixnum" do
55
+ before do
56
+ @size = 3
57
+ @presenter.maximum_size = @size
58
+ end
59
+
60
+ it "sets the maximum size instance variable to the size" do
61
+ @presenter.maximum_size.should eql(@size)
62
+ end
63
+
64
+ it "sets the limit option to the size" do
65
+ @presenter.options.limit.should eql(@size)
66
+ end
67
+ end
68
+
69
+ context "when the size is not a Fixnum" do
70
+ before do
71
+ @size = size = 4
72
+ @presenter.class_eval do
73
+ self.sizes = { :large => size }
74
+ end
75
+ @presenter.maximum_size = :large
76
+ end
77
+
78
+ it "sets the corresponding size" do
79
+ @presenter.maximum_size.should eql(@size)
80
+ end
81
+ end
82
+ end
83
+
84
+ describe "#respond_to?" do
85
+ before { @presenter = TestPresenter.new @subject }
86
+
87
+ context "given the presenter responds to the method" do
88
+ before { @presenter.stub(:foo) { "ok" } }
89
+ specify { @presenter.respond_to?(:foo).should be_true }
90
+ end
91
+
92
+ context "given the presenter does not respond to the method" do
93
+ before { @presenter.stub(:proxy_respond_to?) { |method| false } }
94
+
95
+ context "and the collection responds to the method" do
96
+ specify { @presenter.respond_to?(:find).should be_true }
97
+ end
98
+
99
+ context "and the collection does not respond to the method" do
100
+ before { @presenter.collection.stub(:respond_to?) { |method| false } }
101
+ specify { @presenter.respond_to?(:foo).should be_false }
102
+ end
103
+ end
104
+ end
105
+
106
+ describe "#method_missing" do
107
+ before do
108
+ @presenter = TestPresenter.new @subject
109
+ end
110
+
111
+ context "given the collection responds to the method" do
112
+
113
+ context "and the method returns an ActiveRecord::Relation" do
114
+ before do
115
+ @presenter.maximum_size = 2
116
+ @presenter.instance_variable_set :@options, :awesome => true
117
+ @method = [:limit, 1]
118
+ @result = @presenter.method_missing(*@method)
119
+ end
120
+ subject { @result }
121
+
122
+ describe "the result" do
123
+ specify { should be_a_kind_of Brentano::Presenter }
124
+
125
+ it "should have the same maximum size as receiver" do
126
+ @presenter.maximum_size.should eql(@result.maximum_size)
127
+ end
128
+
129
+ it "should have the same options as the receiver" do
130
+ @presenter.options.should eql(@result.options)
131
+ end
132
+
133
+ it "should have the collection set to the returned ActiveRecord::Relation" do
134
+ # Use #to_sql to compare the same method on the presenters collection
135
+ @result.collection.to_sql.should eql(@presenter.collection.send(*@method).to_sql)
136
+ end
137
+ end
138
+ end
139
+
140
+ context "and the method does not return an ActiveRecord::Relation" do
141
+ describe "the result" do
142
+ it "should be the same as if the method was sent to the collection directly" do
143
+ @presenter.method_missing(:to_a).should eql(@presenter.collection.to_a)
144
+ end
145
+ end
146
+ end
147
+ end
148
+ end
149
+
150
+ describe "#as_json" do
151
+ before { @presenter = TestPresenter.new @subject }
152
+ it "delegates to the collection" do
153
+ @presenter.as_json.should eql(@presenter.collection.as_json)
154
+ end
155
+ end
156
+
157
+ describe "#to_sql" do
158
+ before { @presenter = TestPresenter.new @subject }
159
+ it "delegates to the collection" do
160
+ @presenter.to_sql.should eql(@presenter.collection.to_sql)
161
+ end
162
+ end
163
+
164
+ end
@@ -0,0 +1 @@
1
+ require File.join(File.dirname(__FILE__), 'spec_helper')
@@ -0,0 +1,26 @@
1
+ SPEC_DIR = File.dirname(__FILE__)
2
+ lib_path = File.expand_path("#{SPEC_DIR}/../lib")
3
+ $LOAD_PATH.unshift lib_path unless $LOAD_PATH.include?(lib_path)
4
+
5
+ require 'rails'
6
+ require 'active_record'
7
+ require 'active_support/core_ext'
8
+
9
+ require 'brentano'
10
+
11
+ Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each { |f| require f }
12
+
13
+ RSpec.configure do |config|
14
+
15
+ config.before(:all) do
16
+ TestMigration.up
17
+ post = Post.new
18
+ 50.times { post.comments << Comment.new }
19
+ post.save
20
+ end
21
+
22
+ config.after(:all) do
23
+ TestMigration.down
24
+ end
25
+
26
+ end
@@ -0,0 +1,29 @@
1
+ dbconfig = {
2
+ :adapter => 'sqlite3',
3
+ :database => ':memory:'
4
+ }
5
+
6
+ ActiveRecord::Base.establish_connection(dbconfig)
7
+ ActiveRecord::Migration.verbose = false
8
+
9
+ class TestMigration < ActiveRecord::Migration
10
+ def self.up
11
+ create_table :posts, :force => true
12
+ create_table :comments, :force => true do |t|
13
+ t.references :post
14
+ end
15
+ end
16
+
17
+ def self.down
18
+ drop_table :posts
19
+ drop_table :comments
20
+ end
21
+ end
22
+
23
+ class Post < ActiveRecord::Base
24
+ has_many :comments
25
+ end
26
+
27
+ class Comment < ActiveRecord::Base
28
+ belongs_to :post
29
+ end
@@ -0,0 +1,22 @@
1
+ class TestPresenter < Brentano::Presenter
2
+
3
+ self.sizes = {
4
+ :large => 4
5
+ }
6
+
7
+ def relation
8
+ subject.comments
9
+ end
10
+
11
+ end
12
+
13
+ module CustomFinisher
14
+
15
+ def finish
16
+ super do |with|
17
+ with.absolute_limit = false
18
+ with.allowed_scopes = [ :by_rank ]
19
+ end
20
+ end
21
+
22
+ end
metadata CHANGED
@@ -1,12 +1,8 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: brentano
3
3
  version: !ruby/object:Gem::Version
4
- prerelease: false
5
- segments:
6
- - 0
7
- - 0
8
- - 1
9
- version: 0.0.1
4
+ prerelease:
5
+ version: 0.0.2
10
6
  platform: ruby
11
7
  authors:
12
8
  - Roberto Thais
@@ -14,7 +10,7 @@ autorequire:
14
10
  bindir: bin
15
11
  cert_chain: []
16
12
 
17
- date: 2011-01-24 00:00:00 -05:00
13
+ date: 2011-06-03 00:00:00 -04:00
18
14
  default_executable:
19
15
  dependencies:
20
16
  - !ruby/object:Gem::Dependency
@@ -25,10 +21,7 @@ dependencies:
25
21
  requirements:
26
22
  - - ~>
27
23
  - !ruby/object:Gem::Version
28
- segments:
29
- - 3
30
- - 0
31
- version: "3.0"
24
+ version: "3"
32
25
  type: :runtime
33
26
  version_requirements: *id001
34
27
  - !ruby/object:Gem::Dependency
@@ -39,24 +32,18 @@ dependencies:
39
32
  requirements:
40
33
  - - ~>
41
34
  - !ruby/object:Gem::Version
42
- segments:
43
- - 3
44
- - 0
45
- version: "3.0"
35
+ version: "3"
46
36
  type: :runtime
47
37
  version_requirements: *id002
48
38
  - !ruby/object:Gem::Dependency
49
- name: actionpack
39
+ name: railties
50
40
  prerelease: false
51
41
  requirement: &id003 !ruby/object:Gem::Requirement
52
42
  none: false
53
43
  requirements:
54
44
  - - ~>
55
45
  - !ruby/object:Gem::Version
56
- segments:
57
- - 3
58
- - 0
59
- version: "3.0"
46
+ version: "3"
60
47
  type: :runtime
61
48
  version_requirements: *id003
62
49
  - !ruby/object:Gem::Dependency
@@ -65,14 +52,44 @@ dependencies:
65
52
  requirement: &id004 !ruby/object:Gem::Requirement
66
53
  none: false
67
54
  requirements:
68
- - - ~>
55
+ - - ">="
69
56
  - !ruby/object:Gem::Version
70
- segments:
71
- - 0
72
- - 4
73
57
  version: "0.4"
74
58
  type: :runtime
75
59
  version_requirements: *id004
60
+ - !ruby/object:Gem::Dependency
61
+ name: rails
62
+ prerelease: false
63
+ requirement: &id005 !ruby/object:Gem::Requirement
64
+ none: false
65
+ requirements:
66
+ - - "="
67
+ - !ruby/object:Gem::Version
68
+ version: 3.0.7
69
+ type: :development
70
+ version_requirements: *id005
71
+ - !ruby/object:Gem::Dependency
72
+ name: sqlite3
73
+ prerelease: false
74
+ requirement: &id006 !ruby/object:Gem::Requirement
75
+ none: false
76
+ requirements:
77
+ - - ~>
78
+ - !ruby/object:Gem::Version
79
+ version: 1.3.3
80
+ type: :development
81
+ version_requirements: *id006
82
+ - !ruby/object:Gem::Dependency
83
+ name: rspec
84
+ prerelease: false
85
+ requirement: &id007 !ruby/object:Gem::Requirement
86
+ none: false
87
+ requirements:
88
+ - - ~>
89
+ - !ruby/object:Gem::Version
90
+ version: "2"
91
+ type: :development
92
+ version_requirements: *id007
76
93
  description: Brentano helps you present ActiveRecord collections to your controllers and avoid repetitive ORM logic
77
94
  email:
78
95
  - roberto.n.thais@gmail.com
@@ -85,15 +102,21 @@ extra_rdoc_files: []
85
102
  files:
86
103
  - .gitignore
87
104
  - Gemfile
105
+ - Gemfile.lock
88
106
  - README.md
89
107
  - Rakefile
90
108
  - brentano.gemspec
91
109
  - lib/brentano.rb
92
110
  - lib/brentano/presenter.rb
93
111
  - lib/brentano/query.rb
94
- - lib/brentano/rails.rb
95
- - lib/brentano/rails/helpers.rb
112
+ - lib/brentano/railtie.rb
96
113
  - lib/brentano/version.rb
114
+ - rails/helpers.rb
115
+ - spec/presenter_spec.rb
116
+ - spec/query_spec.rb
117
+ - spec/spec_helper.rb
118
+ - spec/support/active_record.rb
119
+ - spec/support/presenters.rb
97
120
  has_rdoc: true
98
121
  homepage: ""
99
122
  licenses: []
@@ -108,23 +131,23 @@ required_ruby_version: !ruby/object:Gem::Requirement
108
131
  requirements:
109
132
  - - ">="
110
133
  - !ruby/object:Gem::Version
111
- segments:
112
- - 0
113
134
  version: "0"
114
135
  required_rubygems_version: !ruby/object:Gem::Requirement
115
136
  none: false
116
137
  requirements:
117
138
  - - ">="
118
139
  - !ruby/object:Gem::Version
119
- segments:
120
- - 0
121
140
  version: "0"
122
141
  requirements: []
123
142
 
124
- rubyforge_project: brentano
125
- rubygems_version: 1.3.7
143
+ rubyforge_project: Brentano
144
+ rubygems_version: 1.6.2
126
145
  signing_key:
127
146
  specification_version: 3
128
147
  summary: Classy presenters for Rails 3
129
- test_files: []
130
-
148
+ test_files:
149
+ - spec/presenter_spec.rb
150
+ - spec/query_spec.rb
151
+ - spec/spec_helper.rb
152
+ - spec/support/active_record.rb
153
+ - spec/support/presenters.rb