diff --git a/.gitignore b/.gitignore index 08cf2d70..0d871ae7 100644 --- a/.gitignore +++ b/.gitignore @@ -55,4 +55,7 @@ yarn-error.log docker.conf /documentation_jitsi_admin/node_modules/ -/secretStorage/.Halite* \ No newline at end of file +/secretStorage/.Halite* +###> phpstan/phpstan ### +phpstan.neon +###< phpstan/phpstan ### diff --git a/composer.json b/composer.json index ee025db7..4e6919a5 100644 --- a/composer.json +++ b/composer.json @@ -60,6 +60,7 @@ "vich/uploader-bundle": "^1.13" }, "require-dev": { + "phpstan/phpstan": "^1.10", "phpunit/phpunit": "^9.5", "symfony/browser-kit": "6.2.*", "symfony/css-selector": "6.2.*", @@ -102,6 +103,7 @@ "cache:clear": "symfony-cmd", "assets:install %PUBLIC_DIR%": "symfony-cmd" }, + "phpstan": "php vendor/bin/phpstan analyze -c phpstan.dist.neon", "post-install-cmd": [ "@auto-scripts" ], diff --git a/composer.lock b/composer.lock index 8d96745c..0c1366a4 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": "032e3f507e51377d9a60572e16ee7f34", + "content-hash": "d8672350cfee7cca166f191429f34cf6", "packages": [ { "name": "behat/transliterator", @@ -10975,6 +10975,68 @@ }, "time": "2022-02-21T01:04:05+00:00" }, + { + "name": "phpstan/phpstan", + "version": "1.10.59", + "source": { + "type": "git", + "url": "https://github.com/phpstan/phpstan.git", + "reference": "e607609388d3a6d418a50a49f7940e8086798281" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpstan/phpstan/zipball/e607609388d3a6d418a50a49f7940e8086798281", + "reference": "e607609388d3a6d418a50a49f7940e8086798281", + "shasum": "" + }, + "require": { + "php": "^7.2|^8.0" + }, + "conflict": { + "phpstan/phpstan-shim": "*" + }, + "bin": [ + "phpstan", + "phpstan.phar" + ], + "type": "library", + "autoload": { + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "PHPStan - PHP Static Analysis Tool", + "keywords": [ + "dev", + "static analysis" + ], + "support": { + "docs": "https://phpstan.org/user-guide/getting-started", + "forum": "https://github.com/phpstan/phpstan/discussions", + "issues": "https://github.com/phpstan/phpstan/issues", + "security": "https://github.com/phpstan/phpstan/security/policy", + "source": "https://github.com/phpstan/phpstan-src" + }, + "funding": [ + { + "url": "https://github.com/ondrejmirtes", + "type": "github" + }, + { + "url": "https://github.com/phpstan", + "type": "github" + }, + { + "url": "https://tidelift.com/funding/github/packagist/phpstan/phpstan", + "type": "tidelift" + } + ], + "time": "2024-02-20T13:59:13+00:00" + }, { "name": "phpunit/php-code-coverage", "version": "9.2.29", @@ -12895,5 +12957,5 @@ "ext-iconv": "*" }, "platform-dev": [], - "plugin-api-version": "2.3.0" + "plugin-api-version": "2.1.0" } diff --git a/config/services.yaml b/config/services.yaml index 4442d7f5..b170a708 100644 --- a/config/services.yaml +++ b/config/services.yaml @@ -36,6 +36,11 @@ services: # add more service definitions when explicit configuration is needed # please note that last definitions always *replace* previous ones + App\Service\CronService: + arguments: + $cronIPAdress: '%cronIPAdress%' + $cronToken: '%cronToken%' + app.menu.service: class: App\Service\MenuService arguments: [ "@knp_menu.factory" ] diff --git a/phpstan.dist.neon b/phpstan.dist.neon new file mode 100644 index 00000000..73adfad9 --- /dev/null +++ b/phpstan.dist.neon @@ -0,0 +1,8 @@ +parameters: + level: 0 + paths: + - bin/ + - config/ + - public/ + - src/ + - tests/ diff --git a/src/Controller/FormsController.php b/src/Controller/FormsController.php index 880e2cad..fad314ce 100644 --- a/src/Controller/FormsController.php +++ b/src/Controller/FormsController.php @@ -202,7 +202,7 @@ public function editFormulare( $this->em->persist($newForms); $this->em->persist($forms); $this->em->flush(); - $this->addSuccess($this->translator->trans(id: 'save.successful', domain: 'general')); + $this->addSuccessMessage($this->translator->trans(id: 'save.successful', domain: 'general')); return $this->redirectToRoute( 'forms_edit', diff --git a/src/Controller/KursController.php b/src/Controller/KursController.php index cb790203..2b07596c 100644 --- a/src/Controller/KursController.php +++ b/src/Controller/KursController.php @@ -90,7 +90,7 @@ public function editKurs( $team = $currentTeamService->getCurrentTeam($user); $kurs = $academyLessonRepository->find($request->get('id')); - if ($securityService->teamArrayDataCheck($kurs, $team) === false) { + if ($securityService->teamArrayDataCheck($kurs, $team, $user) === false) { return $this->redirectToRoute('akademie_admin'); } @@ -136,7 +136,7 @@ public function kursAnmelden( $team = $currentTeamService->getCurrentTeam($user); $kurs = $academyLessonRepository->find($request->get('id')); - if ($securityService->teamArrayDataCheck($kurs, $team) === false) { + if ($securityService->teamArrayDataCheck($kurs, $team, $user) === false) { return $this->redirectToRoute('akademie_admin'); } @@ -171,7 +171,7 @@ public function kursDeaktivieren( $team = $currentTeamService->getCurrentTeam($user); $kurs = $academyLessonRepository->find($request->get('id')); - if (!$securityService->teamArrayDataCheck($kurs, $team)) { + if (!$securityService->teamArrayDataCheck($kurs, $team, $user)) { return $this->redirectToRoute('akademie_admin'); } diff --git a/src/Controller/LoginController.php b/src/Controller/LoginController.php index 174642ba..a0ddeb1b 100644 --- a/src/Controller/LoginController.php +++ b/src/Controller/LoginController.php @@ -5,6 +5,7 @@ use KnpU\OAuth2ClientBundle\Client\ClientRegistry; use KnpU\OAuth2ClientBundle\Client\Provider\Auth0Client; +use League\OAuth2\Client\Provider\Exception\IdentityProviderException; use Stevenmaguire\OAuth2\Client\Provider\Keycloak; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Response; diff --git a/src/Controller/SoftwareController.php b/src/Controller/SoftwareController.php index e756c1b0..321fd8b7 100644 --- a/src/Controller/SoftwareController.php +++ b/src/Controller/SoftwareController.php @@ -192,7 +192,7 @@ public function deleteConfig( if ($securityService->teamDataCheck($config->getSoftware(), $team) && $securityService->adminCheck($user, $team)) { $this->em->remove($config); $this->em->flush(); - $this->addSuccess($this->translator->trans(id: 'config.delete', domain: 'software')); + $this->addSuccessMessage($this->translator->trans(id: 'config.delete', domain: 'software')); return $this->redirectToRoute( 'software_edit', [ diff --git a/src/Controller/TeamController.php b/src/Controller/TeamController.php index 116d67ee..53bd677a 100644 --- a/src/Controller/TeamController.php +++ b/src/Controller/TeamController.php @@ -123,6 +123,7 @@ public function create( Request $request, SecurityService $securityService, TeamRepository $teamRepository, + CurrentTeamService $currentTeamService, ): Response { $user = $this->getUser(); @@ -157,7 +158,7 @@ public function create( $this->addSuccessMessage($this->translator->trans(id: 'team.created', domain: 'team')); if ($_ENV['APP_DEMO']) { - $teamService->switchToTeam((string) $nTeam->getId()); + $currentTeamService->switchToTeam((string) $nTeam->getId()); return $this->redirectToRoute('dashboard'); } diff --git a/src/Entity/Preset.php b/src/Entity/Preset.php index 1f386a31..22365dee 100644 --- a/src/Entity/Preset.php +++ b/src/Entity/Preset.php @@ -12,6 +12,8 @@ abstract class Preset #[ORM\Column(type: 'boolean')] protected $inherited = false; + protected $ignoredInTeams; + public function isInherited(): bool { return $this->inherited; diff --git a/src/Entity/VVT.php b/src/Entity/VVT.php index 0335a603..6accd7b6 100644 --- a/src/Entity/VVT.php +++ b/src/Entity/VVT.php @@ -524,6 +524,8 @@ public function getActivDsfa() /** * @return Collection|VVTDsfa[] */ + // TODO: Move method into App\Repository\VVTRepository + /* public function getLatestDsfa() { return $this->createQueryBuilder('d') @@ -531,6 +533,7 @@ public function getLatestDsfa() ->getQuery() ->getResult(); } + */ public function getUser(): ?User { diff --git a/src/Repository/FileRepository.php b/src/Repository/FileRepository.php index d76fa060..3d62fd7d 100644 --- a/src/Repository/FileRepository.php +++ b/src/Repository/FileRepository.php @@ -2,9 +2,9 @@ namespace App\Repository; -use App\Entity\File; use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository; use Doctrine\Persistence\ManagerRegistry; +use Symfony\Component\HttpFoundation\File\File; /** * @method File|null find($id, $lockMode = null, $lockVersion = null) diff --git a/src/Repository/VVTDatenkategorieRepository.php b/src/Repository/VVTDatenkategorieRepository.php index 1b27cbcb..874e01bf 100644 --- a/src/Repository/VVTDatenkategorieRepository.php +++ b/src/Repository/VVTDatenkategorieRepository.php @@ -12,7 +12,6 @@ use App\Entity\VVTDatenkategorie; use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository; use Doctrine\Persistence\ManagerRegistry; -use function Doctrine\ORM\QueryBuilder; /** * @method VVTDatenkategorie|null find($id, $lockMode = null, $lockVersion = null) diff --git a/src/Security/KeycloakAuthenticator.php b/src/Security/KeycloakAuthenticator.php index d81f78d4..5257004c 100644 --- a/src/Security/KeycloakAuthenticator.php +++ b/src/Security/KeycloakAuthenticator.php @@ -123,6 +123,7 @@ private function getTeamsFromKeycloakGroups(ResourceOwnerInterface $keycloakUser private function getEmailForKeycloakUser(ResourceOwnerInterface $keycloakUser): string { try { + // FIXME: ResourceOwnerInterface cannot have method getEmail() return $keycloakUser->getEmail(); } catch (\Exception $e) { try { @@ -130,6 +131,8 @@ private function getEmailForKeycloakUser(ResourceOwnerInterface $keycloakUser): } catch (\Exception $e) { } } + + return ''; } private function getRolesForKeycloakUser(ResourceOwnerInterface $keycloakUser): array diff --git a/src/Service/AkademieService.php b/src/Service/AkademieService.php index d9d3f717..6867e2ad 100644 --- a/src/Service/AkademieService.php +++ b/src/Service/AkademieService.php @@ -18,7 +18,7 @@ class AkademieService { - + private EntityManagerInterface $em; private CurrentTeamService $currentTeamService; private NotificationService $notificationService; private Environment $twig; diff --git a/src/Service/AssignService.php b/src/Service/AssignService.php index 08a8816f..2c5cb364 100644 --- a/src/Service/AssignService.php +++ b/src/Service/AssignService.php @@ -29,7 +29,7 @@ class AssignService { - + private EntityManagerInterface $em; private FormFactoryInterface $formBuilder; private NotificationService $notificationService; private Environment $twig; diff --git a/src/Service/CronService.php b/src/Service/CronService.php index d29e1962..202340d7 100644 --- a/src/Service/CronService.php +++ b/src/Service/CronService.php @@ -26,6 +26,8 @@ public function __construct( private TranslatorInterface $translator, private NotificationService $notificationService, private Environment $environment, + private string $cronIPAdress, + private string $cronToken, ) { } @@ -34,7 +36,7 @@ function check($request) { $message = false; - if ($request->get('token') !== $this->getParameter('cronToken')) { + if ($request->get('token') !== $this->cronToken) { $message = [ 'error' => true, @@ -45,7 +47,7 @@ function check($request) $this->logger->error($message['hinweis'], $message); } - if ($this->getParameter('cronIPAdress') !== $request->getClientIp()) { + if ($this->cronIPAdress !== $request->getClientIp()) { $message = [ 'error' => true, 'hinweis' => $this->translator->trans(id: 'cron.ip.unauthorized', domain: 'service'), @@ -71,7 +73,7 @@ public function sendEmailsForAcademy() if (!$buchung->getInvitation()) { $content = $this->environment->render('email/neuerKurs.html.twig', ['buchung' => $buchung, 'team' => $buchung->getUser()->getTeams()->get(0)]); $buchung->setInvitation(true); - $em->persist($buchung); + $this->em->persist($buchung); ++$countNeu; } else { $content = $this->environment->render('email/errinnerungKurs.html.twig', ['buchung' => $buchung, 'team' => $buchung->getUser()->getTeams()->get(0)]); diff --git a/src/Service/SecurityService.php b/src/Service/SecurityService.php index 37dbf375..d3ef599c 100644 --- a/src/Service/SecurityService.php +++ b/src/Service/SecurityService.php @@ -84,7 +84,7 @@ public function superAdminCheck(User $user): bool return false; } - public function teamArrayDataCheck($data, $team): bool + public function teamArrayDataCheck($data, $team, $user): bool { if (!$this->teamCheck($team)) { return false; @@ -96,7 +96,7 @@ public function teamArrayDataCheck($data, $team): bool 'typ' => 'LOGIN', 'error' => true, 'hinweis' => $this->translator->trans(id: 'error.userNotFoundInArray', domain: 'general'), - 'user' => $this->getUser()->getUsername()]; + 'user' => $user->getUsername()]; $this->logger->error($message['typ'], $message); return false; } diff --git a/src/Service/TeamService.php b/src/Service/TeamService.php index 0e340cd7..eb9344a9 100644 --- a/src/Service/TeamService.php +++ b/src/Service/TeamService.php @@ -10,6 +10,7 @@ use App\Entity\AuditTomZiele; +use App\Entity\DatenweitergabeGrundlagen; use App\Entity\DatenweitergabeStand; use App\Entity\Produkte; use App\Entity\Team; @@ -27,7 +28,6 @@ use App\Repository\VVTRisikenRepository; use App\Repository\VVTStatusRepository; use Doctrine\ORM\EntityManagerInterface; -use Proxies\__CG__\App\Entity\DatenweitergabeGrundlagen; use Symfony\Component\Routing\Generator\UrlGeneratorInterface; use Symfony\Contracts\Translation\TranslatorInterface; diff --git a/src/Service/VVTDatenkategorieService.php b/src/Service/VVTDatenkategorieService.php index 0e568244..b223fb92 100644 --- a/src/Service/VVTDatenkategorieService.php +++ b/src/Service/VVTDatenkategorieService.php @@ -88,6 +88,7 @@ function findLatestKategorie(VVTDatenkategorie $VVTDatenkategorie): ?VVTDatenkat $act = $next; } + return null; } function newVVTDatenkategorie(Team $team, User $user) diff --git a/symfony.lock b/symfony.lock index 4329d2e8..879ad102 100644 --- a/symfony.lock +++ b/symfony.lock @@ -219,6 +219,18 @@ "phpstan/phpdoc-parser": { "version": "1.2.0" }, + "phpstan/phpstan": { + "version": "1.10", + "recipe": { + "repo": "github.com/symfony/recipes-contrib", + "branch": "main", + "version": "1.0", + "ref": "5e490cc197fb6bb1ae22e5abbc531ddc633b6767" + }, + "files": [ + "phpstan.dist.neon" + ] + }, "phpunit/php-code-coverage": { "version": "9.2.10" },