Skip to content

Commit

Permalink
Merge pull request #37438 from owncloud/check-link-password-events
Browse files Browse the repository at this point in the history
emit events for before-after-failed link password checks
  • Loading branch information
phil-davis authored May 26, 2020
2 parents 8e65760 + 0dfa157 commit df64083
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 2 deletions.
6 changes: 6 additions & 0 deletions changelog/unreleased/37438
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
Enhancement: Add 3 new events (before-fail-after) for share password validations

'share.beforepasswordcheck', 'share.afterpasswordcheck' and 'share.failedpasswordcheck'
events have been added for share password validations.

https://github.com/owncloud/core/pull/37438
12 changes: 10 additions & 2 deletions lib/private/Share20/Manager.php
Original file line number Diff line number Diff line change
Expand Up @@ -1474,6 +1474,10 @@ public function getShareByToken($token) {

/**
* Verify the password of a public share
* Dispatches following events:
* 'share.beforepasswordcheck' is dispatched before every password verification
* 'share.afterpasswordcheck' is dispatched after successful password verifications
* 'share.failedpasswordcheck' is dispatched after unsuccessful password verifications
*
* @param \OCP\Share\IShare $share
* @param string $password
Expand All @@ -1488,12 +1492,16 @@ public function checkPassword(\OCP\Share\IShare $share, $password) {
if ($password === null || $share->getPassword() === null) {
return false;
}

$beforeEvent = new GenericEvent(null, ['shareObject' => $share]);
$this->eventDispatcher->dispatch('share.beforepasswordcheck', $beforeEvent);
$newHash = '';
if (!$this->hasher->verify($password, $share->getPassword(), $newHash)) {
$failEvent = new GenericEvent(null, ['shareObject' => $share]);
$this->eventDispatcher->dispatch('share.failedpasswordcheck', $failEvent);
return false;
}

$afterEvent = new GenericEvent(null, ['shareObject' => $share]);
$this->eventDispatcher->dispatch('share.afterpasswordcheck', $afterEvent);
if (!empty($newHash)) {
$share->setPassword($newHash);
$provider = $this->factory->getProviderForType($share->getShareType());
Expand Down
33 changes: 33 additions & 0 deletions tests/lib/Share20/ManagerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -3151,17 +3151,50 @@ public function testCheckPasswordInvalidPassword() {

$this->hasher->method('verify')->with('invalidpassword', 'password', '')->willReturn(false);

$calledBeforeEvent = [];
$this->eventDispatcher->addListener('share.beforepasswordcheck',
function (GenericEvent $event) use (&$calledBeforeEvent) {
$calledBeforeEvent[] = 'share.beforepasswordcheck';
$calledBeforeEvent[] = $event;
});
$calledFailEvent = [];
$this->eventDispatcher->addListener('share.failedpasswordcheck',
function (GenericEvent $event) use (&$calledFailEvent) {
$calledFailEvent[] = 'share.failedpasswordcheck';
$calledFailEvent[] = $event;
});
$this->assertFalse($this->manager->checkPassword($share, 'invalidpassword'));
$this->assertEquals('share.beforepasswordcheck', $calledBeforeEvent[0]);
$this->assertEquals('share.failedpasswordcheck', $calledFailEvent[0]);
$this->assertInstanceOf(GenericEvent::class, $calledBeforeEvent[1]);
$this->assertInstanceOf(GenericEvent::class, $calledFailEvent[1]);
}

public function testCheckPasswordValidPassword() {
$share = $this->createMock('\OCP\Share\IShare');
$share->method('getShareType')->willReturn(\OCP\Share::SHARE_TYPE_LINK);
$share->method('getPassword')->willReturn('passwordHash');

$calledBeforeEvent = [];
$this->eventDispatcher->addListener('share.beforepasswordcheck',
function (GenericEvent $event) use (&$calledBeforeEvent) {
$calledBeforeEvent[] = 'share.beforepasswordcheck';
$calledBeforeEvent[] = $event;
});
$calledAfterEvent = [];
$this->eventDispatcher->addListener('share.afterpasswordcheck',
function (GenericEvent $event) use (&$calledAfterEvent) {
$calledAfterEvent[] = 'share.afterpasswordcheck';
$calledAfterEvent[] = $event;
});

$this->hasher->method('verify')->with('password', 'passwordHash', '')->willReturn(true);

$this->assertTrue($this->manager->checkPassword($share, 'password'));
$this->assertEquals('share.beforepasswordcheck', $calledBeforeEvent[0]);
$this->assertEquals('share.afterpasswordcheck', $calledAfterEvent[0]);
$this->assertInstanceOf(GenericEvent::class, $calledBeforeEvent[1]);
$this->assertInstanceOf(GenericEvent::class, $calledAfterEvent[1]);
}

public function testCheckPasswordUpdateShare() {
Expand Down

0 comments on commit df64083

Please sign in to comment.