delete the token in case an exception is thrown when decrypting the password
This commit is contained in:
parent
af707fba41
commit
69dafd727d
|
@ -22,6 +22,7 @@
|
||||||
|
|
||||||
namespace OC\Authentication\Token;
|
namespace OC\Authentication\Token;
|
||||||
|
|
||||||
|
use Exception;
|
||||||
use OC\Authentication\Exceptions\InvalidTokenException;
|
use OC\Authentication\Exceptions\InvalidTokenException;
|
||||||
use OCP\AppFramework\Db\DoesNotExistException;
|
use OCP\AppFramework\Db\DoesNotExistException;
|
||||||
use OCP\AppFramework\Utility\ITimeFactory;
|
use OCP\AppFramework\Utility\ITimeFactory;
|
||||||
|
@ -192,7 +193,13 @@ class DefaultTokenProvider implements IProvider {
|
||||||
*/
|
*/
|
||||||
private function decryptPassword($password, $token) {
|
private function decryptPassword($password, $token) {
|
||||||
$secret = $this->config->getSystemValue('secret');
|
$secret = $this->config->getSystemValue('secret');
|
||||||
return $this->crypto->decrypt($password, $token . $secret);
|
try {
|
||||||
|
return $this->crypto->decrypt($password, $token . $secret);
|
||||||
|
} catch (Exception $ex) {
|
||||||
|
// Delete the invalid token
|
||||||
|
$this->invalidateToken($token);
|
||||||
|
throw new InvalidTokenException();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -69,10 +69,10 @@ use OCP\Session\Exceptions\SessionNotAvailableException;
|
||||||
* @package OC\User
|
* @package OC\User
|
||||||
*/
|
*/
|
||||||
class Session implements IUserSession, Emitter {
|
class Session implements IUserSession, Emitter {
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @var Manager $manager
|
* @var Manager $manager
|
||||||
*/
|
*/
|
||||||
|
|
||||||
private $manager;
|
private $manager;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -107,8 +107,7 @@ class Session implements IUserSession, Emitter {
|
||||||
* @param IProvider $tokenProvider
|
* @param IProvider $tokenProvider
|
||||||
* @param IProvider[] $tokenProviders
|
* @param IProvider[] $tokenProviders
|
||||||
*/
|
*/
|
||||||
public function __construct(IUserManager $manager, ISession $session, ITimeFactory $timeFacory, $tokenProvider,
|
public function __construct(IUserManager $manager, ISession $session, ITimeFactory $timeFacory, $tokenProvider, array $tokenProviders = []) {
|
||||||
array $tokenProviders = []) {
|
|
||||||
$this->manager = $manager;
|
$this->manager = $manager;
|
||||||
$this->session = $session;
|
$this->session = $session;
|
||||||
$this->timeFacory = $timeFacory;
|
$this->timeFacory = $timeFacory;
|
||||||
|
@ -230,7 +229,14 @@ class Session implements IUserSession, Emitter {
|
||||||
$lastCheck = $this->session->get('last_login_check') ? : 0;
|
$lastCheck = $this->session->get('last_login_check') ? : 0;
|
||||||
$now = $this->timeFacory->getTime();
|
$now = $this->timeFacory->getTime();
|
||||||
if ($lastCheck < ($now - 60 * 5)) {
|
if ($lastCheck < ($now - 60 * 5)) {
|
||||||
$pwd = $this->tokenProvider->getPassword($token, $sessionId);
|
try {
|
||||||
|
$pwd = $this->tokenProvider->getPassword($token, $sessionId);
|
||||||
|
} catch (InvalidTokenException $ex) {
|
||||||
|
// An invalid token password was used -> log user out
|
||||||
|
$this->logout();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if ($this->manager->checkPassword($user->getUID(), $pwd) === false) {
|
if ($this->manager->checkPassword($user->getUID(), $pwd) === false) {
|
||||||
// Password has changed -> log user out
|
// Password has changed -> log user out
|
||||||
$this->logout();
|
$this->logout();
|
||||||
|
|
|
@ -54,7 +54,8 @@ class DefaultTokenProviderTest extends TestCase {
|
||||||
->method('getTime')
|
->method('getTime')
|
||||||
->will($this->returnValue($this->time));
|
->will($this->returnValue($this->time));
|
||||||
|
|
||||||
$this->tokenProvider = new DefaultTokenProvider($this->mapper, $this->crypto, $this->config, $this->logger, $this->timeFactory);
|
$this->tokenProvider = new DefaultTokenProvider($this->mapper, $this->crypto, $this->config, $this->logger,
|
||||||
|
$this->timeFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testGenerateToken() {
|
public function testGenerateToken() {
|
||||||
|
@ -118,6 +119,36 @@ class DefaultTokenProviderTest extends TestCase {
|
||||||
$this->assertEquals('passme', $actual);
|
$this->assertEquals('passme', $actual);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @expectedException \OC\Authentication\Exceptions\InvalidTokenException
|
||||||
|
*/
|
||||||
|
public function testGetPasswordDeletesInvalidToken() {
|
||||||
|
$token = 'token1234';
|
||||||
|
$tk = new DefaultToken();
|
||||||
|
$tk->setPassword('someencryptedvalue');
|
||||||
|
/* @var $tokenProvider DefaultTokenProvider */
|
||||||
|
$tokenProvider = $this->getMockBuilder('\OC\Authentication\Token\DefaultTokenProvider')
|
||||||
|
->setMethods([
|
||||||
|
'invalidateToken'
|
||||||
|
])
|
||||||
|
->setConstructorArgs([$this->mapper, $this->crypto, $this->config, $this->logger,
|
||||||
|
$this->timeFactory])
|
||||||
|
->getMock();
|
||||||
|
$this->config->expects($this->once())
|
||||||
|
->method('getSystemValue')
|
||||||
|
->with('secret')
|
||||||
|
->will($this->returnValue('1f4h9s'));
|
||||||
|
$this->crypto->expects($this->once())
|
||||||
|
->method('decrypt')
|
||||||
|
->with('someencryptedvalue', $token . '1f4h9s')
|
||||||
|
->will($this->throwException(new \Exception('some crypto error occurred')));
|
||||||
|
$tokenProvider->expects($this->once())
|
||||||
|
->method('invalidateToken')
|
||||||
|
->with($token);
|
||||||
|
|
||||||
|
$tokenProvider->getPassword($tk, $token);
|
||||||
|
}
|
||||||
|
|
||||||
public function testInvalidateToken() {
|
public function testInvalidateToken() {
|
||||||
$this->mapper->expects($this->once())
|
$this->mapper->expects($this->once())
|
||||||
->method('invalidate')
|
->method('invalidate')
|
||||||
|
|
Loading…
Reference in New Issue