@@ -28,8 +28,9 @@ namespace MongoDB.Driver
2828 /// </summary>
2929 public static class MongoDefaults
3030 {
31- // public static fields
31+ // private static fields
3232 private static bool __assignIdOnInsert = true ;
33+ private static Func < BsonDocument , bool > __canCommandBeSentToSecondary = CanCommandBeSendToSecondaryDefault ;
3334 private static TimeSpan __connectTimeout = TimeSpan . FromSeconds ( 30 ) ;
3435 private static TimeSpan __maxConnectionIdleTime = TimeSpan . FromMinutes ( 10 ) ;
3536 private static TimeSpan __maxConnectionLifeTime = TimeSpan . FromMinutes ( 30 ) ;
@@ -38,6 +39,18 @@ public static class MongoDefaults
3839 private static int __minConnectionPoolSize = 0 ;
3940 private static SafeMode __safeMode = SafeMode . False ;
4041 private static TimeSpan __secondaryAcceptableLatency = TimeSpan . FromMilliseconds ( 15 ) ;
42+ private static HashSet < string > __secondaryOkCommands = new HashSet < string > ( StringComparer . InvariantCultureIgnoreCase )
43+ {
44+ "group" ,
45+ "aggregate" ,
46+ "collStats" ,
47+ "dbStats" ,
48+ "count" ,
49+ "distinct" ,
50+ "geoNear" ,
51+ "geoSearch" ,
52+ "geoWalk"
53+ } ;
4154 private static TimeSpan __socketTimeout = TimeSpan . Zero ; // use operating system default (presumably infinite)
4255 private static int __tcpReceiveBufferSize = 64 * 1024 ; // 64KiB (note: larger than 2MiB fails on Mac using Mono)
4356 private static int __tcpSendBufferSize = 64 * 1024 ; // 64KiB (TODO: what is the optimum value for the buffers?)
@@ -55,6 +68,24 @@ public static bool AssignIdOnInsert
5568 set { __assignIdOnInsert = value ; }
5669 }
5770
71+ /// <summary>
72+ /// Gets or sets a delegate that informs the driver whether or not a command is allowed
73+ /// to be sent to a secondary.
74+ /// </summary>
75+ public static Func < BsonDocument , bool > CanCommandBeSentToSecondary
76+ {
77+ get { return __canCommandBeSentToSecondary ; }
78+ set
79+ {
80+ if ( value == null )
81+ {
82+ throw new ArgumentNullException ( "value" ) ;
83+ }
84+
85+ __canCommandBeSentToSecondary = value ;
86+ }
87+ }
88+
5889 /// <summary>
5990 /// Gets the actual wait queue size (either WaitQueueSize or WaitQueueMultiple x MaxConnectionPoolSize).
6091 /// </summary>
@@ -225,5 +256,38 @@ public static TimeSpan WaitQueueTimeout
225256 get { return __waitQueueTimeout ; }
226257 set { __waitQueueTimeout = value ; }
227258 }
259+
260+ // private static methods
261+ private static bool CanCommandBeSendToSecondaryDefault ( BsonDocument document )
262+ {
263+ if ( document . ElementCount == 0 )
264+ {
265+ return false ;
266+ }
267+
268+ var command = document . GetElement ( 0 ) ;
269+
270+ if ( __secondaryOkCommands . Contains ( command . Name ) )
271+ {
272+ return true ;
273+ }
274+
275+ if ( ! command . Value . IsBsonDocument )
276+ {
277+ return false ;
278+ }
279+
280+ if ( command . Name . Equals ( "mapreduce" , StringComparison . InvariantCultureIgnoreCase ) )
281+ {
282+ var options = command . Value . AsBsonDocument ;
283+ BsonValue outValue ;
284+ if ( options . TryGetValue ( "out" , out outValue ) && outValue . IsBsonDocument )
285+ {
286+ return outValue . AsBsonDocument . Contains ( "inline" ) ;
287+ }
288+ }
289+
290+ return false ;
291+ }
228292 }
229- }
293+ }
0 commit comments