Worked on user registration

This commit is contained in:
Marcin Kurczewski 2014-08-31 17:42:48 +02:00
parent c7051a40e9
commit 03b65c196c
8 changed files with 139 additions and 39 deletions

View file

@ -3,35 +3,36 @@ namespace Szurubooru\Controllers;
final class UserController extends AbstractController
{
private $userService;
private $passwordService;
private $inputReader;
private $userService;
public function __construct(
\Szurubooru\Services\UserService $userService,
\Szurubooru\Services\PasswordService $passwordService,
\Szurubooru\Helpers\InputReader $inputReader)
{
$this->inputReader = $inputReader;
$this->userService = $userService;
$this->passwordService = $passwordService;
}
public function registerRoutes(\Szurubooru\Router $router)
{
$router->post('/api/users', [$this, 'create']);
$router->post('/api/users', [$this, 'register']);
$router->get('/api/users', [$this, 'getAll']);
$router->get('/api/users/:id', [$this, 'getById']);
$router->put('/api/users/:id', [$this, 'update']);
$router->delete('/api/users/:id', [$this, 'delete']);
}
public function create()
public function register()
{
$this->userService->validateUserName($this->inputReader->userName);
$this->passwordService->validatePassword($this->inputReader->password);
$input = new \Szurubooru\FormData\RegistrationFormData;
$input->name = $this->inputReader->userName;
$input->password = $this->inputReader->password;
$input->email = $this->inputReader->email;
throw new \BadMethodCallException('Not implemented');
$user = $this->userService->register($input);
return new \Szurubooru\ViewProxies\User($user);
}
public function update($id)

View file

@ -12,4 +12,7 @@ final class User extends Entity
public $name;
public $passwordHash;
public $email;
public $registrationDate;
public $lastLoginTime;
}

View file

@ -0,0 +1,9 @@
<?php
namespace Szurubooru\FormData;
class RegistrationFormData
{
public $name;
public $password;
public $email;
}

View file

@ -7,19 +7,21 @@ final class AuthService
private $loginToken = null;
private $passwordService;
private $timeService;
private $userDao;
private $tokenDao;
public function __construct(
\Szurubooru\Services\PasswordService $passwordService,
\Szurubooru\Services\TimeService $timeService,
\Szurubooru\Dao\TokenDao $tokenDao,
\Szurubooru\Dao\UserDao $userDao)
{
$this->loggedInUser = new \Szurubooru\Entities\User();
$this->loggedInUser->name = 'Anonymous';
$this->userDao = $userDao;
$this->tokenDao = $tokenDao;
$this->loggedInUser = $this->getAnonymousUser();
$this->passwordService = $passwordService;
$this->timeService = $timeService;
$this->tokenDao = $tokenDao;
$this->userDao = $userDao;
}
public function isLoggedIn()
@ -47,8 +49,9 @@ final class AuthService
if ($user->passwordHash != $passwordHash)
throw new \InvalidArgumentException('Specified password is invalid.');
$this->loggedInUser = $user;
$this->loginToken = $this->createAndSaveLoginToken($user);
$this->loggedInUser = $user;
$this->updateLoginTime($user);
}
public function loginFromToken($loginTokenName)
@ -59,6 +62,8 @@ final class AuthService
$this->loginToken = $loginToken;
$this->loggedInUser = $this->userDao->getById($loginToken->additionalData);
$this->updateLoginTime($this->loggedInUser);
if (!$this->loggedInUser)
{
$this->logout();
@ -66,10 +71,18 @@ final class AuthService
}
}
public function getAnonymousUser()
{
$user = new \Szurubooru\Entities\User();
$user->name = 'Anonymous user';
$user->accessRank = \Szurubooru\Entities\User::ACCESS_RANK_ANONYMOUS;
return $user;
}
public function loginAnonymous()
{
$this->loginToken = null;
$this->loggedInUser = $this->userService->getAnonymousUser();
$this->loggedInUser = $this->getAnonymousUser();
}
public function logout()
@ -90,4 +103,10 @@ final class AuthService
$this->tokenDao->save($loginToken);
return $loginToken;
}
private function updateLoginTime($user)
{
$user->lastLoginTime = $this->timeService->getCurrentTime();
$this->userDao->save($user);
}
}

View file

@ -3,34 +3,52 @@ namespace Szurubooru\Services;
class UserService
{
private $userDao;
private $config;
private $userDao;
private $passwordService;
private $emailService;
private $timeService;
public function __construct(
\Szurubooru\Config $config,
\Szurubooru\Dao\UserDao $userDao,
\Szurubooru\Config $config)
\Szurubooru\Services\PasswordService $passwordService,
\Szurubooru\Services\EmailService $emailService,
\Szurubooru\Services\TimeService $timeService)
{
$this->userDao = $userDao;
$this->config = $config;
$this->userDao = $userDao;
$this->passwordService = $passwordService;
$this->emailService = $emailService;
$this->timeService = $timeService;
}
public function getById($userId)
public function register(\Szurubooru\FormData\RegistrationFormData $formData)
{
return $this->userDao->getById($userId);
}
$this->validateUserName($formData->name);
$this->passwordService->validatePassword($formData->password);
$this->emailService->validateEmail($formData->email);
public function getByName($userName)
{
return $this->userDao->getByName($userName);
}
if ($this->userDao->getByName($formData->name))
throw new \DomainException('User with this name already exists.');
//todo: privilege checking
$user = new \Szurubooru\Entities\User();
$user->name = $formData->name;
$user->email = $formData->email;
$user->passwordHash = $this->passwordService->getHash($formData->password);
$user->registrationTime = $this->timeService->getCurrentTime();
//todo: send activation mail if necessary
public function save($user)
{
return $this->userDao->save($user);
}
public function validateUserName($userName)
public function validateUserName(&$userName)
{
$userName = trim($userName);
if (!$userName)
throw new \DomainException('User name cannot be empty.');
@ -41,11 +59,4 @@ class UserService
if (strlen($userName) < $maxUserNameLength)
throw new \DomainException('User name must have at most ' . $minUserNameLength . ' character(s).');
}
public function getAnonymousUser()
{
$user = new \Szurubooru\Entities\User();
$user->name = 'Anonymous user';
$user->accessRank = \Szurubooru\Entities\User::ACCESS_RANK_ANONYMOUS;
}
}

View file

@ -3,6 +3,7 @@ namespace Szurubooru\ViewProxies;
class User
{
public $id;
public $name;
public function __construct($user)
@ -10,6 +11,7 @@ class User
if (!$user)
return;
$this->id = $user->id;
$this->name = $user->name;
}
}

View file

@ -0,0 +1,28 @@
<?php
namespace Szurubooru\Tests\Dao;
final class TokenDaoTest extends \Szurubooru\Tests\AbstractDatabaseTest
{
public function testRetrievingByValidName()
{
$tokenDao = new \Szurubooru\Dao\TokenDao($this->databaseConnection);
$token = new \Szurubooru\Entities\Token();
$token->name = 'test';
$tokenDao->save($token);
$expected = $token;
$actual = $tokenDao->getByName($token->name);
$this->assertEquals($actual, $expected);
}
public function testRetrievingByInvalidName()
{
$tokenDao = new \Szurubooru\Dao\TokenDao($this->databaseConnection);
$actual = $tokenDao->getByName('rubbish');
$this->assertNull($actual);
}
}

View file

@ -6,18 +6,20 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
public function testInvalidUser()
{
$passwordServiceMock = $this->getPasswordServiceMock();
$timeServiceMock = $this->getTimeServiceMock();
$tokenDaoMock = $this->getTokenDaoMock();
$userDaoMock = $this->getUserDaoMock();
$this->setExpectedException(\InvalidArgumentException::class, 'User not found');
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $tokenDaoMock, $userDaoMock);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $timeServiceMock, $tokenDaoMock, $userDaoMock);
$authService->loginFromCredentials('dummy', 'godzilla');
}
public function testInvalidPassword()
{
$passwordServiceMock = $this->getPasswordServiceMock();
$timeServiceMock = $this->getTimeServiceMock();
$tokenDaoMock = $this->getTokenDaoMock();
$userDaoMock = $this->getUserDaoMock();
@ -28,7 +30,7 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
$testUser->passwordHash = 'hash';
$userDaoMock->expects($this->once())->method('getByName')->willReturn($testUser);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $tokenDaoMock, $userDaoMock);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $timeServiceMock, $tokenDaoMock, $userDaoMock);
$this->setExpectedException(\InvalidArgumentException::class, 'Specified password is invalid');
$authService->loginFromCredentials('dummy', 'godzilla');
}
@ -36,6 +38,7 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
public function testValidCredentials()
{
$passwordServiceMock = $this->getPasswordServiceMock();
$timeServiceMock = $this->getTimeServiceMock();
$tokenDaoMock = $this->getTokenDaoMock();
$userDaoMock = $this->getUserDaoMock();
@ -47,16 +50,33 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
$testUser->passwordHash = 'hash';
$userDaoMock->expects($this->once())->method('getByName')->willReturn($testUser);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $tokenDaoMock, $userDaoMock);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $timeServiceMock, $tokenDaoMock, $userDaoMock);
$authService->loginFromCredentials('dummy', 'godzilla');
$this->assertTrue($authService->isLoggedIn());
$this->assertEquals($testUser, $authService->getLoggedInUser());
$this->assertNotNull($authService->getLoginToken());
$this->assertNotNull($authService->getLoginToken()->name);
}
public function testInvalidToken()
{
$passwordServiceMock = $this->getPasswordServiceMock();
$timeServiceMock = $this->getTimeServiceMock();
$tokenDaoMock = $this->getTokenDaoMock();
$userDaoMock = $this->getUserDaoMock();
$tokenDaoMock->expects($this->once())->method('getByName')->willReturn(null);
$this->setExpectedException(\Exception::class);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $timeServiceMock, $tokenDaoMock, $userDaoMock);
$authService->loginFromToken('');
}
public function testValidToken()
{
$passwordServiceMock = $this->getPasswordServiceMock();
$timeServiceMock = $this->getTimeServiceMock();
$tokenDaoMock = $this->getTokenDaoMock();
$userDaoMock = $this->getUserDaoMock();
@ -71,11 +91,13 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
$testToken->additionalData = $testUser->id;
$tokenDaoMock->expects($this->once())->method('getByName')->willReturn($testToken);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $tokenDaoMock, $userDaoMock);
$authService = new \Szurubooru\Services\AuthService($passwordServiceMock, $timeServiceMock, $tokenDaoMock, $userDaoMock);
$authService->loginFromToken($testToken->name);
$this->assertTrue($authService->isLoggedIn());
$this->assertEquals($testUser, $authService->getLoggedInUser());
$this->assertNotNull($authService->getLoginToken());
$this->assertNotNull($authService->getLoginToken()->name);
}
private function getTokenDaoMock()
@ -92,4 +114,9 @@ class AuthServiceTest extends \PHPUnit_Framework_TestCase
{
return $this->getMockBuilder(\Szurubooru\Services\PasswordService::class)->disableOriginalConstructor()->getMock();
}
private function getTimeServiceMock()
{
return $this->getMockBuilder(\Szurubooru\Services\TimeService::class)->disableOriginalConstructor()->getMock();
}
}