Pull to refresh
35
0
Илья Сазонов @poxvuibr

Software developer

Send message
Впрочем, непонятно, что это перетягивание Кнута на свою сторону даёт любому из оппонентов :)

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

Ну камон, это какое-то агрессивное передёргивание слов оппонента

Ну нет )). Это агрессивная попытка побудить оппонента прямо сказать, что он с цитатой из Кнута не согласен )).


вполне понятно же, что человек имел в виду

Вроде понятно. Но и позиция того же Кнута, она немного сложнее, чем многие думают. Цитата про 12 процентов, она, кажется на предыдущей странице по отношению к цитате про преджевременную оптимизацию.

Я написал ровно то, что написал.

Вы написали, что полностью согласны с Кнутом, а я процитировал Кнута. С этой цитатой вы, как я понимаю, тоже согласны.

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

И с тем, что 12 процентное повышение производительности, легко получаемое, никогда не сочтут незначительным, тоже согласны?

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

Перья уже были у динозавров, крылья у некоторых из них тоже были и похоже, что некоторые из тех, что с крыльями, даже могли летать. У предков птиц уже было почти всё, что того, чтобы полететь. нужно было только немного подкрутить настройки.


Пасть там убрать, зубы всякие, хвост подрезать, крыло отрегулировать и так далее. С производительностью всё было уже готово. Включая производительную систему дыхания. И производительный мозг.

Насчёт экраноплана не скажу, не в курсе. А вот с эволюцией ситуация такая, что кости были с пустотами ещё у динозавров. И судя по всему даже у предков динозавров.

Я работаю с джавой, ангуляр трогаю изредка. Тем не менее настоятельно рекомендую не делать так никогда.


Если нужна логика из CustomerService — нужно инджектить CustomerService. Если нужна логика из AdditionalService, нужно инджектить AdditionalService. Если нужна логика из обоих, то нужно инджектить оба.


Приём, описываемый в статье имеет, смысл только если все классы из проекта используют методы и из AdditionalService и из CustomerService. Даже в этой подозрительной ситуации я бы инджектил сервисы отдельно. В крайнем случае выделил бы обёртку для используемых во всех классах методов. Но мне представить такую ситуацию очень непросто.


Лично я выступаю за то, чтобы просто вообще запретить наследование в компонентах, чтобы ни у кого не возникло соблазна сделать что-то похожее на описанное в статье. В таких случая нужно использовать композицию. Как и 90% остальных случаев.

Мне кажется, это не аргумент.

Это распространённое мнение. Оно подкрепляется тем, что если не делать моков, то получается тестирование интеграции методов между собой, что скорее хорошо, чем плохо.


Если падает тест А и тест Б, причем известно что функция А вызывает Б, то чинится Б а потом смотрится, помогло ли это для А или нет.

Разработчику, который будет править тест придётся потратить время, чтобы понять кто там кого вызывает и какой тест надо чинить в первую очередь. Это и то, что одна правка разваливает много тестов, может даже повредить внедрению юнит тестирования на проекте.


А вот в этот момент как раз стоит сказать "такие разработчики нам не нужны".

Этот момент ещё нужно вовремя отсечь, что не так просто, как кажется. Легче запрещать чекстайлом всё и с запасом.


Скажите, вы в основном работаете в команде? И ещё интересно какого размера команда, если так.


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

Я пытаюсь понять ценность этого. То есть “надо замокать” — окей, я понял вашу позицию. Но я не понимаю зачем её мокать?

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


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


Также, когда мы захотим эту функцию порефакторить, упадёт не только её тест, но и тесты кода, который её вызывает. Это не проблема, если разработчик постоянно запускает тесты, но по моим наблюдениям, разработчик долго правит код, а потом тесты падают уже на CI. И поди потом разбери, почему упали тесты.


Возможно вы скажете, что такие разработчики нам не нужны, но кто тогда будет работать? )))


И? Вот вы сделаете мок (псевдокод) capitalize.mock(“foo”, “Foo”).mock(“bar”, “Bar”)… Чем он лучше просто вызова capitalize?

Это непростой вопрос, поскольку метод capitalize очень очень простой. Если бы он был библиотечным, я бы даже не подумал его мокать.


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


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


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


Дальше выяснится, что в capitalize могут передать и целый текст и хорошо бы учесть это в коде. И некоторые слова в тексте надо будет капсить, поэтому рядом с методом будет список таких слов.


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


Следующим шагом решат что слова для капса надо добавлять через админку. А значит в методе понадобится доступ к базе данных. Думаете, его перенесут в сервис? Нет, там просто вызовут Context.getBean и спокойно продолжат использовать его в статическом контексте. Потому что для этого не придётся делать правки по всему коду, а при переносе в сервис придётся.


Может быть вы думаете, что всё это страшилки, которые выдумали взрослые? Я тоже думал, пока мне лично не пришлось объяснять людям, что так делать нельзя. И вы знаете, не убедил! Делали через “ну так уж и быть, раз тебе так печёт, то ладно”.


Перефразируя известное изречение скажу, что каждый статический метод в большом проекте неконтролируемо растёт, пока не поучает возможность отсылать электронную почту

Хм. При чём тут мой бог? Ничего не понял.

Да всё просто )).


Вы там успокаивали окружающих, что в Джаву синтаксический сахар точно не проползёт.


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


Я со своей стороны утверждал, что Ломбок кроет новые языки в том смысле, что в нём запилят фичи, которые не запилят в языках. Не и ещё его можно использовать с восьмой Джавой, хотя там я этого не сказал.


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


Вот это я имел в виду, когда использовал фигуру речи “где теперь ваш бог”.


Кроме того, я ведь обращался не только к вам. Другие люди рядом в комментариях говорили, что Ломбок он только сокращает геттеры и всё такое, а тут БАХ и вот.


Я, кстати, тоже участвовал в поддержке ломбоковских extension-методов в IntelliJ IDEA.

Тем самым добавляя в Джаву синтаксический сахар, который вам не нравится ))

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

Ваша позиция мне понятна, но я с вами категорически не согласен.


В своём примере я говорю про функцию, которая капитализирует не все слова, использующую функцию capitalize, которая капитализирует все.


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


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

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


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


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


Рефакторить такой код тоже сложно, потому что понять что в тесте очень непросто. Он получается запутанным.


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


С появлением методов расширения увидеть такой статический метод в ревью будет ещё сложнее и объяснять придётся ещё дольше.


P.S. Даже с capitalize всё не так просто, как кажется. Потому что возможно бизнес логика требует капитализировать слова в определённых случаях. И одна из методик тестирования такого кода — передавать мок и проверять, что код вызвает этот метод.

Делать какой-нибудь IntegerToStringConverter синглтон для подобной функции это очень сильно

Вот представьте себе, насколько сильно я утомлён статическими методами, что готов пойти даже на ЭТО, чтобы полностью устранить эту проблему? Ну и ещё вы возможно, не каждый день работаете со спрингом, там подклчение такого синглтона делается в одну строку кода. От применения статического метода не отличается считай ничем.


И вот, тут появляется такая фича, для которой нужно написать этих статических методов.

И что для вас это меняет?

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


Вот вам сильно принципиально, capitalize() это метод который объявлен на строке самими Богами джава-стд или это приехало из библиотеки StringUtils

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


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

Конкретно в случае джавы со спрингом разница ещё в том, что статический метод замокать нельзя, а метод экземпляра — можно.

Не, ну вы написали что у вас есть А и Б. Синглтоны и т.п. и статические методы — но связи между двумя этими вещами напрямую не провели.

Не провёл. На всякий случай раскрою свою мысль. Если объект класса один и соответственно экземпляров методов тоже по одному, то разработчик часто решает, что раз так, то тогда правильно сделать метод статическим. Так ещё понятнее, что второго экземпляра делать не планируется. Код, по мнению многих людей, становится чище (я с этим категорически не согласен). И ещё включается неверное применяемый в данном контексте принцип KISS. Раз можно следать статический метод — зачем делать метод, которому нужен экземпляр объекта?

А ничего, что в голосовании пункт «Зло» пока лидирует?

Вот прямо сейчас 16 голосов тех, кто использует Ломбок и 13 человек, которые считают Ломбок злом. Не факт, что те, кто считает Ломбок злом не используют его. Я, например, использую только в путь )). Даже, наверное, могу сказать, что будущее джавы за чем-то ломбокоподобным.

Вообще, это не совсем очевидно

Я бы даже сказал, что совсем не очевидно.


Возможно, вы так считаете, потому что у вас «Спринговые синглтоны и всё такое.»?

Да, я по-моему так и написал ))

Мне вот интересно — а откуда такой хейт методов расширения?

Не уверен, как относится к этим метода прогрессивная общественность, но своё мнение изложить могу.


Я занимаюсь разработкой бэкенда на java. Везде, естественно Spring. Спринговые синглтоны и всё такое. В общем объекты многих классов существуют в единственном экземпляре. А раз так, то почему не сделать методы такого класса статическими, да? Ну оно же само собой напрашивается!


И делают и каждый раз приходится объяснять, что не надо так делать НИКОГДА. Я, когда объяснял где-то в стопятидесятый раз, пришёл к выводу, что статические методы нужно запретить совсем. Даже какие-то типа String intToStr(int num). Потому что проблем с объяснением, почему именно тут нельзя делать статический метод больше, чем пользы от этих методов.


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


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

Идея добавить методов к уже существующим классам мне скорее симпатична, чем отвратительна. Можно будет построить свою уютную джаву с прикольными цепочками методов и нескучным API платформенных классов.


Но я всегда предпочитал 5 классов по 2 метода одному классу с десятью методами. Расширения делают скорее вот этот второй подход. Хотя методы разнесены по разным файлам, может это не так страшно. Я подробно не думал на эту тему, однако с вашими рассуждениями про удобство скорее согласен.


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

Как мне кажется, до сих пор, Lombok использовался для того, чтобы сократить усилия программиста на создание кода. Все эти геттеры, сеттеры и конструкторы с билдерами, разработчик написал бы и сам и сделал это почти так же как это делает Lombok.


Поэтому код после деломбокизации выглядел почти так, как будто его писал человек. Но тут другая история. Во-первых, цепочки вызовов превратятся во вложенные вызовы, то есть изменится то, как выглядит код. Во-вторых, что более важно, статические методы, которые были написаны для расширения классов — они никуда не денутся. Ох это будет славная охота!

Разработчики плагина открыли двери, которые лучше было держать закрытыми.


Да, Ломбок, это мог уже давно, но плагин это не поддерживал, а то чего не поддерживает Идея — не существует. Можно было бы запретить Lombok, но его сейчас используют считай везде. А запретить использование отдельной фичи значительно труднее, чем запретить библиотеку целиком.


Так поприветствуем же целые библиотеки, посвящённые тому, чтобы де факто добавлять методы в final класс String! Подготовимся к встрече с разработчиками, которые уверены, что метод capitalize был в этом классе всегда, потому что они не сталкивались с джавой без Lombok!


Есть только одна надежда. Может быть, такие вот библиотеки надо подключать в виде исходников, чтобы код собирался с ними? Если нет, то всё уже потеряно.


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


Что lany, ppopoff, gsaw из дискуссии в https://habr.com/en/post/538280, где теперь ваш бог?

Удерживать внимание помогает не только яркая речь.

Вот мы и подошли к тому, что было в заголовке


Есть много приёмов.

Нука нука!


Можно в презентацию картинки прикольные вставлять

Можно! Запишем один приём!


можно формулировать классные вопросы для аудитории и вести диалог.

И красноречие для этого совершенно не нужно, да? ))


Можно истории из жизни рассказывать

Определённо не имеет никакого отношение к красноречию!


или интересные метафоры подбирать.

Да вы издеваетесь! ))

Information

Rating
Does not participate
Date of birth
Registered
Activity