diff --git a/.env b/.env index acb7a76..fb98156 100644 --- a/.env +++ b/.env @@ -31,9 +31,3 @@ APP_SECRET= ###> nelmio/cors-bundle ### CORS_ALLOW_ORIGIN='^https?://(localhost|127\.0\.0\.1)(:[0-9]+)?$' ###< nelmio/cors-bundle ### - -###> lexik/jwt-authentication-bundle ### -JWT_SECRET_KEY=%kernel.project_dir%/config/jwt/private.pem -JWT_PUBLIC_KEY=%kernel.project_dir%/config/jwt/public.pem -JWT_PASSPHRASE= -###< lexik/jwt-authentication-bundle ### diff --git a/composer.json b/composer.json index 649c736..c59530e 100644 --- a/composer.json +++ b/composer.json @@ -12,6 +12,8 @@ "doctrine/doctrine-bundle": "^2.7", "doctrine/doctrine-migrations-bundle": "^3.2", "doctrine/orm": "^2.13", + "easycorp/easyadmin-bundle": "^4.5", + "friendsofsymfony/rest-bundle": "^3.4", "gesdinet/jwt-refresh-token-bundle": "^1.1", "lexik/jwt-authentication-bundle": "^2.16", "nelmio/cors-bundle": "^2.2", @@ -23,6 +25,7 @@ "symfony/expression-language": "6.1.*", "symfony/flex": "^2", "symfony/framework-bundle": "6.1.*", + "symfony/http-client": "6.1.*", "symfony/monolog-bundle": "^3.8", "symfony/property-access": "6.1.*", "symfony/property-info": "6.1.*", @@ -31,6 +34,7 @@ "symfony/security-bundle": "6.1.*", "symfony/serializer": "6.1.*", "symfony/string": "6.1.*", + "symfony/translation": "6.1.*", "symfony/twig-bundle": "6.1.*", "symfony/validator": "6.1.*", "symfony/yaml": "6.1.*", diff --git a/composer.lock b/composer.lock index 098f4ef..159874e 100644 --- a/composer.lock +++ b/composer.lock @@ -4,7 +4,7 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "984adecf9340acbd23f44d6b93a14c8e", + "content-hash": "f6247629338a762db6d91613154d8e15", "packages": [ { "name": "api-platform/core", @@ -1536,6 +1536,99 @@ }, "time": "2022-05-23T21:33:49+00:00" }, + { + "name": "easycorp/easyadmin-bundle", + "version": "v4.5.1", + "source": { + "type": "git", + "url": "https://github.com/EasyCorp/EasyAdminBundle.git", + "reference": "9c00e8128b99000e8e400315abe740f864d3e6e4" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/EasyCorp/EasyAdminBundle/zipball/9c00e8128b99000e8e400315abe740f864d3e6e4", + "reference": "9c00e8128b99000e8e400315abe740f864d3e6e4", + "shasum": "" + }, + "require": { + "doctrine/doctrine-bundle": "^2.5", + "doctrine/orm": "^2.10", + "ext-json": "*", + "php": ">=8.0.2", + "symfony/asset": "^5.4|^6.0", + "symfony/cache": "^5.4|^6.0", + "symfony/config": "^5.4|^6.0", + "symfony/dependency-injection": "^5.4|^6.0", + "symfony/deprecation-contracts": "^3.0", + "symfony/doctrine-bridge": "^5.4|^6.0", + "symfony/event-dispatcher": "^5.4|^6.0", + "symfony/filesystem": "^5.4|^6.0", + "symfony/form": "^5.4|^6.0", + "symfony/framework-bundle": "^5.4|^6.0", + "symfony/http-foundation": "^5.4|^6.0", + "symfony/http-kernel": "^5.4|^6.0", + "symfony/intl": "^5.4|^6.0", + "symfony/property-access": "^5.4|^6.0", + "symfony/security-bundle": "^5.4|^6.0", + "symfony/string": "^5.4|^6.0", + "symfony/translation": "^5.4|^6.0", + "symfony/twig-bundle": "^5.4|^6.0", + "symfony/uid": "^5.4|^6.0", + "symfony/validator": "^5.4|^6.0" + }, + "require-dev": { + "doctrine/doctrine-fixtures-bundle": "^3.4", + "phpstan/extension-installer": "^1.2", + "phpstan/phpstan": "^1.9", + "phpstan/phpstan-phpunit": "^1.2", + "phpstan/phpstan-strict-rules": "^1.4", + "phpstan/phpstan-symfony": "^1.2", + "psr/log": "^1.0", + "symfony/browser-kit": "^5.4|^6.0", + "symfony/css-selector": "^5.4|^6.0", + "symfony/dom-crawler": "^5.4|^6.0", + "symfony/phpunit-bridge": "^5.4|^6.0" + }, + "type": "symfony-bundle", + "extra": { + "branch-alias": { + "dev-master": "4.0.x-dev" + } + }, + "autoload": { + "psr-4": { + "EasyCorp\\Bundle\\EasyAdminBundle\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Project Contributors", + "homepage": "https://github.com/EasyCorp/EasyAdminBundle/graphs/contributors" + } + ], + "description": "Admin generator for Symfony applications", + "homepage": "https://github.com/EasyCorp/EasyAdminBundle", + "keywords": [ + "admin", + "backend", + "generator" + ], + "support": { + "issues": "https://github.com/EasyCorp/EasyAdminBundle/issues", + "source": "https://github.com/EasyCorp/EasyAdminBundle/tree/v4.5.1" + }, + "funding": [ + { + "url": "https://github.com/javiereguiluz", + "type": "github" + } + ], + "time": "2023-01-19T19:18:11+00:00" + }, { "name": "fig/link-util", "version": "1.2.0", @@ -1679,6 +1772,112 @@ ], "time": "2022-05-05T09:31:05+00:00" }, + { + "name": "friendsofsymfony/rest-bundle", + "version": "3.4.0", + "source": { + "type": "git", + "url": "https://github.com/FriendsOfSymfony/FOSRestBundle.git", + "reference": "b888195589d245002880d07073ef23ab60e3795d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/FriendsOfSymfony/FOSRestBundle/zipball/b888195589d245002880d07073ef23ab60e3795d", + "reference": "b888195589d245002880d07073ef23ab60e3795d", + "shasum": "" + }, + "require": { + "php": "^7.2|^8.0", + "symfony/config": "^4.4|^5.3|^6.0", + "symfony/dependency-injection": "^4.4|^5.3|^6.0", + "symfony/event-dispatcher": "^4.4|^5.3|^6.0", + "symfony/framework-bundle": "^4.4.1|^5.0|^6.0", + "symfony/http-foundation": "^4.4|^5.3|^6.0", + "symfony/http-kernel": "^4.4|^5.3|^6.0", + "symfony/routing": "^4.4|^5.3|^6.0", + "symfony/security-core": "^4.4|^5.3|^6.0", + "willdurand/jsonp-callback-validator": "^1.0|^2.0", + "willdurand/negotiation": "^2.0|^3.0" + }, + "conflict": { + "doctrine/annotations": "<1.12", + "jms/serializer": "<1.13.0", + "jms/serializer-bundle": "<2.4.3|3.0.0", + "sensio/framework-extra-bundle": "<6.1", + "symfony/error-handler": "<4.4.1" + }, + "require-dev": { + "doctrine/annotations": "^1.13.2", + "friendsofphp/php-cs-fixer": "^3.0", + "jms/serializer": "^1.13|^2.0|^3.0", + "jms/serializer-bundle": "^2.4.3|^3.0.1|^4.0|^5.0@beta", + "psr/http-message": "^1.0", + "psr/log": "^1.0|^2.0|^3.0", + "sensio/framework-extra-bundle": "^6.1", + "symfony/asset": "^4.4|^5.3|^6.0", + "symfony/browser-kit": "^4.4|^5.3|^6.0", + "symfony/css-selector": "^4.4|^5.3|^6.0", + "symfony/expression-language": "^4.4|^5.3|^6.0", + "symfony/form": "^4.4|^5.3|^6.0", + "symfony/mime": "^4.4|^5.3|^6.0", + "symfony/phpunit-bridge": "^5.3|^6.0", + "symfony/security-bundle": "^4.4|^5.3|^6.0", + "symfony/serializer": "^4.4|^5.3|^6.0", + "symfony/twig-bundle": "^4.4|^5.3|^6.0", + "symfony/validator": "^4.4|^5.3|^6.0", + "symfony/web-profiler-bundle": "^4.4|^5.3|^6.0", + "symfony/yaml": "^4.4|^5.3|^6.0" + }, + "suggest": { + "jms/serializer-bundle": "Add support for advanced serialization capabilities, recommended, requires ^2.0|^3.0", + "sensio/framework-extra-bundle": "Add support for the request body converter and the view response listener, requires ^3.0", + "symfony/serializer": "Add support for basic serialization capabilities and xml decoding, requires ^2.7|^3.0", + "symfony/validator": "Add support for validation capabilities in the ParamFetcher, requires ^2.7|^3.0" + }, + "type": "symfony-bundle", + "extra": { + "branch-alias": { + "3.x-dev": "3.1-dev" + } + }, + "autoload": { + "psr-4": { + "FOS\\RestBundle\\": "" + }, + "exclude-from-classmap": [ + "Resources/", + "Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Lukas Kahwe Smith", + "email": "smith@pooteeweet.org" + }, + { + "name": "Konstantin Kudryashov", + "email": "ever.zet@gmail.com" + }, + { + "name": "FriendsOfSymfony Community", + "homepage": "https://github.com/friendsofsymfony/FOSRestBundle/contributors" + } + ], + "description": "This Bundle provides various tools to rapidly develop RESTful API's with Symfony", + "homepage": "http://friendsofsymfony.github.com", + "keywords": [ + "rest" + ], + "support": { + "issues": "https://github.com/FriendsOfSymfony/FOSRestBundle/issues", + "source": "https://github.com/FriendsOfSymfony/FOSRestBundle/tree/3.4.0" + }, + "time": "2022-09-18T04:54:54+00:00" + }, { "name": "gesdinet/jwt-refresh-token-bundle", "version": "v1.1.1", @@ -4129,6 +4328,108 @@ ], "time": "2022-08-07T09:39:47+00:00" }, + { + "name": "symfony/form", + "version": "v6.1.11", + "source": { + "type": "git", + "url": "https://github.com/symfony/form.git", + "reference": "b137b4acac416062d50d5f2c6d524ee5185ef2a0" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/form/zipball/b137b4acac416062d50d5f2c6d524ee5185ef2a0", + "reference": "b137b4acac416062d50d5f2c6d524ee5185ef2a0", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "symfony/deprecation-contracts": "^2.1|^3", + "symfony/event-dispatcher": "^5.4|^6.0", + "symfony/options-resolver": "^5.4|^6.0", + "symfony/polyfill-ctype": "~1.8", + "symfony/polyfill-intl-icu": "^1.21", + "symfony/polyfill-mbstring": "~1.0", + "symfony/property-access": "^5.4|^6.0", + "symfony/service-contracts": "^1.1|^2|^3" + }, + "conflict": { + "phpunit/phpunit": "<5.4.3", + "symfony/console": "<5.4", + "symfony/dependency-injection": "<5.4", + "symfony/doctrine-bridge": "<5.4", + "symfony/error-handler": "<5.4", + "symfony/framework-bundle": "<5.4", + "symfony/http-kernel": "<5.4", + "symfony/translation": "<5.4", + "symfony/translation-contracts": "<1.1.7", + "symfony/twig-bridge": "<5.4" + }, + "require-dev": { + "doctrine/collections": "^1.0|^2.0", + "symfony/config": "^5.4|^6.0", + "symfony/console": "^5.4|^6.0", + "symfony/dependency-injection": "^5.4|^6.0", + "symfony/expression-language": "^5.4|^6.0", + "symfony/html-sanitizer": "^6.1", + "symfony/http-foundation": "^5.4|^6.0", + "symfony/http-kernel": "^5.4|^6.0", + "symfony/intl": "^5.4|^6.0", + "symfony/security-csrf": "^5.4|^6.0", + "symfony/translation": "^5.4|^6.0", + "symfony/uid": "^5.4|^6.0", + "symfony/validator": "^5.4|^6.0", + "symfony/var-dumper": "^5.4|^6.0" + }, + "suggest": { + "symfony/security-csrf": "For protecting forms against CSRF attacks.", + "symfony/twig-bridge": "For templating with Twig.", + "symfony/validator": "For form validation." + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Form\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Allows to easily create, process and reuse HTML forms", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/form/tree/v6.1.11" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2023-01-01T08:36:55+00:00" + }, { "name": "symfony/framework-bundle", "version": "v6.1.3", @@ -4281,37 +4582,49 @@ "time": "2022-07-29T06:42:38+00:00" }, { - "name": "symfony/http-foundation", - "version": "v6.1.3", + "name": "symfony/http-client", + "version": "v6.1.7", "source": { "type": "git", - "url": "https://github.com/symfony/http-foundation.git", - "reference": "b03712c93759a81fc243ecc18ec4637958afebdb" + "url": "https://github.com/symfony/http-client.git", + "reference": "f515d066728774efb34347a87580621416ca8968" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/http-foundation/zipball/b03712c93759a81fc243ecc18ec4637958afebdb", - "reference": "b03712c93759a81fc243ecc18ec4637958afebdb", + "url": "https://api.github.com/repos/symfony/http-client/zipball/f515d066728774efb34347a87580621416ca8968", + "reference": "f515d066728774efb34347a87580621416ca8968", "shasum": "" }, "require": { "php": ">=8.1", - "symfony/deprecation-contracts": "^2.1|^3", - "symfony/polyfill-mbstring": "~1.1" + "psr/log": "^1|^2|^3", + "symfony/http-client-contracts": "^3", + "symfony/service-contracts": "^1.0|^2|^3" }, - "require-dev": { - "predis/predis": "~1.0", - "symfony/cache": "^5.4|^6.0", - "symfony/expression-language": "^5.4|^6.0", - "symfony/mime": "^5.4|^6.0" + "provide": { + "php-http/async-client-implementation": "*", + "php-http/client-implementation": "*", + "psr/http-client-implementation": "1.0", + "symfony/http-client-implementation": "3.0" }, - "suggest": { - "symfony/mime": "To use the file extension guesser" + "require-dev": { + "amphp/amp": "^2.5", + "amphp/http-client": "^4.2.1", + "amphp/http-tunnel": "^1.0", + "amphp/socket": "^1.1", + "guzzlehttp/promises": "^1.4", + "nyholm/psr7": "^1.0", + "php-http/httplug": "^1.0|^2.0", + "psr/http-client": "^1.0", + "symfony/dependency-injection": "^5.4|^6.0", + "symfony/http-kernel": "^5.4|^6.0", + "symfony/process": "^5.4|^6.0", + "symfony/stopwatch": "^5.4|^6.0" }, "type": "library", "autoload": { "psr-4": { - "Symfony\\Component\\HttpFoundation\\": "" + "Symfony\\Component\\HttpClient\\": "" }, "exclude-from-classmap": [ "/Tests/" @@ -4323,18 +4636,18 @@ ], "authors": [ { - "name": "Fabien Potencier", - "email": "fabien@symfony.com" + "name": "Nicolas Grekas", + "email": "p@tchwork.com" }, { "name": "Symfony Community", "homepage": "https://symfony.com/contributors" } ], - "description": "Defines an object-oriented layer for the HTTP specification", + "description": "Provides powerful methods to fetch HTTP resources synchronously or asynchronously", "homepage": "https://symfony.com", "support": { - "source": "https://github.com/symfony/http-foundation/tree/v6.1.3" + "source": "https://github.com/symfony/http-client/tree/v6.1.7" }, "funding": [ { @@ -4350,40 +4663,193 @@ "type": "tidelift" } ], - "time": "2022-07-27T15:50:51+00:00" + "time": "2022-10-28T16:23:08+00:00" }, { - "name": "symfony/http-kernel", - "version": "v6.1.3", + "name": "symfony/http-client-contracts", + "version": "v3.1.1", "source": { "type": "git", - "url": "https://github.com/symfony/http-kernel.git", - "reference": "0692bc185a1dbb54864686a1fc6785667279da70" + "url": "https://github.com/symfony/http-client-contracts.git", + "reference": "fd038f08c623ab5d22b26e9ba35afe8c79071800" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/http-kernel/zipball/0692bc185a1dbb54864686a1fc6785667279da70", - "reference": "0692bc185a1dbb54864686a1fc6785667279da70", + "url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/fd038f08c623ab5d22b26e9ba35afe8c79071800", + "reference": "fd038f08c623ab5d22b26e9ba35afe8c79071800", "shasum": "" }, "require": { - "php": ">=8.1", - "psr/log": "^1|^2|^3", - "symfony/error-handler": "^6.1", - "symfony/event-dispatcher": "^5.4|^6.0", - "symfony/http-foundation": "^5.4|^6.0", - "symfony/polyfill-ctype": "^1.8" + "php": ">=8.1" }, - "conflict": { - "symfony/browser-kit": "<5.4", - "symfony/cache": "<5.4", - "symfony/config": "<6.1", - "symfony/console": "<5.4", - "symfony/dependency-injection": "<6.1", - "symfony/doctrine-bridge": "<5.4", - "symfony/form": "<5.4", - "symfony/http-client": "<5.4", - "symfony/mailer": "<5.4", + "suggest": { + "symfony/http-client-implementation": "" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "3.1-dev" + }, + "thanks": { + "name": "symfony/contracts", + "url": "https://github.com/symfony/contracts" + } + }, + "autoload": { + "psr-4": { + "Symfony\\Contracts\\HttpClient\\": "" + }, + "exclude-from-classmap": [ + "/Test/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Generic abstractions related to HTTP clients", + "homepage": "https://symfony.com", + "keywords": [ + "abstractions", + "contracts", + "decoupling", + "interfaces", + "interoperability", + "standards" + ], + "support": { + "source": "https://github.com/symfony/http-client-contracts/tree/v3.1.1" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2022-04-22T07:30:54+00:00" + }, + { + "name": "symfony/http-foundation", + "version": "v6.1.3", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-foundation.git", + "reference": "b03712c93759a81fc243ecc18ec4637958afebdb" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-foundation/zipball/b03712c93759a81fc243ecc18ec4637958afebdb", + "reference": "b03712c93759a81fc243ecc18ec4637958afebdb", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "symfony/deprecation-contracts": "^2.1|^3", + "symfony/polyfill-mbstring": "~1.1" + }, + "require-dev": { + "predis/predis": "~1.0", + "symfony/cache": "^5.4|^6.0", + "symfony/expression-language": "^5.4|^6.0", + "symfony/mime": "^5.4|^6.0" + }, + "suggest": { + "symfony/mime": "To use the file extension guesser" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\HttpFoundation\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Defines an object-oriented layer for the HTTP specification", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/http-foundation/tree/v6.1.3" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2022-07-27T15:50:51+00:00" + }, + { + "name": "symfony/http-kernel", + "version": "v6.1.3", + "source": { + "type": "git", + "url": "https://github.com/symfony/http-kernel.git", + "reference": "0692bc185a1dbb54864686a1fc6785667279da70" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/http-kernel/zipball/0692bc185a1dbb54864686a1fc6785667279da70", + "reference": "0692bc185a1dbb54864686a1fc6785667279da70", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "psr/log": "^1|^2|^3", + "symfony/error-handler": "^6.1", + "symfony/event-dispatcher": "^5.4|^6.0", + "symfony/http-foundation": "^5.4|^6.0", + "symfony/polyfill-ctype": "^1.8" + }, + "conflict": { + "symfony/browser-kit": "<5.4", + "symfony/cache": "<5.4", + "symfony/config": "<6.1", + "symfony/console": "<5.4", + "symfony/dependency-injection": "<6.1", + "symfony/doctrine-bridge": "<5.4", + "symfony/form": "<5.4", + "symfony/http-client": "<5.4", + "symfony/mailer": "<5.4", "symfony/messenger": "<5.4", "symfony/translation": "<5.4", "symfony/twig-bridge": "<5.4", @@ -4462,6 +4928,86 @@ ], "time": "2022-07-29T12:59:10+00:00" }, + { + "name": "symfony/intl", + "version": "v6.1.11", + "source": { + "type": "git", + "url": "https://github.com/symfony/intl.git", + "reference": "776bfc0379adcb11ece25aa2aa7ddf87a22533c1" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/intl/zipball/776bfc0379adcb11ece25aa2aa7ddf87a22533c1", + "reference": "776bfc0379adcb11ece25aa2aa7ddf87a22533c1", + "shasum": "" + }, + "require": { + "php": ">=8.1" + }, + "require-dev": { + "symfony/filesystem": "^5.4|^6.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Intl\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Bernhard Schussek", + "email": "bschussek@gmail.com" + }, + { + "name": "Eriksen Costa", + "email": "eriksen.costa@infranology.com.br" + }, + { + "name": "Igor Wiedler", + "email": "igor@wiedler.ch" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides a PHP replacement layer for the C intl extension that includes additional data from the ICU library", + "homepage": "https://symfony.com", + "keywords": [ + "i18n", + "icu", + "internationalization", + "intl", + "l10n", + "localization" + ], + "support": { + "source": "https://github.com/symfony/intl/tree/v6.1.11" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2023-01-01T08:36:55+00:00" + }, { "name": "symfony/mime", "version": "v6.1.4", @@ -4707,6 +5253,73 @@ ], "time": "2022-05-10T14:24:36+00:00" }, + { + "name": "symfony/options-resolver", + "version": "v6.1.11", + "source": { + "type": "git", + "url": "https://github.com/symfony/options-resolver.git", + "reference": "ae355b19e11d9eb1f757fa072a3886429946b6f6" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/options-resolver/zipball/ae355b19e11d9eb1f757fa072a3886429946b6f6", + "reference": "ae355b19e11d9eb1f757fa072a3886429946b6f6", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "symfony/deprecation-contracts": "^2.1|^3" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\OptionsResolver\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides an improved replacement for the array_replace PHP function", + "homepage": "https://symfony.com", + "keywords": [ + "config", + "configuration", + "options" + ], + "support": { + "source": "https://github.com/symfony/options-resolver/tree/v6.1.11" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2023-01-01T08:36:55+00:00" + }, { "name": "symfony/password-hasher", "version": "v6.1.3", @@ -4780,29 +5393,110 @@ "time": "2022-07-20T14:45:06+00:00" }, { - "name": "symfony/polyfill-intl-grapheme", - "version": "v1.26.0", + "name": "symfony/polyfill-intl-grapheme", + "version": "v1.26.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-intl-grapheme.git", + "reference": "433d05519ce6990bf3530fba6957499d327395c2" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/433d05519ce6990bf3530fba6957499d327395c2", + "reference": "433d05519ce6990bf3530fba6957499d327395c2", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "suggest": { + "ext-intl": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.26-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "files": [ + "bootstrap.php" + ], + "psr-4": { + "Symfony\\Polyfill\\Intl\\Grapheme\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for intl's grapheme_* functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "grapheme", + "intl", + "polyfill", + "portable", + "shim" + ], + "support": { + "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.26.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2022-05-24T11:49:31+00:00" + }, + { + "name": "symfony/polyfill-intl-icu", + "version": "v1.27.0", "source": { "type": "git", - "url": "https://github.com/symfony/polyfill-intl-grapheme.git", - "reference": "433d05519ce6990bf3530fba6957499d327395c2" + "url": "https://github.com/symfony/polyfill-intl-icu.git", + "reference": "a3d9148e2c363588e05abbdd4ee4f971f0a5330c" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/433d05519ce6990bf3530fba6957499d327395c2", - "reference": "433d05519ce6990bf3530fba6957499d327395c2", + "url": "https://api.github.com/repos/symfony/polyfill-intl-icu/zipball/a3d9148e2c363588e05abbdd4ee4f971f0a5330c", + "reference": "a3d9148e2c363588e05abbdd4ee4f971f0a5330c", "shasum": "" }, "require": { "php": ">=7.1" }, "suggest": { - "ext-intl": "For best performance" + "ext-intl": "For best performance and support of other locales than \"en\"" }, "type": "library", "extra": { "branch-alias": { - "dev-main": "1.26-dev" + "dev-main": "1.27-dev" }, "thanks": { "name": "symfony/polyfill", @@ -4814,8 +5508,14 @@ "bootstrap.php" ], "psr-4": { - "Symfony\\Polyfill\\Intl\\Grapheme\\": "" - } + "Symfony\\Polyfill\\Intl\\Icu\\": "" + }, + "classmap": [ + "Resources/stubs" + ], + "exclude-from-classmap": [ + "/Tests/" + ] }, "notification-url": "https://packagist.org/downloads/", "license": [ @@ -4831,18 +5531,18 @@ "homepage": "https://symfony.com/contributors" } ], - "description": "Symfony polyfill for intl's grapheme_* functions", + "description": "Symfony polyfill for intl's ICU-related data and classes", "homepage": "https://symfony.com", "keywords": [ "compatibility", - "grapheme", + "icu", "intl", "polyfill", "portable", "shim" ], "support": { - "source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.26.0" + "source": "https://github.com/symfony/polyfill-intl-icu/tree/v1.27.0" }, "funding": [ { @@ -4858,7 +5558,7 @@ "type": "tidelift" } ], - "time": "2022-05-24T11:49:31+00:00" + "time": "2022-11-03T14:55:06+00:00" }, { "name": "symfony/polyfill-intl-idn", @@ -5182,6 +5882,88 @@ ], "time": "2020-10-23T14:02:19+00:00" }, + { + "name": "symfony/polyfill-uuid", + "version": "v1.27.0", + "source": { + "type": "git", + "url": "https://github.com/symfony/polyfill-uuid.git", + "reference": "f3cf1a645c2734236ed1e2e671e273eeb3586166" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/polyfill-uuid/zipball/f3cf1a645c2734236ed1e2e671e273eeb3586166", + "reference": "f3cf1a645c2734236ed1e2e671e273eeb3586166", + "shasum": "" + }, + "require": { + "php": ">=7.1" + }, + "provide": { + "ext-uuid": "*" + }, + "suggest": { + "ext-uuid": "For best performance" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-main": "1.27-dev" + }, + "thanks": { + "name": "symfony/polyfill", + "url": "https://github.com/symfony/polyfill" + } + }, + "autoload": { + "files": [ + "bootstrap.php" + ], + "psr-4": { + "Symfony\\Polyfill\\Uuid\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Grégoire Pineau", + "email": "lyrixx@lyrixx.info" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Symfony polyfill for uuid functions", + "homepage": "https://symfony.com", + "keywords": [ + "compatibility", + "polyfill", + "portable", + "uuid" + ], + "support": { + "source": "https://github.com/symfony/polyfill-uuid/tree/v1.27.0" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2022-11-03T14:55:06+00:00" + }, { "name": "symfony/property-access", "version": "v6.1.3", @@ -6258,6 +7040,102 @@ ], "time": "2022-07-27T15:50:51+00:00" }, + { + "name": "symfony/translation", + "version": "v6.1.6", + "source": { + "type": "git", + "url": "https://github.com/symfony/translation.git", + "reference": "e6cd330e5a072518f88d65148f3f165541807494" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/translation/zipball/e6cd330e5a072518f88d65148f3f165541807494", + "reference": "e6cd330e5a072518f88d65148f3f165541807494", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "symfony/polyfill-mbstring": "~1.0", + "symfony/translation-contracts": "^2.3|^3.0" + }, + "conflict": { + "symfony/config": "<5.4", + "symfony/console": "<5.4", + "symfony/dependency-injection": "<5.4", + "symfony/http-kernel": "<5.4", + "symfony/twig-bundle": "<5.4", + "symfony/yaml": "<5.4" + }, + "provide": { + "symfony/translation-implementation": "2.3|3.0" + }, + "require-dev": { + "psr/log": "^1|^2|^3", + "symfony/config": "^5.4|^6.0", + "symfony/console": "^5.4|^6.0", + "symfony/dependency-injection": "^5.4|^6.0", + "symfony/finder": "^5.4|^6.0", + "symfony/http-client-contracts": "^1.1|^2.0|^3.0", + "symfony/http-kernel": "^5.4|^6.0", + "symfony/intl": "^5.4|^6.0", + "symfony/polyfill-intl-icu": "^1.21", + "symfony/routing": "^5.4|^6.0", + "symfony/service-contracts": "^1.1.2|^2|^3", + "symfony/yaml": "^5.4|^6.0" + }, + "suggest": { + "psr/log-implementation": "To use logging capability in translator", + "symfony/config": "", + "symfony/yaml": "" + }, + "type": "library", + "autoload": { + "files": [ + "Resources/functions.php" + ], + "psr-4": { + "Symfony\\Component\\Translation\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides tools to internationalize your application", + "homepage": "https://symfony.com", + "support": { + "source": "https://github.com/symfony/translation/tree/v6.1.6" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2022-10-07T08:04:03+00:00" + }, { "name": "symfony/translation-contracts", "version": "v3.1.1", @@ -6547,6 +7425,80 @@ ], "time": "2022-05-27T16:55:36+00:00" }, + { + "name": "symfony/uid", + "version": "v6.1.11", + "source": { + "type": "git", + "url": "https://github.com/symfony/uid.git", + "reference": "7c53913df24517eb5e0fab4caf294e84fcecc277" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/uid/zipball/7c53913df24517eb5e0fab4caf294e84fcecc277", + "reference": "7c53913df24517eb5e0fab4caf294e84fcecc277", + "shasum": "" + }, + "require": { + "php": ">=8.1", + "symfony/polyfill-uuid": "^1.15" + }, + "require-dev": { + "symfony/console": "^5.4|^6.0" + }, + "type": "library", + "autoload": { + "psr-4": { + "Symfony\\Component\\Uid\\": "" + }, + "exclude-from-classmap": [ + "/Tests/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Grégoire Pineau", + "email": "lyrixx@lyrixx.info" + }, + { + "name": "Nicolas Grekas", + "email": "p@tchwork.com" + }, + { + "name": "Symfony Community", + "homepage": "https://symfony.com/contributors" + } + ], + "description": "Provides an object-oriented API to generate and represent UIDs", + "homepage": "https://symfony.com", + "keywords": [ + "UID", + "ulid", + "uuid" + ], + "support": { + "source": "https://github.com/symfony/uid/tree/v6.1.11" + }, + "funding": [ + { + "url": "https://symfony.com/sponsor", + "type": "custom" + }, + { + "url": "https://github.com/fabpot", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/symfony/symfony", + "type": "tidelift" + } + ], + "time": "2023-01-01T08:36:55+00:00" + }, { "name": "symfony/validator", "version": "v6.1.3", @@ -7217,6 +8169,49 @@ }, "time": "2022-06-03T18:03:27+00:00" }, + { + "name": "willdurand/jsonp-callback-validator", + "version": "v2.0.0", + "source": { + "type": "git", + "url": "https://github.com/willdurand/JsonpCallbackValidator.git", + "reference": "738c36e91d4d7e0ff0cac145f77057e0fb88526e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/willdurand/JsonpCallbackValidator/zipball/738c36e91d4d7e0ff0cac145f77057e0fb88526e", + "reference": "738c36e91d4d7e0ff0cac145f77057e0fb88526e", + "shasum": "" + }, + "require": { + "php": ">=7.1.0" + }, + "require-dev": { + "symfony/phpunit-bridge": "^5.0" + }, + "type": "library", + "autoload": { + "psr-0": { + "JsonpCallbackValidator": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "William Durand", + "email": "will+git@drnd.me" + } + ], + "description": "JSONP callback validator.", + "support": { + "issues": "https://github.com/willdurand/JsonpCallbackValidator/issues", + "source": "https://github.com/willdurand/JsonpCallbackValidator/tree/v2.0.0" + }, + "time": "2022-01-30T20:33:09+00:00" + }, { "name": "willdurand/negotiation", "version": "3.1.0", diff --git a/config/bundles.php b/config/bundles.php index 21bfd62..def907b 100644 --- a/config/bundles.php +++ b/config/bundles.php @@ -14,4 +14,5 @@ Symfony\Bundle\WebProfilerBundle\WebProfilerBundle::class => ['dev' => true, 'test' => true], Gesdinet\JWTRefreshTokenBundle\GesdinetJWTRefreshTokenBundle::class => ['all' => true], Vich\UploaderBundle\VichUploaderBundle::class => ['all' => true], + EasyCorp\Bundle\EasyAdminBundle\EasyAdminBundle::class => ['all' => true], ]; diff --git a/config/packages/api_platform.yaml b/config/packages/api_platform.yaml index 37ee9c1..c40ef8f 100644 --- a/config/packages/api_platform.yaml +++ b/config/packages/api_platform.yaml @@ -8,6 +8,4 @@ api_platform: api_keys: apiKey: name: Authorization - type: header - - \ No newline at end of file + type: header \ No newline at end of file diff --git a/config/packages/framework.yaml b/config/packages/framework.yaml index 7853e9e..338ad7a 100644 --- a/config/packages/framework.yaml +++ b/config/packages/framework.yaml @@ -11,6 +11,7 @@ framework: cookie_secure: auto cookie_samesite: lax storage_factory_id: session.storage.factory.native + cookie_lifetime: 3600 # Durée de vie de 1 heure (en secondes) #esi: true #fragments: true diff --git a/config/packages/lexik_jwt_authentication.yaml b/config/packages/lexik_jwt_authentication.yaml index 5ce0b5f..59f44c6 100644 --- a/config/packages/lexik_jwt_authentication.yaml +++ b/config/packages/lexik_jwt_authentication.yaml @@ -2,4 +2,5 @@ lexik_jwt_authentication: secret_key: '%env(resolve:JWT_SECRET_KEY)%' public_key: '%env(resolve:JWT_PUBLIC_KEY)%' pass_phrase: '%env(JWT_PASSPHRASE)%' - user_identity_field: email \ No newline at end of file + user_identity_field: id + diff --git a/config/packages/security.yaml b/config/packages/security.yaml index b12ee59..4b577c2 100644 --- a/config/packages/security.yaml +++ b/config/packages/security.yaml @@ -9,7 +9,9 @@ security: entity: class: App\Entity\User property: email - + jwt: + lexik_jwt: + class: App\Entity\User firewalls: dev: pattern: ^/(_(profiler|wdt)|css|images|js)/ @@ -28,7 +30,7 @@ security: success_handler: lexik_jwt_authentication.handler.authentication_success failure_handler: lexik_jwt_authentication.handler.authentication_failure api: - provider: app_user_provider + provider: jwt pattern: ^/api/ stateless: true entry_point: jwt diff --git a/config/packages/translation.yaml b/config/packages/translation.yaml new file mode 100644 index 0000000..abb76aa --- /dev/null +++ b/config/packages/translation.yaml @@ -0,0 +1,13 @@ +framework: + default_locale: en + translator: + default_path: '%kernel.project_dir%/translations' + fallbacks: + - en +# providers: +# crowdin: +# dsn: '%env(CROWDIN_DSN)%' +# loco: +# dsn: '%env(LOCO_DSN)%' +# lokalise: +# dsn: '%env(LOKALISE_DSN)%' diff --git a/config/services.yaml b/config/services.yaml index 2d6a76f..9562580 100644 --- a/config/services.yaml +++ b/config/services.yaml @@ -22,3 +22,8 @@ services: # add more service definitions when explicit configuration is needed # please note that last definitions always *replace* previous ones + + acme_api.event.authentication_success_listener: + class: App\EventSubscriber\AuthenticationSuccessEventSubscriber + tags: + - { name: kernel.event_listener, event: lexik_jwt_authentication.on_authentication_success, method: onLexikJwtAuthenticationOnAuthenticationSuccess } diff --git a/migrations/Version20221129225510.php b/migrations/Version20221129225510.php new file mode 100644 index 0000000..6f5ec5a --- /dev/null +++ b/migrations/Version20221129225510.php @@ -0,0 +1,31 @@ +addSql('ALTER TABLE user CHANGE name pseudo VARCHAR(255) DEFAULT NULL'); + } + + public function down(Schema $schema): void + { + // this down() migration is auto-generated, please modify it to your needs + $this->addSql('ALTER TABLE user CHANGE pseudo name VARCHAR(255) DEFAULT NULL'); + } +} diff --git a/migrations/Version20230125181907.php b/migrations/Version20230125181907.php new file mode 100644 index 0000000..7916675 --- /dev/null +++ b/migrations/Version20230125181907.php @@ -0,0 +1,31 @@ +addSql('ALTER TABLE article ADD synopsis LONGTEXT NOT NULL, CHANGE img_id img_id INT DEFAULT NULL'); + } + + public function down(Schema $schema): void + { + // this down() migration is auto-generated, please modify it to your needs + $this->addSql('ALTER TABLE article DROP synopsis, CHANGE img_id img_id INT DEFAULT 17'); + } +} diff --git a/migrations/Version20230126205721.php b/migrations/Version20230126205721.php new file mode 100644 index 0000000..e8e435f --- /dev/null +++ b/migrations/Version20230126205721.php @@ -0,0 +1,31 @@ +addSql('ALTER TABLE article ADD file_path VARCHAR(255) DEFAULT NULL'); + } + + public function down(Schema $schema): void + { + // this down() migration is auto-generated, please modify it to your needs + $this->addSql('ALTER TABLE article DROP file_path'); + } +} diff --git a/migrations/Version20230126230112.php b/migrations/Version20230126230112.php new file mode 100644 index 0000000..4d957a8 --- /dev/null +++ b/migrations/Version20230126230112.php @@ -0,0 +1,31 @@ +addSql('ALTER TABLE article DROP file_path'); + } + + public function down(Schema $schema): void + { + // this down() migration is auto-generated, please modify it to your needs + $this->addSql('ALTER TABLE article ADD file_path VARCHAR(255) DEFAULT NULL'); + } +} diff --git a/migrations/Version20230221200901.php b/migrations/Version20230221200901.php new file mode 100644 index 0000000..df44497 --- /dev/null +++ b/migrations/Version20230221200901.php @@ -0,0 +1,31 @@ +addSql('CREATE TABLE contact (id INT AUTO_INCREMENT NOT NULL, prenom VARCHAR(255) NOT NULL, nom VARCHAR(255) NOT NULL, entreprise VARCHAR(255) NOT NULL, email VARCHAR(255) NOT NULL, message LONGTEXT NOT NULL, created_at DATETIME NOT NULL COMMENT \'(DC2Type:datetime_immutable)\', PRIMARY KEY(id)) DEFAULT CHARACTER SET utf8mb4 COLLATE `utf8mb4_unicode_ci` ENGINE = InnoDB'); + } + + public function down(Schema $schema): void + { + // this down() migration is auto-generated, please modify it to your needs + $this->addSql('DROP TABLE contact'); + } +} diff --git a/public/media/630cc40fcef4a_php.png b/public/media/630cc40fcef4a_php.png deleted file mode 100644 index d029a3a..0000000 Binary files a/public/media/630cc40fcef4a_php.png and /dev/null differ diff --git a/public/media/634428fc47a2b_taxi.png b/public/media/634428fc47a2b_taxi.png deleted file mode 100644 index 944c71c..0000000 Binary files a/public/media/634428fc47a2b_taxi.png and /dev/null differ diff --git a/public/media/63f698ee1c854_seo.webp b/public/media/63f698ee1c854_seo.webp new file mode 100644 index 0000000..9a6f9bb Binary files /dev/null and b/public/media/63f698ee1c854_seo.webp differ diff --git a/public/media/64613f5004a12_conception.jpg b/public/media/64613f5004a12_conception.jpg new file mode 100644 index 0000000..8171f31 Binary files /dev/null and b/public/media/64613f5004a12_conception.jpg differ diff --git a/public/media/64614412b815a_vitesse-chargement.jpg b/public/media/64614412b815a_vitesse-chargement.jpg new file mode 100644 index 0000000..57ce647 Binary files /dev/null and b/public/media/64614412b815a_vitesse-chargement.jpg differ diff --git a/public/media/64615265799a5_application.jpg b/public/media/64615265799a5_application.jpg new file mode 100644 index 0000000..b190095 Binary files /dev/null and b/public/media/64615265799a5_application.jpg differ diff --git a/public/media/646153a54781e_application.jpg b/public/media/646153a54781e_application.jpg new file mode 100644 index 0000000..6616708 Binary files /dev/null and b/public/media/646153a54781e_application.jpg differ diff --git a/public/media/6461568875aec_phishing.jpg b/public/media/6461568875aec_phishing.jpg new file mode 100644 index 0000000..54dd0cd Binary files /dev/null and b/public/media/6461568875aec_phishing.jpg differ diff --git a/public/media/646158217e594_mdp.jpg b/public/media/646158217e594_mdp.jpg new file mode 100644 index 0000000..253c2cc Binary files /dev/null and b/public/media/646158217e594_mdp.jpg differ diff --git a/public/media/6461f01832ff9_donnees-client.jpg b/public/media/6461f01832ff9_donnees-client.jpg new file mode 100644 index 0000000..743589b Binary files /dev/null and b/public/media/6461f01832ff9_donnees-client.jpg differ diff --git a/public/media/6461f292b5c15_securise.webp b/public/media/6461f292b5c15_securise.webp new file mode 100644 index 0000000..059b2fa Binary files /dev/null and b/public/media/6461f292b5c15_securise.webp differ diff --git a/public/media/6461f56574062_design-web.jpg b/public/media/6461f56574062_design-web.jpg new file mode 100644 index 0000000..6ec5097 Binary files /dev/null and b/public/media/6461f56574062_design-web.jpg differ diff --git a/public/media/6461f750f05c8_palette-color.jpg b/public/media/6461f750f05c8_palette-color.jpg new file mode 100644 index 0000000..c45c2e6 Binary files /dev/null and b/public/media/6461f750f05c8_palette-color.jpg differ diff --git a/public/media/6461f8844a877_palette-color.jpg b/public/media/6461f8844a877_palette-color.jpg new file mode 100644 index 0000000..9784bd9 Binary files /dev/null and b/public/media/6461f8844a877_palette-color.jpg differ diff --git a/public/media/6461f947070e3_typography.jpg b/public/media/6461f947070e3_typography.jpg new file mode 100644 index 0000000..a234ed5 Binary files /dev/null and b/public/media/6461f947070e3_typography.jpg differ diff --git a/public/media/6461fa61546c1_icons.jpg b/public/media/6461fa61546c1_icons.jpg new file mode 100644 index 0000000..b657218 Binary files /dev/null and b/public/media/6461fa61546c1_icons.jpg differ diff --git a/public/media/646200f9bd27a_systeme-exploitation.jpg b/public/media/646200f9bd27a_systeme-exploitation.jpg new file mode 100644 index 0000000..1d824f3 Binary files /dev/null and b/public/media/646200f9bd27a_systeme-exploitation.jpg differ diff --git a/public/media/646202bc825ea_microsoft-office.jpg b/public/media/646202bc825ea_microsoft-office.jpg new file mode 100644 index 0000000..6a975f2 Binary files /dev/null and b/public/media/646202bc825ea_microsoft-office.jpg differ diff --git a/public/media/646204f9a54a8_navigation-web.jpg b/public/media/646204f9a54a8_navigation-web.jpg new file mode 100644 index 0000000..fd33efd Binary files /dev/null and b/public/media/646204f9a54a8_navigation-web.jpg differ diff --git a/public/media/646208d1e0dfa_blockchain.jpg b/public/media/646208d1e0dfa_blockchain.jpg new file mode 100644 index 0000000..104cac3 Binary files /dev/null and b/public/media/646208d1e0dfa_blockchain.jpg differ diff --git a/public/media/64620c22055a9_ia.jpg b/public/media/64620c22055a9_ia.jpg new file mode 100644 index 0000000..0ffe1af Binary files /dev/null and b/public/media/64620c22055a9_ia.jpg differ diff --git a/public/media/646214dea2152_vr.jpg b/public/media/646214dea2152_vr.jpg new file mode 100644 index 0000000..8fb32e6 Binary files /dev/null and b/public/media/646214dea2152_vr.jpg differ diff --git a/public/media/646216cd74e40_chatbots.jpg b/public/media/646216cd74e40_chatbots.jpg new file mode 100644 index 0000000..144c01d Binary files /dev/null and b/public/media/646216cd74e40_chatbots.jpg differ diff --git a/src/Controller/Admin/DashboardController.php b/src/Controller/Admin/DashboardController.php new file mode 100644 index 0000000..69eb99d --- /dev/null +++ b/src/Controller/Admin/DashboardController.php @@ -0,0 +1,46 @@ +container->get(AdminUrlGenerator::class); + // return $this->redirect($adminUrlGenerator->setController(OneOfYourCrudController::class)->generateUrl()); + + // Option 2. You can make your dashboard redirect to different pages depending on the user + // + // if ('jane' === $this->getUser()->getUsername()) { + // return $this->redirect('...'); + // } + + // Option 3. You can render some custom template to display a proper dashboard with widgets, etc. + // (tip: it's easier if your template extends from @EasyAdmin/page/content.html.twig) + // + // return $this->render('some/path/my-dashboard.html.twig'); + } + + public function configureDashboard(): Dashboard + { + return Dashboard::new() + ->setTitle('BlogApiPlatform'); + } + + public function configureMenuItems(): iterable + { + yield MenuItem::linkToDashboard('Dashboard', 'fa fa-home'); + // yield MenuItem::linkToCrud('The Label', 'fas fa-list', EntityClass::class); + } +} diff --git a/src/Controller/CreateMediaObjectAction.php b/src/Controller/CreateMediaObjectAction.php index 7790687..289e2b3 100644 --- a/src/Controller/CreateMediaObjectAction.php +++ b/src/Controller/CreateMediaObjectAction.php @@ -41,8 +41,8 @@ private function checkingFile($uploadedFile): ?bool $size = $file->getSize(); $error = $file->getError(); - $extensions = ['jpg','png', 'jpeg', 'gif']; - $maxSize = 600000; + $extensions = ['jpg','png', 'jpeg', 'gif', 'svg', 'webp']; + $maxSize = 4900000; if(in_array($extension, $extensions)) { @@ -55,13 +55,13 @@ private function checkingFile($uploadedFile): ?bool } else { - throw new Exception('the size of the file is too big'); + throw new Exception("La taille du fichier est trop volumineux ; ne doit pas depasser 90Mo"); } return true; } else{ - throw new Exception('the format isn\'t supported'); + throw new Exception("Le format n'est pas supporté"); } } } \ No newline at end of file diff --git a/src/DataPersister/ArticleDataPersister.php b/src/DataPersister/ArticleDataPersister.php index b883a84..4e39e89 100644 --- a/src/DataPersister/ArticleDataPersister.php +++ b/src/DataPersister/ArticleDataPersister.php @@ -5,6 +5,7 @@ use App\Entity\Article; use ApiPlatform\Core\DataPersister\ContextAwareDataPersisterInterface; use App\Entity\Category; +use App\Entity\User; use Doctrine\ORM\EntityManagerInterface; use Symfony\Component\HttpFoundation\RequestStack; use Symfony\Component\HttpFoundation\Request; @@ -55,6 +56,8 @@ public function supports($data, array $context = []): bool /** * @param Article $data + * @param array $context + * @return object|void */ public function persist($data, array $context = []) { @@ -63,7 +66,13 @@ public function persist($data, array $context = []) // Set the author if it's a new article if($this->_request->getMethod() === 'POST') { - $data->setAuthorArticle($this->_security->getUser()); + $user = $this->_security->getUser(); + if ($user instanceof User) { + $userId = $user->getId(); + $userRepo = $this->_em->getRepository(User::class); + $user = $userRepo->find($userId); + $data->setAuthorArticle($user); + } } // Set the updatedAt value if it's a PUT or PATCH request diff --git a/src/DataPersister/UserDataPersister.php b/src/DataPersister/UserDataPersister.php index b102fa4..fa32840 100644 --- a/src/DataPersister/UserDataPersister.php +++ b/src/DataPersister/UserDataPersister.php @@ -37,7 +37,7 @@ public function supports($data, array $context = []): bool } /** - * créer ou mettre à jour les données données + * Créer ou mettre à jour les données reçu * @param User $data */ public function persist($data, array $context = []) @@ -48,6 +48,12 @@ public function persist($data, array $context = []) $data->eraseCredentials(); } + // Verification de l'email + $existEmail = $this->_em->getRepository(user::class)->findOneBy(['email' => $data->getEmail()]); + if($existEmail) { + throw new \InvalidArgumentException('Cet email est déjà prit'); + } + $this->_em->persist($data); $this->_em->flush(); } @@ -58,7 +64,7 @@ public function persist($data, array $context = []) */ public function remove($data, array $context = []) { - $this->_entityManager->remove($data); - $this->_entityManager->flush(); + $this->_em->remove($data); + $this->_em->flush(); } -} \ No newline at end of file +} diff --git a/src/Encoder/MultipartDecoder.php b/src/Encoder/MultipartDecoder.php new file mode 100644 index 0000000..0a9100a --- /dev/null +++ b/src/Encoder/MultipartDecoder.php @@ -0,0 +1,41 @@ +requestStack->getCurrentRequest(); + + if (!$request) { + return null; + } + + return array_map(static function (string $element) { + // Multipart form values will be encoded in JSON. + $decoded = json_decode($element, true); + + return \is_array($decoded) ? $decoded : $element; + }, $request->request->all()) + $request->files->all(); + } + + /** + * {@inheritdoc} + */ + public function supportsDecoding(string $format): bool + { + return self::FORMAT === $format; + } +} \ No newline at end of file diff --git a/src/Entity/Article.php b/src/Entity/Article.php index 72134e3..9e4af27 100644 --- a/src/Entity/Article.php +++ b/src/Entity/Article.php @@ -2,12 +2,15 @@ namespace App\Entity; +use ApiPlatform\Core\Annotation\ApiFilter; +use App\Entity\Category; use Doctrine\DBAL\Types\Types; use Doctrine\ORM\Mapping as ORM; use App\Repository\ArticleRepository; use Doctrine\Common\Collections\Collection; use ApiPlatform\Core\Annotation\ApiResource; use ApiPlatform\Core\Annotation\ApiSubresource; +use ApiPlatform\Core\Bridge\Doctrine\Orm\Filter\SearchFilter; use Doctrine\Common\Collections\ArrayCollection; use Symfony\Component\Validator\Constraints\Valid; use Symfony\Component\Serializer\Annotation\Groups; @@ -17,35 +20,37 @@ #[ORM\Entity(repositoryClass: ArticleRepository::class)] +#[ApiFilter(SearchFilter::class, properties: ["content" => "partial"])] #[ApiResource( normalizationContext: [ 'groups' => ['read:articles'], 'openapi_definition_name' => 'collection' ], denormalizationContext: ['groups' => ['write:article']], - paginationItemsPerPage: 10, - paginationMaximumItemsPerPage: 20, + paginationItemsPerPage: 12, paginationClientItemsPerPage: true, + order: ["createdAt" => "DESC"], collectionOperations: [ 'get', "post" => [ "security_post_denormalize" => "is_granted('ARTICLE_CREATE', object)", - "security_post_denormalize_message" => "Only Admins and Authors can add Articles.", + "security_post_denormalize_message" => "Vous n'avez pas les droits pour ajouter un article !", ], ], itemOperations: [ 'get' => [ 'normalization_context' => [ - 'openapi_definition_name' => 'item' + 'openapi_definition_name' => 'item', + 'groups' => ['read:articles','read:article'] ], ], "put" => [ "security" => "is_granted('ARTICLE_EDIT', object)", - "security_message" => "Sorry, but you are not the actual Article owner." + "security_message" => "Désolé vous n'avez pas les droits pour modifier l'article !" ], 'delete' => [ "security" => "is_granted('ARTICLE_DELETE', object)", - "security_message" => "Sorry, but you are not the actual Article owner." + "security_message" => "Désolé vous n'avez pas les droits pour supprimer l'article !" ], ], )] @@ -69,24 +74,29 @@ class Article private ?string $slug = null; #[ORM\Column(type: Types::TEXT)] - #[Groups(['read:articles', 'write:article'])] + #[Groups(['read:article', 'read:articles', 'write:article'])] private ?string $content = null; + #[ORM\Column(type: Types::TEXT)] + #[Groups(['read:article', 'read:articles', 'write:article'])] + private ?string $synopsis = null; + #[ORM\Column] - #[Groups('read:articles')] - #[Context([DateTimeNormalizer::FORMAT_KEY => 'd-m-Y h:i:s'])] + #[Groups('read:articles', 'read:users')] + #[Context([DateTimeNormalizer::FORMAT_KEY => 'd/m/Y'])] private ?\DateTimeImmutable $createdAt = null; #[ORM\Column(nullable: true)] + #[Groups('read:articles', 'read:users')] private ?\DateTimeImmutable $updatedAt = null; #[ORM\Column(options: ["default" => 0])] - #[Groups(['read:articles'])] + #[Groups(['read:articles', 'read:users', "write:article"])] private ?bool $isPublished = false; #[ORM\ManyToOne(targetEntity: MediaObject::class)] #[ORM\JoinColumn(nullable: true)] - #[Groups(['read:articles','write:article'])] + #[Groups(['read:articles','write:article', 'read:article'])] public ?MediaObject $img = null; #[ORM\OneToMany(mappedBy: 'article', targetEntity: Comment::class, orphanRemoval: true)] @@ -96,7 +106,7 @@ class Article #[ORM\ManyToMany(targetEntity: Category::class, inversedBy: 'articles', cascade: ['persist'])] #[ - Groups(['read:articles', 'write:article']), + Groups(['read:articles', 'read:article', 'read:category', 'write:article']), Valid() ] private Collection $categories; @@ -106,6 +116,7 @@ class Article #[Groups(['read:articles'])] private ?User $authorArticle = null; + public function __construct() { $this->createdAt = new \DateTimeImmutable(); $this->comments = new ArrayCollection(); @@ -266,4 +277,16 @@ public function setAuthorArticle(?User $authorArticle): self return $this; } + + public function getSynopsis(): ?string + { + return $this->synopsis; + } + + public function setSynopsis(string $synopsis): self + { + $this->synopsis = $synopsis; + + return $this; + } } diff --git a/src/Entity/Category.php b/src/Entity/Category.php index 563b40d..73c08fe 100644 --- a/src/Entity/Category.php +++ b/src/Entity/Category.php @@ -39,7 +39,7 @@ class Category #[ORM\Id] #[ORM\GeneratedValue] #[ORM\Column] - #[Groups('read:article')] + #[Groups(['read:categories', 'read:articles'])] private ?int $id = null; #[ORM\Column(length: 255, unique: true)] diff --git a/src/Entity/Comment.php b/src/Entity/Comment.php index 77650a7..883a874 100644 --- a/src/Entity/Comment.php +++ b/src/Entity/Comment.php @@ -46,20 +46,20 @@ class Comment #[ORM\Id] #[ORM\GeneratedValue] #[ORM\Column] - #[Groups(['read:comments', 'read:articles', 'read:users'])] + #[Groups(['read:comments', 'read:article', 'read:users'])] private ?int $id = null; #[ORM\Column(type: Types::TEXT)] - #[Groups(['read:comments', 'write:comment', 'read:articles'])] + #[Groups(['read:comments', 'write:comment', 'read:article', 'read:users'])] private ?string $content = null; #[ORM\Column] - #[Groups(['read:comments', 'read:articles'])] + #[Groups(['read:comments', 'read:article'])] #[Context([DateTimeNormalizer::FORMAT_KEY => 'd-m-Y h:i:s'])] private ?\DateTimeImmutable $createdAt = null; #[ORM\Column(nullable: true)] - #[Groups(['read:comments', 'read:articles'])] + #[Groups(['read:comments', 'read:article'])] private ?\DateTimeImmutable $updatedAt = null; #[ORM\ManyToOne(inversedBy: 'comments')] @@ -70,7 +70,7 @@ class Comment #[ORM\ManyToOne(inversedBy: 'comments')] #[ORM\JoinColumn(nullable: false)] - #[Groups(['read:comments', 'write:user'])] + #[Groups(['read:comments', 'read:article'])] private ?User $authorComment = null; diff --git a/src/Entity/Contact.php b/src/Entity/Contact.php new file mode 100644 index 0000000..bf3a002 --- /dev/null +++ b/src/Entity/Contact.php @@ -0,0 +1,143 @@ + ['read:contact']], + denormalizationContext: ['groups' => ['write:contact']], + collectionOperations: [ + 'get', + "post", + ], + itemOperations: [ + 'get', + "put", + 'delete' => [ + "security" => "is_granted('ROLE_ADMIN')", + "security_message" => "Désolé vous n'avez pas les droits pour supprimer cet utilisateur !", + ], + ], +)] +class Contact +{ + #[ORM\Id] + #[ORM\GeneratedValue] + #[ORM\Column] + #[Groups(['read:contact'])] + private ?int $id = null; + + #[ORM\Column(length: 255)] + #[Groups(['read:contact', 'write:contact'])] + private ?string $prenom = null; + + #[ORM\Column(length: 255)] + #[Groups(['read:contact', 'write:contact'])] + private ?string $nom = null; + + #[ORM\Column(length: 255)] + #[Groups(['read:contact', 'write:contact'])] + private ?string $entreprise = null; + + #[ORM\Column(length: 255)] + #[Groups(['read:contact', 'write:contact'])] + private ?string $email = null; + + #[ORM\Column(type: Types::TEXT)] + #[Groups(['read:contact', 'write:contact'])] + private ?string $message = null; + + #[ORM\Column] + #[Groups(['read:contact'])] + #[Context([DateTimeNormalizer::FORMAT_KEY => 'd/m/Y à H:i'])] + private ?\DateTimeImmutable $createdAt = null; + + public function __construct() { + $this->createdAt = new \DateTimeImmutable(); + } + + public function getId(): ?int + { + return $this->id; + } + + public function getPrenom(): ?string + { + return $this->prenom; + } + + public function setPrenom(string $prenom): self + { + $this->prenom = $prenom; + + return $this; + } + + public function getNom(): ?string + { + return $this->nom; + } + + public function setNom(string $nom): self + { + $this->nom = $nom; + + return $this; + } + + public function getEntreprise(): ?string + { + return $this->entreprise; + } + + public function setEntreprise(string $entreprise): self + { + $this->entreprise = $entreprise; + + return $this; + } + + public function getEmail(): ?string + { + return $this->email; + } + + public function setEmail(string $email): self + { + $this->email = $email; + + return $this; + } + + public function getMessage(): ?string + { + return $this->message; + } + + public function setMessage(string $message): self + { + $this->message = $message; + + return $this; + } + + public function getCreatedAt(): ?\DateTimeImmutable + { + return $this->createdAt; + } + + public function setCreatedAt(\DateTimeImmutable $createdAt): self + { + $this->createdAt = $createdAt; + + return $this; + } +} diff --git a/src/Entity/MediaObject.php b/src/Entity/MediaObject.php index f4de790..f35b1fe 100644 --- a/src/Entity/MediaObject.php +++ b/src/Entity/MediaObject.php @@ -23,11 +23,12 @@ normalizationContext: ['groups' => ['media_object:read']], itemOperations: [ 'get', - 'delete' => ["security" => "is_granted('MEDIA_DELETE',object)"] + 'delete' => ["security" => "is_granted('ROLE_AUTHOR')"] ], collectionOperations: [ 'get', 'post' => [ + "security" => "is_granted('ROLE_AUTHOR')", 'controller' => CreateMediaObjectAction::class, 'deserialize' => false, 'validation_groups' => ['Default', 'media_object_create'], @@ -54,10 +55,11 @@ class MediaObject { #[ORM\Id, ORM\Column, ORM\GeneratedValue] + #[Groups(['media_object:read','read:articles', 'read:article'])] private ?int $id = null; #[ApiProperty(iri: 'https://schema.org/contentUrl')] - #[Groups(['media_object:read','read:articles'])] + #[Groups(['media_object:read','read:articles', 'read:article'])] public ?string $contentUrl = null; /** diff --git a/src/Entity/User.php b/src/Entity/User.php index fc9d584..28095bf 100644 --- a/src/Entity/User.php +++ b/src/Entity/User.php @@ -2,18 +2,19 @@ namespace App\Entity; -use ApiPlatform\Core\Annotation\ApiResource; +use Doctrine\ORM\Mapping as ORM; use App\Repository\UserRepository; -use Doctrine\Common\Collections\ArrayCollection; use Doctrine\Common\Collections\Collection; -use Doctrine\ORM\Mapping as ORM; -use Lexik\Bundle\JWTAuthenticationBundle\Security\User\JWTUserInterface; -use Symfony\Component\Security\Core\User\PasswordAuthenticatedUserInterface; -use Symfony\Component\Security\Core\User\UserInterface; +use ApiPlatform\Core\Annotation\ApiResource; +use Doctrine\Common\Collections\ArrayCollection; +use Symfony\Component\Validator\Constraints\Regex; use Symfony\Component\Serializer\Annotation\Groups; -use Symfony\Component\Serializer\Annotation\SerializedName; +use Symfony\Component\Validator\Constraints as Assert; +use Symfony\Component\Security\Core\User\UserInterface; use Symfony\Component\Validator\Constraints\Expression; -use Symfony\Component\Validator\Constraints\Regex; +use Symfony\Component\Serializer\Annotation\SerializedName; +use Lexik\Bundle\JWTAuthenticationBundle\Security\User\JWTUserInterface; +use Symfony\Component\Security\Core\User\PasswordAuthenticatedUserInterface; #[ORM\Entity(repositoryClass: UserRepository::class)] #[ApiResource( @@ -24,41 +25,43 @@ paginationClientItemsPerPage: true, collectionOperations: [ 'get', - "post" + "post" => [ + "security" => "is_granted('ROLE_ADMIN')", + "security_message" => "Désolé vous n'avez pas les droits pour ajouter un utilisateur !", + ], ], itemOperations: [ - 'get' => [ - 'normalization_context' => [ - 'openapi_definition_name' => 'item' - ], - ], + 'get', "put" => [ "security" => "is_granted('USER_EDIT', object)", - "security_message" => "Sorry, but you are not the actual User owner.", + "security_message" => "Désolé vous n'avez pas les droits pour modifier cet utilisateur !", ], 'delete' => [ "security" => "is_granted('USER_DELETE', object)", - "security_message" => "Sorry, but you are not the actual User owner.", + "security_message" => "Désolé vous n'avez pas les droits pour supprimer cet utilisateur !", ], ], )] -class User implements UserInterface, PasswordAuthenticatedUserInterface + +class User implements UserInterface, PasswordAuthenticatedUserInterface, JWTUserInterface { #[ORM\Id] #[ORM\GeneratedValue] #[ORM\Column] - #[Groups(['read:users', 'read:articles'])] + #[Groups(['read:users', 'read:article'])] private ?int $id = null; - #[ORM\Column(length: 180, unique: true)] - #[Groups(['read:users', 'write:user'])] + #[ORM\Column(length: 180, unique: true, name: 'email', type: 'string')] + #[Groups(['read:users', 'write:user', 'read:article'])] + #[Assert\Email] private ?string $email = null; #[ORM\Column(length: 255, nullable: true)] - #[Groups(['read:users', 'write:user', 'read:articles'])] - private ?string $name = null; + #[Groups(['read:users', 'write:user', 'read:article', 'read:articles'])] + private ?string $pseudo = null; #[ORM\Column] + #[Groups(['read:users', 'write:user'])] private array $roles = []; /** @@ -73,20 +76,18 @@ class User implements UserInterface, PasswordAuthenticatedUserInterface pattern:"/(?=.*[A-Z])(?=.*[a-z])(?=.*[0-9]).{7,}/", message: "Le mot de passe doit contenir minimum 7 caractères dont un chiffre, une lettre majuscule et une lettre minuscule" )] - #[Groups(['write:user'])] + #[Groups(['write:user', 'read:users'])] private ?string $plainPassword = null; - - #[SerializedName('confirmed password')] #[Regex( pattern:"/(?=.*[A-Z])(?=.*[a-z])(?=.*[0-9]).{7,}/", - message: "Le mot de passe doit contenir minimum 7 caractères dont un chiffre, une lettre majuscule et une lettre minuscule" + message: "Le mot de passe doit commencer par une majuscule et contenir minimum 7 caractères dont un chiffre, une lettre majuscule et une lettre minuscule" )] #[Expression( "this.getPlainPassword() === this.getPasswordBis()", message: "Passwords does not match" )] - #[Groups(['write:user'])] + #[Groups(['write:user', 'read:users'])] private ?string $passwordBis = null; #[ORM\OneToMany(mappedBy: 'authorArticle', targetEntity: Article::class)] @@ -94,7 +95,6 @@ class User implements UserInterface, PasswordAuthenticatedUserInterface private Collection $articles; #[ORM\OneToMany(mappedBy: 'authorComment', targetEntity: Comment::class)] - #[Groups(['read:users'])] private Collection $comments; @@ -145,8 +145,8 @@ public function getUserIdentifier(): string public function getRoles(): array { $roles = $this->roles; - // guarantee every user at least has ROLE_USER - $roles[] = 'ROLE_USER'; + // guarantee every user at least has ROLE_VISITOR + $roles[] = 'ROLE_VISITOR'; return array_unique($roles); } @@ -182,14 +182,14 @@ public function eraseCredentials() $this->plainPassword = null; } - public function getname(): ?string + public function getPseudo(): ?string { - return $this->name; + return $this->pseudo; } - public function setname(?string $name): self + public function setPseudo(?string $pseudo): self { - $this->name = $name; + $this->pseudo = $pseudo; return $this; } @@ -277,4 +277,12 @@ public function removeComment(Comment $comment): self return $this; } + + public static function createFromPayload($id, array $payload) + { + $user = new user(); + $user->setId($id); + $user->setRoles($payload['roles']); + return $user; + } } diff --git a/src/EventSubscriber/AuthenticationSuccessEventSubscriber.php b/src/EventSubscriber/AuthenticationSuccessEventSubscriber.php new file mode 100644 index 0000000..61fd643 --- /dev/null +++ b/src/EventSubscriber/AuthenticationSuccessEventSubscriber.php @@ -0,0 +1,42 @@ +_em = $em; + } + + public function onLexikJwtAuthenticationOnAuthenticationSuccess(AuthenticationSuccessEvent $event): void + { + $data = $event->getData(); + $user = $event->getUser(); + + if(!$user instanceof User) { + return; + } + $data['user'] = array( + 'id' => $user->getId(), + 'roles' => $user->getRoles(), + 'name' => $user->getPseudo(), + ); + + $event->setData($data); + } + + public static function getSubscribedEvents(): array + { + return [ + 'lexik_jwt_authentication.on_authentication_success' => 'onLexikJwtAuthenticationOnAuthenticationSuccess', + ]; + } +} diff --git a/src/Repository/ContactRepository.php b/src/Repository/ContactRepository.php new file mode 100644 index 0000000..dcfdeb0 --- /dev/null +++ b/src/Repository/ContactRepository.php @@ -0,0 +1,66 @@ + + * + * @method Contact|null find($id, $lockMode = null, $lockVersion = null) + * @method Contact|null findOneBy(array $criteria, array $orderBy = null) + * @method Contact[] findAll() + * @method Contact[] findBy(array $criteria, array $orderBy = null, $limit = null, $offset = null) + */ +class ContactRepository extends ServiceEntityRepository +{ + public function __construct(ManagerRegistry $registry) + { + parent::__construct($registry, Contact::class); + } + + public function add(Contact $entity, bool $flush = false): void + { + $this->getEntityManager()->persist($entity); + + if ($flush) { + $this->getEntityManager()->flush(); + } + } + + public function remove(Contact $entity, bool $flush = false): void + { + $this->getEntityManager()->remove($entity); + + if ($flush) { + $this->getEntityManager()->flush(); + } + } + +// /** +// * @return Contact[] Returns an array of Contact objects +// */ +// public function findByExampleField($value): array +// { +// return $this->createQueryBuilder('c') +// ->andWhere('c.exampleField = :val') +// ->setParameter('val', $value) +// ->orderBy('c.id', 'ASC') +// ->setMaxResults(10) +// ->getQuery() +// ->getResult() +// ; +// } + +// public function findOneBySomeField($value): ?Contact +// { +// return $this->createQueryBuilder('c') +// ->andWhere('c.exampleField = :val') +// ->setParameter('val', $value) +// ->getQuery() +// ->getOneOrNullResult() +// ; +// } +} diff --git a/src/Security/Voter/ArticleVoter.php b/src/Security/Voter/ArticleVoter.php index 1fb5b3c..c6bb88c 100644 --- a/src/Security/Voter/ArticleVoter.php +++ b/src/Security/Voter/ArticleVoter.php @@ -3,6 +3,8 @@ namespace App\Security\Voter; use App\Entity\Article; +use App\Entity\User; +use Doctrine\ORM\EntityManagerInterface; use Symfony\Component\Security\Core\User\UserInterface; use Symfony\Component\Security\Core\Authorization\Voter\Voter; use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; @@ -15,9 +17,11 @@ class ArticleVoter extends Voter const DELETE = 'ARTICLE_DELETE'; private $security; + private $em; - public function __construct(Security $security) { + public function __construct(Security $security, EntityManagerInterface $em) { $this->security = $security; + $this->em = $em; } protected function supports(string $attribute, $subject): bool @@ -36,9 +40,13 @@ protected function voteOnAttribute(string $attribute, $subject, TokenInterface $ { $user = $token->getUser(); - if (!$user instanceof UserInterface) { + if (!$user instanceof UserInterface || !$user instanceof User) { return false; } + + $userId = $user->getId(); + $userRepo = $this->em->getRepository(User::class); + $user = $user = $userRepo->find($userId); // Admin all granted if($this->security->isGranted('ROLE_ADMIN')) { diff --git a/src/Security/Voter/CategoryVoter.php b/src/Security/Voter/CategoryVoter.php index 879defc..551a792 100644 --- a/src/Security/Voter/CategoryVoter.php +++ b/src/Security/Voter/CategoryVoter.php @@ -46,7 +46,7 @@ protected function voteOnAttribute($attribute, $subject, TokenInterface $token): } // Admin and Author all granted - if($this->security->isGranted('ROLE_ADMIN', 'ROLE_AUTHOR')) { + if($this->security->isGranted('ROLE_ADMIN')) { return true; } } diff --git a/src/Security/Voter/MediaObjectVoter.php b/src/Security/Voter/MediaObjectVoter.php index 5f4d3c9..08fc85c 100644 --- a/src/Security/Voter/MediaObjectVoter.php +++ b/src/Security/Voter/MediaObjectVoter.php @@ -11,7 +11,6 @@ class MediaObjectVoter extends Voter { const CREATE = 'MEDIA_CREATE'; - const EDIT = 'MEDIA_EDIT'; const DELETE = 'MEDIA_DELETE'; private $security; @@ -22,7 +21,7 @@ public function __construct(Security $security) { protected function supports(string $attribute, $subject): bool { - return in_array($attribute, [self::CREATE, self::EDIT, self::DELETE]) + return in_array($attribute, [self::CREATE, self::DELETE]) && $subject instanceof MediaObject; } @@ -41,9 +40,9 @@ protected function voteOnAttribute(string $attribute, $subject, TokenInterface $ } // Admin and Author all granted - if($this->security->isGranted('ROLE_ADMIN', 'ROLE_AUTHOR')) { + if($this->security->isGranted('ROLE_ADMIN')) { return true; - } + } } } \ No newline at end of file diff --git a/src/Security/Voter/UserVoter.php b/src/Security/Voter/UserVoter.php index 2878eee..d89af16 100644 --- a/src/Security/Voter/UserVoter.php +++ b/src/Security/Voter/UserVoter.php @@ -3,6 +3,7 @@ namespace App\Security\Voter; use App\Entity\User; +use Doctrine\ORM\EntityManagerInterface; use Symfony\Component\Security\Core\User\UserInterface; use Symfony\Component\Security\Core\Authorization\Voter\Voter; use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; @@ -14,9 +15,11 @@ class UserVoter extends Voter public const DELETE = 'USER_DELETE'; private $security; + private $em; - public function __construct(Security $security){ + public function __construct(Security $security, EntityManagerInterface $em){ $this->security = $security; + $this->em = $em; } protected function supports(string $attribute, $subject): bool @@ -35,9 +38,12 @@ protected function voteOnAttribute(string $attribute, $subject, TokenInterface $ { $user = $token->getUser(); - if (!$user instanceof UserInterface) { + if (!$user instanceof UserInterface || !$user instanceof User) { return false; } + $userId = $user->getId(); + $userRepo = $this->em->getRepository(User::class); + $user = $user = $userRepo->find($userId); // Le rôle 'admin' a touts les accès if($this->security->isGranted('ROLE_ADMIN')) { @@ -48,7 +54,7 @@ protected function voteOnAttribute(string $attribute, $subject, TokenInterface $ switch ($attribute) { case self::EDIT: case self::DELETE: - if($user === $subject->getUserIdentifier()) { + if($user === $subject) { return true; break; } diff --git a/src/Serializer/UploadedFileDenormalizer.php b/src/Serializer/UploadedFileDenormalizer.php new file mode 100644 index 0000000..72b64b4 --- /dev/null +++ b/src/Serializer/UploadedFileDenormalizer.php @@ -0,0 +1,26 @@ +