Skip to content

Commit 04b1cc3

Browse files
committed
PHPC-1387: Consider error document for cursor exceptions
This allows executeQuery() to throw a CommandException, which exposes the error document. In 1.6+, it will also ensure that error labels are set on any RuntimeException thrown during cursor iteration, which is relevant for transactions.
1 parent 092d82d commit 04b1cc3

File tree

3 files changed

+35
-5
lines changed

3 files changed

+35
-5
lines changed

php_phongo.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -190,7 +190,7 @@ void phongo_throw_exception_from_bson_error_t(bson_error_t* error TSRMLS_DC)
190190
zend_throw_exception(phongo_exception_from_mongoc_domain(error->domain, error->code), error->message, error->code TSRMLS_CC);
191191
}
192192

193-
void phongo_throw_exception_from_bson_error_t_and_reply(bson_error_t* error, bson_t* reply TSRMLS_DC)
193+
void phongo_throw_exception_from_bson_error_t_and_reply(bson_error_t* error, const bson_t* reply TSRMLS_DC)
194194
{
195195
/* Server errors (other than ExceededTimeLimit) and write concern errors
196196
* may use CommandException and report the result document for the
@@ -737,7 +737,7 @@ bool phongo_execute_bulk_write(mongoc_client_t* client, const char* namespace, p
737737
* returned and an exception is thrown. */
738738
bool phongo_cursor_advance_and_check_for_error(mongoc_cursor_t* cursor TSRMLS_DC) /* {{{ */
739739
{
740-
const bson_t* doc;
740+
const bson_t* doc = NULL;
741741

742742
if (!mongoc_cursor_next(cursor, &doc)) {
743743
bson_error_t error = { 0 };
@@ -748,8 +748,8 @@ bool phongo_cursor_advance_and_check_for_error(mongoc_cursor_t* cursor TSRMLS_DC
748748
}
749749

750750
/* Could simply be no docs, which is not an error */
751-
if (mongoc_cursor_error(cursor, &error)) {
752-
phongo_throw_exception_from_bson_error_t(&error TSRMLS_CC);
751+
if (mongoc_cursor_error_document(cursor, &error, &doc)) {
752+
phongo_throw_exception_from_bson_error_t_and_reply(&error, doc TSRMLS_CC);
753753
return false;
754754
}
755755
}

php_phongo.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ void phongo_throw_exception(php_phongo_error_domain_t domain TSRMLS
111111
#endif /* PHP_VERSION_ID < 70000 */
112112
;
113113
void phongo_throw_exception_from_bson_error_t(bson_error_t* error TSRMLS_DC);
114-
void phongo_throw_exception_from_bson_error_t_and_reply(bson_error_t* error, bson_t* reply TSRMLS_DC);
114+
void phongo_throw_exception_from_bson_error_t_and_reply(bson_error_t* error, const bson_t* reply TSRMLS_DC);
115115

116116
/* This enum is used for processing options in phongo_execute_parse_options and
117117
* selecting a libmongoc function to use in phongo_execute_command. The values
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
--TEST--
2+
MongoDB\Driver\Manager::executeQuery() exposes error document via CommandException
3+
--SKIPIF--
4+
<?php require __DIR__ . "/../utils/basic-skipif.inc"; ?>
5+
<?php skip_if_not_live(); ?>
6+
<?php skip_if_server_version('<', '3.2'); ?>
7+
--FILE--
8+
<?php
9+
require_once __DIR__ . "/../utils/basic.inc";
10+
11+
$manager = new MongoDB\Driver\Manager(URI);
12+
$query = new MongoDB\Driver\Query(['$foo' => 1]);
13+
14+
try {
15+
$manager->executeQuery(NS, $query);
16+
} catch (\MongoDB\Driver\Exception\CommandException $e) {
17+
printf("%s(%d): %s\n", get_class($e), $e->getCode(), $e->getMessage());
18+
$doc = $e->getResultDocument();
19+
var_dump($doc->errmsg === $e->getMessage());
20+
var_dump($doc->code === $e->getCode());
21+
}
22+
23+
?>
24+
===DONE===
25+
<?php exit(0); ?>
26+
--EXPECT--
27+
MongoDB\Driver\Exception\CommandException(2): unknown top level operator: $foo
28+
bool(true)
29+
bool(true)
30+
===DONE===

0 commit comments

Comments
 (0)