Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion data/doctrine/fixtures/UserLoader.php
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ public function load(ObjectManager $manager): void
->setIdentity('[email protected]')
->usePassword('dotkernel')
->setStatus(UserStatusEnum::Active)
->setIsDeleted(false)
->setHash(User::generateHash())
->addRole($guestRole)
->addRole($userRole);
Expand Down
2 changes: 1 addition & 1 deletion data/doctrine/migrations/Version20241030082958.php
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ public function up(Schema $schema): void
$this->addSql('CREATE TABLE oauth_clients (id INT UNSIGNED AUTO_INCREMENT NOT NULL, name VARCHAR(40) NOT NULL, secret VARCHAR(100) DEFAULT NULL, redirect VARCHAR(191) NOT NULL, revoked TINYINT(1) DEFAULT 0 NOT NULL, isConfidential TINYINT(1) DEFAULT 0 NOT NULL, user_id BINARY(16) DEFAULT NULL, INDEX IDX_13CE8101A76ED395 (user_id), PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE oauth_refresh_tokens (id INT UNSIGNED AUTO_INCREMENT NOT NULL, revoked TINYINT(1) DEFAULT 0 NOT NULL, expires_at DATETIME NOT NULL, access_token_id INT UNSIGNED DEFAULT NULL, INDEX IDX_5AB6872CCB2688 (access_token_id), PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE oauth_scopes (id INT UNSIGNED AUTO_INCREMENT NOT NULL, scope VARCHAR(191) NOT NULL, PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE user (uuid BINARY(16) NOT NULL, identity VARCHAR(191) NOT NULL, password VARCHAR(191) NOT NULL, status ENUM(\'active\', \'pending\') DEFAULT \'pending\' NOT NULL, isDeleted TINYINT(1) NOT NULL, hash VARCHAR(64) NOT NULL, created DATETIME NOT NULL, updated DATETIME DEFAULT NULL, UNIQUE INDEX UNIQ_8D93D6496A95E9C4 (identity), UNIQUE INDEX UNIQ_8D93D649D1B862B8 (hash), PRIMARY KEY(uuid)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE user (uuid BINARY(16) NOT NULL, identity VARCHAR(191) NOT NULL, password VARCHAR(191) NOT NULL, status ENUM(\'active\', \'pending\', \'deleted\') DEFAULT \'pending\' NOT NULL, hash VARCHAR(64) NOT NULL, created DATETIME NOT NULL, updated DATETIME DEFAULT NULL, UNIQUE INDEX UNIQ_8D93D6496A95E9C4 (identity), UNIQUE INDEX UNIQ_8D93D649D1B862B8 (hash), PRIMARY KEY(uuid)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE user_roles (userUuid BINARY(16) NOT NULL, roleUuid BINARY(16) NOT NULL, INDEX IDX_54FCD59FD73087E9 (userUuid), INDEX IDX_54FCD59F88446210 (roleUuid), PRIMARY KEY(userUuid, roleUuid)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE user_avatar (uuid BINARY(16) NOT NULL, name VARCHAR(191) NOT NULL, created DATETIME NOT NULL, updated DATETIME DEFAULT NULL, userUuid BINARY(16) DEFAULT NULL, UNIQUE INDEX UNIQ_73256912D73087E9 (userUuid), PRIMARY KEY(uuid)) DEFAULT CHARACTER SET utf8mb4');
$this->addSql('CREATE TABLE user_detail (uuid BINARY(16) NOT NULL, firstName VARCHAR(191) DEFAULT NULL, lastName VARCHAR(191) DEFAULT NULL, email VARCHAR(191) NOT NULL, created DATETIME NOT NULL, updated DATETIME DEFAULT NULL, userUuid BINARY(16) DEFAULT NULL, UNIQUE INDEX UNIQ_4B5464AED73087E9 (userUuid), PRIMARY KEY(uuid)) DEFAULT CHARACTER SET utf8mb4');
Expand Down
22 changes: 2 additions & 20 deletions src/User/src/Entity/User.php
Original file line number Diff line number Diff line change
Expand Up @@ -51,9 +51,6 @@ class User extends AbstractEntity implements UserEntityInterface
#[ORM\Column(type: 'user_status_enum', options: ['default' => UserStatusEnum::Pending])]
protected UserStatusEnum $status = UserStatusEnum::Pending;

#[ORM\Column(name: "isDeleted", type: "boolean")]
protected bool $isDeleted = false;

#[ORM\Column(name: "hash", type: "string", length: 64, unique: true)]
protected string $hash;

Expand Down Expand Up @@ -103,18 +100,6 @@ public function setStatus(UserStatusEnum $status): self
return $this;
}

public function isDeleted(): bool
{
return $this->isDeleted;
}

public function setIsDeleted(bool $isDeleted): self
{
$this->isDeleted = $isDeleted;

return $this;
}

public function getHash(): string
{
return $this->hash;
Expand Down Expand Up @@ -273,11 +258,9 @@ public function isPending(): bool
return $this->status === UserStatusEnum::Pending;
}

public function markAsDeleted(): self
public function isDeleted(): bool
{
$this->isDeleted = true;

return $this;
return $this->status === UserStatusEnum::Deleted;
}

public function renewHash(): self
Expand Down Expand Up @@ -311,7 +294,6 @@ public function getArrayCopy(): array
'hash' => $this->getHash(),
'identity' => $this->getIdentity(),
'status' => $this->getStatus(),
'isDeleted' => $this->isDeleted(),
'avatar' => $this->getAvatar()?->getArrayCopy(),
'detail' => $this->getDetail()->getArrayCopy(),
'roles' => $this->getRoles()->map(function (UserRole $userRole) {
Expand Down
1 change: 1 addition & 0 deletions src/User/src/Enum/UserStatusEnum.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,5 @@ enum UserStatusEnum: string
{
case Active = 'active';
case Pending = 'pending';
case Deleted = 'deleted';
}
1 change: 0 additions & 1 deletion src/User/src/OpenAPI.php
Original file line number Diff line number Diff line change
Expand Up @@ -1067,7 +1067,6 @@
new OA\Property(property: 'hash', type: 'string'),
new OA\Property(property: 'identity', type: 'string'),
new OA\Property(property: 'status', type: 'string', example: UserStatusEnum::Active),
new OA\Property(property: 'isDeleted', type: 'boolean', example: false),
new OA\Property(property: 'avatar', ref: '#/components/schemas/UserAvatar', nullable: true),
new OA\Property(property: 'detail', ref: '#/components/schemas/UserDetail'),
new OA\Property(
Expand Down
18 changes: 5 additions & 13 deletions src/User/src/Repository/UserRepository.php
Original file line number Diff line number Diff line change
Expand Up @@ -52,17 +52,6 @@ public function getUsers(array $filters = []): UserCollection
$qb->andWhere('user.status = :status')->setParameter('status', $filters['status']);
}

if (isset($filters['deleted'])) {
switch ($filters['deleted']) {
case 'true':
$qb->andWhere('user.isDeleted = :isDeleted')->setParameter('isDeleted', true);
break;
case 'false':
$qb->andWhere('user.isDeleted = :isDeleted')->setParameter('isDeleted', false);
break;
}
}

if (! empty($filters['search'])) {
$qb->andWhere(
$qb->expr()->orX(
Expand All @@ -78,6 +67,8 @@ public function getUsers(array $filters = []): UserCollection
$qb->andWhere('roles.name = :role')->setParameter('role', $filters['role']);
}

//ignore deleted users
$qb->andWhere('user.status != :status')->setParameter('status', UserStatusEnum::Deleted);
$qb->getQuery()->useQueryCache(true);

return new UserCollection($qb, false);
Expand Down Expand Up @@ -115,8 +106,9 @@ public function getUserEntityByUserCredentials(
$qb->select(['u.password', 'u.status'])
->from(User::class, 'u')
->andWhere('u.identity = :identity')
->andWhere('u.isDeleted = 0')
->setParameter('identity', $username);
->andWhere('u.status != :status')
->setParameter('identity', $username)
->setParameter('status', UserStatusEnum::Deleted);
break;
default:
throw new OAuthServerException(Message::INVALID_CLIENT_ID, 6, 'invalid_client', 401);
Expand Down
10 changes: 3 additions & 7 deletions src/User/src/Service/UserService.php
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,7 @@ public function deleteUser(User $user): User
{
$this->revokeTokens($user);

return $this->anonymizeUser($user->markAsDeleted());
return $this->anonymizeUser($user->setStatus(UserStatusEnum::Deleted));
}

/**
Expand Down Expand Up @@ -198,7 +198,7 @@ public function findResetPasswordByHash(?string $hash): UserResetPassword
public function findByEmail(string $email): User
{
$user = $this->userDetailRepository->findOneBy(['email' => $email])?->getUser();
if (! $user instanceof User) {
if (! $user instanceof User || $user->isDeleted()) {
throw new NotFoundException(Message::USER_NOT_FOUND);
}

Expand All @@ -219,7 +219,7 @@ public function findByIdentity(string $identity): ?User
public function findOneBy(array $params = []): User
{
$user = $this->userRepository->findOneBy($params);
if (! $user instanceof User) {
if (! $user instanceof User || $user->isDeleted()) {
throw new NotFoundException(Message::USER_NOT_FOUND);
}

Expand Down Expand Up @@ -370,10 +370,6 @@ public function updateUser(User $user, array $data = []): User
$user->setStatus($data['status']);
}

if (isset($data['isDeleted'])) {
$user->setIsDeleted($data['isDeleted']);
}

if (isset($data['hash'])) {
$user->setHash($data['hash']);
}
Expand Down
2 changes: 0 additions & 2 deletions test/Functional/AdminTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -401,15 +401,13 @@ public function testAdminCanCreateUserAccount(): void
$this->assertArrayHasKey('hash', $data);
$this->assertArrayHasKey('identity', $data);
$this->assertArrayHasKey('status', $data);
$this->assertArrayHasKey('isDeleted', $data);
$this->assertArrayHasKey('avatar', $data);
$this->assertArrayHasKey('detail', $data);
$this->assertArrayHasKey('roles', $data);
$this->assertNotEmpty($data['uuid']);
$this->assertNotEmpty($data['hash']);
$this->assertSame($userData['identity'], $data['identity']);
$this->assertSame(UserStatusEnum::Pending->value, $data['status']);
$this->assertFalse($data['isDeleted']);
$this->assertEmpty($data['avatar']);
$this->assertEmpty($data['resetPasswords']);
$this->assertArrayHasKey('firstName', $data['detail']);
Expand Down
1 change: 0 additions & 1 deletion test/Functional/UserTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,6 @@ public function testRegisterAccount(): void

$this->assertSame($user['identity'], $data['identity']);
$this->assertSame(UserStatusEnum::Pending->value, $data['status']);
$this->assertFalse($data['isDeleted']);
$this->assertArrayHasKey('detail', $data);
$this->assertArrayHasKey('email', $data['detail']);
$this->assertArrayHasKey('firstName', $data['detail']);
Expand Down
3 changes: 2 additions & 1 deletion test/Unit/App/Middleware/AuthorizationMiddlewareTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
use Api\App\UserIdentity;
use Api\User\Entity\User;
use Api\User\Entity\UserRole;
use Api\User\Enum\UserStatusEnum;
use Api\User\Repository\UserRepository;
use Fig\Http\Message\StatusCodeInterface;
use Laminas\Diactoros\ServerRequest;
Expand Down Expand Up @@ -108,7 +109,7 @@ public function testAuthorizationInactiveUser(): void

public function testAuthorizationUserNotFoundOrDeleted(): void
{
$user = (new User())->markAsDeleted();
$user = (new User())->setStatus(UserStatusEnum::Deleted);
$this->userRepository->method('findOneBy')->willReturn($user);
$this->authorization->method('isGranted')->willReturn(false);

Expand Down
1 change: 0 additions & 1 deletion test/Unit/User/Service/UserServiceTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,6 @@ public function testCreateUser(): void
$this->assertSame($data['detail']['lastName'], $user->getDetail()->getLastName());
$this->assertSame($data['detail']['email'], $user->getDetail()->getEmail());
$this->assertSame(UserStatusEnum::Pending, $user->getStatus());
$this->assertFalse($user->isDeleted());
$this->assertFalse($user->isActive());
}

Expand Down
Loading