Pull to refresh

Comments 26

Искренне не понял, причем тут слово «Полиморфизм». Возможно вы имели в виду что-то другое? Например «тайп-хинтинг»?

P.S. За вот такое:
include_once("{$dir}{$sep}traits{$sep}Validator.php");

я обычно увольняю…
Надеюсь, вы так не пишете в продакшн-коде? Советовал бы вам отредактировать, заменив на привычные пути, __DIR__, без скобок и двойных кавычек…
Искренне не понял, причем тут слово «Полиморфизм». Возможно вы имели в виду что-то другое? Например «тайп-хинтинг»?

Да. Всё же я имел ввиду определение типов.
А под словом «полиморфизм» здесь предполагалось то, что один и тот же трейт можно использовать во всех классах, к которому трейт присоединён.
Поправлюсь в терминологии.

P.S. За вот такое:
include_once("{$dir}{$sep}traits{$sep}Validator.php");

я обычно увольняю…

Просто дурная привычка пилить всё на скорую руку.
Добавил в статью автозагрузку классов вместо include-ов.
Даже на скорую руку такого нарочно не придумаешь. Как вы вообще приходите к таким «решениям»?
И что изменилось в итоге? Так и остались dirname(__FILE__), дебильные двойные кавычки и скобки, а еще _once в автозагрузчике ))

Я бы вам искренне советовал убрать статью в черновики и переделать.

Очень много ляпов, которые мешают даже понять ее (статью) идею.
Ну раз уж очень хочется, то хорошо, можно и так написать:
$separator = DIRECTORY_SEPARATOR;
$basePath = __DIR__ . $sep;

$traitsFolderName = 'traits';
include_once($basePath . $traitsFolderName . $separator . 'Validator.php');

$modelsFolderName = 'models';
include_once($basePath . $modelsFolderName . $separator . 'Pen.php');
include_once($basePath . $modelsFolderName . $separator . 'Notebook.php');

Выглядит более элегантно по сравнению с предыдущим вариантом.
Это отвратительно выглядит. Вы знакомы со стандартами PSR?
$basePath = __DIR__. $sep;

С чего вы взяли вообще что конечный слэш является частью пути? Где, в какой спецификации, в какой файловой системе это так?

Почему вдруг для трейтов нужна отдельная папка, а для неких «моделей» — другая? Откуда берется такая структура?

И вопросов подобных миллион.
С чего вы взяли вообще что конечный слэш является частью пути? Где, в какой спецификации, в какой файловой системе это так?

Это просто пример. Можно его сколь угодно доводить до идеального состояния, но конечной целью было не создать целое приложение, а протестировать работоспособность одного трейта на примере пары классов.
Почему вдруг для трейтов нужна отдельная папка, а для неких «моделей» — другая? Откуда берется такая структура?

Можно запихнуть всё и в одну папку models, нет никаких проблем)
Это просто пример.

Это небрежность, идентичная непрофессионализму. Имхо.
Чтобы не быть голословным, приведу пример относительно (!) нормального автозагрузчика:

const VENDOR = 'YourVendorName';
const SRC_PATH = __DIR__ . '/src'; // к примеру

spl_autoload_register(function ($class) {
    if (0 === strpos($class, VENDOR)) {
        $file = SRC_PATH  
          . str_replace('\\', '/', preg_replace('~^' . VENDOR . '~', '', $class)) 
          . '.php';
        if (is_readable($file)) {
            require $file;
        }
    }
});


Писал на калькуляторе в метро, так что могут быть ошибки ))
Не поленился и почитал всю ветку переписки. Просто любопытно, зачем Вы так осаждаете человека?

Я долго писал обстоятельный комментарий, но потом всё стёр, потому что, мне кажется, тут можно обойтись одной строкой:


"Вот так, с помощью нехитрых приспособлений, буханку белого (или чёрного) хлеба можно превратить в троллейбус. Но зачем?"

public function insertSort(ArrayForSorting &$sortArray)
Объекты передаются по ссылке, амперсанд не нужен.

// дабы не нарушать святы принципы полиморфизма,
// будем возвращать пустой массив в случае ошибки валидации,
// а не false или какой-нибудь -1.
Вместо возврата корректного ответа на ошибочные аргументы, лучше кидать исключение. И при чем тут принципы полиморфизма?

Ну и лучше все же на 7 переходить. А то тут просится картинка с буханкой-троллейбусом.
Вместо возврата корректного ответа на ошибочные аргументы, лучше кидать исключение.

Это в трейте и реализовано.

И при чем тут принципы полиморфизма?

Да, про полиморфизм я не к месту написал, признаю.

Ну и лучше все же на 7 переходить. А то тут просится картинка с буханкой-троллейбусом.

Многие хостинг-провайдеры до сих пор остались в прошлом веке со старыми версиями.
Зачем вообще работать с хостинг-провайдерами? Вы к ним приколочены гвоздями? Простейший VPS, где можно поставить любую версию, стоит 150 рублей в месяц. Расскажите — чем лучше «хостинг»?
Расскажите — чем лучше «хостинг»?

Согласен, ничем.
(Если не считать того, что всё за тебя уже настроено заранее)
(Если не считать того, что всё за тебя уже настроено заранее)

sudo apt install php php-common php-mysql mysql apache2
Базовый веб-сервер, не особо заморачиваясь со всякими http/2, rabbitmq, zabbix и прочими фенечками, устанавливается на VPS минут за 15, 10 из которых вы будете пить чай.

Я вижу шаред-хостинги только как площадку для какого-то самопального блога на вордпрессе от человека, который немножко перерос простые html странички, но не хочет изучать программирование.

Не говоря уже о том, что сейчас каждый первый VPS хостинг умеет сразу ставить шаблоны LAMP/LEMP

tldr Давайте валидировать входные данные ручками все правила валидации сложим в трейт который будем подключать.


Реальность такова что "строгую" типизацию ввели как раз из за того что люди очень много валидировали параметры ручками и это вынесли на уровень языка, значит это уже делали до вас и ничего нового тому кому нужна статическая типизация вы не сказали.


Далее trait далеко не лучшая идея для хранения этих проверок, можно с тем же успехом сделать Util\Assert и кучу статических методов которые дерграть, это как пример, или сложить в функцию которую импортить.


Следующее аргумент функции валидации это массив где магическое имя ключа и значение которое он должен проверить, на самом деле лучше сделать что то типо assertString($arg...), assertInt($arg...), assertNotNull($arg ...)


Следующее ваш способ валидации предполагает выкидывания исключений, это сделано для того чтобы в коде меньше проверять ответы и в случае чего падать в корку, но это далеко не лучшая практика потому что ошибка в данных это нормальная ситуация и она должна быть обработано и по возможности без исключений, поэтому имя в виде валидации не очень здесь подходит.


tdlr С учетом всего выше сказанного вы просто написали еще одну библиотеку содержащую assert которых и так было достаточно и которые учитывают все мои замечания указанные выше.


Ну а теперь немножко позитива то что вы думаете над такими проблемами это хорошо и попытка сделать инструмент который можно было бы переиспользовать это тоже хорошо и попытка им поделится, вы как минимум получите замечания (рекомендации) по его улучшению и работая над его улучшением будете улучшать свои навыки и это лично для вас будет плюсом ну и попутно для других.


А сейчас посмотрите https://packagist.org/search/?q=assert количество библиотек и по смотрите как они решают подобную проблему может что полезное для себя узнаете.


Кстате еще один интересный подход http://php.net/manual/ru/book.stream.php можно с помощью эту функциональности сделать что то типо преобразования одного кода в другой и установить эти проверки на этапе "компиляции" и тогда ручные проверки делать не обязательно, можно например сразу код писать в стиле php 7 но для запуска его в php5 надо будет его преобразовать, выглядит забавно чисто с точки зрения иследования, на продакшене я бы такое применять не стал

Согласен со всем, кроме
далеко не лучшая практика потому что ошибка в данных это нормальная ситуация и она должна быть обработано и по возможности без исключений

Ошибка валидации — это классическое исключение. Не фатальная ошибка, но нечто, что ждет нашей реакции и делает дальнейшее линейное выполнение программы невозможным или бессмысленным.

Другое дело, что надо исключения в валидации немного не так топорно использовать, конечно же.

давайте я немного поясню


Валидация подразумевает два состояния, валидно и не валидно и если не валидно должен быть функционал получения текста что именно не валидно, это нужно для того чтобы выбросить соответствующий тип исключения с соответствующим текстом в том месте где вы вызывали валидацию, также вместо исключения может быть предусмотренно поведение в случае невалидных данных


Например у вас спрашивают год рождения вы указываете 2222 с точки зрения валидации это не правильно год рождения не может быть больше текущего года и прекращать и падать всему приложению нет нужды, потому что после вашего кода может быть например логирование в приложение которое залогировало входящий запрос, а выходящий (ответ) не залогировало, вы можете сказать так сделайте логирование в обработке exception но это не правильно вы начинаете делать ветвление логики и писать ее в обработку исключения потом может появится еще что то.


Вторая причина почему валидация не должна падать в корку это когда в форме спрашивают дату рождения и вы указываете 34.34.2222 тут сразу несколько ошибок валидации, неправильный номер месяца так как он больше 12, не правильный день и не правильный год, в случае валидации которая падает с exception она будет каждый этот exception выкидывать по одному, вы заметите что это должно проверятся на клиенте(js) и к вам уже приходить валидно и backend не обязан давать человеко читаемый текст, поэтому мы можем ронять приложение, но ронять резко приложение плохо смотри пункт один что могут быть события в конце обработки запроса.


В противовес слову validation есть assert который как раз утверждение и если оно не истинно оно валится с исключением.


tldr Я как потенциальный пользователь этого трейта видя validation ожидаю там валидацию, а не assertation, поэтому вам нужно или сделать там валидацию или переназвать метод на assertation, второе как мне кажется более правильно и менее трудо затратно, просто я имею ввиду что вы выбрали плохое имя для метода.


Надеюсь я чуть прояснил ситуацию

Мне «прояснять» ничего не нужно. У вас фундаментальная ошибка в рассуждениях:
прекращать и падать всему приложению нет нужды

С чего вы взяли, что исключение — это «прекращать и падать»? Исключение — это инкапсулировать, передавать и управлять потоком.

Избавьтесь уже от парадигмы «исключение — значит падение». Это просто объект, инкапсулирующий в себе информацию о случившемся. И не более того. Плюс способ передать этот объект вверх по стеку.

Вот опять:
assert который как раз утверждение и если оно не истинно оно валится с исключением

Что за чушь? Почему «валится»? Выбрасывает исключение, уважаемый, выбрасывает. А вы — ловите. Если у вас что-то «валится» — вы хреновый программист и не умеете пользоваться исключениями. И assert() тоже.

давайте сразу проясним


Валится значит выполнение программы дальше бесмысленно, она останавливает обработку запроса корректно сообщая о том что завершена с ошибкой.


Далее вы предлагаете вести разработку в стиле "Exception Drive Development (EDD)" и кидаться ими по стеку и заниматься рыбалкой (вылавливанием) я конечно понимаю что она имеет право на жизнь как например "GOTO Drive Development"(GTD) она даже может быть чуть похожа, но заниматься этим я этим все таки не буду, при этом я прекрасно знаю о важности обработки исключений и о том что есть RuntimeException и что в ходе обработки исключений программа может вернутся к нормальному исполнению (обработка с возвратом).


EDD и GDD это естественно выдуманные слова.


Для передачи сообщений вверх по стеку я предпочитаю использовать древнюю магию return и код который старается однозначна себя вести и использовать исключения по назначению, а не вместо return.


Я на своем подходе не настаиваю я просто пояснил как бы я и некоторые другие люди могут воспринимать валидацию и если моя позиция не сходится с вашей здесь нет ничего страшного.


Теперь по поводу кто какой программист это наверно не вам решать, о том навыках использования исключениями тоже, но как и все могу сказать что я далеко не идеальный и всегда бывают баги и если вы в своей жизни не допустили не одной баги в разработке, то либо очень мало разработали, либо еще не знаете о этих багах, ну или не считаете их за баги.


Я же все таки советовал бы почитать http://bfy.tw/BzlD и что исключения это конечно инструмент разработчика, но наверно все таки не ведения разработки через исключения, потому что при большом проекте и таким гуляниям по стеку становится мучительно больно это поддерживать и чем больше проект тем больше это напоминает goto разработку.


и дальнейшее обсуждение возможно будет не очень конструктивным, давайте каждый останется при своем мнение, потому то как использовать исключение это очень спорная тема и существуют разные подходы, о которых я знаю, в том числе и о том вы говорите, но я хочу сказать что есть и другие и иногда они бывают лучше а иногда хуже.

А зачем тогда вообще эта простыня малосвязного текста, переполненного ложными высказываниями?
Далее вы предлагаете вести разработку в стиле «Exception Drive Development (EDD)»

Я ничего вам не предлагал. Перестаньте так болезненно реагировать на существование внешнего мира не совсем совпадающего с вашими представлениями о нём.

Дык это и статья не для седьмой версии, в которой всё за тебя интерпретатор провалидировал.
Поэтому про жуть и мрак в плане «к чему пользоваться старьём» – тут согласен.
Если вы что-то другое имели ввиду — то распишите подробнее.
Если коротко, используйте инструмент по назначению..)
Sign up to leave a comment.

Articles