Предлагаем вашему вниманию очередную подборку со ссылками на новости и материалы.
Приятного чтения!
Новости и релизы
- WordPress 4.7.2 — Обновление примечательно тем, что в нем без огласки была устранена критическая уязвимость, позволяющая удалённому атакующему без аутентификации изменить содержимое любой страницы через манипуляцию с REST API.
Несмотря на то что уязвимости подвержены только WordPress версий 4.7.0 и 4.7.1, по интернету прокатилась волна автоматизированных атак. Взлому уже подверглись более 1,5 миллиона ресурсов. - PhpStorm 2017.1 EAP 171.3019 — В свежей EAP версии добавлена поддержка Codeception.
- Go! AOP Framework 2.1.0 — В релизе поддержка PHP 7.1 и несколько новых возможностей.
- PHPUnit 6.0.0 — Данный релиз требует PHP версии не ниже 7.0, также для большинства классов теперь используются пространства имен вместо префиксов. Полный список изменений тут. Небольшой туториал по миграции.
- Релиз LiveStreet 2.0
- Yii 2.0.11
PHP
- RFC: Make Libsodium a Core Extension — Предложение включить криптографическую библиотеку Libsodium в ядро успешно прошло голосование и будет реализовано уже в PHP 7.2. Сообщество также проголосовало за использование префиксного синтаксиса
sodium_*
вместо пространства имен\Sodium\*
. Тем не менее уже доступна обертка firehed/sodium для использования функций через пространство имен. Нельзя не отметить иронию автора.
- RFC: Arrow Functions — Четвертая попытка добавить короткий синтаксис для анонимных функций в PHP.
Первое предложение с конструкцией вида:$x ~> $x + $y
не прошло голосование. Затем был предложен альтернативный синтаксис:function($x) => $x + $y
. Дальше выносился на рассмотрение синтаксис:^($x) => $x + $y
. На этот раз предлагается использоватьfn(parameter_list) => expr
:
function ($x) use ($y) { return $x + $y; } // Эквивалентно: fn($x) => $x + $y
Кстати, инструмент 3v4l.org позволяет протестировать код на RFC, для которых существует ветка с реализацией, в частности, для Arrow Functions.
Инструменты
- wapmorgan/Morphos — Морфологическое решение на PHP для русского языка: склонение имен и существительных, плюрализация, количественные числительные.
- wapmorgan/BinaryStream — Библиотека для удобного чтения бинарных файлов.
- 1ma/RedisSessionHandler — Обработчик сессии для Redis, в котором по сравнению со встроенным в phpredis исправлены ошибка блокировки и реализована защита от фиксации сессии.
- peridot-php/peridot — BDD-фреймворк для тестирования. Туториал по использованию. Имеется плагин для параллельного запуска тестов peridot-php/peridot-concurrency.
- ericmann/sessionz — Альтернативный менеджер сессий. Видеотуториал.
- tommy-muehle/php-composer-plugin-devenv — Дев-окружение для разработки плагинов для Composer и пост от автора в поддержку.
- maghead/maghead — ORM для PHP 7 с кодогенерацией и другими фишками. Судя по бенчмарку, довольно быстрая.
- wizaplace/github-to-mysql — Скрипт для синхронизации данных из GitHub (issues, labels, ...) в MySQL.
- maennchen/ZipStream-PHP — Библиотека позволяет создавать zip-архив на лету и писать в поток. Пост в поддержку.
- patrickschur/language-detection — Библиотека для определения языка по заданной строке.
- SocialConnect/auth — Библиотека для аутентификации через соц. сервисы (OAuth1/2, OpenID, OpenIDConnect). 20+ провайдеров из коробки (VK, FB, G+, Twitter, Steam и т.д.).
Материалы для обучения
PHP 7
- PHP’s not dead! — О миграции на PHP 7 в OLX.
- Путеводитель по нововведениям PHP 7.0 и 7.1
Symfony
- mnapoli/fluent-symfony — Конфигурация DI-контейнера с текучим интерфейсом.
- wallabag/wallabag — Read-it-later (Pocket, Readability, Instapaper) сервис на базе Symfony. Доступен также код приложений на iOS, Android, и расширения для Chrome.
- gpslab/geoip2 — Symfony Bundle для Maxmind GeoIP2 API. Прислал ghost404.
- Symfony Demo 1.0.0 — Официальное приложение на Symfony с демонстрацией лучших практик.
- В Symfony 3.3 будет реализован стандарт PSR-11 для контейнеров — Голосование по стандарту PSR-11 подходит к концу и с большой вероятностью пройдет успешно.
- Неделя Symfony #527 (30 января — 5 февраля 2017)
- Неделя Symfony #528 (6-12 февраля 2017)
Yii
- Yii2 Inspections for IntelliJ IDEA (PhpStorm) 1.0.0
- craftcms/cms — CMS на основе Yii 2.
Laravel
- 13 генераторов админок для Laravel
- Масштабирование Laravel с помощью AWS Elastic Beanstalk
- Laracon Online — Анонсирована онлайн-конференция по Laravel, которая пройдет 8 марта.
- Криптографически безопасная разработка на PHP
- Приведение типов и внедрение объекта — О том, почему небезопасно использовать
unserialize()
с пользовательскими данными на примере исследования ExpressionEngine. - Awesome Composer — Подборка материалов, плагинов, и полезных ресурсов по Composer.
- Как сделать PHP еще более современным? С помощью препроцессинга! — preprocess.io — под капотом используется уже известный marcioAlmada/yay.
- Туториал по работе с Reddit API
- Короткое введение в TypeScript для PHP-разработчиков
- Вводный туториал по использованию RabbitMQ
- Запускаем PHPUnit тесты внутри Docker-контейнера из PhpStorm
- Пагинация коллекций данных с помощью zend-paginator
- Об ответах с ошибками API в PSR-7
- Заметка об использовании констант в PHP-приложении
- Введение в проектирование сущностей, проблемы создания объектов
- Tarantool: Хороший, Плохой, Злой
- Как создать Viber-бота с помощью PHP
- Отчет и материалы конференции MageConf 2016
Занимательное
- Немного истории PHP — Расмус Лердорф опубликовал changelog ранних версий PHP 1.90 — 2.0.1.
- hannob/php-crashers — Примеры скриптов, которые вызывают segfault в PHP
- Рейтинг e-commerce платформ с открытым исходным кодом
- XSS game — Мини-игра от Google для тренировки навыков поиска XSS-уязвимостей.
Спасибо за внимание!
Если вы заметили ошибку или неточность — сообщите, пожалуйста, в личку.
Вопросы и предложения пишите на почту или в твиттер.
Прислать ссылку
Быстрый поиск по всем дайджестам
< Предыдущий выпуск: PHP-Дайджест № 101
Комментарии (62)
vshemarov
13.02.2017 09:16+1Немного удивляет упорство людей, которые так настойчиво пытаются внедрить короткий синтаксис. Прям какая-то «битва за сахар»
ellrion
13.02.2017 10:25+1удивляет нежелание его принимать. Последнее время ананимок в коде очень много. И код бы стал гораздо приятнее.
Fesor
13.02.2017 10:59+1Сейчас напоролись на то что ключевое слово
fn
не хотят вводить (есть жеfunction
уже). Ну и в целом будет нарушение обратной совместимости. Потому обсуждается альтернативый вариант синтаксиса:
$fn = |$x| => $x * 2; array_reduce($arr, |$str, $chunk| => $str . $chunk, '');
ellrion
13.02.2017 11:05по мне так
fn
выглядит самым приятным и логичным из 4 вариантов (5 если считать еще и|
). Как раз сокращенноеfunction
.Fesor
13.02.2017 11:19оно всем нравится, но если у вас в коде есть функция с именем
fn
то при обновлении все сломается, чего нельзя делать до выхода 8-ой версии. Потому возможный компромис это|$x| => $x
.
LastDragon
13.02.2017 11:05+2мдя… чем, интересно, широкоиспользуемый
() => $x * 2;
не нравится? (парсер же вроде нормальный уже?)Fesor
13.02.2017 11:23+3(парсер же вроде нормальный уже?)
Да, нормальный LR(1) парсер. Что значит единичка? Это означает что дальше чем на одину лексему вперед вам видеть не дают. То есть вы должны понимать является ли выражение лямбдой либо с самого первого токена либо на один токен вперед.
С выражениями типа
$x => $x * 2
проблема заключается в том, что=>
используется в разных контекстах и с такой записью невозможно точно определить что это за выражение не разобрав его до конца. Ну и в целом остаются конфликты сyield $key => $value
. Потому без ключевого слова или специального символа в начале лямбды не обойтись.
Если что в python например ввели ключевое слово
lambda
, в ruby у нас примерно такой же вариант как предлагают в php:|x| => x * 2
ну и т.д.
franzose
14.02.2017 14:35И вы, кажется, даже в слове «анонимок» не сделали ошибки в контексте данного случая...)
TrogWarZ
13.02.2017 12:25Я, например, жду и буду настойчиво рад когда в языке всё-таки будет определён этот сахар. Многие вещи проще сделать через анонимные функции (лениво впилить ленивость, например).
И дело не в том, что писать на сколько-то символов больше (автокомплит IDE нивелирует), а в том, что текущий синтаксис сильно «шумит» – у меня бывает, что «накладные символы» по длине такие же как полезное действие в функции, – такое сложно распарсить глазами и понять.
Да и IDE обычно фолдит такие вещи – приходится кликать в однострочники чтобы посмотреть что они делают что-то похожее на array_column, только для объектов или считают среднее арифметическое по аттрибуту из коллекции. С коротким синтаксисом это распознаётся глазом гораздо быстрее. По крайней мере, лично моим – точно быстрее.gro
13.02.2017 12:51Текущий синтаксис шумит, новый будет сливаться.
Вон, JS со стрелочными функциями последнее время всё больше на brainfuck похоже становится.Fesor
13.02.2017 13:17новый будет сливаться.
как напишите так и будет. Не спроста в текущих RFC не предлагается поддержки нескольких выражений на лямбду. Это слегка противоречит идее "функциональных выражений". Так что сливать не должно.
JS со стрелочными функциями последнее время всё больше на brainfuck похоже становится.
Да нет, как раз таки все хорошо. Бывает что разработчики злоупотребляют но… в среднем выходит читаемо.
Fesor
13.02.2017 13:16+1пока не ввели какой-то синтаксис для лямбд и вы работаете в продуктах Jetbrains можно этим пользоваться: https://github.com/vkurdin/idea-php-lambda-folding
Anexroid
13.02.2017 14:22+2hannob/php-crashers — Примеры скриптов, которые вызывают segfault в PHP
Неверно, там всё таки примеры не с segfault в классическом его понимании, а банальная бесконечная рекурсия, таких примеров можно миллион сделать.
saggid
Большое спасибо за дайджест)
Кому-то жить не хочется, если он не ощущает себя
важной жопойпишущим качественный ООП-код?)igordata
saggid
Очень много всяких вещей в программировании программисты делают без реального обоснования с точки зрения пользы для программного кода.
Найс фингс — это ложить все функции в свои неймспейсы? Может вообще удалить функции и оставить только их ооп-вариации? Чтобы совсем как у взрослых было?
И чем лучше от этого станет код? Тем что объектов станет больше? Тем что use-директив в начале файла добавится?
Удивительно, как часто программисты любят называть "клевыми штуками" пустые с рациональной точки зрения вещи.
Глобальные функции просты и очень удобны в использовании. Я очень рад, что они есть в php, и сам часто расширяю код проекта своими собственными функциями. Выглядит красиво, работается удобно, понимается легко. Разве не к этому надо стремиться при написании большого проекта?
Fesor
Мне нравится идея. что в начале файла есть эдакие "импорты" других модулей, и можно быстро увидеть зависимости кода. Позволяют за несколько секунд понять насколько все хорошо или плохо.
нэймспейсы лишь позволяют прибраться в глобальной области видимости, функции как были глобально доступными так и остаются. Не понимаю почему вы так завелись.
выглядит некрасиво. работается удобно до какого-то момента, в целом же в вашем коде просто увеличивается количество шума. И если проект большой, то это будет сильно влиять на читаемость кода, и как следствие, поддерживать такой код будет чуть-чуть да дороже.
saggid
У нас довольно большой проект, разбитый на модули. Даже в этом случае я пока не вижу необходимости раскладывать функции каждого модуля в свой неймспейс. Хотя возможно в будущем будет смысл, да. Так как мы и префиксы для названий функций не используем.
saggid
Приведу несколько примеров кода нашего проекта. Скажем, есть у нас модель текстовых данных одного объекта. И вот там есть вот такой метод:
Как видим, здесь вызывается функция. Она парсит строку и возвращает нужный HTML код. Разве не просто и красиво?
Или вот ещё пример, метод класса лекции в нашем проекте:
Как видим, тут используется функция link_to_lesson. Она генерирует ссылку на блок контента лекции определённого курса. Эта функция используется в том числе в шаблонах проекта, а также в прочих PHP классах, например в генераторе карт сайтов… В общем, одна функция — используется везде, где нужно. Разве не удобно?
Или вот ещё один очень простой хелпер в модели пользователя, тут вообще всё просто:
Ну и напоследок — метод в классе авторизации для создания нового пользователя для проекта, который тоже использует по большей части функции:
gro
Несомненно, все здесь присутствующие, в восторге от ваших успехов.
saggid
Я не имею права показать и доказать свою точку зрения на практических примерах из своего реального проекта?
Fesor
Вам код ревью сделать и описать проблемы?
saggid
Да я вроде и сам вполне нормально могу работать с проектами. И сам занимаюсь код ревью. Проблемы, что тут вы пишете — они больше из пальца высосаны, и реальной проблемы не составляют. Я это уже обсуждал в своей отдельной статье на хабре с людьми. Да, если есть желание — можете подключаться к тем обсуждениям. Только пожалуйста прочитайте сначала мои разъяснения, чтобы не проходиться повторно по одним и тем же темам.
Fesor
Если вы не пишите тестов — то да, согласен. В целом это все проблемы людей которые не хотят тратить деньги на ручное тестирование.
p.s. Если что меня не напрягают функции как таковые, меня напрягают
event
,current_user
иsend_email_to_user
. К примеру у меня нотификации отправляются так:Профит — легко тестировать, легко поддерживать, разделение ответственности, нет волшебных строковых констант в коде, легко рефакторить, большая часть тупых багов выявляется статическим анализом.
saggid
На самом деле тестируется все это без проблем, и мы пишем тесты в проекте, правда на столь активно.
И пара функций здесь вообще из ларавел взяты, они есть из коробки: event и session. Ларавел тоже вроде покрыт тестами.
Тупые баги тоже вроде находятся без проблем) я только не понял что за статический анализатор.
bohdan4ik
Узнаю laravel. Там много всяких штуковин, вроде
event
,session
,Auth::user()
,DB::table('smth')->insert()
. Снаружи выглядит весьма сурово, но это всё фасады на магии __callStatic. Внутри работает service locator и dependency injection (если есть желание — можно использовать только DI, без магических геттеров).event:
https://github.com/laravel/framework/blob/5.4/src/Illuminate/Foundation/helpers.php#L477
app:
https://github.com/laravel/framework/blob/5.4/src/Illuminate/Foundation/helpers.php#L99
Нотификации, путь слабых:
Нотификации, ваш путь (здесь могу ошибиться с выбором внедряемого класса, только начинаю осваивать laravel):
P.S.: ура, markdown разметка для отхабренных! :)
saggid
в этом же и дело. первый вариант — не путь слабых. а самый короткий путь.
практической разницы вообще никакой между этими двумя вариантами
ellrion
собственно вы и показали что используете префиксы:
ace_editor_
,send_email_
saggid
Это не префиксы :) Префиксы тогда должны быть например так:
strings_ace_editor_parse
. То есть, функция из ядра проекта, отвечающая за работу со строками.Или
education_link_to_lesson
. То есть, функция из модуля интерактивных уроков.Но лучше тут конечно неймспейсы наверное сделать всё-таки, если что-то делать. Просто красивее выйдет в итоге для нашего проекта, как мне кажется. А что насчёт ядра PHP — то там как-то они всё равно очень логично всё делают, даже без неймспейсов.
Fesor
вообще-то нет. У вас префикс —
ace_editor
— определяет к какому модулю они принадлежат.Да, выйдет что-то типа
saggid
Всё-таки не так на самом деле. Для этого ейс эдитора всего одна функция в проекте. И она лежит среди других функций для работы со строками.
Поэтому я и говорил о том, что в нашем проекте если неймспейсы делать функциям, то можно сделать например… вот так, чтоли:
Но в данный момент я лично не ощущаю в этом нужды. И так всё вполне красиво и удобно.
Fesor
Вот вы в своем коде указали что используете функцию
bcrypt
. Вместо нее стоило бы использовать абстракцию —password_hash
. Заметте то обе эти функции не будут лежать в нэймспейсеstring
так как то что они используют строки в качестве значений, это не основная цель. Точно так же и вашace_editor_parse
— его задача не просто со строками работать, а парсить с какой-то целью (скорее всего что-то связанное с ace_editor). Ну и исходя из этого и надо дробить на модули.saggid
Это хелпер Laravel, идущий из коробки. Я его использую просто потому что во фреймворке это считается правильным кодом. Можно конечно и об абстракции было подумать.
С остальным согласен, оно немного не до конца хорошо раскидано) но опять же. Работе сильно не мешает. Как-нибудь может немного наведу там порядок просто, раскидаю функции по более корректным папкам)
Fesor
эх… ох уж этот глобальный доступ к зависимостям...
Metus
Я не очень люблю критиковать чужой код, да и Вам вряд ли это понравится, но раз уж Вы его выложили, то, думаю, имею право высказаться.
Если я вижу такое у кого-то из коллег, то требую переписать.
У вас current_user() как определяется? Я полагаю, берётся из сессии, кук, заголовка — это всё накроется медным тазом, когда захочется вызвать данный код из консоли.
Почему данные HTTP-запроса (или хз вообще какого запроса — тут не ясно) протекают в модель, которая вообще не должна быть привязана ни к какому интерфейсу взаимодействия с приложением? И как это тестировать?
Тут я вообще не понял, такое ощущение, что прикрутили события после того как сделали отправку писем, но забыли сделать рефакторинг. Если у вас идёт вызов двух функций, от которых тем более не требуется ответ, почему нельзя их же обработать через этот event?
И останется только:
И я ничего не говорю про то, что ваш код абсолютно не модулен и попытка использовать его без изменений вне рамок первоначального плана практически невозможна, как и тестирование. Это лапша.
saggid
Ну что вы сразу обидными словами кидаетесь) Всё прекрасно тестируется, не стоит торопиться с выводами.
Не накроется, не беспокойтесь. Функция
current_user()
— это просто удобная обёртка над основным синглтон-классом авторизации Laravel:Класс
Auth
, в котором вызывается статический метод, тоже без всяких проблем тестируется: потому что это фасад Laravel, и он тоже идёт из коробки во фреймворке.В тестах у нас пишется вот такой код:
$this->actingAs($user)
— стандартная функция из набора инструментов Laravel для тестирования проекта. Ну и да… оно вызывается из консоли.Я не особо согласен с этим. Не обязательно ведь теперь засовывать в реакцию на эвент вообще всю логику создания пользователя. Просто есть основные действия при создании пользователя, которые являются ядром проекта, и есть некоторые дополнительные, которые выполняются модулями проекта. Поэтому для модулей и был сделан эвент.
Metus
Вы правда не видите проблем в том, что модель напрямую обращается к параметрам запроса?
saggid
Чтобы я увидел реальную проблему, опишите пожалуйста ситуацию, когда это будет мешать нормальной работе проекта. Только не какие-то абстрактные идеи и предположения, пожалуйста. Какой-то конкретный юз-кейс.
Потому что это вот и есть основная проблема многих программистов: они берут какую-то теоретическую некорректность и начинают учить других писать код, основываясь на неё. В общем-то, изначально я про это и писал, в самом первом своём комментарии к этому посту.
Metus
Проблема в том, что с одной и той же моделью можно работать разными способами — запросы будут разные.
Сейчас она обращается к сессии.
Потом понадобилось сделать консольную команду (не тест), чтобы сделать что-нибудь с пользователями. Как в данном случае будет работать Auth::user()? Как сделать пользователя авторизованным?
saggid
Не понял проблему. Опишите пожалуйста более конкретную ситуацию.
Да не к сессии эта функция обращается) А к синглтон-сервису в ларавел фреймворке, я ведь написал)
Указать, какой пользователь в данный момент авторизован — очень просто. Вам поможет любой из методов, описанных в официальной документации к Laravel.
Соответственно, сервис будет возвращать того пользователя, которого вы указали в качестве авторизованного.
Metus
Синглтон сервис в ларавеле по умолчанию обращается к сессии.
Если сервис зависит от абстрактной сессии (в данный момент это просто HTTP-сессия), то модель, зависящая от этого сервиса зависит и от сессии.
Так что именно к сессии она и обращается (хоть и не напрямую).
И да, можно сделать так
И всё это будет работать. Но это будет понятно только тому, кто изначально писал этот код.
saggid
Всё-таки, снова слона из мухи раздуваете.
Я честно не вижу здесь чего-то сложного и плохого. Стандартный сервис авторизации вы можете расширить своим собственным классом и реализовать там такую логику, какая будет нужна лично вам. Этим и прекрасна архитектура Laravel: при наличии нормальных мозгов, вы можете без особых проблем переписать и расширить логику работы фреймворка.
Metus
Сервис авторизации стандартный, но использование его нестандартное.
Есть объект $user.
Человек видит в нём метод isCurrentUser. Без копания в коде (а в идеале нужно смотреть только на сигнатуру метода) не понятно как заставить его работать, и будет ли он работать вообще без дополнительных манипуляций.
Что делать разработчику?
Всё это неясно. Именно в этом проблема таких неявных и при этом жёстких зависимостей.
Объект должен быть максимально самодостаточным и его зависимости должны быть явными. Если этого нет — его просто неудобно использовать.
saggid
Ну у вас опять начинается теоретика. Я ведь просил без неё.
В ларавел не зря есть понятие сервис-провайдеров, а также двух этапов их инициализации: регистрация и загрузка.
Уже после этого будет запущен различный код вашего приложения. Будь то консольная команда, будь то ваше API, или же самый обычный GET-запрос на вебсайт.
Если вы будете отталкиваться от архитектуры фреймворка, у вас не будет возникать этих вопросов, которые вы сейчас задаёте. Да, надо знать немного больше. Да, это выходит за рамки каких-то типичных абстрактных Единственно Истинных правил написания ПО. Если для вас критично им следовать — то я могу только сказать, что это просто ошибочное мышление.
Как пишет Стивен Макконнел в своей книге "Совершенный Код":
Очень хороший абзац, на мой взгляд. Поразмышляйте над ним, особенно над первым предложением в нём.
Metus
Какая уж тут теоретика?
Конкретный случай. Разработчику нужно вызвать код
Он знает, что этот метод корректно работает в контроллере.
Но сейчас ему нужно вызвать этот код в консоли, а завтра в контексте API-контроллера.
Будет ли это работать без предварительных приготовлений где-то в сервис-провайдере? Нет.
Знает ли об этом разработчик? Нет. Всё что у него есть — это метод, который каким-то образом (видимо, по контексту вызова) определяет, авторизован пользователь, или нет. Как он определяет — разработчик не знает. Он и не должен знать — инкапсуляция.
К вопросу о простоте, он мог бы вызвать:
и он знал бы, что обращается к сервису авторизации, который может быть как-то сконфигурирован как угодно.
Он мог бы сделать ещё проще, в случае, если ему приходит токен в заголовке и работа с сессией не нужна.
Но у него есть этот волшебный метод isCurrentUser, который скрывает всю информацию об использовании сервиса.
Он и не должен ничего этого знать.
Почему Вы всё время пытаетесь рассказать как работают сервис-провайдеры в ларавеле? Мои претензии не к ним, а непосредственно к модели User.
saggid
Потому что вполне нормально, что авторизация может работать на уровне сервис провайдеров или middleware. Поэтому я вам и указываю на них.
Абсолютно нормально, что один уровень приложения зависит от другого уровня приложения. И ведь точно также, указанный вами код
Auth::user() && Auth::user()->id == $user->id
будет зависеть от всего, что вы перечислили.Если вы это не хотите признавать, почему это должно быть моей проблемой? Я же просто добавил удобный метод для модели пользователя.
Metus
Конечно нормально. В приложении всегда один уровень зависит от другого.
В тему цитат приведу первые 4 строчки философии python:
Метод isCurrentUser неявный и запутанный.
Неявный потому как данные зависимости, простите за тавтологию, не являются явными.
Запутанный из-за того, что зависимость кольцевая: модель пользователя (модель бизнес-логики) зависит, от сервиса более высокого уровня (который её и использует).
saggid
Оно вполне явное и вполне простое. Вот вы реально нашли такую мелочь и пытаетесь из неё хоть что-то вывести.
Давайте заниматься полезными делами, за все сообщения спасибо, но я с вами всё равно не согласен. Любые правила полезны до тех пор, пока мы не стремимся довести их до фанатичного применения во всех ситуациях. До свидания.
ellrion
Т.е. вы предлагаете везде копипастить код ?
Ну это тоже не дело.
Но повторение кода тоже зло. Именно из-за этого есть "магия" которая позволяет убрать копипаст. Так что тут нужен баланс и компромисс.
Metus
Нет, я предлагаю вынести метод isCurrentUser из модели. При желании, расширить Auth и вынести данную логику туда.
Либо можно вообще сделать трейт для контроллеров. Потому как решать, авторизован пользователь или нет должны именно они.
Fesor
Нормально — это когда у нас нижние уровни не зависят от верхних. У вас же штуки из верхних уровней тянутся вниз.
я в своем коде в модулях нижних уровнях просто передаю юзера если надо. Они не лазают за ними сами. Это и удобнее, и читается проще, и с точки зрения масштабирования логики норм. И самое интересное — это не дольше по времени. То есть минусов вообще никаких. Ну и в Laravel5.3+ нормальный IoC есть что бы не страдать чушью из 4-ой.
saggid
Можете привести какие-то конкретные примеры, чего "нормального" появилось в сервис контейнере в ларавел 5.3+?
Ну и я снова не сильно согласен в целом. Опять до фанатизма доходите, извините. Пусть в одном месте проекта у нас вытаскивается модель текущего пользователя. Текущий пользователь — он на то и текущий. Он один. Его даже менять не нужно в 99% ситуаций жизни проекта, но даже если поменяешь в основном синглтон классе авторизации — то в других местах приложения всё отработает как полагается. Да, это чуть чуть менее явно, также как с эвентами, про которые я вам уже говорил в другом комментарии. Но я не могу назвать это полностью плохим подходом, который не имеет права на жизнь. Иначе и эвенты бы тоже надо было закидать камнями, но почему-то этого ведь никто не делает?
Fesor
Так как бы я этого и не говорю. Для маленьких/средних проектов с учетом нормальных сервис-локаторов ларавели жить можно.
Тут опять же. Ивенты нужны дабы снизить связанность. Например у меня есть модуль каталога товаров, и по изменению товара я должен сообщить всем заинтересованным модулям что я что-то поменял. Например модуль поиска, который должен синхронизировать данные в другой базе данных (эластике например). В этом случае у меня модуль поиска зависит от модуля каталога, но модуль каталога ничего не знает о модуле поиска.
Другой вопрос что просто так их выкидывать когда еще данные небыли записаны в базу так себе идея. Потому я использую доменные ивенты для этого (они сначала собираются а потом, после коммита транзакции, файрятся). Ну и в целом в пределах одного модуля использование ивентов уже не оправдано. Или же если у нас нет проблемы циклических зависимостей модулей, лучше явно что-то дернуть.
Словом, все относительно. Нет абсолютных правил. Но есть лучшие практики которым стоит придерживаться.
pbatanov
С чего бы эвенты надо закидать камнями? Эвенты — это документированная точка расширения вашего приложения, вы как бы говорите разработчикам — «Э-гей, вот здесь вы можете изменить
мирданные или отреагировать на них, вот вам событие, которое их инкапсулирует». Событие вполне себе может быть VO, если планируется только реакция на событие, или может быть мутирующим, если вы хотите чтобы расширения как-то дополнили или изменили ваши данные. Т.е. вы сами полностью управляет процессом реакции на события за счет паттернов.Не знаю за ларавель, но в симфони евенты, как и все остальное, полностью DIC-based, это значит что можно найти все зарегистрированные листнеры (либо посмотреть в рантайме, если вы подписываетесь в рантайме).
Синглтоны и статические фасады же позволяют вам обращаться, в том числе к мутирующим сервисам из любого места, что обычно при недостатке контроля или компетенции приводит к лапше в коде.
Я в целом согласен с Fesor, однако уточню, что в целом можно писать какой угодно код, если он никогда не будет никому показан. В противном случае лучше пользоваться вот теми самыми принципами из питона выше.
Metus
Помимо классических HTTP-страниц и консоли, Ваше приложение может выступать в роли API-сервера, а там вообще довольно часто авторизация определяется токеном, который клиент отправляет в заголовках запроса — без всяких сессий.
saggid
Ответил вам наверху на вопрос по этой теме) Уверяю вас, это не проблема. Просто авторизуем пользователя самостоятельно, так, как вам нужно.
Fesor
нэймспейсы не имеют никакого отношения к ООП. Это просто способ сделать более удобное API, без префиксов. Там внутри просто функции.
saggid
Это да, ошибся просто когда писал. Имел ввиду это.