src/Controller/DefaultController.php line 46

Open in your IDE?
  1. <?php
  2. namespace App\Controller;
  3. use App\Entity\AssignedBadge;
  4. use App\Entity\Badge;
  5. use App\Entity\CompanyOrder;
  6. use App\Entity\ErrorStamped;
  7. use App\Entity\Operator;
  8. use App\Entity\Stamped;
  9. use App\Form\StampedInOutType;
  10. use App\Form\StampedMensaSacchettoType;
  11. use App\Form\StampedMensaType;
  12. use App\Repository\StampedRepository;
  13. use App\Service\TimbratoreLogger;
  14. use App\Utils\DateTimeUtils;
  15. use Doctrine\Persistence\ManagerRegistry;
  16. use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
  17. use Symfony\Component\Config\Definition\Exception\Exception;
  18. use Symfony\Component\HttpFoundation\JsonResponse;
  19. use Symfony\Component\HttpFoundation\Request;
  20. use Symfony\Component\HttpFoundation\Response;
  21. use Sensio\Bundle\FrameworkExtraBundle\Configuration\IsGranted;
  22. use Symfony\Component\Routing\Annotation\Route;
  23. class DefaultController extends AbstractController
  24. {
  25. private $doctrine;
  26. private $timbratoreLogger;
  27. public function __construct(
  28. ManagerRegistry $doctrine,
  29. TimbratoreLogger $timbratoreLogger
  30. )
  31. {
  32. $this->doctrine = $doctrine;
  33. $this->timbratoreLogger = $timbratoreLogger;
  34. }
  35. /**
  36. * @Route("/", name="home", methods={"GET","POST"})
  37. * @param StampedRepository $stampedRepository
  38. * @return Response
  39. * @throws \Exception
  40. */
  41. public function index(StampedRepository $stampedRepository): Response
  42. {
  43. if ($this->isGranted("ROLE_ADMIN_EMZA")) {
  44. return $this->redirectToRoute('stamped_index', ['page' => '1', 'companyOrderType' => CompanyOrder::TYPE_EMZA]);
  45. } elseif ($this->isGranted("ROLE_ADMIN")) {
  46. return $this->redirectToRoute('stamped_index', ['page' => '1', 'companyOrderType' => CompanyOrder::TYPE_CANTIERE]);
  47. }elseif ($this->isGranted("ROLE_ADMIN_MENSA")) {
  48. return $this->redirectToRoute('stamped_index', ['page' => '1', 'companyOrderType' => CompanyOrder::TYPE_MENSA]);
  49. }elseif ($this->isGranted("ROLE_ADMIN_CANTIERE")) {
  50. return $this->redirectToRoute('stamped_index', ['page' => '1', 'companyOrderType' => CompanyOrder::TYPE_CANTIERE]);
  51. } elseif ($this->isGranted("ROLE_MENSA_ASPORTO")) {
  52. $form = $this->createForm(StampedMensaSacchettoType::class);
  53. $userCompanyOrder = $this->get('security.token_storage')->getToken()->getUser()->getCompanyOrder();
  54. return $this->render('default/home-mensa-sacchetto.html.twig', [
  55. 'form' => $form->createView(),
  56. 'userCompany' => $userCompanyOrder,
  57. ]);
  58. } elseif ($this->isGranted("ROLE_MENSA")) {
  59. $form = $this->createForm(StampedMensaType::class);
  60. $userCompanyOrder = $this->get('security.token_storage')->getToken()->getUser()->getCompanyOrder();
  61. return $this->render('default/home-mensa.html.twig', [
  62. 'form' => $form->createView(),
  63. 'userCompany' => $userCompanyOrder,
  64. ]);
  65. } else {
  66. $form = $this->createForm(StampedInOutType::class);
  67. $userCompanyOrder = $this->get('security.token_storage')->getToken()->getUser()->getCompanyOrder();
  68. return $this->render('default/home.html.twig', [
  69. 'form' => $form->createView(),
  70. 'userCompany' => $userCompanyOrder,
  71. ]);
  72. }
  73. }
  74. /**
  75. * @Route("/ajax/timbra", name="timbra_ajax", methods={"POST"})
  76. * @param Request $request
  77. * @return Response
  78. * @throws \Exception
  79. */
  80. public function timbraAjax(Request $request): Response
  81. {
  82. $datas = $request->request->get('data');
  83. $result = new JsonResponse(['Inizializzo il result'], Response::HTTP_BAD_REQUEST);
  84. $user = $this->getUser();
  85. $userCompanyOrder = $user instanceof User ? $user->getCompanyOrder() : null;
  86. $this->timbratoreLogger->log(
  87. 'stamp_request_received',
  88. 'INFO',
  89. 'Richiesta di timbrata ricevuta dal timbratore.',
  90. [
  91. 'data_type' => is_array($datas) && isset($datas['type']) ? $datas['type'] : 'Cantiere',
  92. 'items' => is_array($datas) ? (isset($datas['type']) ? 1 : count($datas)) : 0,
  93. ],
  94. $request,
  95. $user instanceof User ? $user : null,
  96. $userCompanyOrder
  97. );
  98. try {
  99. if (array_key_exists('type', $datas) && $datas['type'] === 'MensaSacchetto') {
  100. $typeForm = StampedMensaSacchettoType::class;
  101. $data = [
  102. 'stamped_in_out[Badge' => $datas['stamped_mensa_sacchetto[Badge'],
  103. 'stamped_in_out[InOut' => 'in',
  104. 'stamped_in_out[date' => DateTimeUtils::getNow(),
  105. ];
  106. $bagType = $datas['stamped_mensa_sacchetto[BagType'] ?? null;
  107. $result = $this->saveTimbrate($data, $typeForm, 'MensaSacchetto', $bagType, $request);
  108. } elseif (array_key_exists('type', $datas)) {
  109. $typeForm = StampedMensaType::class;
  110. $data = [
  111. 'stamped_in_out[Badge' => $datas['stamped_mensa[Badge'],
  112. 'stamped_in_out[InOut' => $datas['stamped_mensa[InOut'],
  113. 'stamped_in_out[date' => DateTimeUtils::getNow(),
  114. ];
  115. $result = $this->saveTimbrate($data, $typeForm, 'Mensa', null, $request);
  116. } else {
  117. $typeForm = StampedInOutType::class;
  118. foreach ($datas as $data) {
  119. $result = $this->saveTimbrate($data, $typeForm, 'Cantiere', null, $request);
  120. }
  121. }
  122. } catch (\Throwable $ex) {
  123. $this->timbratoreLogger->log(
  124. 'stamp_ajax_exception',
  125. 'ERROR',
  126. $ex->getMessage(),
  127. [
  128. 'exception' => get_class($ex),
  129. 'file' => $ex->getFile(),
  130. 'line' => $ex->getLine(),
  131. ],
  132. $request,
  133. $user instanceof User ? $user : null,
  134. $userCompanyOrder
  135. );
  136. $result = new JsonResponse(['Non ci sono dati da processare'], Response::HTTP_BAD_REQUEST);
  137. }
  138. $this->timbratoreLogger->log(
  139. $result->getStatusCode() >= 400 ? 'stamp_request_failed' : 'stamp_request_completed',
  140. $result->getStatusCode() >= 400 ? 'ERROR' : 'INFO',
  141. 'Elaborazione richiesta timbrata completata.',
  142. ['status' => $result->getStatusCode()],
  143. $request,
  144. $user instanceof User ? $user : null,
  145. $userCompanyOrder
  146. );
  147. return $result;
  148. }
  149. /**
  150. * @Route("/ajax/timbratore-log", name="timbratore_log_ajax", methods={"POST"})
  151. * @IsGranted("ROLE_USER")
  152. */
  153. public function timbratoreLogAjax(Request $request): JsonResponse
  154. {
  155. $user = $this->getUser();
  156. $companyOrder = $user instanceof User ? $user->getCompanyOrder() : null;
  157. $payload = $request->request->all();
  158. if (str_starts_with((string) $request->headers->get('Content-Type'), 'application/json')) {
  159. $raw = $request->getContent();
  160. $decoded = json_decode($raw, true);
  161. if (is_array($decoded)) {
  162. $payload = $decoded;
  163. }
  164. }
  165. $event = isset($payload['event']) ? trim((string) $payload['event']) : '';
  166. $level = isset($payload['level']) ? strtoupper(trim((string) $payload['level'])) : 'INFO';
  167. $message = isset($payload['message']) ? (string) $payload['message'] : null;
  168. $clientId = isset($payload['clientId']) ? (string) $payload['clientId'] : null;
  169. $page = isset($payload['page']) ? (string) $payload['page'] : null;
  170. $context = [];
  171. if (isset($payload['context'])) {
  172. if (is_string($payload['context'])) {
  173. $decodedContext = json_decode($payload['context'], true);
  174. if (is_array($decodedContext)) {
  175. $context = $decodedContext;
  176. }
  177. } elseif (is_array($payload['context'])) {
  178. $context = $payload['context'];
  179. }
  180. }
  181. if ($page !== null) {
  182. $context['page'] = substr($page, 0, 1000);
  183. }
  184. if ($event === '') {
  185. return new JsonResponse(['error' => 'Evento mancante'], Response::HTTP_BAD_REQUEST);
  186. }
  187. $this->timbratoreLogger->log(
  188. $event,
  189. $level,
  190. $message,
  191. $context,
  192. $request,
  193. $user instanceof User ? $user : null,
  194. $companyOrder,
  195. $clientId
  196. );
  197. return new JsonResponse(['ok' => true], Response::HTTP_OK);
  198. }
  199. /**
  200. * Salva una nuova timbrata (entrata o uscita) per un operatore.
  201. *
  202. * FUNZIONAMENTO MULTI-CANTIERE - CHIAVE DEL SISTEMA:
  203. * La timbrata viene associata al cantiere del TIMBRATORE ($userCompanyOrder), NON al cantiere di appartenenza dell'operatore.
  204. * Questo permette ad un operatore registrato su un cantiere di timbrare liberamente su qualsiasi altro timbratore.
  205. *
  206. * FLUSSO OPERATIVO:
  207. * 1. Identifica l'operatore tramite il badge scansionato
  208. * 2. Recupera il cantiere del timbratore corrente ($userCompanyOrder = cantiere dove si trova fisicamente il timbratore)
  209. * 3. Verifica duplicati SOLO per la coppia (operatore + cantiere timbratore) nelle ultime N ore
  210. * - N = 12h per le mense (tipi 'Mensa' e 'MensaSacchetto')
  211. * - N = 4h per il timbratore cantiere (tipo 'Cantiere')
  212. * 4. Salva la timbrata associandola al cantiere del timbratore
  213. *
  214. * ESEMPIO PRATICO MULTI-CANTIERE (finestra default = 4h):
  215. * Operatore "Mario Rossi" registrato su Sovere:
  216. * - Scenario A: Timbra su timbratore di Sovere
  217. * → $userCompanyOrder = Sovere
  218. * → Controllo duplicati su (Mario + Sovere)
  219. * → Timbrata salvata con companyOrder = Sovere
  220. *
  221. * - Scenario B: Timbra su timbratore di Brescia
  222. * → $userCompanyOrder = Brescia
  223. * → Controllo duplicati su (Mario + Brescia) - cantiere diverso, nessun problema!
  224. * → Timbrata salvata con companyOrder = Brescia
  225. *
  226. * - Scenario C: Ritorna su timbratore di Sovere dopo 30 minuti
  227. * → $userCompanyOrder = Sovere
  228. * → Controllo duplicati su (Mario + Sovere) - trova timbrata precedente nella finestra!
  229. * → Timbrata BLOCCATA (duplicato)
  230. *
  231. * LOGICA ANTI-DUPLICATO:
  232. * - Per ENTRATE: chiama getStampedWithinHoursEntry($userCompanyOrder, $operatorId, $duplicateCheckHours)
  233. * - Per USCITE: chiama getStampedWithinHoursRelease($userCompanyOrder, $operatorId, $duplicateCheckHours)
  234. * - Se trova duplicato E operatore non è isMulti → blocca la timbrata
  235. * - Se NON trova duplicato OPPURE operatore è isMulti (mensa) → salva la timbrata
  236. *
  237. * GESTIONE ERRORI:
  238. * - Badge non trovato → salva in ErrorStamped
  239. * - Badge non assegnato → salva in ErrorStamped
  240. * - Form non valido → ritorna errore 400
  241. *
  242. * @param array $data Dati form con badge, tipo timbrata (in/out), data
  243. * @param string $typeForm Tipo form (StampedInOutType, StampedMensaType, StampedMensaSacchettoType)
  244. * @param string $t Tipo timbrata ('Cantiere', 'Mensa', 'MensaSacchetto')
  245. * @return JsonResponse Risposta JSON con esito operazione
  246. * @throws \Exception
  247. */
  248. public function saveTimbrate($data, $typeForm, $t, ?string $bagType = null, ?Request $request = null): JsonResponse
  249. {
  250. $form = $this->createForm($typeForm);
  251. $form->submit($data);
  252. if ($form->isSubmitted() && $form->isValid()) {
  253. $actionForm = $data['stamped_in_out[InOut'];
  254. $badgeForm = $data['stamped_in_out[Badge'];
  255. $entityManager = $this->doctrine->getManager();
  256. // PUNTO CHIAVE MULTI-CANTIERE: il companyOrder è del TIMBRATORE, non dell'operatore
  257. // Questo permette di salvare la timbrata sul cantiere dove si trova fisicamente il timbratore
  258. $user = $this->getUser();
  259. $userCompanyOrder = $user instanceof User ? $user->getCompanyOrder() : null;
  260. $this->timbratoreLogger->log(
  261. 'stamp_processing_started',
  262. 'INFO',
  263. 'Inizio elaborazione timbrata.',
  264. [
  265. 'type' => $t,
  266. 'action' => $data['stamped_in_out[InOut'] ?? null,
  267. 'badge' => $data['stamped_in_out[Badge'] ?? null,
  268. 'bagType' => $bagType,
  269. ],
  270. $request,
  271. $user instanceof User ? $user : null,
  272. $userCompanyOrder
  273. );
  274. // Determina se il timbratore corrente è una Mensa (Type = 2)
  275. $isCurrentOrderMensa = ($userCompanyOrder && $userCompanyOrder->getType() == 2);
  276. // Finestra anti-duplicato: 12h per le mense (Mensa e MensaSacchetto), 4h per il timbratore cantiere
  277. $duplicateCheckHours = ($t === 'Mensa' || $t === 'MensaSacchetto') ? 12 : 4;
  278. $assignedBadgeRepository = $entityManager->getRepository(AssignedBadge::class);
  279. $badgeRepository = $entityManager->getRepository(Badge::class);
  280. $stampedRepository = $entityManager->getRepository(Stamped::class);
  281. $errorStamped = new ErrorStamped();
  282. $errorStamped->setCompanyOrder($userCompanyOrder);
  283. $errorStamped->setCodBadge($badgeForm);
  284. $stamped = new Stamped();
  285. /** @var Badge $badge */
  286. $badge = $badgeRepository->findOneBy(['codBadge' => $badgeForm]);
  287. if (!$badge) {
  288. $this->timbratoreLogger->log(
  289. 'badge_not_found',
  290. 'WARNING',
  291. 'Badge non trovato in archivio.',
  292. ['badge' => $badgeForm, 'action' => $actionForm, 'type' => $t],
  293. $request,
  294. $user instanceof User ? $user : null,
  295. $userCompanyOrder
  296. );
  297. } else {
  298. $this->timbratoreLogger->log(
  299. 'badge_found',
  300. 'DEBUG',
  301. 'Badge trovato in archivio.',
  302. ['badgeId' => $badge->getId(), 'badge' => $badgeForm],
  303. $request,
  304. $user instanceof User ? $user : null,
  305. $userCompanyOrder
  306. );
  307. }
  308. $dataIn = DateTimeUtils::getNow();
  309. $dataOut = DateTimeUtils::getNow();
  310. try {
  311. if (isset($data['stamped_in_out[date']) && $data['stamped_in_out[date']) {
  312. if ($actionForm === 'in') {
  313. $dataIn = $t === 'Cantiere' ? new \DateTime($data['stamped_in_out[date']) : DateTimeUtils::getNow();
  314. } elseif ($actionForm === 'out') {
  315. $dataOut = $t === 'Cantiere' ? new \DateTime($data['stamped_in_out[date']) : DateTimeUtils::getNow();
  316. }
  317. }
  318. } catch (\Throwable $e) {
  319. $this->timbratoreLogger->log(
  320. 'stamp_date_error',
  321. 'ERROR',
  322. 'Errore nella data della timbrata.',
  323. [
  324. 'exception' => get_class($e),
  325. 'error' => $e->getMessage(),
  326. 'action' => $actionForm,
  327. ],
  328. $request,
  329. $user instanceof User ? $user : null,
  330. $userCompanyOrder
  331. );
  332. return new JsonResponse(['Non ci sono settate le date di timbrata'], Response::HTTP_BAD_REQUEST);
  333. }
  334. if ($badge) {
  335. $idBadge = $badge->getId();
  336. /** @var AssignedBadge $assignedBadge */
  337. $assignedBadge = $assignedBadgeRepository->findOneBy(['badge' => $idBadge]);
  338. if ($assignedBadge) {
  339. $operatorBadge = $assignedBadge->getOperator()->getId();
  340. $this->timbratoreLogger->log(
  341. 'badge_assigned',
  342. 'INFO',
  343. 'Badge associato a un operatore.',
  344. [
  345. 'badgeId' => $badge->getId(),
  346. 'operatorId' => $operatorBadge,
  347. 'action' => $actionForm,
  348. ],
  349. $request,
  350. $user instanceof User ? $user : null,
  351. $userCompanyOrder
  352. );
  353. $operatorRepository = $entityManager->getRepository(Operator::class);
  354. /** @var Operator $op */
  355. $op = $operatorRepository->findOneBy(['id' => $operatorBadge]);
  356. if ($actionForm === 'out') {
  357. /** @var Stamped $stamped */
  358. $stamped = $stampedRepository->getStamped($userCompanyOrder, $operatorBadge);
  359. if ($stamped) {
  360. // CONTROLLO DUPLICATI CON NUOVA LOGICA MENSA
  361. $stampedRecent = $stampedRepository->getStampedWithinHoursRelease($userCompanyOrder, $operatorBadge, $duplicateCheckHours, $isCurrentOrderMensa);
  362. if (!$stampedRecent) {
  363. $stamped->setReleaseDate($dataOut);
  364. $this->timbratoreLogger->log(
  365. 'stamp_release_updated',
  366. 'INFO',
  367. 'Uscita associata a una timbrata di entrata esistente.',
  368. [
  369. 'stampedId' => $stamped->getId(),
  370. 'operatorId' => $operatorBadge,
  371. 'action' => $actionForm,
  372. ],
  373. $request,
  374. $user instanceof User ? $user : null,
  375. $userCompanyOrder
  376. );
  377. } else {
  378. $this->timbratoreLogger->log(
  379. 'stamp_release_duplicate_ignored',
  380. 'WARNING',
  381. 'Uscita duplicata ignorata perché esiste già una timbrata recente.',
  382. [
  383. 'stampedId' => $stamped->getId(),
  384. 'operatorId' => $operatorBadge,
  385. 'duplicateCheckHours' => $duplicateCheckHours,
  386. ],
  387. $request,
  388. $user instanceof User ? $user : null,
  389. $userCompanyOrder
  390. );
  391. }
  392. } else {
  393. /** @var Stamped $stampedWithinFourHours */
  394. $stampedWithinFourHours = $stampedRepository->getStampedWithinHoursRelease($userCompanyOrder, $operatorBadge, $duplicateCheckHours, $isCurrentOrderMensa);
  395. if ($stampedWithinFourHours and $op->getIsMulti() === false and $this->isMensaRole()) {
  396. $this->timbratoreLogger->log(
  397. 'duplicate_blocked',
  398. 'WARNING',
  399. 'Timbrata bloccata perché già presente nella finestra anti-duplicato.',
  400. [
  401. 'operatorId' => $operatorBadge,
  402. 'action' => $actionForm,
  403. 'duplicateCheckHours' => $duplicateCheckHours,
  404. ],
  405. $request,
  406. $user instanceof User ? $user : null,
  407. $userCompanyOrder
  408. );
  409. return new JsonResponse(['Non puoi mangiare in mensa piu volte nel giro di poco'], Response::HTTP_BAD_REQUEST);
  410. }
  411. // Crea una nuova timbrata se non esiste duplicato nella finestra $duplicateCheckHours OPPURE se operatore è multi per mensa
  412. if (!$stampedWithinFourHours || ($op->getIsMulti() === true && $this->isMensaRole())) {
  413. $stamped = new Stamped();
  414. $stamped->setCompanyOrder($userCompanyOrder);
  415. $stamped->setOperator($op);
  416. $stamped->setReleaseDate($dataOut);
  417. $stamped->setStatus(Stamped::STATUS_ERROR);
  418. } else {
  419. // Se esiste un duplicato e non è multi, non creiamo un nuovo record
  420. $this->timbratoreLogger->log(
  421. 'stamp_duplicate_ignored',
  422. 'WARNING',
  423. 'Nuova timbrata ignorata perché duplicata.',
  424. [
  425. 'operatorId' => $operatorBadge,
  426. 'action' => $actionForm,
  427. 'duplicateCheckHours' => $duplicateCheckHours,
  428. ],
  429. $request,
  430. $user instanceof User ? $user : null,
  431. $userCompanyOrder
  432. );
  433. $stamped = null;
  434. }
  435. }
  436. } elseif ($actionForm === 'in') {
  437. // CONTROLLO DUPLICATI CON NUOVA LOGICA MENSA
  438. /** @var Stamped $stampedWithinFourHours */
  439. $stampedWithinFourHours = $stampedRepository->getStampedWithinHoursEntry($userCompanyOrder, $operatorBadge, $duplicateCheckHours, $isCurrentOrderMensa);
  440. if ($stampedWithinFourHours and $op->getIsMulti() === false and $this->isMensaRole()) {
  441. $this->timbratoreLogger->log(
  442. 'duplicate_blocked',
  443. 'WARNING',
  444. 'Timbrata bloccata perché già presente nella finestra anti-duplicato.',
  445. [
  446. 'operatorId' => $operatorBadge,
  447. 'action' => $actionForm,
  448. 'duplicateCheckHours' => $duplicateCheckHours,
  449. ],
  450. $request,
  451. $user instanceof User ? $user : null,
  452. $userCompanyOrder
  453. );
  454. return new JsonResponse(['Non puoi mangiare in mensa piu volte nel giro di poco'], Response::HTTP_BAD_REQUEST);
  455. }
  456. // Crea una timbrata se non esiste duplicato nella finestra $duplicateCheckHours OPPURE se operatore è multi per mensa
  457. if (!$stampedWithinFourHours || ($op->getIsMulti() === true && $this->isMensaRole())) {
  458. $stamped->setEntryDate($dataIn);
  459. $stamped->setCompanyOrder($userCompanyOrder);
  460. $stamped->setOperator($op);
  461. if ($this->isMensaRole()) {
  462. $stamped->setReleaseDate($dataIn);
  463. }
  464. } else {
  465. // Se esiste un duplicato e non è multi, non creiamo un nuovo record
  466. $this->timbratoreLogger->log(
  467. 'stamp_duplicate_ignored',
  468. 'WARNING',
  469. 'Nuova timbrata ignorata perché duplicata.',
  470. [
  471. 'operatorId' => $operatorBadge,
  472. 'action' => $actionForm,
  473. 'duplicateCheckHours' => $duplicateCheckHours,
  474. ],
  475. $request,
  476. $user instanceof User ? $user : null,
  477. $userCompanyOrder
  478. );
  479. $stamped = null;
  480. }
  481. }
  482. // Salvo solo se stamped non è null (non è un duplicato)
  483. if ($stamped !== null) {
  484. if ($bagType !== null) {
  485. $stamped->setBagType($bagType);
  486. }
  487. $entityManager->persist($stamped);
  488. $entityManager->flush();
  489. $this->timbratoreLogger->log(
  490. 'stamp_saved',
  491. 'INFO',
  492. 'Timbrata salvata correttamente.',
  493. [
  494. 'stampedId' => $stamped->getId(),
  495. 'operatorId' => $stamped->getOperator() ? $stamped->getOperator()->getId() : null,
  496. 'companyOrderId' => $stamped->getCompanyOrder() ? $stamped->getCompanyOrder()->getId() : null,
  497. 'action' => $actionForm,
  498. 'bagType' => $bagType,
  499. ],
  500. $request,
  501. $user instanceof User ? $user : null,
  502. $userCompanyOrder
  503. );
  504. }
  505. } else {
  506. $this->timbratoreLogger->log(
  507. 'badge_not_assigned',
  508. 'WARNING',
  509. 'Badge trovato ma non assegnato a un operatore.',
  510. ['badgeId' => $badge->getId(), 'badge' => $badgeForm, 'action' => $actionForm],
  511. $request,
  512. $user instanceof User ? $user : null,
  513. $userCompanyOrder
  514. );
  515. $errorStamped->setNBadge($badge->getNBadge());
  516. if ($actionForm === 'out') {
  517. $errorStamped->setReleaseDate($dataOut);
  518. } elseif ($actionForm === 'in') {
  519. $errorStamped->setEntryDate($dataIn);
  520. if ($this->isMensaRole()) {
  521. $this->timbratoreLogger->log(
  522. 'operator_not_registered',
  523. 'WARNING',
  524. 'Operatore non registrato/associato al badge.',
  525. ['badge' => $badgeForm, 'action' => $actionForm],
  526. $request,
  527. $user instanceof User ? $user : null,
  528. $userCompanyOrder
  529. );
  530. return new JsonResponse(['Non sei registrato, richiedere al responsabile l inserimento a sistema'], Response::HTTP_BAD_REQUEST);
  531. }
  532. }
  533. $errorStamped->setType(ErrorStamped::TYPE_ERROR_ASSIGNED);
  534. $entityManager->persist($errorStamped);
  535. $entityManager->flush();
  536. $this->timbratoreLogger->log(
  537. 'error_stamped_saved',
  538. 'WARNING',
  539. 'Errore di timbratura registrato in ErrorStamped.',
  540. [
  541. 'errorType' => $errorStamped->getType(),
  542. 'badge' => $badgeForm,
  543. 'action' => $actionForm,
  544. ],
  545. $request,
  546. $user instanceof User ? $user : null,
  547. $userCompanyOrder
  548. );
  549. }
  550. } else {
  551. if ($actionForm === 'out') {
  552. $errorStamped->setReleaseDate($dataOut);
  553. } elseif ($actionForm === 'in') {
  554. $errorStamped->setEntryDate($dataIn);
  555. if ($this->isMensaRole()) {
  556. $this->timbratoreLogger->log(
  557. 'operator_not_registered',
  558. 'WARNING',
  559. 'Operatore non registrato/associato al badge.',
  560. ['badge' => $badgeForm, 'action' => $actionForm],
  561. $request,
  562. $user instanceof User ? $user : null,
  563. $userCompanyOrder
  564. );
  565. return new JsonResponse(['Non sei registrato, richiedere al responsabile l inserimento a sistema'], Response::HTTP_BAD_REQUEST);
  566. }
  567. }
  568. $errorStamped->setType(ErrorStamped::TYPE_ERROR_ASSIGNED);
  569. $entityManager->persist($errorStamped);
  570. $entityManager->flush();
  571. $this->timbratoreLogger->log(
  572. 'error_stamped_saved',
  573. 'WARNING',
  574. 'Badge non riconosciuto: errore di timbratura registrato.',
  575. [
  576. 'errorType' => $errorStamped->getType(),
  577. 'badge' => $badgeForm,
  578. 'action' => $actionForm,
  579. ],
  580. $request,
  581. $user instanceof User ? $user : null,
  582. $userCompanyOrder
  583. );
  584. }
  585. } else {
  586. $this->timbratoreLogger->log(
  587. 'stamp_form_invalid',
  588. 'ERROR',
  589. 'Il form della timbrata non è valido.',
  590. [
  591. 'type' => $t,
  592. 'formErrors' => (string) $form->getErrors(true),
  593. ],
  594. $request,
  595. $this->getUser() instanceof User ? $this->getUser() : null,
  596. $this->getUser() instanceof User ? $this->getUser()->getCompanyOrder() : null
  597. );
  598. return new JsonResponse(['Il form non è valido contattare l amministratore'], Response::HTTP_BAD_REQUEST);
  599. }
  600. if ($stamped && $badge && $this->isMensaRole() && $stamped->getId()) {
  601. $responseData = [
  602. 'ok',
  603. 'stampedId' => $stamped->getId(),
  604. 'badgeStamped' => $badge->getNBadge(),
  605. 'codOperator' => $stamped->getOperator()->getId(),
  606. 'dataStamped' => $stamped->getCreatedAt() ? $stamped->getCreatedAt()->format('d-m-Y H:i:s') : DateTimeUtils::getNow()->format('d-m-Y H:i:s')
  607. ];
  608. if ($stamped->getBagType() !== null) {
  609. $responseData['bagType'] = $stamped->getBagType();
  610. $responseData['bagTypeLabel'] = Stamped::BAG_TYPE_LABELS[$stamped->getBagType()] ?? $stamped->getBagType();
  611. }
  612. return new JsonResponse($responseData, Response::HTTP_OK);
  613. } else {
  614. return new JsonResponse(['ok'], Response::HTTP_OK);
  615. }
  616. }
  617. /**
  618. * @Route("/delete-multiple-ids", name="delete_multiple_ids", methods={"DELETE"})
  619. * @IsGranted ("ROLE_ADMIN")
  620. *
  621. * @param Request $request
  622. * @return Response
  623. */
  624. public function deleteAjax(Request $request): Response
  625. {
  626. if (!$request->request->get('type')) {
  627. return new JsonResponse(['Error, missing type parameter'], Response::HTTP_BAD_REQUEST);
  628. }
  629. $ids = $request->request->get('ids');
  630. if (!$ids || !is_array($request->request->get('ids'))) {
  631. return new JsonResponse(['Error ids not valid'], Response::HTTP_BAD_REQUEST);
  632. }
  633. switch ($request->request->get('type')) {
  634. case 'stamped':
  635. $result = $this->deleteMultipleIds($ids, Stamped::class);
  636. break;
  637. default:
  638. return new JsonResponse(['Error, this type is not registered'], Response::HTTP_BAD_REQUEST);
  639. }
  640. return $result ? new JsonResponse(['ok'], Response::HTTP_OK) : new JsonResponse(['Error while deleting records'], Response::HTTP_BAD_REQUEST);
  641. }
  642. private function isMensaRole(): bool
  643. {
  644. return $this->isGranted("ROLE_MENSA") || $this->isGranted("ROLE_MENSA_ASPORTO");
  645. }
  646. private function deleteMultipleIds(array $ids, $className)
  647. {
  648. try {
  649. $qb = $this->doctrine->getManager()->createQueryBuilder();
  650. $qb->delete($className, 'e')
  651. ->andWhere('e.id IN (:id)')
  652. ->setParameter('id', $ids);
  653. return $qb->getQuery()->execute();
  654. } catch (Exception $e) {
  655. return false;
  656. }
  657. }
  658. }