diff options
author | David Storch <david.storch@10gen.com> | 2014-11-13 14:15:22 -0500 |
---|---|---|
committer | David Storch <david.storch@10gen.com> | 2014-11-14 12:02:29 -0500 |
commit | 2de05fd1e465a2889c0f1035709710da8b0ad041 (patch) | |
tree | 16779d33ff82f402a2191a1da5fe09cfb1c97618 /src/mongo/shell/explain_query.js | |
parent | 7ad98f86d290ffc00849f701b93e7a0aaa0c5be9 (diff) | |
download | mongo-2de05fd1e465a2889c0f1035709710da8b0ad041.tar.gz |
SERVER-16053 shell retries using $explain if explain cmd not found on a shard
Also adds multi-version test for explain.
Diffstat (limited to 'src/mongo/shell/explain_query.js')
-rw-r--r-- | src/mongo/shell/explain_query.js | 46 |
1 files changed, 33 insertions, 13 deletions
diff --git a/src/mongo/shell/explain_query.js b/src/mongo/shell/explain_query.js index 0036d2be11f..cb7af06cddd 100644 --- a/src/mongo/shell/explain_query.js +++ b/src/mongo/shell/explain_query.js @@ -5,6 +5,10 @@ var DBExplainQuery = (function() { + // We expect to get back a "command not found" error in a sharded configuration if any + // of the shards have not been upgraded and don't implement the explain command. + var CMD_NOT_FOUND_CODE = 59; + // // Private methods. // @@ -52,6 +56,28 @@ var DBExplainQuery = (function() { } } + /** + * Where possible, the explain query will be sent to the server as an explain command. + * However, if one of the nodes we are talking to (either a standalone or a shard in + * a sharded cluster) is of a version that doesn't have the explain command, we will + * use this function to fall back on the $explain query option. + */ + function explainWithLegacyQueryOption(explainQuery) { + // The wire protocol version indicates that the server does not have the explain + // command. Add $explain to the query and send it to the server. + var clone = explainQuery._query.clone(); + clone._addSpecial("$explain", true); + var result = clone.next(); + + // Remove some fields from the explain if verbosity is + // just "queryPlanner". + if ("queryPlanner" === explainQuery._verbosity) { + removeVerboseFields(result); + } + + return Explainable.throwOrReturn(result); + } + function constructor(query, verbosity) { // @@ -135,22 +161,16 @@ var DBExplainQuery = (function() { explainCmd["verbosity"] = this._verbosity; var explainResult = this._query._db.runCommand(explainCmd); + if (!explainResult.ok && explainResult.code === CMD_NOT_FOUND_CODE) { + // One of the shards doesn't have the explain command available. Retry using + // the legacy $explain format, which should be supported by all shards. + return explainWithLegacyQueryOption(this); + } + return Explainable.throwOrReturn(explainResult); } else { - // The wire protocol version indicates that the server does not have the explain - // command. Add $explain to the query and send it to the server. - var clone = this._query.clone(); - clone._addSpecial("$explain", true); - var result = clone.next(); - - // Remove some fields from the explain if verbosity is - // just "queryPlanner". - if ("queryPlanner" === this._verbosity) { - removeVerboseFields(result); - } - - return Explainable.throwOrReturn(result); + return explainWithLegacyQueryOption(this); } } |