Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 1966a0c

Browse files
Merge v2.1 into v2.x (#1748)
2 parents 5185890 + 002fad6 commit 1966a0c

File tree

5 files changed

+128
-12
lines changed

5 files changed

+128
-12
lines changed

‎src/Client.php

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,8 @@ class Client
8282

8383
private WriteConcern $writeConcern;
8484

85+
private bool $autoEncryptionEnabled;
86+
8587
/**
8688
* Constructs a new Client instance.
8789
*
@@ -133,6 +135,7 @@ public function __construct(?string $uri = null, array $uriOptions = [], array $
133135
$this->uri = $uri ?? self::DEFAULT_URI;
134136
$this->builderEncoder = $driverOptions['builderEncoder'] ?? new BuilderEncoder();
135137
$this->typeMap = $driverOptions['typeMap'];
138+
$this->autoEncryptionEnabled = isset($driverOptions['autoEncryption']['keyVaultNamespace']);
136139

137140
$driverOptions = array_diff_key($driverOptions, ['builderEncoder' => 1, 'typeMap' => 1]);
138141

@@ -270,7 +273,7 @@ public function dropDatabase(string $databaseName, array $options = []): void
270273
*/
271274
public function getCollection(string $databaseName, string $collectionName, array $options = []): Collection
272275
{
273-
$options += ['typeMap' => $this->typeMap, 'builderEncoder' => $this->builderEncoder];
276+
$options += ['typeMap' => $this->typeMap, 'builderEncoder' => $this->builderEncoder, 'autoEncryptionEnabled' => $this->autoEncryptionEnabled];
274277

275278
return new Collection($this->manager, $databaseName, $collectionName, $options);
276279
}
@@ -285,7 +288,7 @@ public function getCollection(string $databaseName, string $collectionName, arra
285288
*/
286289
public function getDatabase(string $databaseName, array $options = []): Database
287290
{
288-
$options += ['typeMap' => $this->typeMap, 'builderEncoder' => $this->builderEncoder];
291+
$options += ['typeMap' => $this->typeMap, 'builderEncoder' => $this->builderEncoder, 'autoEncryptionEnabled' => $this->autoEncryptionEnabled];
289292

290293
return new Database($this->manager, $databaseName, $options);
291294
}

‎src/Collection.php

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@
7575
use function array_key_exists;
7676
use function current;
7777
use function is_array;
78+
use function is_bool;
7879
use function strlen;
7980

8081
class Collection
@@ -100,6 +101,8 @@ class Collection
100101

101102
private WriteConcern $writeConcern;
102103

104+
private bool $autoEncryptionEnabled;
105+
103106
/**
104107
* Constructs new Collection instance.
105108
*
@@ -167,12 +170,17 @@ public function __construct(private Manager $manager, private string $databaseNa
167170
throw InvalidArgumentException::invalidType('"writeConcern" option', $options['writeConcern'], WriteConcern::class);
168171
}
169172

173+
if (isset($options['autoEncryptionEnabled']) && ! is_bool($options['autoEncryptionEnabled'])) {
174+
throw InvalidArgumentException::invalidType('"autoEncryptionEnabled" option', $options['autoEncryptionEnabled'], 'boolean');
175+
}
176+
170177
$this->builderEncoder = $options['builderEncoder'] ?? new BuilderEncoder();
171178
$this->codec = $options['codec'] ?? null;
172179
$this->readConcern = $options['readConcern'] ?? $this->manager->getReadConcern();
173180
$this->readPreference = $options['readPreference'] ?? $this->manager->getReadPreference();
174181
$this->typeMap = $options['typeMap'] ?? self::DEFAULT_TYPE_MAP;
175182
$this->writeConcern = $options['writeConcern'] ?? $this->manager->getWriteConcern();
183+
$this->autoEncryptionEnabled = $options['autoEncryptionEnabled'] ?? false;
176184
}
177185

178186
/**
@@ -511,9 +519,9 @@ public function drop(array $options = []): void
511519

512520
$server = select_server_for_write($this->manager, $options);
513521

514-
if (! isset($options['encryptedFields'])) {
522+
if ($this->autoEncryptionEnabled && ! isset($options['encryptedFields'])) {
515523
$options['encryptedFields'] = get_encrypted_fields_from_driver($this->databaseName, $this->collectionName, $this->manager)
516-
?? get_encrypted_fields_from_server($this->databaseName, $this->collectionName, $this->manager, $server);
524+
?? get_encrypted_fields_from_server($this->databaseName, $this->collectionName, $server);
517525
}
518526

519527
$operation = isset($options['encryptedFields'])

‎src/Database.php

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@
5454
use Throwable;
5555

5656
use function is_array;
57+
use function is_bool;
5758
use function strlen;
5859

5960
class Database
@@ -77,6 +78,8 @@ class Database
7778

7879
private WriteConcern $writeConcern;
7980

81+
private bool $autoEncryptionEnabled;
82+
8083
/**
8184
* Constructs new Database instance.
8285
*
@@ -133,11 +136,16 @@ public function __construct(private Manager $manager, private string $databaseNa
133136
throw InvalidArgumentException::invalidType('"writeConcern" option', $options['writeConcern'], WriteConcern::class);
134137
}
135138

139+
if (isset($options['autoEncryptionEnabled']) && ! is_bool($options['autoEncryptionEnabled'])) {
140+
throw InvalidArgumentException::invalidType('"autoEncryptionEnabled" option', $options['autoEncryptionEnabled'], 'boolean');
141+
}
142+
136143
$this->builderEncoder = $options['builderEncoder'] ?? new BuilderEncoder();
137144
$this->readConcern = $options['readConcern'] ?? $this->manager->getReadConcern();
138145
$this->readPreference = $options['readPreference'] ?? $this->manager->getReadPreference();
139146
$this->typeMap = $options['typeMap'] ?? self::DEFAULT_TYPE_MAP;
140147
$this->writeConcern = $options['writeConcern'] ?? $this->manager->getWriteConcern();
148+
$this->autoEncryptionEnabled = $options['autoEncryptionEnabled'] ?? false;
141149
}
142150

143151
/**
@@ -372,9 +380,9 @@ public function dropCollection(string $collectionName, array $options = []): voi
372380
$options['writeConcern'] = $this->writeConcern;
373381
}
374382

375-
if (! isset($options['encryptedFields'])) {
383+
if ($this->autoEncryptionEnabled && ! isset($options['encryptedFields'])) {
376384
$options['encryptedFields'] = get_encrypted_fields_from_driver($this->databaseName, $collectionName, $this->manager)
377-
?? get_encrypted_fields_from_server($this->databaseName, $collectionName, $this->manager, $server);
385+
?? get_encrypted_fields_from_server($this->databaseName, $collectionName, $server);
378386
}
379387

380388
$operation = isset($options['encryptedFields'])
@@ -401,6 +409,7 @@ public function getCollection(string $collectionName, array $options = []): Coll
401409
'readPreference' => $this->readPreference,
402410
'typeMap' => $this->typeMap,
403411
'writeConcern' => $this->writeConcern,
412+
'autoEncryptionEnabled' => $this->autoEncryptionEnabled,
404413
];
405414

406415
return new Collection($this->manager, $this->databaseName, $collectionName, $options);

‎src/functions.php

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -198,13 +198,8 @@ function get_encrypted_fields_from_driver(string $databaseName, string $collecti
198198
* @see Collection::drop()
199199
* @see Database::dropCollection()
200200
*/
201-
function get_encrypted_fields_from_server(string $databaseName, string $collectionName, Manager$manager, Server $server): array|object|null
201+
function get_encrypted_fields_from_server(string $databaseName, string $collectionName, Server $server): array|object|null
202202
{
203-
// No-op if the encryptedFieldsMap autoEncryption driver option was omitted
204-
if ($manager->getEncryptedFieldsMap() === null) {
205-
return null;
206-
}
207-
208203
$collectionInfoIterator = (new ListCollections($databaseName, ['filter' => ['name' => $collectionName]]))->execute($server);
209204

210205
foreach ($collectionInfoIterator as $collectionInfo) {
Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
<?php
2+
3+
namespace MongoDB\Tests\Functions;
4+
5+
use MongoDB\BSON\Binary;
6+
use MongoDB\BSON\Regex;
7+
use MongoDB\Collection;
8+
use MongoDB\Database;
9+
use MongoDB\Driver\ClientEncryption;
10+
use MongoDB\Driver\WriteConcern;
11+
use MongoDB\Tests\FunctionalTestCase;
12+
13+
use function preg_quote;
14+
use function str_repeat;
15+
16+
class GetEncryptedFieldsFromServerFunctionalTest extends FunctionalTestCase
17+
{
18+
private ClientEncryption $clientEncryption;
19+
private Collection $keyVaultCollection;
20+
private Database $database;
21+
22+
public function setUp(): void
23+
{
24+
parent::setUp();
25+
26+
$this->skipIfClientSideEncryptionIsNotSupported();
27+
28+
if ($this->isStandalone()) {
29+
$this->markTestSkipped('Queryable encryption requires replica sets');
30+
}
31+
32+
$this->skipIfServerVersion('<', '7.0.0', 'Queryable encryption requires MongoDB 7.0 or later');
33+
34+
$encryptionOptions = [
35+
'keyVaultNamespace' => 'keyvault.datakeys',
36+
'kmsProviders' => [
37+
'local' => [
38+
'key' => new Binary(str_repeat("0円", 96)), // 96-byte local master key
39+
],
40+
],
41+
];
42+
$client = static::createTestClient(driverOptions: ['autoEncryption' => $encryptionOptions]);
43+
44+
// Ensure the key vault collection is dropped before each test
45+
$this->keyVaultCollection = $client->getCollection('keyvault', 'datakeys', ['writeConcern' => new WriteConcern(WriteConcern::MAJORITY)]);
46+
$this->keyVaultCollection->drop();
47+
48+
$this->clientEncryption = $client->createClientEncryption($encryptionOptions);
49+
50+
$this->database = $client->getDatabase($this->getDatabaseName());
51+
}
52+
53+
public function tearDown(): void
54+
{
55+
$this->keyVaultCollection?->drop();
56+
}
57+
58+
/** @see https://jira.mongodb.org/browse/PHPLIB-1702 */
59+
public function testDatabaseDropCollectionConsultsEncryptedFieldsFromServer(): void
60+
{
61+
$this->database->createEncryptedCollection(
62+
$this->getCollectionName(),
63+
$this->clientEncryption,
64+
'local',
65+
null,
66+
['encryptedFields' => ['fields' => []]],
67+
);
68+
69+
$this->assertCountCollections(3, $this->getCollectionName(), 'createEncryptedCollection should create three collections');
70+
71+
$this->database->dropCollection($this->getCollectionName());
72+
73+
$this->assertCountCollections(0, $this->getCollectionName());
74+
}
75+
76+
/** @see https://jira.mongodb.org/browse/PHPLIB-1702 */
77+
public function testCollectionDropConsultsEncryptedFieldsFromServer(): void
78+
{
79+
$this->database->createEncryptedCollection(
80+
$this->getCollectionName(),
81+
$this->clientEncryption,
82+
'local',
83+
null,
84+
['encryptedFields' => ['fields' => []]],
85+
);
86+
87+
$this->assertCountCollections(3, $this->getCollectionName(), 'createEncryptedCollection should create three collections');
88+
89+
$this->database->getCollection($this->getCollectionName())->drop();
90+
91+
$this->assertCountCollections(0, $this->getCollectionName());
92+
}
93+
94+
private function assertCountCollections(int $expected, $collectionName, string $message = ''): void
95+
{
96+
$collectionNames = $this->database->listCollectionNames([
97+
'filter' => ['name' => new Regex(preg_quote($collectionName))],
98+
]);
99+
$this->assertCount($expected, $collectionNames, $message);
100+
}
101+
}

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /