Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
Y
yii2
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
PSDI Army
yii2
Commits
5dffd72c
Commit
5dffd72c
authored
Nov 06, 2014
by
Klimov Paul
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Added support for 'findAndModify' operation at `yii\mongodb\Query` and `yii\mongodb\ActiveQuery`
parent
8376f446
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
144 additions
and
48 deletions
+144
-48
ActiveQuery.php
extensions/mongodb/ActiveQuery.php
+50
-31
CHANGELOG.md
extensions/mongodb/CHANGELOG.md
+1
-0
Query.php
extensions/mongodb/Query.php
+60
-17
ActiveRecordTest.php
tests/unit/extensions/mongodb/ActiveRecordTest.php
+12
-0
QueryRunTest.php
tests/unit/extensions/mongodb/QueryRunTest.php
+21
-0
No files found.
extensions/mongodb/ActiveQuery.php
View file @
5dffd72c
...
...
@@ -135,21 +135,8 @@ class ActiveQuery extends Query implements ActiveQueryInterface
{
$cursor
=
$this
->
buildCursor
(
$db
);
$rows
=
$this
->
fetchRows
(
$cursor
);
if
(
!
empty
(
$rows
))
{
$models
=
$this
->
createModels
(
$rows
);
if
(
!
empty
(
$this
->
with
))
{
$this
->
findWith
(
$this
->
with
,
$models
);
}
if
(
!
$this
->
asArray
)
{
foreach
(
$models
as
$model
)
{
$model
->
afterFind
();
}
}
return
$models
;
}
else
{
return
[];
}
return
$this
->
populate
(
$rows
);
}
/**
...
...
@@ -164,24 +151,30 @@ class ActiveQuery extends Query implements ActiveQueryInterface
{
$row
=
parent
::
one
(
$db
);
if
(
$row
!==
false
)
{
if
(
$this
->
asArray
)
{
$model
=
$row
;
}
else
{
/* @var $class ActiveRecord */
$class
=
$this
->
modelClass
;
$model
=
$class
::
instantiate
(
$row
);
$class
::
populateRecord
(
$model
,
$row
);
}
if
(
!
empty
(
$this
->
with
))
{
$models
=
[
$model
];
$this
->
findWith
(
$this
->
with
,
$models
);
$model
=
$models
[
0
];
}
if
(
!
$this
->
asArray
)
{
$model
->
afterFind
();
}
$models
=
$this
->
populate
([
$row
]);
return
reset
(
$models
)
?:
null
;
}
else
{
return
null
;
}
}
return
$model
;
/**
* Performs 'findAndModify' query and returns a single row of result.
* Warning: in case 'new' option is set to 'false' (which is by default) usage of this method may lead
* to unexpected behavior at some Active Record features, because object will be populated by outdated data.
* @param array $update update criteria
* @param array $options list of options in format: optionName => optionValue.
* @param Connection $db the Mongo connection used to execute the query.
* @return ActiveRecord|array|null the original document, or the modified document when $options['new'] is set.
* Depending on the setting of [[asArray]], the query result may be either an array or an ActiveRecord object.
* Null will be returned if the query results in nothing.
*/
public
function
oneWithUpdate
(
$update
,
$options
=
[],
$db
=
null
)
{
$row
=
parent
::
oneWithUpdate
(
$update
,
$options
,
$db
);
if
(
$row
!==
null
)
{
$models
=
$this
->
populate
([
$row
]);
return
reset
(
$models
)
?:
null
;
}
else
{
return
null
;
}
...
...
@@ -205,4 +198,30 @@ class ActiveQuery extends Query implements ActiveQueryInterface
return
$db
->
getCollection
(
$this
->
from
);
}
/**
* Converts the raw query results into the format as specified by this query.
* This method is internally used to convert the data fetched from MongoDB
* into the format as required by this query.
* @param array $rows the raw query result from MongoDB
* @return array the converted query result
*/
public
function
populate
(
$rows
)
{
if
(
empty
(
$rows
))
{
return
[];
}
$models
=
$this
->
createModels
(
$rows
);
if
(
!
empty
(
$this
->
with
))
{
$this
->
findWith
(
$this
->
with
,
$models
);
}
if
(
!
$this
->
asArray
)
{
foreach
(
$models
as
$model
)
{
$model
->
afterFind
();
}
}
return
$models
;
}
}
extensions/mongodb/CHANGELOG.md
View file @
5dffd72c
...
...
@@ -5,6 +5,7 @@ Yii Framework 2 mongodb extension Change Log
-----------------------
-
Enh #3855: Added debug toolbar panel for MongoDB (klimov-paul)
-
Enh #5592: Added support for 'findAndModify' operation at
`yii\mongodb\Query`
and
`yii\mongodb\ActiveQuery`
(klimov-paul)
2.0.0 October 12, 2014
...
...
extensions/mongodb/Query.php
View file @
5dffd72c
...
...
@@ -102,24 +102,9 @@ class Query extends Component implements QueryInterface
*/
protected
function
buildCursor
(
$db
=
null
)
{
if
(
$this
->
where
===
null
)
{
$where
=
[];
}
else
{
$where
=
$this
->
where
;
}
$selectFields
=
[];
if
(
!
empty
(
$this
->
select
))
{
foreach
(
$this
->
select
as
$fieldName
)
{
$selectFields
[
$fieldName
]
=
true
;
}
}
$cursor
=
$this
->
getCollection
(
$db
)
->
find
(
$where
,
$selectFields
);
$cursor
=
$this
->
getCollection
(
$db
)
->
find
(
$this
->
composeCondition
(),
$this
->
composeSelectFields
());
if
(
!
empty
(
$this
->
orderBy
))
{
$sort
=
[];
foreach
(
$this
->
orderBy
as
$fieldName
=>
$sortOrder
)
{
$sort
[
$fieldName
]
=
$sortOrder
===
SORT_DESC
?
\MongoCollection
::
DESCENDING
:
\MongoCollection
::
ASCENDING
;
}
$cursor
->
sort
(
$sort
);
$cursor
->
sort
(
$this
->
composeSort
());
}
$cursor
->
limit
(
$this
->
limit
);
$cursor
->
skip
(
$this
->
offset
);
...
...
@@ -214,6 +199,23 @@ class Query extends Component implements QueryInterface
}
/**
* Performs 'findAndModify' query and returns a single row of result.
* @param array $update update criteria
* @param array $options list of options in format: optionName => optionValue.
* @param Connection $db the Mongo connection used to execute the query.
* @return array|null the original document, or the modified document when $options['new'] is set.
*/
public
function
oneWithUpdate
(
$update
,
$options
=
[],
$db
=
null
)
{
$collection
=
$this
->
getCollection
(
$db
);
if
(
!
empty
(
$this
->
orderBy
))
{
$options
[
'sort'
]
=
$this
->
composeSort
();
}
return
$collection
->
findAndModify
(
$this
->
composeCondition
(),
$update
,
$this
->
composeSelectFields
(),
$options
);
}
/**
* Returns the number of records.
* @param string $q kept to match [[QueryInterface]], its value is ignored.
* @param Connection $db the Mongo connection used to execute the query.
...
...
@@ -353,4 +355,45 @@ class Query extends Component implements QueryInterface
return
$result
;
}
}
/**
* Composes condition from raw [[where]] value.
* @return array conditions.
*/
private
function
composeCondition
()
{
if
(
$this
->
where
===
null
)
{
return
[];
}
else
{
return
$this
->
where
;
}
}
/**
* Composes select fields from raw [[select]] value.
* @return array select fields.
*/
private
function
composeSelectFields
()
{
$selectFields
=
[];
if
(
!
empty
(
$this
->
select
))
{
foreach
(
$this
->
select
as
$fieldName
)
{
$selectFields
[
$fieldName
]
=
true
;
}
}
return
$selectFields
;
}
/**
* Composes sort specification from raw [[orderBy]] value.
* @return array sort specification.
*/
private
function
composeSort
()
{
$sort
=
[];
foreach
(
$this
->
orderBy
as
$fieldName
=>
$sortOrder
)
{
$sort
[
$fieldName
]
=
$sortOrder
===
SORT_DESC
?
\MongoCollection
::
DESCENDING
:
\MongoCollection
::
ASCENDING
;
}
return
$sort
;
}
}
tests/unit/extensions/mongodb/ActiveRecordTest.php
View file @
5dffd72c
...
...
@@ -263,4 +263,16 @@ class ActiveRecordTest extends MongoDbTestCase
$this
->
assertNotEmpty
(
$rowRefreshed
);
$this
->
assertEquals
(
7
,
$rowRefreshed
->
status
);
}
public
function
testFindOneWithUpdate
()
{
$searchName
=
'name7'
;
$newName
=
'new name'
;
$customer
=
Customer
::
find
()
->
where
([
'name'
=>
$searchName
])
->
oneWithUpdate
([
'$set'
=>
[
'name'
=>
$newName
]],
[
'new'
=>
true
]);
$this
->
assertTrue
(
$customer
instanceof
Customer
);
$this
->
assertEquals
(
$newName
,
$customer
->
name
);
}
}
tests/unit/extensions/mongodb/QueryRunTest.php
View file @
5dffd72c
...
...
@@ -211,6 +211,27 @@ class QueryRunTest extends MongoDbTestCase
$this
->
assertEquals
(
$rows
,
$rowsUppercase
);
}
public
function
testOneWithUpdate
()
{
$connection
=
$this
->
getConnection
();
$query
=
new
Query
();
$searchName
=
'name5'
;
$newName
=
'new name'
;
$row
=
$query
->
from
(
'customer'
)
->
where
([
'name'
=>
$searchName
])
->
oneWithUpdate
([
'$set'
=>
[
'name'
=>
$newName
]],
[
'new'
=>
false
],
$connection
);
$this
->
assertEquals
(
$searchName
,
$row
[
'name'
]);
$searchName
=
'name7'
;
$newName
=
'new name'
;
$row
=
$query
->
from
(
'customer'
)
->
where
([
'name'
=>
$searchName
])
->
oneWithUpdate
([
'$set'
=>
[
'name'
=>
$newName
]],
[
'new'
=>
true
],
$connection
);
$this
->
assertEquals
(
$newName
,
$row
[
'name'
]);
}
/**
* @see https://github.com/yiisoft/yii2/issues/4879
*
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment