Как стать автором
Обновить

Комментарии 12

вы не сможете написать модульный тест без использования таких паттернов, как Dependency Injection, DI Container, и так далее.

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

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

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

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

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

С этой формулировкой почти согласен. Автор поста же категорично утвержает что без таких паттернов никак, с этим я не согласен. Я правда вообще делю код на многоразовый и одноразовый. Одноразовый это всякие гуи, хендлеры взаимодействия и прочая бизнес логика которая вызывается из одного места для одной цели. Как правило у такого кода много зависимостей (от данных, от вью, особенностей местного законодательства, от чёрта лысого), нет смысла в рефакторинге, нет внятной спецификации. Такой код я не вижу смысла покрывать тестами. А вот код ядра системы, библиотеки, утилиты я отношу к многоразовому, как правило у такого кода немного зависимостей, простой и понятный апи и их тестировать удобно можно и нужно, и часто без DI.

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

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

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

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

и их тестировать удобно можно и нужно, и часто без DI.

Для меня самый простой вид  Dependency Injection это передача аргументов в функцию/конструктор. В таком контексте тесты без DI это редкость, и я бы их скорее компонентными или модульными назвал.

Мимопроходил, но хочется возразить (как и вашему собеседнику ниже). Покрывать код тестами можно с разными целями, но главной (хоть это и вопрос дискуссионный) я бы выделил "улучшение качества", то есть, чтобы приложение "нормально" работало (ожидаемо, без косяков). В таком случае, чем больше протестировано, тем лучше (причём, не формально покрытие, а в более широком смысле). Будет ли этот "одноразовый" код протестирован после разработчика - вопрос организации процесса, но обычно лучше таки протестировать самому - и тут следует учесть, что реально write only код в проекте бывает не так то и часто, кто его знает, когда и что придётся менять.

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

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

Почему вы думаете, что парадигмы привносят только ограничения? Мне кажется довольно странным мир, где есть некоторое универсальное супер-программирование в котором всё можно, и где вся наша задача в том, что бы ограничить свои возможности, что бы не выстрелить себе же в ногу. На ассемблере можно написать всё, да, но то что на самом деле привнесли первые языки программирования -- новый способ мыслить о программах. Именно привнесли, а не ограничили. Например, в создании Тони Хоаром быстрой сортировки огромную роль сыграло его знакомство с Алголом, где крайне элегантно вводилась рекурсия -- он просто не думал так до этого (https://youtu.be/tAl6wzDTrJA -- около 14:40). Так же и другие парадигмы больше привносят новых способов мыслить о программе, чем ограничивают уже существующие. Подчеркну, что формулировка структурного программирования как "не используй goto" -- крайнее упрощение.

При этом я конечно понимаю основную мысль, что программировать сложно, возможностей невероятно много (вероятно даже избыточно много), и хорошо себя ограничивать и поддерживать дисциплину. Только вот например Дейкстра в своей Дисциплине Программирования имел в виду (насколько я понял) не следование некоторым ограничивающим правилам, которые приведут вас к безошибочному коду -- но напротив, он признавал принципиальную сложность программирования и предлагал дисциплину в смысле научной дисциплины, когда вы полностью осознаёте свои программы и можете доказать их корректность, а не просто показывать тестами и поддерживать различными методиками их около-работоспособность (вспомните его "Program testing can be used to show the presence of bugs, but never to show their absence!" или даже "software engineering has accepted as its charter "How to program if you cannot."").

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

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

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

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

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

Все же я отлично обхожусь без них.

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

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации