8000 feat(security): add JWT login, roles and security routes · sjunior-dev/symfony-api-test@e44cda4 · GitHub
[go: up one dir, main page]

Skip to content 8000

Commit e44cda4

Browse files
committed
feat(security): add JWT login, roles and security routes
1 parent 1b47729 commit e44cda4

File tree

10 files changed

+358
-17
lines changed

10 files changed

+358
-17
lines changed

.gitignore

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,3 +88,7 @@ yarn-error.log
8888
.idea/
8989
**/yarn-cache
9090
**.php-cs-fixer.cache
91+
92+
###> lexik/jwt-authentication-bundle ###
93+
/config/jwt/*.pem
94+
###< lexik/jwt-authentication-bundle ###

composer.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
"ext-ctype": "*",
99
"ext-iconv": "*",
1010
"doctrine/doctrine-migrations-bundle": "^3.3",
11+
"lexik/jwt-authentication-bundle": "^3.0",
1112
"phpdocumentor/reflection-docblock": "^5.4",
1213
"phpstan/phpdoc-parser": "^1.29",
1314
"symfony/console": "7.0.*",

composer.lock

Lines changed: 253 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

config/bundles.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,4 +11,5 @@
1111
Zenstruck\Foundry\ZenstruckFoundryBundle::class => ['dev' => true, 'test' => true],
1212
Doctrine\Bundle\MigrationsBundle\DoctrineMigrationsBundle::class => ['all' => true],
1313
Symfony\Bundle\SecurityBundle\SecurityBundle::class => ['all' => true],
14+
Lexik\Bundle\JWTAuthenticationBundle\LexikJWTAuthenticationBundle::class => ['all' => true],
1415
];
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
lexik_jwt_authentication:
2+
secret_key: '%env(resolve:JWT_SECRET_KEY)%'
3+
public_key: '%env(resolve:JWT_PUBLIC_KEY)%'
4+
pass_phrase: '%env(JWT_PASSPHRASE)%'
5+
token_ttl: 3600
6+
7+
when@dev:
8+
lexik_jwt_authentication:
9+
token_ttl: 43200 # 12h

config/packages/security.yaml

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,22 @@ security:
99
entity:
1010
class: App\Entity\User
1111
property: email
12+
1213
firewalls:
14+
login:
15+
pattern: ^/api/login
16+
stateless: true
17+
json_login:
18+
check_path: /api/login_check
19+
username_path: email
20+
success_handler: lexik_jwt_authentication.handler.authentication_success
21+
failure_handler: lexik_jwt_authentication.handler.authentication_failure
22+
23+
api:
24+
pattern: ^/api
25+
stateless: true
26+
jwt: ~
27+
1328
dev:
1429
pattern: ^/(_(profiler|wdt)|css|images|js)/
1530
security: false
@@ -26,8 +41,13 @@ security:
2641
# Easy way to control access for large sections of your site
2742
# Note: Only the *first* access control that matches will be used
2843
access_control:
29-
# - { path: ^/admin, roles: ROLE_ADMIN }
44+
- { path: ^/api/admin/v1, roles: ROLE_ADMIN }
45+
- { path: ^/api/login, roles: PUBLIC_ACCESS }
46+
- { path: ^/api, roles: IS_AUTHENTICATED_FULLY }
47+
3048
# - { path: ^/profile, roles: ROLE_USER }
49+
role_hierarchy:
50+
ROLE_ADMIN: ROLE_USER
3151

3252
when@test:
3353
security:

config/routes.yaml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,6 @@ controllers:
33
path: ../src/Controller/
44
namespace: App\Controller
55
type: attribute
6+
7+
api_login_check:
8+
path: /api/login_check
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
<?php
2+
3+
namespace App\Controller;
4+
5+
use App\Entity\User;
6+
use App\Service\UserService;
7+
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
8+
use Symfony\Component\HttpFoundation\JsonResponse;
9+
use Symfony\Component\HttpFoundation\Request;
10+
use Symfony\Component\HttpFoundation\Response;
11+
use Symfony\Component\Routing\Attribute\Route;
12+
13+
#[Route('/api/admin/v1', name: 'api_admin_v1_', format: 'json')]
14+
class UserAdminController extends AbstractController
15+
{
16+
public function __construct(
17+
public readonly UserService $userService
18+
) {
19+
}
20+
21+
#[Route('/user', name: 'user_create', methods: ['POST'])]
22+
public function create(Request $request): JsonResponse
23+
{
24+
$user = $this->userService->store($request);
25+
26+
return $this->json([
27+
'data' => $user,
28+
], Response::HTTP_CREATED);
29+
}
30+
31+
#[Route('/{reference}/user', name: 'user_view', methods: ['GET'])]
32+
public function view(User $user): Response
33+
{
34+
return $this->json([
35+
'data' => $user,
36+
]);
37+
}
38+
39+
#[Route('/{reference}/user', name: 'user_update', methods: ['PUT'])]
40+
public function update(User $user, Request $request): Response
41+
{
42+
$user = $this->userService->store($request, $user);
43+
44+
return $this->json([
45+
'data' => $user,
46+
]);
47+
}
48+
}

0 commit comments

Comments
 (0)
0