Skip to content
This repository was archived by the owner on Feb 1, 2022. It is now read-only.

Commit 072e324

Browse files
committed
Merge pull request #846
2 parents 58c2081 + f78ba16 commit 072e324

File tree

2 files changed

+99
-14
lines changed

2 files changed

+99
-14
lines changed

collection.c

Lines changed: 24 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1400,13 +1400,14 @@ PHP_METHOD(MongoCollection, findOne)
14001400
Atomically update and return a document */
14011401
PHP_METHOD(MongoCollection, findAndModify)
14021402
{
1403-
zval *query, *update = 0, *fields = 0, *options = 0;
1403+
HashTable *query = NULL, *update = NULL, *fields = NULL;
1404+
zval *zquery = NULL, *zupdate = NULL, *zfields = NULL, *options = NULL;
14041405
zval *cmd, *retval, **values;
14051406
mongo_connection *used_connection;
14061407
mongo_collection *c;
14071408
mongo_db *db;
14081409

1409-
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a!|a!a!a!", &query, &update, &fields, &options) == FAILURE) {
1410+
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "H!|H!H!a!", &query, &update, &fields, &options) == FAILURE) {
14101411
return;
14111412
}
14121413

@@ -1421,18 +1422,27 @@ PHP_METHOD(MongoCollection, findAndModify)
14211422
add_assoc_zval(cmd, "findandmodify", c->name);
14221423
zval_add_ref(&c->name);
14231424

1424-
if (query && zend_hash_num_elements(Z_ARRVAL_P(query)) > 0) {
1425-
add_assoc_zval(cmd, "query", query);
1426-
zval_add_ref(&query);
1425+
if (query && zend_hash_num_elements(query) > 0) {
1426+
MAKE_STD_ZVAL(zquery);
1427+
array_init(zquery);
1428+
zend_hash_copy(HASH_P(zquery), query, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *));
1429+
add_assoc_zval(cmd, "query", zquery);
14271430
}
1428-
if (update && zend_hash_num_elements(Z_ARRVAL_P(update)) > 0) {
1429-
add_assoc_zval(cmd, "update", update);
1430-
zval_add_ref(&update);
1431+
1432+
if (update && zend_hash_num_elements(update) > 0) {
1433+
MAKE_STD_ZVAL(zupdate);
1434+
array_init(zupdate);
1435+
zend_hash_copy(HASH_P(zupdate), update, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *));
1436+
add_assoc_zval(cmd, "update", zupdate);
14311437
}
1432-
if (fields && zend_hash_num_elements(Z_ARRVAL_P(fields)) > 0) {
1433-
add_assoc_zval(cmd, "fields", fields);
1434-
zval_add_ref(&fields);
1438+
1439+
if (fields && zend_hash_num_elements(fields) > 0) {
1440+
MAKE_STD_ZVAL(zfields);
1441+
array_init(zfields);
1442+
zend_hash_copy(HASH_P(zfields), fields, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *));
1443+
add_assoc_zval(cmd, "fields", zfields);
14351444
}
1445+
14361446
if (options && zend_hash_num_elements(Z_ARRVAL_P(options)) > 0) {
14371447
zval *temp;
14381448
zend_hash_merge(HASH_P(cmd), HASH_P(options), (void (*)(void*))zval_add_ref, &temp, sizeof(zval*), 1);
@@ -3064,9 +3074,9 @@ ZEND_BEGIN_ARG_INFO_EX(arginfo_find_one, 0, ZEND_RETURN_VALUE, 0)
30643074
ZEND_END_ARG_INFO()
30653075

30663076
ZEND_BEGIN_ARG_INFO_EX(arginfo_findandmodify, 0, ZEND_RETURN_VALUE, 1)
3067-
ZEND_ARG_ARRAY_INFO(0, query, 1)
3068-
ZEND_ARG_ARRAY_INFO(0, update, 1)
3069-
ZEND_ARG_ARRAY_INFO(0, fields, 1)
3077+
ZEND_ARG_INFO(0, query)
3078+
ZEND_ARG_INFO(0, update)
3079+
ZEND_ARG_INFO(0, fields)
30703080
ZEND_ARG_ARRAY_INFO(0, options, 1)
30713081
ZEND_END_ARG_INFO()
30723082

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
--TEST--
2+
MongoCollection::findAndModify() requires query, update, and fields to be a hash
3+
--SKIPIF--
4+
<?php require_once "tests/utils/standalone.inc"; ?>
5+
--FILE--
6+
<?php require_once "tests/utils/server.inc"; ?>
7+
<?php
8+
9+
$host = MongoShellServer::getStandaloneInfo();
10+
$m = new MongoClient($host);
11+
$c = $m->selectCollection(dbname(), collname(__FILE__));
12+
$c->drop();
13+
14+
$c->insert(array('x' => 1));
15+
16+
$document = $c->findAndModify(
17+
array('x' => 1),
18+
array('$inc' => array('x' => 1)),
19+
array('x' => 1),
20+
array('new' => true)
21+
);
22+
23+
printf("Set x to %d\n", $document['x']);
24+
25+
$document = $c->findAndModify(
26+
(object) array('x' => 2),
27+
(object) array('$inc' => array('x' => 1)),
28+
(object) array('x' => 1),
29+
array('new' => true)
30+
);
31+
32+
printf("Set x to %d\n", $document['x']);
33+
34+
$document = $c->findAndModify(
35+
1,
36+
array('$inc' => array('x' => 1)),
37+
array('x' => 1),
38+
array('new' => true)
39+
);
40+
41+
var_dump($document);
42+
43+
$document = $c->findAndModify(
44+
array('x' => 3),
45+
true,
46+
array('x' => 1),
47+
array('new' => true)
48+
);
49+
50+
var_dump($document);
51+
52+
$document = $c->findAndModify(
53+
array('x' => 3),
54+
array('$inc' => array('x' => 1)),
55+
'foo',
56+
array('new' => true)
57+
);
58+
59+
var_dump($document);
60+
61+
?>
62+
===DONE===
63+
--EXPECTF--
64+
Set x to 2
65+
Set x to 3
66+
67+
Warning: MongoCollection::findAndModify() expects parameter 1 to be array, integer given in %s on line %d
68+
NULL
69+
70+
Warning: MongoCollection::findAndModify() expects parameter 2 to be array, boolean given in %s on line %d
71+
NULL
72+
73+
Warning: MongoCollection::findAndModify() expects parameter 3 to be array, string given in %s on line %d
74+
NULL
75+
===DONE===

0 commit comments

Comments
 (0)