diff --git a/lib/mongo/cursor.rb b/lib/mongo/cursor.rb index be6e110..9128b14 100644 --- a/lib/mongo/cursor.rb +++ b/lib/mongo/cursor.rb @@ -71,6 +71,20 @@ module XGen o end + # Get the size of the results set for this query. + # + # Returns the number of objects in the results set for this query. Does + # not take limit and skip into account. Raises OperationFailure on a + # database error. + def count + command = OrderedHash["count", @collection.name, + "query", @query.selector] + response = @db.db_command(command) + return response['n'].to_i if response['ok'] == 1 + return 0 if response['errmsg'] == "ns missing" + raise OperationFailure, "Count failed: #{response['errmsg']}" + end + # Iterate over each object, yielding it to the given block. At most # @num_to_return records are returned (or all of them, if # @num_to_return is 0). diff --git a/test/test_cursor.rb b/test/test_cursor.rb index 7446259..ef84078 100644 --- a/test/test_cursor.rb +++ b/test/test_cursor.rb @@ -31,6 +31,33 @@ class CursorTest < Test::Unit::TestCase assert_kind_of Numeric, explaination['nscanned'] end + def test_count + @@coll.clear + + assert_equal 0, @@coll.find().count() + + 10.times do |i| + @@coll.save("x" => i) + end + + assert_equal 10, @@coll.find().count() + assert_kind_of Integer, @@coll.find().count() + assert_equal 10, @@coll.find({}, :limit => 5).count() + assert_equal 10, @@coll.find({}, :offset => 5).count() + + assert_equal 1, @@coll.find({"x" => 1}).count() + assert_equal 5, @@coll.find({"x" => {"$lt" => 5}}).count() + + a = @@coll.find() + b = a.count() + a.each do |doc| + break + end + assert_equal b, a.count() + + assert_equal 0, @@db['acollectionthatdoesn'].count() + end + def test_close_no_query_sent begin cursor = @@coll.find('a' => 1)