mongo_mapper 0.8.0 → 0.8.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/lib/mongo_mapper.rb CHANGED
@@ -65,22 +65,6 @@ module MongoMapper
65
65
  autoload :OneEmbeddedProxy, 'mongo_mapper/plugins/associations/one_embedded_proxy'
66
66
  autoload :InArrayProxy, 'mongo_mapper/plugins/associations/in_array_proxy'
67
67
  end
68
-
69
- module DynamicQuerying
70
- autoload :DynamicFinder, 'mongo_mapper/plugins/dynamic_querying/dynamic_finder'
71
- end
72
-
73
- module Keys
74
- autoload :Key, 'mongo_mapper/plugins/keys/key'
75
- end
76
-
77
- module Querying
78
- autoload :Decorator, 'mongo_mapper/plugins/querying/decorator'
79
- end
80
- end
81
-
82
- module Support
83
- autoload :DescendantAppends, 'mongo_mapper/support/descendant_appends'
84
68
  end
85
69
 
86
70
  extend Connection
@@ -90,5 +74,7 @@ Dir[File.join(File.dirname(__FILE__), 'mongo_mapper', 'extensions', '*.rb')].eac
90
74
  require extension
91
75
  end
92
76
 
77
+ require 'mongo_mapper/support/descendant_appends'
78
+
93
79
  # FIXME: autoload with proxy is failing, need to investigate
94
80
  require 'mongo_mapper/plugins/associations/proxy'
@@ -3,7 +3,7 @@ module MongoMapper
3
3
  module Plugins
4
4
  module Associations
5
5
  class InArrayProxy < Collection
6
- include MongoMapper::Plugins::DynamicQuerying::ClassMethods
6
+ include DynamicQuerying::ClassMethods
7
7
 
8
8
  def find(*args)
9
9
  query.find(*scoped_ids(args))
@@ -3,35 +3,8 @@ module MongoMapper
3
3
  module Plugins
4
4
  module Associations
5
5
  class ManyDocumentsProxy < Collection
6
- include MongoMapper::Plugins::DynamicQuerying::ClassMethods
7
-
8
- def find(*args)
9
- query.find(*args)
10
- end
11
-
12
- def find!(*args)
13
- query.find!(*args)
14
- end
15
-
16
- def paginate(options)
17
- query.paginate(options)
18
- end
19
-
20
- def all(options={})
21
- query(options).all
22
- end
23
-
24
- def first(options={})
25
- query(options).first
26
- end
27
-
28
- def last(options={})
29
- query(options).last
30
- end
31
-
32
- def count(options={})
33
- query(options).count
34
- end
6
+ include DynamicQuerying::ClassMethods
7
+ include Querying::PluckyMethods
35
8
 
36
9
  def replace(docs)
37
10
  load_target
@@ -93,8 +66,17 @@ module MongoMapper
93
66
  def query(options={})
94
67
  klass.
95
68
  query(association.query_options).
96
- update(options).
97
- update(criteria)
69
+ update(options).update(criteria)
70
+ end
71
+
72
+ def method_missing(method, *args, &block)
73
+ if klass.respond_to?(method)
74
+ result = klass.send(method, *args, &block)
75
+ result.is_a?(Plucky::Query) ?
76
+ query.merge(result) : super
77
+ else
78
+ super
79
+ end
98
80
  end
99
81
 
100
82
  def criteria
@@ -18,7 +18,7 @@ module MongoMapper
18
18
  end
19
19
 
20
20
  def reload
21
- if doc = self.class.query.find_one(:_id => id)
21
+ if doc = collection.find_one(:_id => id)
22
22
  tap do |instance|
23
23
  instance.class.associations.each_key do |association_name|
24
24
  send(association_name).reset if respond_to?(association_name)
@@ -1,4 +1,6 @@
1
1
  # encoding: UTF-8
2
+ require 'mongo_mapper/plugins/dynamic_querying/dynamic_finder'
3
+
2
4
  module MongoMapper
3
5
  module Plugins
4
6
  module DynamicQuerying
@@ -30,21 +30,34 @@ module MongoMapper
30
30
  @identity_map = v
31
31
  end
32
32
 
33
- def find_one(options={})
34
- query = query(options)
35
-
36
- if query.simple? && identity_map.key?(query[:_id])
37
- identity_map[query[:_id]]
38
- else
39
- super.tap do |document|
40
- remove_documents_from_map(document) if query.fields?
33
+ module IdentityMapQueryMethods
34
+ def all(opts={})
35
+ query = clone.update(opts)
36
+ super.tap do |docs|
37
+ model.remove_documents_from_map(docs) if query.fields?
38
+ end
39
+ end
40
+
41
+ def find_one(opts={})
42
+ query = clone.update(opts)
43
+
44
+ if query.simple? && model.identity_map[query[:_id]]
45
+ model.identity_map[query[:_id]]
46
+ else
47
+ super.tap do |doc|
48
+ model.remove_documents_from_map(doc) if query.fields?
49
+ end
41
50
  end
42
51
  end
43
52
  end
44
53
 
45
- def find_many(options)
46
- super.tap do |documents|
47
- remove_documents_from_map(documents) if query(options).fields?
54
+ def query(opts={})
55
+ super.extend(IdentityMapQueryMethods)
56
+ end
57
+
58
+ def remove_documents_from_map(*documents)
59
+ documents.flatten.compact.each do |document|
60
+ identity_map.delete(document['_id'])
48
61
  end
49
62
  end
50
63
 
@@ -88,12 +101,6 @@ module MongoMapper
88
101
  end
89
102
 
90
103
  private
91
- def remove_documents_from_map(*documents)
92
- documents.flatten.compact.each do |document|
93
- identity_map.delete(document._id)
94
- end
95
- end
96
-
97
104
  def selecting_fields?(options)
98
105
  !options[:fields].nil?
99
106
  end
@@ -1,4 +1,6 @@
1
1
  # encoding: UTF-8
2
+ require 'mongo_mapper/plugins/keys/key'
3
+
2
4
  module MongoMapper
3
5
  module Plugins
4
6
  module Keys
@@ -1,61 +1,21 @@
1
1
  # encoding: UTF-8
2
+ require 'mongo_mapper/plugins/querying/decorator'
3
+ require 'mongo_mapper/plugins/querying/plucky_methods'
4
+
2
5
  module MongoMapper
3
6
  module Plugins
4
7
  module Querying
5
8
  module ClassMethods
6
- def find(*args)
7
- options = args.extract_options!
8
- return nil if args.size == 0
9
-
10
- if args.first.is_a?(Array) || args.size > 1
11
- find_some(args, options)
12
- else
13
- find_one(options.merge(:_id => args[0]))
14
- end
15
- end
16
-
17
- def find!(*args)
18
- options = args.extract_options!
19
- raise DocumentNotFound, "Couldn't find without an ID" if args.size == 0
9
+ include PluckyMethods
20
10
 
21
- if args.first.is_a?(Array) || args.size > 1
22
- find_some!(args, options)
23
- else
24
- find_one(options.merge(:_id => args[0])) ||
25
- raise(DocumentNotFound, "Document match #{options.inspect} does not exist
26
- in #{collection.name} collection")
27
- end
28
- end
29
-
30
- def find_each(options={})
31
- query(options).find_each.each { |doc| yield load(doc) }
11
+ def find_each(opts={})
12
+ super(opts).each { |doc| yield load(doc) }
32
13
  end
33
14
 
34
15
  def find_by_id(id)
35
16
  find_one(:_id => id)
36
17
  end
37
18
 
38
- def first(options={})
39
- find_one(options)
40
- end
41
-
42
- # All bets are off an actual order if you provide none.
43
- def last(options={})
44
- find_one(query(options).reverse.to_hash)
45
- end
46
-
47
- def all(options={})
48
- find_many(options)
49
- end
50
-
51
- def count(options={})
52
- query(options).count
53
- end
54
-
55
- def exists?(options={})
56
- !count(options).zero?
57
- end
58
-
59
19
  def first_or_create(args)
60
20
  first(args) || create(args.reject { |key, value| !key?(key) })
61
21
  end
@@ -97,30 +57,10 @@ module MongoMapper
97
57
  find_each(options) { |document| document.destroy }
98
58
  end
99
59
 
100
- def where(options={})
101
- query.where(options)
102
- end
103
-
104
- def fields(*args)
105
- query.fields(*args)
106
- end
107
-
108
- def limit(*args)
109
- query.limit(*args)
110
- end
111
-
112
- def skip(*args)
113
- query.skip(*args)
114
- end
115
-
116
- def sort(*args)
117
- query.sort(*args)
118
- end
119
-
120
60
  # @api private for now
121
61
  def query(options={})
122
62
  Plucky::Query.new(collection).tap do |query|
123
- query.extend(MongoMapper::Plugins::Querying::Decorator)
63
+ query.extend(Decorator)
124
64
  query.object_ids(object_id_keys)
125
65
  query.update(options)
126
66
  query.model(self)
@@ -3,7 +3,7 @@ module MongoMapper
3
3
  module Plugins
4
4
  module Querying
5
5
  module Decorator
6
- include MongoMapper::Plugins::DynamicQuerying::ClassMethods
6
+ include DynamicQuerying::ClassMethods
7
7
 
8
8
  def model(model=nil)
9
9
  return @model if model.nil?
@@ -0,0 +1,15 @@
1
+ # encoding: UTF-8
2
+ require 'forwardable'
3
+
4
+ module MongoMapper
5
+ module Plugins
6
+ module Querying
7
+ module PluckyMethods
8
+ extend Forwardable
9
+ def_delegators :query, :where, :fields, :limit, :skip, :sort,
10
+ :count, :last, :first, :all, :paginate,
11
+ :find, :find!, :exists?, :exist?, :find_each
12
+ end
13
+ end
14
+ end
15
+ end
@@ -5,13 +5,13 @@ module MongoMapper
5
5
  def self.configure(model)
6
6
  model.class_eval do
7
7
  include Validatable
8
- extend Plugins::Validations::DocumentMacros
8
+ extend Validations::DocumentMacros
9
9
  end
10
10
  end
11
11
 
12
12
  module DocumentMacros
13
13
  def validates_uniqueness_of(*args)
14
- add_validations(args, MongoMapper::Plugins::Validations::ValidatesUniquenessOf)
14
+ add_validations(args, Validations::ValidatesUniquenessOf)
15
15
  end
16
16
  end
17
17
 
@@ -1,4 +1,4 @@
1
1
  # encoding: UTF-8
2
2
  module MongoMapper
3
- Version = '0.8.0'
3
+ Version = '0.8.1'
4
4
  end
File without changes
@@ -345,6 +345,45 @@ class ManyDocumentsProxyTest < Test::Unit::TestCase
345
345
  end
346
346
  end
347
347
 
348
+ context "sexy querying" do
349
+ should "work with where" do
350
+ @project1.statuses.where(:name => 'New').all.should == [@brand_new]
351
+ end
352
+
353
+ should "work with sort" do
354
+ @project1.statuses.sort(:name).all.should == [@complete, @brand_new]
355
+ end
356
+
357
+ should "work with limit" do
358
+ @project1.statuses.sort(:name).limit(1).all.should == [@complete]
359
+ end
360
+
361
+ should "work with skip" do
362
+ @project1.statuses.sort(:name).skip(1).all.should == [@brand_new]
363
+ end
364
+
365
+ should "work with fields" do
366
+ @project1.statuses.fields(:position).all.each do |status|
367
+ status.position.should_not be_nil
368
+ status.name.should be_nil
369
+ end
370
+ end
371
+
372
+ should "work with scopes" do
373
+ @project1.statuses.complete.all.should == [@complete]
374
+ end
375
+
376
+ should "work with methods on class that return query" do
377
+ @project1.statuses.by_position(1).first.should == @brand_new
378
+ end
379
+
380
+ should "not work with methods on class that do not return query" do
381
+ Status.class_eval { def self.foo; 'foo' end }
382
+ lambda { @project1.statuses.foo }.
383
+ should raise_error(NoMethodError)
384
+ end
385
+ end
386
+
348
387
  context "all" do
349
388
  should "work" do
350
389
  @project1.statuses.all(:order => "position asc").should == [@brand_new, @complete]
@@ -327,7 +327,7 @@ class IdentityMapTest < Test::Unit::TestCase
327
327
 
328
328
  should "return nil for document id not found in collection" do
329
329
  assert_in_map(@person)
330
- @person_class.find_by_id(1234).should be_nil
330
+ @person_class.find_by_id(BSON::ObjectID.new).should be_nil
331
331
  end
332
332
  end
333
333
 
@@ -342,13 +342,13 @@ class IdentityMapTest < Test::Unit::TestCase
342
342
  @person_class.first(:_id => @person.id, :select => 'name').should == @person
343
343
  @person_class.first(:_id => @person.id, 'fields' => ['name']).should == @person
344
344
  @person_class.last(:_id => @person.id, :select => 'name', :order => 'name').should == @person
345
- @person_class.find(@person.id, :select => 'name').should == @person
345
+ @person_class.fields(:name).find(@person.id).should == @person
346
346
  @person_class.all(:_id => @person.id, :select => 'name').should == [@person]
347
347
  assert_not_in_map(@person)
348
348
  end
349
349
 
350
350
  should "return nil if not found" do
351
- @person_class.find(1234, :select => 'name').should be_nil
351
+ @person_class.fields(:name).find(BSON::ObjectID.new).should be_nil
352
352
  end
353
353
  end
354
354
 
data/test/models.rb CHANGED
@@ -143,6 +143,12 @@ end
143
143
  class Status
144
144
  include MongoMapper::Document
145
145
 
146
+ scope :complete, where(:name => 'Complete')
147
+
148
+ def self.by_position(position)
149
+ where(:position => position)
150
+ end
151
+
146
152
  key :project_id, ObjectId
147
153
  key :target_id, ObjectId
148
154
  key :target_type, String
data/test/test_helper.rb CHANGED
@@ -1,19 +1,23 @@
1
- require File.expand_path(File.dirname(__FILE__) + '/../lib/mongo_mapper')
2
- require 'fileutils'
3
-
4
- gem 'jnunemaker-matchy', '0.4.0'
5
- gem 'shoulda', '2.10.2'
6
- gem 'json', '>= 1.2.3'
7
- gem 'timecop', '0.3.1'
8
- gem 'mocha', '0.9.8'
1
+ require 'rubygems'
2
+ gem 'activesupport', ENV['ACTIVE_SUPPORT_VERSION']
3
+ gem 'json', '~> 1.2.3'
4
+ gem 'jnunemaker-matchy', '~> 0.4.0'
5
+ gem 'shoulda', '~> 2.10.2'
6
+ gem 'timecop', '~> 0.3.1'
7
+ gem 'mocha', '~> 0.9.8'
9
8
 
9
+ $:.unshift File.expand_path(File.dirname(__FILE__) + '/../lib')
10
+ require 'mongo_mapper'
11
+ require 'fileutils'
10
12
  require 'ostruct'
13
+ require 'pp'
14
+
15
+ require 'active_support/version'
16
+ require 'json'
17
+ require 'matchy'
11
18
  require 'shoulda'
12
19
  require 'timecop'
13
- require 'matchy'
14
20
  require 'mocha'
15
- require 'json'
16
- require 'pp'
17
21
 
18
22
  class Test::Unit::TestCase
19
23
  def Doc(name=nil, &block)
@@ -96,3 +100,5 @@ logger = Logger.new(log_dir + '/test.log')
96
100
  MongoMapper.connection = Mongo::Connection.new('127.0.0.1', 27017, :logger => logger)
97
101
  MongoMapper.database = "mm-test-#{RUBY_VERSION.gsub('.', '-')}"
98
102
  MongoMapper.database.collections.each { |c| c.drop_indexes }
103
+
104
+ puts "\n--- Active Support Version: #{ActiveSupport::VERSION::STRING} ---\n"
metadata CHANGED
@@ -5,8 +5,8 @@ version: !ruby/object:Gem::Version
5
5
  segments:
6
6
  - 0
7
7
  - 8
8
- - 0
9
- version: 0.8.0
8
+ - 1
9
+ version: 0.8.1
10
10
  platform: ruby
11
11
  authors:
12
12
  - John Nunemaker
@@ -14,7 +14,7 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-06-16 00:00:00 -04:00
17
+ date: 2010-06-18 00:00:00 -04:00
18
18
  default_executable: mmconsole
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
@@ -55,8 +55,8 @@ dependencies:
55
55
  segments:
56
56
  - 0
57
57
  - 3
58
- - 0
59
- version: 0.3.0
58
+ - 1
59
+ version: 0.3.1
60
60
  type: :runtime
61
61
  version_requirements: *id003
62
62
  - !ruby/object:Gem::Dependency
@@ -64,7 +64,7 @@ dependencies:
64
64
  prerelease: false
65
65
  requirement: &id004 !ruby/object:Gem::Requirement
66
66
  requirements:
67
- - - ">="
67
+ - - ~>
68
68
  - !ruby/object:Gem::Version
69
69
  segments:
70
70
  - 1
@@ -78,7 +78,7 @@ dependencies:
78
78
  prerelease: false
79
79
  requirement: &id005 !ruby/object:Gem::Requirement
80
80
  requirements:
81
- - - ">="
81
+ - - ~>
82
82
  - !ruby/object:Gem::Version
83
83
  segments:
84
84
  - 0
@@ -92,7 +92,7 @@ dependencies:
92
92
  prerelease: false
93
93
  requirement: &id006 !ruby/object:Gem::Requirement
94
94
  requirements:
95
- - - ">="
95
+ - - ~>
96
96
  - !ruby/object:Gem::Version
97
97
  segments:
98
98
  - 2
@@ -106,7 +106,7 @@ dependencies:
106
106
  prerelease: false
107
107
  requirement: &id007 !ruby/object:Gem::Requirement
108
108
  requirements:
109
- - - ">="
109
+ - - ~>
110
110
  - !ruby/object:Gem::Version
111
111
  segments:
112
112
  - 0
@@ -120,7 +120,7 @@ dependencies:
120
120
  prerelease: false
121
121
  requirement: &id008 !ruby/object:Gem::Requirement
122
122
  requirements:
123
- - - ">="
123
+ - - ~>
124
124
  - !ruby/object:Gem::Version
125
125
  segments:
126
126
  - 0
@@ -199,6 +199,7 @@ files:
199
199
  - lib/mongo_mapper/plugins/persistence.rb
200
200
  - lib/mongo_mapper/plugins/protected.rb
201
201
  - lib/mongo_mapper/plugins/querying/decorator.rb
202
+ - lib/mongo_mapper/plugins/querying/plucky_methods.rb
202
203
  - lib/mongo_mapper/plugins/querying.rb
203
204
  - lib/mongo_mapper/plugins/rails.rb
204
205
  - lib/mongo_mapper/plugins/safe.rb
@@ -212,7 +213,7 @@ files:
212
213
  - lib/mongo_mapper/support/descendant_appends.rb
213
214
  - lib/mongo_mapper/version.rb
214
215
  - lib/mongo_mapper.rb
215
- - test/active_model_lint_test.rb
216
+ - test/_NOTE_ON_TESTING
216
217
  - test/functional/associations/test_belongs_to_polymorphic_proxy.rb
217
218
  - test/functional/associations/test_belongs_to_proxy.rb
218
219
  - test/functional/associations/test_in_array_proxy.rb
@@ -247,7 +248,7 @@ files:
247
248
  - test/functional/test_userstamps.rb
248
249
  - test/functional/test_validations.rb
249
250
  - test/models.rb
250
- - test/NOTE_ON_TESTING
251
+ - test/test_active_model_lint.rb
251
252
  - test/test_helper.rb
252
253
  - test/unit/associations/test_base.rb
253
254
  - test/unit/associations/test_proxy.rb