Skip to content

Commit f6504e7

Browse files
authored
Merge pull request #54263 from nextcloud/backport/54233/stable30
2 parents d308e61 + a79ced0 commit f6504e7

3 files changed

Lines changed: 102 additions & 141 deletions

File tree

apps/encryption/lib/Crypto/EncryptAll.php

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
use OCA\Encryption\KeyManager;
1313
use OCA\Encryption\Users\Setup;
1414
use OCA\Encryption\Util;
15+
use OCP\Files\FileInfo;
1516
use OCP\IConfig;
1617
use OCP\IL10N;
1718
use OCP\IUser;
@@ -246,15 +247,19 @@ protected function encryptUsersFiles($uid, ProgressBar $progress, $userCount) {
246247
while ($root = array_pop($directories)) {
247248
$content = $this->rootView->getDirectoryContent($root);
248249
foreach ($content as $file) {
249-
$path = $root . '/' . $file['name'];
250-
if ($this->rootView->is_dir($path)) {
250+
$path = $root . '/' . $file->getName();
251+
if ($file->isShared()) {
252+
$progress->setMessage("Skip shared file/folder $path");
253+
$progress->advance();
254+
continue;
255+
} elseif ($file->getType() === FileInfo::TYPE_FOLDER) {
251256
$directories[] = $path;
252257
continue;
253258
} else {
254259
$progress->setMessage("encrypt files for user $userCount: $path");
255260
$progress->advance();
256261
try {
257-
if ($this->encryptFile($path) === false) {
262+
if ($this->encryptFile($file, $path) === false) {
258263
$progress->setMessage("encrypt files for user $userCount: $path (already encrypted)");
259264
$progress->advance();
260265
}
@@ -275,17 +280,9 @@ protected function encryptUsersFiles($uid, ProgressBar $progress, $userCount) {
275280
}
276281
}
277282

278-
/**
279-
* encrypt file
280-
*
281-
* @param string $path
282-
* @return bool
283-
*/
284-
protected function encryptFile($path) {
285-
283+
protected function encryptFile(FileInfo $fileInfo, string $path): bool {
286284
// skip already encrypted files
287-
$fileInfo = $this->rootView->getFileInfo($path);
288-
if ($fileInfo !== false && $fileInfo->isEncrypted()) {
285+
if ($fileInfo->isEncrypted()) {
289286
return true;
290287
}
291288

apps/encryption/tests/Crypto/EncryptAllTest.php

Lines changed: 76 additions & 89 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
<?php
22

3+
declare(strict_types=1);
4+
35
/**
46
* SPDX-FileCopyrightText: 2016-2024 Nextcloud GmbH and Nextcloud contributors
57
* SPDX-FileCopyrightText: 2016 ownCloud, Inc.
@@ -31,52 +33,23 @@
3133

3234
class EncryptAllTest extends TestCase {
3335

34-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCA\Encryption\KeyManager */
35-
protected $keyManager;
36-
37-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCA\Encryption\Util */
38-
protected $util;
39-
40-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\IUserManager */
41-
protected $userManager;
42-
43-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCA\Encryption\Users\Setup */
44-
protected $setupUser;
45-
46-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OC\Files\View */
47-
protected $view;
48-
49-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\IConfig */
50-
protected $config;
51-
52-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\Mail\IMailer */
53-
protected $mailer;
54-
55-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\IL10N */
56-
protected $l;
57-
58-
/** @var \PHPUnit\Framework\MockObject\MockObject | IFactory */
59-
protected $l10nFactory;
60-
61-
/** @var \PHPUnit\Framework\MockObject\MockObject | \Symfony\Component\Console\Helper\QuestionHelper */
62-
protected $questionHelper;
63-
64-
/** @var \PHPUnit\Framework\MockObject\MockObject | \Symfony\Component\Console\Input\InputInterface */
65-
protected $inputInterface;
66-
67-
/** @var \PHPUnit\Framework\MockObject\MockObject | \Symfony\Component\Console\Output\OutputInterface */
68-
protected $outputInterface;
69-
70-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\UserInterface */
71-
protected $userInterface;
72-
73-
/** @var \PHPUnit\Framework\MockObject\MockObject | \OCP\Security\ISecureRandom */
74-
protected $secureRandom;
75-
36+
protected KeyManager&MockObject $keyManager;
37+
protected Util&MockObject $util;
38+
protected IUserManager&MockObject $userManager;
39+
protected Setup&MockObject $setupUser;
40+
protected View&MockObject $view;
41+
protected IConfig&MockObject $config;
42+
protected IMailer&MockObject $mailer;
43+
protected IL10N&MockObject $l;
44+
protected IFactory&MockObject $l10nFactory;
45+
protected \Symfony\Component\Console\Helper\QuestionHelper&MockObject $questionHelper;
46+
protected \Symfony\Component\Console\Input\InputInterface&MockObject $inputInterface;
47+
protected \Symfony\Component\Console\Output\OutputInterface&MockObject $outputInterface;
48+
protected UserInterface&MockObject $userInterface;
49+
protected ISecureRandom&MockObject $secureRandom;
7650
protected LoggerInterface&MockObject $logger;
7751

78-
/** @var EncryptAll */
79-
protected $encryptAll;
52+
protected EncryptAll $encryptAll;
8053

8154
protected function setUp(): void {
8255
parent::setUp();
@@ -109,7 +82,7 @@ protected function setUp(): void {
10982

11083
/**
11184
* We need format method to return a string
112-
* @var OutputFormatterInterface|\PHPUnit\Framework\MockObject\MockObject
85+
* @var OutputFormatterInterface&MockObject
11386
*/
11487
$outputFormatter = $this->createMock(OutputFormatterInterface::class);
11588
$outputFormatter->method('isDecorated')->willReturn(false);
@@ -141,6 +114,13 @@ protected function setUp(): void {
141114
);
142115
}
143116

117+
protected function createFileInfoMock($type, string $name): FileInfo&MockObject {
118+
$fileInfo = $this->createMock(FileInfo::class);
119+
$fileInfo->method('getType')->willReturn($type);
120+
$fileInfo->method('getName')->willReturn($name);
121+
return $fileInfo;
122+
}
123+
144124
public function testEncryptAll(): void {
145125
/** @var EncryptAll&MockObject $encryptAll */
146126
$encryptAll = $this->getMockBuilder(EncryptAll::class)
@@ -160,7 +140,7 @@ public function testEncryptAll(): void {
160140
$this->logger,
161141
]
162142
)
163-
->setMethods(['createKeyPairs', 'encryptAllUsersFiles', 'outputPasswords'])
143+
->onlyMethods(['createKeyPairs', 'encryptAllUsersFiles', 'outputPasswords'])
164144
->getMock();
165145

166146
$this->util->expects($this->any())->method('isMasterKeyEnabled')->willReturn(false);
@@ -190,7 +170,7 @@ public function testEncryptAllWithMasterKey(): void {
190170
$this->logger,
191171
]
192172
)
193-
->setMethods(['createKeyPairs', 'encryptAllUsersFiles', 'outputPasswords'])
173+
->onlyMethods(['createKeyPairs', 'encryptAllUsersFiles', 'outputPasswords'])
194174
->getMock();
195175

196176
$this->util->expects($this->any())->method('isMasterKeyEnabled')->willReturn(true);
@@ -221,7 +201,7 @@ public function testCreateKeyPairs(): void {
221201
$this->logger,
222202
]
223203
)
224-
->setMethods(['setupUserFS', 'generateOneTimePassword'])
204+
->onlyMethods(['setupUserFS', 'generateOneTimePassword'])
225205
->getMock();
226206

227207

@@ -253,8 +233,8 @@ function ($user) {
253233
$this->assertSame('', $userPasswords['user2']);
254234
}
255235

256-
public function testEncryptAllUsersFiles() {
257-
/** @var EncryptAll | \PHPUnit\Framework\MockObject\MockObject $encryptAll */
236+
public function testEncryptAllUsersFiles(): void {
237+
/** @var EncryptAll&MockObject $encryptAll */
258238
$encryptAll = $this->getMockBuilder(EncryptAll::class)
259239
->setConstructorArgs(
260240
[
@@ -272,7 +252,7 @@ public function testEncryptAllUsersFiles() {
272252
$this->logger,
273253
]
274254
)
275-
->setMethods(['encryptUsersFiles'])
255+
->onlyMethods(['encryptUsersFiles'])
276256
->getMock();
277257

278258
$this->util->expects($this->any())->method('isMasterKeyEnabled')->willReturn(false);
@@ -281,17 +261,22 @@ public function testEncryptAllUsersFiles() {
281261
$this->invokePrivate($encryptAll, 'output', [$this->outputInterface]);
282262
$this->invokePrivate($encryptAll, 'userPasswords', [['user1' => 'pwd1', 'user2' => 'pwd2']]);
283263

284-
$encryptAll->expects($this->exactly(2))->method('encryptUsersFiles')
285-
->withConsecutive(
286-
['user1'],
287-
['user2'],
288-
);
264+
$encryptAllCalls = [];
265+
$encryptAll->expects($this->exactly(2))
266+
->method('encryptUsersFiles')
267+
->willReturnCallback(function ($uid) use (&$encryptAllCalls): void {
268+
$encryptAllCalls[] = $uid;
269+
});
289270

290271
$this->invokePrivate($encryptAll, 'encryptAllUsersFiles');
272+
self::assertEquals([
273+
'user1',
274+
'user2',
275+
], $encryptAllCalls);
291276
}
292277

293-
public function testEncryptUsersFiles() {
294-
/** @var EncryptAll | \PHPUnit\Framework\MockObject\MockObject $encryptAll */
278+
public function testEncryptUsersFiles(): void {
279+
/** @var EncryptAll&MockObject $encryptAll */
295280
$encryptAll = $this->getMockBuilder(EncryptAll::class)
296281
->setConstructorArgs(
297282
[
@@ -309,40 +294,39 @@ public function testEncryptUsersFiles() {
309294
$this->logger,
310295
]
311296
)
312-
->setMethods(['encryptFile', 'setupUserFS'])
297+
->onlyMethods(['encryptFile', 'setupUserFS'])
313298
->getMock();
314299

315300
$this->util->expects($this->any())->method('isMasterKeyEnabled')->willReturn(false);
316301

317302
$this->view->expects($this->exactly(2))->method('getDirectoryContent')
318-
->withConsecutive(
319-
['/user1/files'],
320-
['/user1/files/foo'],
321-
)->willReturnOnConsecutiveCalls(
303+
->willReturnMap([
322304
[
323-
['name' => 'foo', 'type' => 'dir'],
324-
['name' => 'bar', 'type' => 'file'],
305+
'/user1/files',
306+
'',
307+
null,
308+
[
309+
$this->createFileInfoMock(FileInfo::TYPE_FOLDER, 'foo'),
310+
$this->createFileInfoMock(FileInfo::TYPE_FILE, 'bar'),
311+
],
325312
],
326313
[
327-
['name' => 'subfile', 'type' => 'file']
328-
]
329-
);
330-
331-
$this->view->expects($this->any())->method('is_dir')
332-
->willReturnCallback(
333-
function ($path) {
334-
if ($path === '/user1/files/foo') {
335-
return true;
336-
}
337-
return false;
338-
}
339-
);
314+
'/user1/files/foo',
315+
'',
316+
null,
317+
[
318+
$this->createFileInfoMock(FileInfo::TYPE_FILE, 'subfile'),
319+
],
320+
],
321+
]);
340322

341-
$encryptAll->expects($this->exactly(2))->method('encryptFile')
342-
->withConsecutive(
343-
['/user1/files/bar'],
344-
['/user1/files/foo/subfile'],
345-
);
323+
$encryptAllCalls = [];
324+
$encryptAll->expects($this->exactly(2))
325+
->method('encryptFile')
326+
->willReturnCallback(function (FileInfo $file, string $path) use (&$encryptAllCalls): bool {
327+
$encryptAllCalls[] = $path;
328+
return true;
329+
});
346330

347331
$outputFormatter = $this->createMock(OutputFormatterInterface::class);
348332
$outputFormatter->method('isDecorated')->willReturn(false);
@@ -352,9 +336,13 @@ function ($path) {
352336
$progressBar = new ProgressBar($this->outputInterface);
353337

354338
$this->invokePrivate($encryptAll, 'encryptUsersFiles', ['user1', $progressBar, '']);
339+
self::assertEquals([
340+
'/user1/files/bar',
341+
'/user1/files/foo/subfile',
342+
], $encryptAllCalls);
355343
}
356344

357-
public function testGenerateOneTimePassword() {
345+
public function testGenerateOneTimePassword(): void {
358346
$password = $this->invokePrivate($this->encryptAll, 'generateOneTimePassword', ['user1']);
359347
$this->assertTrue(is_string($password));
360348
$this->assertSame(8, strlen($password));
@@ -368,12 +356,11 @@ public function testGenerateOneTimePassword() {
368356
* @dataProvider dataTestEncryptFile
369357
* @param $isEncrypted
370358
*/
371-
public function testEncryptFile($isEncrypted) {
359+
public function testEncryptFile($isEncrypted): void {
372360
$fileInfo = $this->createMock(FileInfo::class);
373361
$fileInfo->expects($this->any())->method('isEncrypted')
374362
->willReturn($isEncrypted);
375-
$this->view->expects($this->any())->method('getFileInfo')
376-
->willReturn($fileInfo);
363+
$this->view->expects($this->never())->method('getFileInfo');
377364

378365

379366
if ($isEncrypted) {
@@ -385,11 +372,11 @@ public function testEncryptFile($isEncrypted) {
385372
}
386373

387374
$this->assertTrue(
388-
$this->invokePrivate($this->encryptAll, 'encryptFile', ['foo.txt'])
375+
$this->invokePrivate($this->encryptAll, 'encryptFile', [$fileInfo, 'foo.txt'])
389376
);
390377
}
391378

392-
public function dataTestEncryptFile() {
379+
public static function dataTestEncryptFile(): array {
393380
return [
394381
[true],
395382
[false],

0 commit comments

Comments
 (0)