Просмотр файла app/Classes/Validator.php

Размер файла: 12.42Kb
  1. <?php
  2.  
  3. declare(strict_types=1);
  4.  
  5. namespace App\Classes;
  6.  
  7. use Egulias\EmailValidator\EmailValidator;
  8. use Egulias\EmailValidator\Validation\RFCValidation;
  9. use Illuminate\Http\UploadedFile;
  10.  
  11. /**
  12. * Class Validation data
  13. *
  14. * @license Code and contributions have MIT License
  15. * @link https://visavi.net
  16. * @author Alexander Grigorev <admin@visavi.net>
  17. */
  18. class Validator
  19. {
  20. /**
  21. * @var array validation errors
  22. */
  23. private $errors = [];
  24.  
  25. /**
  26. * Проверяет длину строки
  27. *
  28. * @param mixed $input
  29. * @param int $min
  30. * @param int $max
  31. * @param mixed $label
  32. * @param bool $required
  33. *
  34. * @return Validator
  35. */
  36. public function length($input, int $min, int $max, $label, bool $required = true): Validator
  37. {
  38. if (! $required && blank($input)) {
  39. return $this;
  40. }
  41.  
  42. $input = (string) $input;
  43.  
  44. if (mb_strlen($input, 'utf-8') < $min) {
  45. $this->addError($label, __('validator.length_min', ['length' => $min]));
  46. } elseif (mb_strlen($input, 'utf-8') > $max) {
  47. $this->addError($label, __('validator.length_max', ['length' => $max]));
  48. }
  49.  
  50. return $this;
  51. }
  52.  
  53. /**
  54. * Проверяет число на вхождение в диапазон
  55. *
  56. * @param int|float $input
  57. * @param int|float $min
  58. * @param int|float $max
  59. * @param mixed $label
  60. *
  61. * @return Validator
  62. */
  63. public function between($input, $min, $max, $label): Validator
  64. {
  65. if ($input < $min || $input > $max) {
  66. $this->addError($label, __('validator.between', ['min' => $min, 'max' => $max]));
  67. }
  68.  
  69. return $this;
  70. }
  71.  
  72. /**
  73. * Проверяет на больше чем число
  74. *
  75. * @param int|float $input
  76. * @param int|float $input2
  77. * @param mixed $label
  78. *
  79. * @return Validator
  80. */
  81. public function gt($input, $input2, $label): Validator
  82. {
  83. if ($input <= $input2) {
  84. $this->addError($label);
  85. }
  86.  
  87. return $this;
  88. }
  89.  
  90. /**
  91. * Проверяет на больше чем или равно
  92. *
  93. * @param int|float $input
  94. * @param int|float $input2
  95. * @param mixed $label
  96. *
  97. * @return Validator
  98. */
  99. public function gte($input, $input2, $label): Validator
  100. {
  101. if ($input < $input2) {
  102. $this->addError($label);
  103. }
  104.  
  105. return $this;
  106. }
  107.  
  108. /**
  109. * Проверяет на меньше чем число
  110. *
  111. * @param int|float $input
  112. * @param int|float $input2
  113. * @param mixed $label
  114. *
  115. * @return Validator
  116. */
  117. public function lt($input, $input2, $label): Validator
  118. {
  119. if ($input >= $input2) {
  120. $this->addError($label);
  121. }
  122.  
  123. return $this;
  124. }
  125.  
  126. /**
  127. * Проверяет на меньше чем или равно
  128. *
  129. * @param int|float $input
  130. * @param int|float $input2
  131. * @param mixed $label
  132. *
  133. * @return Validator
  134. */
  135. public function lte($input, $input2, $label): Validator
  136. {
  137. if ($input > $input2) {
  138. $this->addError($label);
  139. }
  140.  
  141. return $this;
  142. }
  143.  
  144. /**
  145. * Проверяет эквивалентны ли данные
  146. *
  147. * @param mixed $input
  148. * @param mixed $input2
  149. * @param mixed $label
  150. *
  151. * @return Validator
  152. */
  153. public function equal($input, $input2, $label): Validator
  154. {
  155. if ($input !== $input2) {
  156. $this->addError($label);
  157. }
  158.  
  159. return $this;
  160. }
  161.  
  162. /**
  163. * Проверяет не эквивалентны ли данные
  164. *
  165. * @param mixed $input
  166. * @param mixed $input2
  167. * @param mixed $label
  168. *
  169. * @return Validator
  170. */
  171. public function notEqual($input, $input2, $label): Validator
  172. {
  173. if ($input === $input2) {
  174. $this->addError($label);
  175. }
  176.  
  177. return $this;
  178. }
  179.  
  180. /**
  181. * Проверяет пустые ли данные
  182. *
  183. * @param mixed $input
  184. * @param mixed $label
  185. *
  186. * @return Validator
  187. */
  188. public function empty($input, $label): Validator
  189. {
  190. if (! empty($input)) {
  191. $this->addError($label);
  192. }
  193.  
  194. return $this;
  195. }
  196.  
  197. /**
  198. * Проверяет не пустые ли данные
  199. *
  200. * @param mixed $input
  201. * @param mixed $label
  202. *
  203. * @return Validator
  204. */
  205. public function notEmpty($input, $label): Validator
  206. {
  207. if (empty($input)) {
  208. $this->addError($label);
  209. }
  210.  
  211. return $this;
  212. }
  213.  
  214. /**
  215. * Проверяет на true
  216. *
  217. * @param mixed $input
  218. * @param mixed $label
  219. *
  220. * @return Validator
  221. */
  222. public function true($input, $label): Validator
  223. {
  224. if (filter_var($input, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) === false) {
  225. $this->addError($label);
  226. }
  227.  
  228. return $this;
  229. }
  230.  
  231. /**
  232. * Проверяет на false
  233. *
  234. * @param mixed $input
  235. * @param mixed $label
  236. *
  237. * @return Validator
  238. */
  239. public function false($input, $label): Validator
  240. {
  241. if (filter_var($input, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) !== false) {
  242. $this->addError($label);
  243. }
  244.  
  245. return $this;
  246. }
  247.  
  248. /**
  249. * Проверяет на вхождение в массив
  250. *
  251. * @param mixed $input
  252. * @param array $haystack
  253. * @param mixed $label
  254. *
  255. * @return Validator
  256. */
  257. public function in($input, array $haystack, $label): Validator
  258. {
  259. if (! is_array($haystack) || ! in_array($input, $haystack, true)) {
  260. $this->addError($label);
  261. }
  262.  
  263. return $this;
  264. }
  265.  
  266. /**
  267. * Проверяет на не вхождение в массив
  268. *
  269. * @param mixed $input
  270. * @param array $haystack
  271. * @param mixed $label
  272. *
  273. * @return Validator
  274. */
  275. public function notIn($input, array $haystack, $label): Validator
  276. {
  277. if (! is_array($haystack) || in_array($input, $haystack, true)) {
  278. $this->addError($label);
  279. }
  280.  
  281. return $this;
  282. }
  283.  
  284. /**
  285. * Проверяет по регулярному выражению
  286. *
  287. * @param mixed $input
  288. * @param string $pattern
  289. * @param mixed $label
  290. * @param bool $required
  291. *
  292. * @return Validator
  293. */
  294. public function regex($input, string $pattern, $label, bool $required = true): Validator
  295. {
  296. if (! $required && blank($input)) {
  297. return $this;
  298. }
  299.  
  300. if (! preg_match($pattern, $input)) {
  301. $this->addError($label);
  302. }
  303.  
  304. return $this;
  305. }
  306.  
  307. /**
  308. * Check float
  309. *
  310. * @param mixed $input
  311. * @param mixed $label
  312. * @param bool $required
  313. *
  314. * @return Validator
  315. */
  316. public function float($input, $label, bool $required = true): Validator
  317. {
  318. if (! $required && blank($input)) {
  319. return $this;
  320. }
  321.  
  322. if (! is_float($input)) {
  323. $this->addError($label);
  324. }
  325.  
  326. return $this;
  327. }
  328.  
  329. /**
  330. * Проверяет адрес сайта
  331. *
  332. * @param mixed $input
  333. * @param mixed $label
  334. * @param bool $required
  335. *
  336. * @return Validator
  337. */
  338. public function url($input, $label, bool $required = true): Validator
  339. {
  340. if (! $required && blank($input)) {
  341. return $this;
  342. }
  343.  
  344. if (! preg_match('|^https?://([а-яa-z0-9_\-\.])+(\.([а-яa-z0-9\/\-?_=#])+)+$|iu', $input)) {
  345. $this->addError($label);
  346. }
  347.  
  348. return $this;
  349. }
  350.  
  351. /**
  352. * Проверяет email
  353. *
  354. * @param mixed $input
  355. * @param mixed $label
  356. * @param bool $required
  357. *
  358. * @return Validator
  359. */
  360. public function email($input, $label, bool $required = true): Validator
  361. {
  362. if (! $required && blank($input)) {
  363. return $this;
  364. }
  365.  
  366. $validator = new EmailValidator();
  367. $checkEmail = $validator->isValid((string) $input, new RFCValidation());
  368.  
  369. if (! $checkEmail || filter_var($input, FILTER_VALIDATE_EMAIL) === false) {
  370. $this->addError($label);
  371. }
  372.  
  373. return $this;
  374. }
  375.  
  376. /**
  377. * Check IP address
  378. *
  379. * @param mixed $input
  380. * @param mixed $label
  381. * @param bool $required
  382. *
  383. * @return Validator
  384. */
  385. public function ip($input, $label, bool $required = true): Validator
  386. {
  387. if (! $required && blank($input)) {
  388. return $this;
  389. }
  390.  
  391. if (filter_var($input, FILTER_VALIDATE_IP) === false) {
  392. $this->addError($label);
  393. }
  394.  
  395. return $this;
  396. }
  397.  
  398. /**
  399. * Check phone
  400. *
  401. * @param mixed $input
  402. * @param mixed $label
  403. * @param bool $required
  404. *
  405. * @return Validator
  406. */
  407. public function phone($input, $label, bool $required = true): Validator
  408. {
  409. if (! $required && blank($input)) {
  410. return $this;
  411. }
  412.  
  413. if (! preg_match('#^\d{8,13}$#', $input)) {
  414. $this->addError($label);
  415. }
  416.  
  417. return $this;
  418. }
  419.  
  420. /**
  421. * Проверяет файл
  422. *
  423. * @param UploadedFile|null $input
  424. * @param array $rules
  425. * @param mixed $label
  426. * @param bool $required
  427. *
  428. * @return Validator
  429. */
  430. public function file(?UploadedFile $input, array $rules, $label, bool $required = true): Validator
  431. {
  432. if (! $required && blank($input)) {
  433. return $this;
  434. }
  435.  
  436. if (! $input instanceof UploadedFile) {
  437. $this->addError($label);
  438. return $this;
  439. }
  440.  
  441. if (! $input->isValid()) {
  442. $this->addError($input->getErrorMessage());
  443. return $this;
  444. }
  445.  
  446. $key = is_array($label) ? key($label) : 0;
  447.  
  448. if (empty($rules['extensions'])) {
  449. $rules['extensions'] = ['jpg', 'jpeg', 'gif', 'png'];
  450. }
  451.  
  452. $extension = strtolower($input->getClientOriginalExtension());
  453.  
  454. if (! in_array($extension, $rules['extensions'], true)) {
  455. $this->addError([$key => __('validator.extension')]);
  456. }
  457.  
  458. if (isset($rules['maxsize']) && $input->getSize() > $rules['maxsize']) {
  459. $this->addError([$key => __('validator.size_max', ['size' => formatSize($rules['maxsize'])])]);
  460. }
  461.  
  462. if (in_array($extension, ['jpg', 'jpeg', 'gif', 'png'], true)) {
  463. [$width, $height] = getimagesize($input->getPathname());
  464.  
  465. if (isset($rules['maxweight'])) {
  466. if ($width > $rules['maxweight'] || $height > $rules['maxweight']) {
  467. $this->addError([$key => __('validator.weight_max', ['weight' => $rules['maxweight']])]);
  468. }
  469. }
  470.  
  471. if (isset($rules['minweight'])) {
  472. if ($width < $rules['minweight'] || $height < $rules['minweight']) {
  473. $this->addError([$key => __('validator.weight_min', ['weight' => $rules['minweight']])]);
  474. }
  475. } elseif (empty($width) || empty($height)) {
  476. $this->addError([$key => __('validator.weight_empty')]);
  477. }
  478. }
  479.  
  480. return $this;
  481. }
  482.  
  483. /**
  484. * Добавляет ошибки в массив
  485. *
  486. * @param mixed $error текст ошибки
  487. * @param string|null $description
  488. *
  489. * @return void
  490. */
  491. public function addError($error, ?string $description = null): void
  492. {
  493. $key = 0;
  494.  
  495. if (is_array($error)) {
  496. $key = key($error);
  497. $error = current($error);
  498. }
  499.  
  500. if (isset($this->errors[$key])) {
  501. $this->errors[] = trim($error . ' ' . $description);
  502. } else {
  503. $this->errors[$key] = trim($error . ' ' . $description);
  504. }
  505. }
  506.  
  507. /**
  508. * Возвращает список ошибок
  509. *
  510. * @return array
  511. */
  512. public function getErrors(): array
  513. {
  514. return $this->errors;
  515. }
  516.  
  517. /**
  518. * Очищает список ошибок
  519. *
  520. * @return void
  521. */
  522. public function clearErrors(): void
  523. {
  524. $this->errors = [];
  525. }
  526.  
  527. /**
  528. * Возвращает успешность валидации
  529. *
  530. * @return bool
  531. */
  532. public function isValid(): bool
  533. {
  534. return empty($this->errors);
  535. }
  536. }