mongo 1.0 → 1.1.5
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/LICENSE.txt +1 -13
- data/{README.rdoc → README.md} +129 -149
- data/Rakefile +94 -58
- data/bin/mongo_console +21 -0
- data/docs/1.0_UPGRADE.md +21 -0
- data/docs/CREDITS.md +123 -0
- data/docs/FAQ.md +112 -0
- data/docs/GridFS.md +158 -0
- data/docs/HISTORY.md +185 -0
- data/docs/REPLICA_SETS.md +75 -0
- data/docs/TUTORIAL.md +247 -0
- data/docs/WRITE_CONCERN.md +28 -0
- data/lib/mongo/collection.rb +225 -105
- data/lib/mongo/connection.rb +374 -315
- data/lib/mongo/cursor.rb +122 -77
- data/lib/mongo/db.rb +109 -85
- data/lib/mongo/exceptions.rb +6 -0
- data/lib/mongo/gridfs/grid.rb +19 -11
- data/lib/mongo/gridfs/grid_ext.rb +36 -9
- data/lib/mongo/gridfs/grid_file_system.rb +15 -9
- data/lib/mongo/gridfs/grid_io.rb +49 -16
- data/lib/mongo/gridfs/grid_io_fix.rb +38 -0
- data/lib/mongo/repl_set_connection.rb +290 -0
- data/lib/mongo/util/conversions.rb +3 -1
- data/lib/mongo/util/core_ext.rb +17 -4
- data/lib/mongo/util/pool.rb +125 -0
- data/lib/mongo/util/server_version.rb +2 -0
- data/lib/mongo/util/support.rb +12 -0
- data/lib/mongo/util/uri_parser.rb +71 -0
- data/lib/mongo.rb +23 -7
- data/{mongo-ruby-driver.gemspec → mongo.gemspec} +9 -7
- data/test/auxillary/1.4_features.rb +2 -2
- data/test/auxillary/authentication_test.rb +1 -1
- data/test/auxillary/autoreconnect_test.rb +1 -1
- data/test/{slave_connection_test.rb → auxillary/slave_connection_test.rb} +6 -6
- data/test/bson/binary_test.rb +15 -0
- data/test/bson/bson_test.rb +537 -0
- data/test/bson/byte_buffer_test.rb +190 -0
- data/test/bson/hash_with_indifferent_access_test.rb +38 -0
- data/test/bson/json_test.rb +17 -0
- data/test/bson/object_id_test.rb +141 -0
- data/test/bson/ordered_hash_test.rb +197 -0
- data/test/collection_test.rb +195 -15
- data/test/connection_test.rb +93 -56
- data/test/conversions_test.rb +1 -1
- data/test/cursor_fail_test.rb +75 -0
- data/test/cursor_message_test.rb +43 -0
- data/test/cursor_test.rb +93 -32
- data/test/db_api_test.rb +28 -55
- data/test/db_connection_test.rb +2 -3
- data/test/db_test.rb +45 -40
- data/test/grid_file_system_test.rb +14 -6
- data/test/grid_io_test.rb +36 -7
- data/test/grid_test.rb +54 -10
- data/test/replica_sets/connect_test.rb +84 -0
- data/test/replica_sets/count_test.rb +35 -0
- data/test/{replica → replica_sets}/insert_test.rb +17 -14
- data/test/replica_sets/pooled_insert_test.rb +55 -0
- data/test/replica_sets/query_secondaries.rb +80 -0
- data/test/replica_sets/query_test.rb +41 -0
- data/test/replica_sets/replication_ack_test.rb +64 -0
- data/test/replica_sets/rs_test_helper.rb +29 -0
- data/test/safe_test.rb +68 -0
- data/test/support/hash_with_indifferent_access.rb +199 -0
- data/test/support/keys.rb +45 -0
- data/test/support_test.rb +19 -0
- data/test/test_helper.rb +53 -15
- data/test/threading/{test_threading_large_pool.rb → threading_with_large_pool_test.rb} +2 -2
- data/test/threading_test.rb +2 -2
- data/test/tools/repl_set_manager.rb +241 -0
- data/test/tools/test.rb +13 -0
- data/test/unit/collection_test.rb +70 -7
- data/test/unit/connection_test.rb +18 -39
- data/test/unit/cursor_test.rb +7 -8
- data/test/unit/db_test.rb +14 -17
- data/test/unit/grid_test.rb +49 -0
- data/test/unit/pool_test.rb +9 -0
- data/test/unit/repl_set_connection_test.rb +82 -0
- data/test/unit/safe_test.rb +125 -0
- metadata +132 -51
- data/bin/bson_benchmark.rb +0 -59
- data/bin/fail_if_no_c.rb +0 -11
- data/examples/admin.rb +0 -43
- data/examples/capped.rb +0 -22
- data/examples/cursor.rb +0 -48
- data/examples/gridfs.rb +0 -44
- data/examples/index_test.rb +0 -126
- data/examples/info.rb +0 -31
- data/examples/queries.rb +0 -70
- data/examples/simple.rb +0 -24
- data/examples/strict.rb +0 -35
- data/examples/types.rb +0 -36
- data/test/replica/count_test.rb +0 -34
- data/test/replica/pooled_insert_test.rb +0 -54
- data/test/replica/query_test.rb +0 -39
data/lib/mongo/db.rb
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# encoding: UTF-8
|
|
2
|
+
|
|
1
3
|
# --
|
|
2
4
|
# Copyright (C) 2008-2010 10gen Inc.
|
|
3
5
|
#
|
|
@@ -27,6 +29,7 @@ module Mongo
|
|
|
27
29
|
SYSTEM_INDEX_COLLECTION = "system.indexes"
|
|
28
30
|
SYSTEM_PROFILE_COLLECTION = "system.profile"
|
|
29
31
|
SYSTEM_USER_COLLECTION = "system.users"
|
|
32
|
+
SYSTEM_JS_COLLECTION = "system.js"
|
|
30
33
|
SYSTEM_COMMAND_COLLECTION = "$cmd"
|
|
31
34
|
|
|
32
35
|
# Counter for generating unique request ids.
|
|
@@ -42,12 +45,15 @@ module Mongo
|
|
|
42
45
|
# Returns the value of the +strict+ flag.
|
|
43
46
|
def strict?; @strict; end
|
|
44
47
|
|
|
45
|
-
# The name of the database.
|
|
46
|
-
attr_reader :name
|
|
48
|
+
# The name of the database and the local safe option.
|
|
49
|
+
attr_reader :name, :safe
|
|
47
50
|
|
|
48
51
|
# The Mongo::Connection instance connecting to the MongoDB server.
|
|
49
52
|
attr_reader :connection
|
|
50
53
|
|
|
54
|
+
# The length of time that Collection.ensure_index should cache index calls
|
|
55
|
+
attr_accessor :cache_time
|
|
56
|
+
|
|
51
57
|
# Instances of DB are normally obtained by calling Mongo#db.
|
|
52
58
|
#
|
|
53
59
|
# @param [String] db_name the database name.
|
|
@@ -57,17 +63,26 @@ module Mongo
|
|
|
57
63
|
# @option options [Boolean] :strict (False) If true, collections must exist to be accessed and must
|
|
58
64
|
# not exist to be created. See DB#collection and DB#create_collection.
|
|
59
65
|
#
|
|
60
|
-
# @option options [Object, #create_pk(doc)] :pk (Mongo::
|
|
66
|
+
# @option options [Object, #create_pk(doc)] :pk (Mongo::ObjectId) A primary key factory object,
|
|
61
67
|
# which should take a hash and return a hash which merges the original hash with any primary key
|
|
62
68
|
# fields the factory wishes to inject. (NOTE: if the object already has a primary key,
|
|
63
69
|
# the factory should not inject a new key).
|
|
64
70
|
#
|
|
71
|
+
# @option options [Boolean, Hash] :safe (false) Set the default safe-mode options
|
|
72
|
+
# propogated to Collection objects instantiated off of this DB. If no
|
|
73
|
+
# value is provided, the default value set on this instance's Connection object will be used. This
|
|
74
|
+
# default can be overridden upon instantiation of any collection by explicity setting a :safe value
|
|
75
|
+
# on initialization
|
|
76
|
+
# @option options [Integer] :cache_time (300) Set the time that all ensure_index calls should cache the command.
|
|
77
|
+
#
|
|
65
78
|
# @core databases constructor_details
|
|
66
79
|
def initialize(db_name, connection, options={})
|
|
67
80
|
@name = Mongo::Support.validate_db_name(db_name)
|
|
68
81
|
@connection = connection
|
|
69
82
|
@strict = options[:strict]
|
|
70
83
|
@pk_factory = options[:pk]
|
|
84
|
+
@safe = options.has_key?(:safe) ? options[:safe] : @connection.safe
|
|
85
|
+
@cache_time = options[:cache_time] || 300 #5 minutes.
|
|
71
86
|
end
|
|
72
87
|
|
|
73
88
|
# Authenticate with the given username and password. Note that mongod
|
|
@@ -85,16 +100,16 @@ module Mongo
|
|
|
85
100
|
#
|
|
86
101
|
# @core authenticate authenticate-instance_method
|
|
87
102
|
def authenticate(username, password, save_auth=true)
|
|
88
|
-
doc = command(:getnonce => 1)
|
|
103
|
+
doc = command({:getnonce => 1}, :check_response => false)
|
|
89
104
|
raise "error retrieving nonce: #{doc}" unless ok?(doc)
|
|
90
105
|
nonce = doc['nonce']
|
|
91
106
|
|
|
92
|
-
auth = OrderedHash.new
|
|
107
|
+
auth = BSON::OrderedHash.new
|
|
93
108
|
auth['authenticate'] = 1
|
|
94
109
|
auth['user'] = username
|
|
95
110
|
auth['nonce'] = nonce
|
|
96
111
|
auth['key'] = Mongo::Support.auth_key(username, password, nonce)
|
|
97
|
-
if ok?(command(auth))
|
|
112
|
+
if ok?(self.command(auth, :check_response => false))
|
|
98
113
|
if save_auth
|
|
99
114
|
@connection.add_auth(@name, username, password)
|
|
100
115
|
end
|
|
@@ -104,6 +119,36 @@ module Mongo
|
|
|
104
119
|
end
|
|
105
120
|
end
|
|
106
121
|
|
|
122
|
+
# Adds a stored Javascript function to the database which can executed
|
|
123
|
+
# server-side in map_reduce, db.eval and $where clauses.
|
|
124
|
+
#
|
|
125
|
+
# @param [String] function_name
|
|
126
|
+
# @param [String] code
|
|
127
|
+
#
|
|
128
|
+
# @return [String] the function name saved to the database
|
|
129
|
+
def add_stored_function(function_name, code)
|
|
130
|
+
self[SYSTEM_JS_COLLECTION].save(
|
|
131
|
+
{
|
|
132
|
+
"_id" => function_name,
|
|
133
|
+
:value => BSON::Code.new(code)
|
|
134
|
+
}
|
|
135
|
+
)
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
# Removes stored Javascript function from the database. Returns
|
|
139
|
+
# false if the function does not exist
|
|
140
|
+
#
|
|
141
|
+
# @param [String] function_name
|
|
142
|
+
#
|
|
143
|
+
# @return [Boolean]
|
|
144
|
+
def remove_stored_function(function_name)
|
|
145
|
+
if self[SYSTEM_JS_COLLECTION].find_one({"_id" => function_name})
|
|
146
|
+
self[SYSTEM_JS_COLLECTION].remove({"_id" => function_name}, :safe => true)
|
|
147
|
+
else
|
|
148
|
+
return false
|
|
149
|
+
end
|
|
150
|
+
end
|
|
151
|
+
|
|
107
152
|
# Adds a user to this database for use with authentication. If the user already
|
|
108
153
|
# exists in the system, the password will be updated.
|
|
109
154
|
#
|
|
@@ -212,24 +257,29 @@ module Mongo
|
|
|
212
257
|
end
|
|
213
258
|
|
|
214
259
|
# Create a new collection.
|
|
215
|
-
oh = OrderedHash.new
|
|
260
|
+
oh = BSON::OrderedHash.new
|
|
216
261
|
oh[:create] = name
|
|
217
262
|
doc = command(oh.merge(options || {}))
|
|
218
|
-
|
|
219
|
-
return Collection.new(self, name, @pk_factory) if ok.kind_of?(Numeric) && (ok.to_i == 1 || ok.to_i == 0)
|
|
263
|
+
return Collection.new(self, name, :pk => @pk_factory) if ok?(doc)
|
|
220
264
|
raise MongoDBError, "Error creating collection: #{doc.inspect}"
|
|
221
265
|
end
|
|
222
266
|
|
|
223
267
|
# Get a collection by name.
|
|
224
268
|
#
|
|
225
269
|
# @param [String] name the collection name.
|
|
270
|
+
# @param [Hash] options any valid options that can me passed to Collection#new.
|
|
226
271
|
#
|
|
227
272
|
# @raise [MongoDBError] if collection does not already exist and we're in +strict+ mode.
|
|
228
273
|
#
|
|
229
274
|
# @return [Mongo::Collection]
|
|
230
|
-
def collection(name)
|
|
231
|
-
|
|
232
|
-
|
|
275
|
+
def collection(name, options={})
|
|
276
|
+
if strict? && !collection_names.include?(name)
|
|
277
|
+
raise Mongo::MongoDBError, "Collection #{name} doesn't exist. Currently in strict mode."
|
|
278
|
+
else
|
|
279
|
+
options[:safe] = options.has_key?(:safe) ? options[:safe] : @safe
|
|
280
|
+
options.merge!(:pk => @pk_factory) unless options[:pk]
|
|
281
|
+
Collection.new(self, name, options)
|
|
282
|
+
end
|
|
233
283
|
end
|
|
234
284
|
alias_method :[], :collection
|
|
235
285
|
|
|
@@ -237,29 +287,29 @@ module Mongo
|
|
|
237
287
|
#
|
|
238
288
|
# @param [String] name
|
|
239
289
|
#
|
|
240
|
-
# @return [Boolean]
|
|
290
|
+
# @return [Boolean] +true+ on success or +false+ if the collection name doesn't exist.
|
|
241
291
|
def drop_collection(name)
|
|
242
292
|
return true unless collection_names.include?(name)
|
|
243
293
|
|
|
244
294
|
ok?(command(:drop => name))
|
|
245
295
|
end
|
|
246
296
|
|
|
247
|
-
#
|
|
248
|
-
# operation for this connection.
|
|
297
|
+
# Run the getlasterror command with the specified replication options.
|
|
249
298
|
#
|
|
250
|
-
# @
|
|
251
|
-
#
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
doc['err']
|
|
256
|
-
end
|
|
257
|
-
|
|
258
|
-
# Get status information from the last operation on this connection.
|
|
299
|
+
# @option opts [Boolean] :fsync (false)
|
|
300
|
+
# @option opts [Integer] :w (nil)
|
|
301
|
+
# @option opts [Integer] :wtimeout (nil)
|
|
302
|
+
#
|
|
303
|
+
# @return [Hash] the entire response to getlasterror.
|
|
259
304
|
#
|
|
260
|
-
# @
|
|
261
|
-
def
|
|
262
|
-
|
|
305
|
+
# @raise [MongoDBError] if the operation fails.
|
|
306
|
+
def get_last_error(opts={})
|
|
307
|
+
cmd = BSON::OrderedHash.new
|
|
308
|
+
cmd[:getlasterror] = 1
|
|
309
|
+
cmd.merge!(opts)
|
|
310
|
+
doc = command(cmd, :check_response => false)
|
|
311
|
+
raise MongoDBError, "error retrieving last error: #{doc.inspect}" unless ok?(doc)
|
|
312
|
+
doc
|
|
263
313
|
end
|
|
264
314
|
|
|
265
315
|
# Return +true+ if an error was caused by the most recently executed
|
|
@@ -267,7 +317,7 @@ module Mongo
|
|
|
267
317
|
#
|
|
268
318
|
# @return [Boolean]
|
|
269
319
|
def error?
|
|
270
|
-
|
|
320
|
+
get_last_error['err'] != nil
|
|
271
321
|
end
|
|
272
322
|
|
|
273
323
|
# Get the most recent error to have occured on this database.
|
|
@@ -295,17 +345,6 @@ module Mongo
|
|
|
295
345
|
command(:reseterror => 1)
|
|
296
346
|
end
|
|
297
347
|
|
|
298
|
-
# @deprecated please use Collection#find to create queries.
|
|
299
|
-
#
|
|
300
|
-
# Returns a Cursor over the query results.
|
|
301
|
-
#
|
|
302
|
-
# Note that the query gets sent lazily; the cursor calls
|
|
303
|
-
# Connection#send_message when needed. If the caller never requests an
|
|
304
|
-
# object from the cursor, the query never gets sent.
|
|
305
|
-
def query(collection, query, admin=false)
|
|
306
|
-
Cursor.new(self, collection, query, admin)
|
|
307
|
-
end
|
|
308
|
-
|
|
309
348
|
# Dereference a DBRef, returning the document it points to.
|
|
310
349
|
#
|
|
311
350
|
# @param [Mongo::DBRef] dbref
|
|
@@ -329,12 +368,11 @@ module Mongo
|
|
|
329
368
|
code = BSON::Code.new(code)
|
|
330
369
|
end
|
|
331
370
|
|
|
332
|
-
oh = OrderedHash.new
|
|
371
|
+
oh = BSON::OrderedHash.new
|
|
333
372
|
oh[:$eval] = code
|
|
334
|
-
oh[:args]
|
|
373
|
+
oh[:args] = args
|
|
335
374
|
doc = command(oh)
|
|
336
|
-
|
|
337
|
-
raise OperationFailure, "eval failed: #{doc['errmsg']}"
|
|
375
|
+
doc['retval']
|
|
338
376
|
end
|
|
339
377
|
|
|
340
378
|
# Rename a collection.
|
|
@@ -343,13 +381,13 @@ module Mongo
|
|
|
343
381
|
# @param [String] to new collection name.
|
|
344
382
|
#
|
|
345
383
|
# @return [True] returns +true+ on success.
|
|
346
|
-
#
|
|
384
|
+
#
|
|
347
385
|
# @raise MongoDBError if there's an error renaming the collection.
|
|
348
386
|
def rename_collection(from, to)
|
|
349
|
-
oh = OrderedHash.new
|
|
387
|
+
oh = BSON::OrderedHash.new
|
|
350
388
|
oh[:renameCollection] = "#{@name}.#{from}"
|
|
351
389
|
oh[:to] = "#{@name}.#{to}"
|
|
352
|
-
doc = command(oh,
|
|
390
|
+
doc = DB.new('admin', @connection).command(oh, :check_response => false)
|
|
353
391
|
ok?(doc) || raise(MongoDBError, "Error renaming collection: #{doc.inspect}")
|
|
354
392
|
end
|
|
355
393
|
|
|
@@ -363,10 +401,10 @@ module Mongo
|
|
|
363
401
|
#
|
|
364
402
|
# @raise MongoDBError if there's an error renaming the collection.
|
|
365
403
|
def drop_index(collection_name, index_name)
|
|
366
|
-
oh = OrderedHash.new
|
|
404
|
+
oh = BSON::OrderedHash.new
|
|
367
405
|
oh[:deleteIndexes] = collection_name
|
|
368
406
|
oh[:index] = index_name
|
|
369
|
-
doc = command(oh)
|
|
407
|
+
doc = command(oh, :check_response => false)
|
|
370
408
|
ok?(doc) || raise(MongoDBError, "Error with drop_index command: #{doc.inspect}")
|
|
371
409
|
end
|
|
372
410
|
|
|
@@ -386,7 +424,6 @@ module Mongo
|
|
|
386
424
|
info
|
|
387
425
|
end
|
|
388
426
|
|
|
389
|
-
|
|
390
427
|
# Return stats on this database. Uses MongoDB's dbstats command.
|
|
391
428
|
#
|
|
392
429
|
# @return [Hash]
|
|
@@ -394,31 +431,13 @@ module Mongo
|
|
|
394
431
|
self.command({:dbstats => 1})
|
|
395
432
|
end
|
|
396
433
|
|
|
397
|
-
# Create a new index on the given collection.
|
|
398
|
-
# Normally called by Collection#create_index.
|
|
399
|
-
#
|
|
400
|
-
# @param [String] collection_name
|
|
401
|
-
# @param [String, Array] field_or_spec either either a single field name
|
|
402
|
-
# or an array of [field name, direction] pairs. Directions should be specified as
|
|
403
|
-
# Mongo::ASCENDING or Mongo::DESCENDING.
|
|
404
|
-
# @param [Boolean] unique if +true+, the created index will enforce a uniqueness constraint.
|
|
405
|
-
#
|
|
406
|
-
# @return [String] the name of the index created.
|
|
407
|
-
#
|
|
408
|
-
# @deprecated
|
|
409
|
-
def create_index(collection_name, field_or_spec, unique=false)
|
|
410
|
-
warn "DB#create_index is now deprecated. Please use Collection#create_index instead."
|
|
411
|
-
self.collection(collection_name).create_index(field_or_spec, :unique => unique)
|
|
412
|
-
end
|
|
413
|
-
|
|
414
434
|
# Return +true+ if the supplied +doc+ contains an 'ok' field with the value 1.
|
|
415
435
|
#
|
|
416
436
|
# @param [Hash] doc
|
|
417
437
|
#
|
|
418
438
|
# @return [Boolean]
|
|
419
439
|
def ok?(doc)
|
|
420
|
-
ok
|
|
421
|
-
ok.kind_of?(Numeric) && ok.to_i == 1
|
|
440
|
+
Mongo::Support.ok?(doc)
|
|
422
441
|
end
|
|
423
442
|
|
|
424
443
|
# Send a command to the database.
|
|
@@ -431,29 +450,34 @@ module Mongo
|
|
|
431
450
|
# to see how it works.
|
|
432
451
|
#
|
|
433
452
|
# @param [OrderedHash, Hash] selector an OrderedHash, or a standard Hash with just one
|
|
434
|
-
# key, specifying the command to be performed.
|
|
453
|
+
# key, specifying the command to be performed. In Ruby 1.9, OrderedHash isn't necessary since
|
|
454
|
+
# hashes are ordered by default.
|
|
435
455
|
#
|
|
436
|
-
# @
|
|
437
|
-
# collection.
|
|
438
|
-
#
|
|
439
|
-
# @param [Boolean] check_response If +true+, will raise an exception if the
|
|
456
|
+
# @option opts [Boolean] :check_response (true) If +true+, raises an exception if the
|
|
440
457
|
# command fails.
|
|
441
|
-
#
|
|
442
|
-
# @param [Socket] sock a socket to use. This is mainly for internal use.
|
|
458
|
+
# @option opts [Socket] :sock a socket to use for sending the command. This is mainly for internal use.
|
|
443
459
|
#
|
|
444
460
|
# @return [Hash]
|
|
445
461
|
#
|
|
446
462
|
# @core commands command_instance-method
|
|
447
|
-
def command(selector,
|
|
463
|
+
def command(selector, opts={})
|
|
464
|
+
check_response = opts.fetch(:check_response, true)
|
|
465
|
+
sock = opts[:sock]
|
|
448
466
|
raise MongoArgumentError, "command must be given a selector" unless selector.is_a?(Hash) && !selector.empty?
|
|
449
|
-
if selector.
|
|
467
|
+
if selector.keys.length > 1 && RUBY_VERSION < '1.9' && selector.class != BSON::OrderedHash
|
|
450
468
|
raise MongoArgumentError, "DB#command requires an OrderedHash when hash contains multiple keys"
|
|
451
469
|
end
|
|
452
470
|
|
|
453
|
-
|
|
454
|
-
|
|
471
|
+
begin
|
|
472
|
+
result = Cursor.new(system_command_collection,
|
|
473
|
+
:limit => -1, :selector => selector, :socket => sock).next_document
|
|
474
|
+
rescue OperationFailure => ex
|
|
475
|
+
raise OperationFailure, "Database command '#{selector.keys.first}' failed: #{ex.message}"
|
|
476
|
+
end
|
|
455
477
|
|
|
456
|
-
if
|
|
478
|
+
if result.nil?
|
|
479
|
+
raise OperationFailure, "Database command '#{selector.keys.first}' failed: returned null."
|
|
480
|
+
elsif (check_response && !ok?(result))
|
|
457
481
|
raise OperationFailure, "Database command '#{selector.keys.first}' failed: #{result.inspect}"
|
|
458
482
|
else
|
|
459
483
|
result
|
|
@@ -494,9 +518,9 @@ module Mongo
|
|
|
494
518
|
#
|
|
495
519
|
# @core profiling profiling_level-instance_method
|
|
496
520
|
def profiling_level
|
|
497
|
-
oh = OrderedHash.new
|
|
521
|
+
oh = BSON::OrderedHash.new
|
|
498
522
|
oh[:profile] = -1
|
|
499
|
-
doc = command(oh)
|
|
523
|
+
doc = command(oh, :check_response => false)
|
|
500
524
|
raise "Error with profile command: #{doc.inspect}" unless ok?(doc) && doc['was'].kind_of?(Numeric)
|
|
501
525
|
case doc['was'].to_i
|
|
502
526
|
when 0
|
|
@@ -515,7 +539,7 @@ module Mongo
|
|
|
515
539
|
#
|
|
516
540
|
# @param [Symbol] level acceptable options are +:off+, +:slow_only+, or +:all+.
|
|
517
541
|
def profiling_level=(level)
|
|
518
|
-
oh = OrderedHash.new
|
|
542
|
+
oh = BSON::OrderedHash.new
|
|
519
543
|
oh[:profile] = case level
|
|
520
544
|
when :off
|
|
521
545
|
0
|
|
@@ -526,7 +550,7 @@ module Mongo
|
|
|
526
550
|
else
|
|
527
551
|
raise "Error: illegal profiling level value #{level}"
|
|
528
552
|
end
|
|
529
|
-
doc = command(oh)
|
|
553
|
+
doc = command(oh, :check_response => false)
|
|
530
554
|
ok?(doc) || raise(MongoDBError, "Error with profile command: #{doc.inspect}")
|
|
531
555
|
end
|
|
532
556
|
|
|
@@ -546,7 +570,7 @@ module Mongo
|
|
|
546
570
|
# @raise [MongoDBError] if the command fails or there's a problem with the validation
|
|
547
571
|
# data, or if the collection is invalid.
|
|
548
572
|
def validate_collection(name)
|
|
549
|
-
doc = command(:validate => name)
|
|
573
|
+
doc = command({:validate => name}, :check_response => false)
|
|
550
574
|
raise MongoDBError, "Error with validate command: #{doc.inspect}" unless ok?(doc)
|
|
551
575
|
result = doc['result']
|
|
552
576
|
raise MongoDBError, "Error with validation data: #{doc.inspect}" unless result.kind_of?(String)
|
data/lib/mongo/exceptions.rb
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
# encoding: UTF-8
|
|
2
|
+
|
|
3
|
+
#
|
|
1
4
|
# --
|
|
2
5
|
# Copyright (C) 2008-2010 10gen Inc.
|
|
3
6
|
#
|
|
@@ -39,6 +42,9 @@ module Mongo
|
|
|
39
42
|
# Raised on failures in connection to the database server.
|
|
40
43
|
class ConnectionError < MongoRubyError; end
|
|
41
44
|
|
|
45
|
+
# Raised on failures in connection to the database server.
|
|
46
|
+
class ReplicaSetConnectionError < ConnectionError; end
|
|
47
|
+
|
|
42
48
|
# Raised on failures in connection to the database server.
|
|
43
49
|
class ConnectionTimeoutError < MongoRubyError; end
|
|
44
50
|
|
data/lib/mongo/gridfs/grid.rb
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# encoding: UTF-8
|
|
2
|
+
|
|
1
3
|
# --
|
|
2
4
|
# Copyright (C) 2008-2010 10gen Inc.
|
|
3
5
|
#
|
|
@@ -18,6 +20,8 @@ module Mongo
|
|
|
18
20
|
|
|
19
21
|
# Implementation of the MongoDB GridFS specification. A file store.
|
|
20
22
|
class Grid
|
|
23
|
+
include GridExt::InstanceMethods
|
|
24
|
+
|
|
21
25
|
DEFAULT_FS_NAME = 'fs'
|
|
22
26
|
|
|
23
27
|
# Initialize a new Grid instance, consisting of a MongoDB database
|
|
@@ -34,30 +38,34 @@ module Mongo
|
|
|
34
38
|
@chunks = @db["#{fs_name}.chunks"]
|
|
35
39
|
@fs_name = fs_name
|
|
36
40
|
|
|
37
|
-
|
|
41
|
+
# Ensure indexes only if not connected to slave.
|
|
42
|
+
unless db.connection.slave_ok?
|
|
43
|
+
@chunks.create_index([['files_id', Mongo::ASCENDING], ['n', Mongo::ASCENDING]], :unique => true)
|
|
44
|
+
end
|
|
38
45
|
end
|
|
39
46
|
|
|
40
|
-
# Store a file in the file store.
|
|
47
|
+
# Store a file in the file store. This method is designed only for writing new files;
|
|
48
|
+
# if you need to update a given file, first delete it using Grid#delete.
|
|
41
49
|
#
|
|
42
50
|
# Note that arbitary metadata attributes can be saved to the file by passing
|
|
43
|
-
# them
|
|
51
|
+
# them in as options.
|
|
44
52
|
#
|
|
45
53
|
# @param [String, #read] data a string or io-like object to store.
|
|
46
54
|
#
|
|
47
|
-
# @
|
|
48
|
-
# @
|
|
49
|
-
# @
|
|
55
|
+
# @option opts [String] :filename (nil) a name for the file.
|
|
56
|
+
# @option opts [Hash] :metadata ({}) any additional data to store with the file.
|
|
57
|
+
# @option opts [ObjectId] :_id (ObjectId) a unique id for
|
|
50
58
|
# the file to be use in lieu of an automatically generated one.
|
|
51
|
-
# @
|
|
59
|
+
# @option opts [String] :content_type ('binary/octet-stream') If no content type is specified,
|
|
52
60
|
# the content type will may be inferred from the filename extension if the mime-types gem can be
|
|
53
61
|
# loaded. Otherwise, the content type 'binary/octet-stream' will be used.
|
|
54
|
-
# @
|
|
55
|
-
# @
|
|
62
|
+
# @option opts [Integer] (262144) :chunk_size size of file chunks in bytes.
|
|
63
|
+
# @option opts [Boolean] :safe (false) When safe mode is enabled, the chunks sent to the server
|
|
56
64
|
# will be validated using an md5 hash. If validation fails, an exception will be raised.
|
|
57
65
|
#
|
|
58
|
-
# @return [Mongo::
|
|
66
|
+
# @return [Mongo::ObjectId] the file's id.
|
|
59
67
|
def put(data, opts={})
|
|
60
|
-
filename = opts
|
|
68
|
+
filename = opts.delete :filename
|
|
61
69
|
opts.merge!(default_grid_io_opts)
|
|
62
70
|
file = GridIO.new(@files, @chunks, filename, 'w', opts=opts)
|
|
63
71
|
file.write(data)
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# encoding: UTF-8
|
|
2
|
+
|
|
1
3
|
# --
|
|
2
4
|
# Copyright (C) 2008-2010 10gen Inc.
|
|
3
5
|
#
|
|
@@ -15,16 +17,41 @@
|
|
|
15
17
|
# ++
|
|
16
18
|
|
|
17
19
|
module Mongo
|
|
18
|
-
module
|
|
19
|
-
|
|
20
|
-
def exists?(criteria)
|
|
21
|
-
BSON::ObjectID:
|
|
22
|
-
@files.find_one(query)
|
|
23
|
-
end
|
|
20
|
+
module GridExt
|
|
21
|
+
module InstanceMethods
|
|
24
22
|
|
|
25
|
-
|
|
26
|
-
|
|
23
|
+
# Check the existence of a file matching the given query selector.
|
|
24
|
+
#
|
|
25
|
+
# Note that this method can be used with both the Grid and GridFileSystem classes. Also
|
|
26
|
+
# keep in mind that if you're going to be performing lots of existence checks, you should
|
|
27
|
+
# keep an instance of Grid or GridFileSystem handy rather than instantiating for each existence
|
|
28
|
+
# check. Alternatively, simply keep a reference to the proper files collection and query that
|
|
29
|
+
# as needed. That's exactly how this methods works.
|
|
30
|
+
#
|
|
31
|
+
# @param [Hash] selector a query selector.
|
|
32
|
+
#
|
|
33
|
+
# @example
|
|
34
|
+
#
|
|
35
|
+
# # Check for the existence of a given filename
|
|
36
|
+
# @grid = GridFileSystem.new(@db)
|
|
37
|
+
# @grid.exist?(:filename => 'foo.txt')
|
|
38
|
+
#
|
|
39
|
+
# # Check for existence filename and content type
|
|
40
|
+
# @grid = GridFileSystem.new(@db)
|
|
41
|
+
# @grid.exist?(:filename => 'foo.txt', :content_type => 'image/jpg')
|
|
42
|
+
#
|
|
43
|
+
# # Check for existence by _id
|
|
44
|
+
# @grid = Grid.new(@db)
|
|
45
|
+
# @grid.exist?(:_id => BSON::ObjectId.from_string('4bddcd24beffd95a7db9b8c8'))
|
|
46
|
+
#
|
|
47
|
+
# # Check for existence by an arbitrary attribute.
|
|
48
|
+
# @grid = Grid.new(@db)
|
|
49
|
+
# @grid.exist?(:tags => {'$in' => ['nature', 'zen', 'photography']})
|
|
50
|
+
#
|
|
51
|
+
# @return [nil, Hash] either nil for the file's metadata as a hash.
|
|
52
|
+
def exist?(selector)
|
|
53
|
+
@files.find_one(selector)
|
|
54
|
+
end
|
|
27
55
|
end
|
|
28
|
-
|
|
29
56
|
end
|
|
30
57
|
end
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# encoding: UTF-8
|
|
2
|
+
|
|
1
3
|
# --
|
|
2
4
|
# Copyright (C) 2008-2010 10gen Inc.
|
|
3
5
|
#
|
|
@@ -19,8 +21,9 @@ module Mongo
|
|
|
19
21
|
# A file store built on the GridFS specification featuring
|
|
20
22
|
# an API and behavior similar to that of a traditional file system.
|
|
21
23
|
class GridFileSystem
|
|
24
|
+
include GridExt::InstanceMethods
|
|
22
25
|
|
|
23
|
-
# Initialize a new
|
|
26
|
+
# Initialize a new GridFileSystem instance, consisting of a MongoDB database
|
|
24
27
|
# and a filesystem prefix if not using the default.
|
|
25
28
|
#
|
|
26
29
|
# @param [Mongo::DB] db a MongoDB database.
|
|
@@ -36,8 +39,11 @@ module Mongo
|
|
|
36
39
|
|
|
37
40
|
@default_query_opts = {:sort => [['filename', 1], ['uploadDate', -1]], :limit => 1}
|
|
38
41
|
|
|
39
|
-
|
|
40
|
-
|
|
42
|
+
# Ensure indexes only if not connected to slave.
|
|
43
|
+
unless db.connection.slave_ok?
|
|
44
|
+
@files.create_index([['filename', 1], ['uploadDate', -1]])
|
|
45
|
+
@chunks.create_index([['files_id', Mongo::ASCENDING], ['n', Mongo::ASCENDING]], :unique => true)
|
|
46
|
+
end
|
|
41
47
|
end
|
|
42
48
|
|
|
43
49
|
# Open a file for reading or writing. Note that the options for this method only apply
|
|
@@ -51,17 +57,17 @@ module Mongo
|
|
|
51
57
|
# or writing to the file.
|
|
52
58
|
# @param [Hash] opts see GridIO#new
|
|
53
59
|
#
|
|
54
|
-
# @
|
|
55
|
-
# @
|
|
60
|
+
# @option opts [Hash] :metadata ({}) any additional data to store with the file.
|
|
61
|
+
# @option opts [ObjectId] :_id (ObjectId) a unique id for
|
|
56
62
|
# the file to be use in lieu of an automatically generated one.
|
|
57
|
-
# @
|
|
63
|
+
# @option opts [String] :content_type ('binary/octet-stream') If no content type is specified,
|
|
58
64
|
# the content type will may be inferred from the filename extension if the mime-types gem can be
|
|
59
65
|
# loaded. Otherwise, the content type 'binary/octet-stream' will be used.
|
|
60
|
-
# @
|
|
61
|
-
# @
|
|
66
|
+
# @option opts [Integer] (262144) :chunk_size size of file chunks in bytes.
|
|
67
|
+
# @option opts [Boolean] :delete_old (false) ensure that old versions of the file are deleted. This option
|
|
62
68
|
# only work in 'w' mode. Certain precautions must be taken when deleting GridFS files. See the notes under
|
|
63
69
|
# GridFileSystem#delete.
|
|
64
|
-
# @
|
|
70
|
+
# @option opts [Boolean] :safe (false) When safe mode is enabled, the chunks sent to the server
|
|
65
71
|
# will be validated using an md5 hash. If validation fails, an exception will be raised.
|
|
66
72
|
#
|
|
67
73
|
# @example
|