Skip to content

Commit 793bb8b

Browse files
committed
PHPLIB-72: Use model class when listing databases
1 parent b573271 commit 793bb8b

File tree

5 files changed

+195
-13
lines changed

5 files changed

+195
-13
lines changed

src/Client.php

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,8 @@
77
use MongoDB\Driver\Manager;
88
use MongoDB\Driver\ReadPreference;
99
use MongoDB\Driver\WriteConcern;
10-
use ArrayIterator;
10+
use MongoDB\Model\DatabaseInfoIterator;
11+
use MongoDB\Model\DatabaseInfoLegacyIterator;
1112
use stdClass;
1213
use UnexpectedValueException;
1314

@@ -54,7 +55,7 @@ public function dropDatabase($databaseName)
5455
* List databases.
5556
*
5657
* @see http://docs.mongodb.org/manual/reference/command/listDatabases/
57-
* @return Traversable
58+
* @return DatabaseInfoIterator
5859
* @throws UnexpectedValueException if the command result is malformed
5960
*/
6061
public function listDatabases()
@@ -73,13 +74,13 @@ function(stdClass $database) { return (array) $database; },
7374
$result['databases']
7475
);
7576

76-
/* Return a Traversable instead of an array in case listDatabases is
77+
/* Return an Iterator instead of an array in case listDatabases is
7778
* eventually changed to return a command cursor, like the collection
7879
* and index enumeration commands. This makes the "totalSize" command
7980
* field inaccessible, but users can manually invoke the command if they
8081
* need that value.
8182
*/
82-
return new ArrayIterator($databases);
83+
return new DatabaseInfoLegacyIterator($databases);
8384
}
8485

8586
/**

src/Model/DatabaseInfo.php

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
3+
namespace MongoDB\Model;
4+
5+
class DatabaseInfo
6+
{
7+
private $empty;
8+
private $name;
9+
private $sizeOnDisk;
10+
11+
/**
12+
* Constructor.
13+
*
14+
* @param array $info Database info
15+
*/
16+
public function __construct(array $info)
17+
{
18+
$this->name = (string) $info['name'];
19+
$this->empty = (boolean) $info['empty'];
20+
$this->sizeOnDisk = (integer) $info['sizeOnDisk'];
21+
}
22+
23+
/**
24+
* Return the database name.
25+
*
26+
* @return string
27+
*/
28+
public function getName()
29+
{
30+
return $this->name;
31+
}
32+
33+
/**
34+
* Return the databases size on disk (in bytes).
35+
*
36+
* @return integer
37+
*/
38+
public function getSizeOnDisk()
39+
{
40+
return $this->sizeOnDisk;
41+
}
42+
43+
/**
44+
* Return whether the database is empty.
45+
*
46+
* @return boolean
47+
*/
48+
public function isEmpty()
49+
{
50+
return $this->empty;
51+
}
52+
}

src/Model/DatabaseInfoIterator.php

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
<?php
2+
3+
namespace MongoDB\Model;
4+
5+
use Iterator;
6+
7+
interface DatabaseInfoIterator extends Iterator
8+
{
9+
/**
10+
* Return the current element as a DatabaseInfo instance.
11+
*
12+
* @return DatabaseInfo
13+
*/
14+
public function current();
15+
}
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
<?php
2+
3+
namespace MongoDB\Model;
4+
5+
class DatabaseInfoLegacyIterator implements DatabaseInfoIterator
6+
{
7+
private $databases;
8+
private $index = 0;
9+
10+
/**
11+
* Constructor.
12+
*
13+
* @param array $databases
14+
*/
15+
public function __construct(array $databases)
16+
{
17+
$this->databases = $databases;
18+
}
19+
20+
/**
21+
* Return the current element as a DatabaseInfo instance.
22+
*
23+
* @see DatabaseInfoIterator::current()
24+
* @see http://php.net/iterator.current
25+
* @return DatabaseInfo
26+
*/
27+
public function current()
28+
{
29+
return new DatabaseInfo(current($this->databases));
30+
}
31+
32+
/**
33+
* Return the key of the current element.
34+
*
35+
* @see http://php.net/iterator.key
36+
* @return integer
37+
*/
38+
public function key()
39+
{
40+
return key($this->databases);
41+
}
42+
43+
/**
44+
* Move forward to next element.
45+
*
46+
* @see http://php.net/iterator.next
47+
*/
48+
public function next()
49+
{
50+
next($this->databases);
51+
}
52+
53+
/**
54+
* Rewind the Iterator to the first element.
55+
*
56+
* @see http://php.net/iterator.rewind
57+
*/
58+
public function rewind()
59+
{
60+
reset($this->databases);
61+
}
62+
63+
/**
64+
* Checks if current position is valid.
65+
*
66+
* @see http://php.net/iterator.valid
67+
* @return boolean
68+
*/
69+
public function valid()
70+
{
71+
return key($this->databases) !== null;
72+
}
73+
}

tests/ClientFunctionalTest.php

Lines changed: 50 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,19 +3,30 @@
33
namespace MongoDB\Tests;
44

55
use MongoDB\Client;
6+
use MongoDB\Driver\Command;
7+
use MongoDB\Model\DatabaseInfo;
68

79
/**
810
* Functional tests for the Client class.
911
*/
1012
class ClientFunctionalTest extends FunctionalTestCase
1113
{
14+
private $client;
15+
16+
public function setUp()
17+
{
18+
parent::setUp();
19+
20+
$this->client = new Client($this->getUri());
21+
$this->client->dropDatabase($this->getDatabaseName());
22+
}
23+
1224
public function testDropDatabase()
1325
{
1426
$writeResult = $this->manager->executeInsert($this->getNamespace(), array('x' => 1));
1527
$this->assertEquals(1, $writeResult->getInsertedCount());
1628

17-
$client = new Client($this->getUri());
18-
$commandResult = $client->dropDatabase($this->getDatabaseName());
29+
$commandResult = $this->client->dropDatabase($this->getDatabaseName());
1930
$this->assertCommandSucceeded($commandResult);
2031
$this->assertCollectionCount($this->getNamespace(), 0);
2132
}
@@ -25,22 +36,52 @@ public function testListDatabases()
2536
$writeResult = $this->manager->executeInsert($this->getNamespace(), array('x' => 1));
2637
$this->assertEquals(1, $writeResult->getInsertedCount());
2738

28-
$client = new Client($this->getUri());
29-
$databases = $client->listDatabases();
39+
$databases = $this->client->listDatabases();
40+
41+
$this->assertInstanceOf('MongoDB\Model\DatabaseInfoIterator', $databases);
42+
43+
foreach ($databases as $database) {
44+
$this->assertInstanceOf('MongoDB\Model\DatabaseInfo', $database);
45+
}
46+
47+
$that = $this;
48+
$this->assertDatabaseExists($this->getDatabaseName(), function(DatabaseInfo $info) use ($that) {
49+
$that->assertFalse($info->isEmpty());
50+
$that->assertGreaterThan(0, $info->getSizeOnDisk());
51+
});
52+
}
53+
54+
/**
55+
* Asserts that a database with the given name exists on the server.
56+
*
57+
* An optional $callback may be provided, which should take a DatabaseInfo
58+
* argument as its first and only parameter. If a DatabaseInfo matching
59+
* the given name is found, it will be passed to the callback, which may
60+
* perform additional assertions.
61+
*
62+
* @param callable $callback
63+
*/
64+
private function assertDatabaseExists($databaseName, $callback = null)
65+
{
66+
if ($callback !== null && ! is_callable($callback)) {
67+
throw new InvalidArgumentException('$callback is not a callable');
68+
}
3069

31-
$this->assertInstanceOf('Traversable', $databases);
70+
$databases = $this->client->listDatabases();
3271

3372
$foundDatabase = null;
3473

3574
foreach ($databases as $database) {
36-
if ($database['name'] === $this->getDatabaseName()) {
75+
if ($database->getName() === $databaseName) {
3776
$foundDatabase = $database;
3877
break;
3978
}
4079
}
4180

42-
$this->assertNotNull($foundDatabase, 'Found test database in list of databases');
43-
$this->assertFalse($foundDatabase['empty'], 'Test database is not empty');
44-
$this->assertGreaterThan(0, $foundDatabase['sizeOnDisk'], 'Test database takes up disk space');
81+
$this->assertNotNull($foundDatabase, sprintf('Found %s database on the server', $databaseName));
82+
83+
if ($callback !== null) {
84+
call_user_func($callback, $foundDatabase);
85+
}
4586
}
4687
}

0 commit comments

Comments
 (0)