Re[13]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 07:36
Оценка: -1
Здравствуйте, varenikAA, Вы писали:

AA>Здравствуйте, netch80, Вы писали:


AA>мы явно говорим на разных языках.


Вполне возможно. При этом в вашем языке отсутствуют чёткие определения, слова меняют смысл как вздумается не то говорящему, не то самим словам, и в результате никто не может понять смысл сказанного, и остаётся только кивать "да, я тебя тоже уважаю".
Что ж, есть места, где такой язык вполне уместен. Но данная дискуссия как-то не очень входит в их набор.
The God is real, unless declared integer.
Re[6]: Тестирование бесполезно
От: Poopy Joe Бельгия  
Дата: 18.06.21 07:43
Оценка: 3 (1) +1 -1
Здравствуйте, netch80, Вы писали:

N>Что TDD это неработающая методика (в чистом виде) — я согласен. Любая практика больше одноразового кода его нарушает.

О чем спор тогда?

N>А вот дальше вы начинаете нести полную чушь, игнорируя реальность и устанавливая некорректные логические связи. Потому что:

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

N>1. Программные тесты отображают спецификацию к компоненту и позволяют её проверить автоматизированно в любой момент.

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

N>Таким образом они ещё и работают регрессионными проверками (если что-то сломали позже, запуск тестов это ловит).

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

N>1) Инверсии — вводится внешняя непрозрачная для логики теста фиксированная модификация, после которой тест может упасть. Проверка заключается в обнаружении планового падения теста.

N>2) Мутации — код компонента или код теста меняется случайным образом и это не должно пройти незамеченным.
Ничего из этого не доказывает ни правильность теста, ни полноту спецификации. Теперь и ты знаешь. Не благодари.
Re[9]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 07:47
Оценка:
Здравствуйте, Sharowarsheg, Вы писали:

N>>>>Вот у меня новая суперсортировка. Я пишу тест: sort([3,2,5,4,1]) == [1,2,3,4,5]. Это дублирование кода сортировки или нет?


ZEN>>>Это сравнение возвращаемой функцией sort() ссылки на объявленный в коде массив. Чего вы этим хотите добиться?


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


S>Это то же самое, что пытаться тестировать, ещё не имея кода.


Ну, я бы сказал, что общего как раз мало.
До кода есть представления о том, что этот код должен делать. Многие из них уже однозначны. Эти представления можно записать формально. Это больше относится к BDD и ATDD, чем TDD, но TDD представляет собой просто введение этой методики в (некорректный) абсолют.

Второе что составляет постулат в TDD — это продвижение мелкими шагами для удовлетворения тестов и только для этого. Это не подходит во многих случаях (в основном это сложные алгоритмические задачи, где не существует промежуточных этапов по одному тесту), и может быть слишком дорого для клеевого кода, но есть много случаев, когда я нашёл это удобным. В частности, это очень хороший путь разбиения объёмной задачи (от объёма которой опускаются руки) до состоящей из мелких, подъёмных задач.

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

Ну а если абьюзить средство... тут уже приводили множество крайних примеров, не хочется повторяться.
The God is real, unless declared integer.
Re[5]: Разработка через тестирование бесполезна
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 18.06.21 08:00
Оценка:
Здравствуйте, Ватакуси, Вы писали:

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


В>Для этого есть компиляторы или хотя бы стат. анализаторы.


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

В>Я вот сейчас работаю с проектом, где до одного места этих микросервисов, которые ещё засунуты в самописный велосипед. 80% тестов ничего не тестируют, а просто добавляют "покрытие".

В>Там тупо всё mocked.

Именно. Тесты проверяют моки По этой причине для рефакторинга нужно отказываться от моков, а дизайнить компоненты таким образом, что бы у нас был такой расклад
1. много дешевых value-check тестов, т.е. тесты вида expect(sin(x)).to.eq(y). Сюда же относится property-based тесты.
2. компромис — если нет способа как п.1, напримпер, стейтфул-механика, то тестируем через state-check. Разумеестся, если можно отказаться от стейт-фул логики, то все тесты перепиливаются как п.1
3. поведенческие — если нет способа п1 и п2. Вот здесь появляются моки,
п.3 — хрупкие тесты, часто вечнозеленые, дают слабые гарантии, их очень дорого писать.

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

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

Иногда такое необходимо, но только если дизайн кривой настолько, что трудно реализовать п1 или п2. или же имем дело с 3rd party компонентами, когда дизайн изменить нельзя.

На мой взгляд, поведенческие тесты должны использоваться где то на самых высоких уровнях, когда система собрана полностью и нет нужды в моках. Т.е. проверяем реакцию системы на действия пользователя по наличию тех или иных вещей — залогинился, значит ожидаем, что после этого появился персональный контент, который соответствует именно этому логину. Вылогинился — ожидаем, что этот контент исчез из показа.
Re[5]: Тестирование бесполезно
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 18.06.21 08:04
Оценка:
Здравствуйте, netch80, Вы писали:

I>> не существует методики ни разработки, ни тестирования, которая может дать гарантию отсутствия ошибок


N>Ну почему же. Формальная верификация даёт такую гарантию — где она применима.


Не дает, т.к. в реализации ты можешь чуточку ошибиться, перепутать = и !=, т.е. минорная ошибка, которая просто портит вывод.

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


N>Есть — полная физическая изоляция


Подловил!!!!111

I>>5. приложение покрывает все известные сценарии, см перечень сценариев

I>>6. приложение покрывает все критические кейсы, см перечень кейсов

N>И обычно последние два пункта доводят требования до состояния полной нереализуемости.


Здесь ничего странного. Сценариев обычно немного, несколько десятков или сотен. Это все реализуемо относительно небольшими затратами.
Re[7]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 08:18
Оценка:
Здравствуйте, Poopy Joe, Вы писали:

PJ>Здравствуйте, netch80, Вы писали:


N>>Что TDD это неработающая методика (в чистом виде) — я согласен. Любая практика больше одноразового кода его нарушает.

PJ>О чем спор тогда?

О множестве важных деталей и о расстановке принципиальных акцентов.

N>>А вот дальше вы начинаете нести полную чушь, игнорируя реальность и устанавливая некорректные логические связи. Потому что:

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

Ап ту ю. Можете игнорировать, но потом нарвётесь — вспомните.

N>>1. Программные тесты отображают спецификацию к компоненту и позволяют её проверить автоматизированно в любой момент.

PJ>Нет, обычно, не отображают. Да, можно выразить спецификацию через тесты.

Вы пропустили, что не "выражают", а именно "отображают". Отображение ограниченно, но искусство программиста — в умении выбрать тесты, которые отражают и типовые, и крайние случаи.

PJ> Так делают через проперти тесты. Проблема с этим подходом только одна: за пределами демонстрационных примеров, типа разворота списка, это сделать достаточно сложно. Во всяком случае в дикой природе встречается в крайне ограниченном виде.


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

Я аналогичным образом разделяю случаи:
1) Алгоритмические задачи. Например, Quicksort. Писать её согласно TDD как-то совсем нереально.
2) Задачи с принципиально неконкретизируемым ответом, но к которым можно применить другие критерии. Например, нейросеть, которая определяет котиков. Она может пропустить 10% котиков тестового набора, если это дозволено.
3) Простые громоздкие задачи со сложным кодом. Например, парсинг HTTP.
4) Простые громоздкие задачи с простым кодом. Например, релеинг запросов бизнес-модели в операторы SQL и обратное преобразование данных.

Общего решения для них не будет. Некоторые подходы работают для всех, но заметно выгибаются.

И вот, кстати, property-based testing пригодно как минимум для 1, 3 и 4.
И я делал такое использование на практике.
Если считать статистически — то и 2.

N>>Таким образом они ещё и работают регрессионными проверками (если что-то сломали позже, запуск тестов это ловит).

PJ>Если бы этот подход работал, то в программе бы не было багов. Вообще. Я думаю ты даже сам в эту "чушь" не веришь.

В ваше утверждение — "Если бы этот подход работал, то в программе бы не было багов" — конечно, не верю. Нет причин в него верить.
Тесты, в отличие от формальной верификации, в принципе не могут покрыть всё. У них и задачи такой нет. Задачи тестов:

1. Показать работоспособность для внешнего контроля (заказчик, QA...), который может вообще не интересоваться тем, что в решении есть программная часть и как она устроена.
2. Дать авторам кода средства поиска ошибок, не найденных никакой верификацией (включая визуальную, как peer review). Критически важно из-за принципиального различия методов работы компьютера и человека (например, человек из-за "замыленного глаза" может в упор не видеть ошибку, и не в состоянии получить результат из 100500 уровней #include).
3. Подтвердить корректность внешних постулатов (например, что open() открывает файл согласно пути и ключам, а не звонит в колокольчик).

И вот именно под решение этих задач их и надо продумывать и писать.

PJ> А с чего начинается правильная работа на багом? Правильно, с написания очередного теста для него. Что доказывает неполноту предыдущей спецификации.


Спецификация меняется под задачи. "Неполнота" предыдущей спецификации, а точнее, вообще её отличие (может что-то вообще меняться несовместимо) — норма разработки. Методология должна это учитывать.
Точно так же она должна учитывать и то, что может оказаться, что под новую спецификацию ничего не надо менять. И так бывает.

N>>1) Инверсии — вводится внешняя непрозрачная для логики теста фиксированная модификация, после которой тест может упасть. Проверка заключается в обнаружении планового падения теста.

N>>2) Мутации — код компонента или код теста меняется случайным образом и это не должно пройти незамеченным.
PJ>Ничего из этого не доказывает ни правильность теста, ни полноту спецификации. Теперь и ты знаешь.

Про полноту спецификации тезис появился только в вашем последнем комментарии. Полная спецификация или нет — вопрос отдельный и к теме тестов напрямую не относящийся, потому что для программиста требуется предельно точное ТЗ. Я не буду рассматривать этот тезис тут.

Правильность теста — точнее, набора тестов — как раз практически подтверждается (слово "доказывается" тут неуместно).

PJ> Не благодари.


Почему, могу и поблагодарить. Только не за осмысленные тезисы (которых не было), а за такие, оппонируя которым, создал себе возможность сформулировать более ясно свои мысли. "Когда б вы знали, из какого сора..." (©)(™)
The God is real, unless declared integer.
Re[6]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 08:34
Оценка:
Здравствуйте, Ikemefula, Вы писали:

I>>> не существует методики ни разработки, ни тестирования, которая может дать гарантию отсутствия ошибок

N>>Ну почему же. Формальная верификация даёт такую гарантию — где она применима.
I>Не дает, т.к. в реализации ты можешь чуточку ошибиться, перепутать = и !=, т.е. минорная ошибка, которая просто портит вывод.

Этого не понял — это для какого языка так?
Если описано внешнее требование, то существенные ошибки приведут к нарушению доказательства.

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

N>>Есть — полная физическая изоляция
I>Подловил!!!!111

Ага

а если серьёзно — то все уязвимости надо формализовать.
Есть принципиально неустранимые за счёт самого факта доступа.
И отличие проблем "не заткнули известный канал атаки" от "не учли все каналы атаки" принципиально — первое это вопрос корректности кода, а второе это уже не к программистам. Прикладной код не обязан защищаться от Meltdown

I>>>5. приложение покрывает все известные сценарии, см перечень сценариев

I>>>6. приложение покрывает все критические кейсы, см перечень кейсов
N>>И обычно последние два пункта доводят требования до состояния полной нереализуемости.

I>Здесь ничего странного. Сценариев обычно немного, несколько десятков или сотен. Это все реализуемо относительно небольшими затратами.


Хм, попытался подсчитать сценарии в своём текущем продукте — со всеми вариациями идёт на десятки тысяч.
А всего-то: паркинг против пикапа, транскодинг/трансрейтинг данных, прохождение NAT, темпы реавторизации, ещё десяток факторов...
и разделить, зараза, нельзя толком...
The God is real, unless declared integer.
Re[8]: Тестирование бесполезно
От: Poopy Joe Бельгия  
Дата: 18.06.21 08:45
Оценка:
Здравствуйте, netch80, Вы писали:

N>О множестве важных деталей и о расстановке принципиальных акцентов.

И в чем заключаются эти акценты?

N>Ап ту ю. Можете игнорировать, но потом нарвётесь — вспомните.

Нарвусь на что? Я очень переживаю о том считаешь ли ты мои слова чушью, это крайне важно для меня.

N>Вы пропустили, что не "выражают", а именно "отображают". Отображение ограниченно, но искусство программиста — в умении выбрать тесты, которые отражают и типовые, и крайние случаи.

И что это отображение дает?

N>И вот, кстати, property-based testing пригодно как минимум для 1, 3 и 4.

Оно пригодно для всех четырех. В теории. На практике какой процент у тебя таких тестов в общем коде? Вот, то-то и оно.

N>В ваше утверждение — "Если бы этот подход работал, то в программе бы не было багов" — конечно, не верю. Нет причин в него верить.

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

N>Тесты, в отличие от формальной верификации, в принципе не могут покрыть всё. У них и задачи такой нет. Задачи тестов:

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

N>1. Показать работоспособность для внешнего контроля (заказчик, QA...), который может вообще не интересоваться тем, что в решении есть программная часть и как она устроена.

Поржал. Сдаешь заказчику программу и на демо показываешь, что все тесты пройдены?

N>3. Подтвердить корректность внешних постулатов (например, что open() открывает файл согласно пути и ключам, а не звонит в колокольчик).

Есть он будет звонить в колокольчик и открывать файл, то твой тест это скорее всего и не заметит.

N>Спецификация меняется под задачи. "Неполнота" предыдущей спецификации, а точнее, вообще её отличие (может что-то вообще меняться несовместимо) — норма разработки. Методология должна это учитывать.

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

N>Про полноту спецификации тезис появился только в вашем последнем комментарии.

Потому я отвечал на пост в котором появилось слово спецификация. Внезапно.

N> Полная спецификация или нет — вопрос отдельный и к теме тестов напрямую не относящийся, потому что для программиста требуется предельно точное ТЗ. Я не буду рассматривать этот тезис тут.

Спецификация, в контексте обсуждения, это описание инварианта функции, которую ты тестируешь. Причем тут "предельно точное ТЗ" и где ты такие вообще видел?
Re[7]: Разработка через тестирование бесполезна
От: Sharov Россия  
Дата: 18.06.21 09:07
Оценка:
Здравствуйте, netch80, Вы писали:


N>Разделение на юнит-тесты и интеграционные — терминологическая нелепость.


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

N>"Модуль" может состоять из других модулей хоть в 10 уровней иерархии.

N>Есть функциональные тесты разного уровня. Для всех внутренние сущности работают как обычно (ну, с поправкой на то, что, например, логгинг может быть отключен или иначе настроен), а внешние мокаются или эмулируются (разница тут неважна). По отношению ко внутренним составляющим это интеграционные тесты, а по отношению к внешним — юнит-тесты. Ну и зачем?

Даже индивидуальный сервис может мокать, например, фс (io). Почему нет? Речь идет об идеологии юнит-тестов -- максимально
абстрагироваться от внешнего мира и сосредоточится только на bl.
Кодом людям нужно помогать!
Re[9]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 09:16
Оценка: +1
Здравствуйте, Poopy Joe, Вы писали:

N>>В ваше утверждение — "Если бы этот подход работал, то в программе бы не было багов" — конечно, не верю. Нет причин в него верить.

PJ>Я не просил верить в мое утверждение. Я спросил веришь ли ты что в программе нет багов. По определению, если тесты описывают спецификацию и они зеленые, то багов нет. Так ведь? Не?

Конечно, нет. Может, у тебя один тест, который проверяет, как main() разбирает аргументы, и он зелёный
Для того, чтобы с достаточной уверенностью доверять результатам тестов, нужно:
1) Разумность самих тестов (метода, набора тестовых данных), с точки зрения нахождения проблем реализации согласно задаче и выбранному методу.
2) Верификация кода (хотя бы визуальная) на то, что реализован действительно нужный подход (а не поставлен, грубо говоря, большой if на конкретные тестируемые случаи).
3) Достаточное покрытие нужного-по-ТЗ кода тестами (несмотря на всю условность этого понятия).
4) Доверие среде и библиотекам.

Вот после этого можно говорить — не абсолютно, но с практически достаточной уверенностью — про отсутствие багов.

И да, в это я верю. Как-то практика показывает, что именно так и оно и работает

N>>Вы пропустили, что не "выражают", а именно "отображают". Отображение ограниченно, но искусство программиста — в умении выбрать тесты, которые отражают и типовые, и крайние случаи.

PJ>И что это отображение дает?

Даёт пункт (1) в списке выше.

N>>И вот, кстати, property-based testing пригодно как минимум для 1, 3 и 4.

PJ>Оно пригодно для всех четырех. В теории. На практике какой процент у тебя таких тестов в общем коде? Вот, то-то и оно.

В зависимости от задачи сильно по-разному.
Были, где, грубо говоря, 90%. Сейчас крайне мало — но это потому, что ресурсов нет. А так я бы и сейчас добавил переменных.

N>>Тесты, в отличие от формальной верификации, в принципе не могут покрыть всё. У них и задачи такой нет. Задачи тестов:

PJ>Задача тестов одна, я ее упоминал выше. Отслеживать изменение поведение кода при рефакторинге.

Если ты используешь тесты ровно для этого — это твои личные ограничения.

PJ> Т.е. это автоматизация рутинной работы. Все! Они совершенно ничего не гарантируют и никогда на это нельзя полагаться. Просто несколько облегчает жизнь.


Не "несколько", а на порядки.
И не "совершенно ничего не гарантируют", а гарантируют поиск >90% багов в обычном применении. Конкретная доля может быть и 95, и 99%, в зависимости от множества факторов.
Как по мне, этого достаточно, чтобы тратить на них приличный кусок времени (условно говоря, половину).

N>>1. Показать работоспособность для внешнего контроля (заказчик, QA...), который может вообще не интересоваться тем, что в решении есть программная часть и как она устроена.

PJ>Поржал. Сдаешь заказчику программу и на демо показываешь, что все тесты пройдены?

А почему ты в этом рассмотрении предполагаешь только внутренние кодовые тесты?
Они могут быть и визуальные, и в режиме чёрного ящика "X на входе — Y на выходе", и массой промежуточных вариантов.

N>>3. Подтвердить корректность внешних постулатов (например, что open() открывает файл согласно пути и ключам, а не звонит в колокольчик).

PJ>Есть он будет звонить в колокольчик и открывать файл, то твой тест это скорее всего и не заметит.

Это ловится на других уровнях и другими методами.

N>>Спецификация меняется под задачи. "Неполнота" предыдущей спецификации, а точнее, вообще её отличие (может что-то вообще меняться несовместимо) — норма разработки. Методология должна это учитывать.

N>>Точно так же она должна учитывать и то, что может оказаться, что под новую спецификацию ничего не надо менять. И так бывает.
PJ>Ниче не понял. Баг это когда ожидается одно, а результат другой. Никакая спецификация тут не меняется.

А кто только что писал про предыдущую спецификацию? Сам уже не помнишь, что писал?

N>>Про полноту спецификации тезис появился только в вашем последнем комментарии.

PJ>Потому я отвечал на пост в котором появилось слово спецификация. Внезапно.

OK. Представим себе, что "спецификация" это "полное и точное ТЗ", и пойдём дальше. Так откуда взялась предыдущая спецификация?

N>>О множестве важных деталей и о расстановке принципиальных акцентов.

PJ>И в чем заключаются эти акценты?

Ну вот я выше и описал. Разница между "ничего не гарантируют" и "статистически гарантируют поиск >90% ошибок", по-твоему, важна или нет?

N>>Ап ту ю. Можете игнорировать, но потом нарвётесь — вспомните.

PJ>Нарвусь на что? Я очень переживаю о том считаешь ли ты мои слова чушью, это крайне важно для меня.

Сарказм понят, но не оценён. Нарвёшься на то, что будешь отказываться от доступных средств из-за гордыни.
The God is real, unless declared integer.
Re[8]: Разработка через тестирование бесполезна
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 09:18
Оценка:
Здравствуйте, Sharov, Вы писали:

N>>Разделение на юнит-тесты и интеграционные — терминологическая нелепость.

S>Не согласен, ибо если для первых полно соотв. библиотек и т.п. , то для второго все индивидуально.

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

N>>"Модуль" может состоять из других модулей хоть в 10 уровней иерархии.

N>>Есть функциональные тесты разного уровня. Для всех внутренние сущности работают как обычно (ну, с поправкой на то, что, например, логгинг может быть отключен или иначе настроен), а внешние мокаются или эмулируются (разница тут неважна). По отношению ко внутренним составляющим это интеграционные тесты, а по отношению к внешним — юнит-тесты. Ну и зачем?

S>Даже индивидуальный сервис может мокать, например, фс (io). Почему нет? Речь идет об идеологии юнит-тестов -- максимально

S>абстрагироваться от внешнего мира и сосредоточится только на bl.

Ну а интеграционные, что, не абстрагируются от внешнего мира?

Или речь про проведение границы между "чистыми" и "нечистыми" функциями?
The God is real, unless declared integer.
Re[9]: Разработка через тестирование бесполезна
От: Sharov Россия  
Дата: 18.06.21 09:23
Оценка:
Здравствуйте, netch80, Вы писали:

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


Это таки важно, если идет обращение к другим модулям\сервисам. Иной раз задолбаешься все поднимать. Замокал и тестируй себе.

S>>Даже индивидуальный сервис может мокать, например, фс (io). Почему нет? Речь идет об идеологии юнит-тестов -- максимально

S>>абстрагироваться от внешнего мира и сосредоточится только на bl.

N>Ну а интеграционные, что, не абстрагируются от внешнего мира?


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

N>Или речь про проведение границы между "чистыми" и "нечистыми" функциями?


В некотором роде да, речь про изоляцию.
Кодом людям нужно помогать!
Re[10]: Разработка через тестирование бесполезна
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 09:41
Оценка:
Здравствуйте, Sharov, Вы писали:

N>>Ну а интеграционные, что, не абстрагируются от внешнего мира?

S>Ну это почти боевая эксплуатация, т.е. как реальный пользователь будет взаимодействовать с системой.
N>>Или речь про проведение границы между "чистыми" и "нечистыми" функциями?
S>В некотором роде да, речь про изоляцию.

Как-то всё это абстрактно. Вот у меня есть:
1. Transport layer.
2. Transaction layer, использует transport layer.
3. Dialog layer, использует transaction layer.
Остановимся на этом (там ещё уровня 4, но не усложняем).

Transport layer незамоканный отправляет в сеть и принимает; замоканный зовёт нужные коллбэки.
Уровень транзакций незамоканный общается с транспортным, замоканный дёргает вызовы некоего мока.
Ну и с третьим точно так же.
Если я тестирую диалоговый уровень — что например по получению "200 OK" произошёл переход состояния объекта Dialog из Trying или Early в Confirmed, и посылаю это как вызов processResponse() от транзакционного модуля, это юнит-тест?
А если я сделаю то же самое, сэмулировав сетевой ответ от транспорта (тогда у транзакционного его processIncoming() опознает ответ, заматчит транзакцию, найдёт коллбэк диалога в её состоянии и вызовет его), это ещё юнит-тест или уже интеграционный?
А если я реально пришлю UDP пакет в транспорт, это уже интеграционный тест или ещё нет?
А если это будет TLS поверх TCP (расшифровка которого делается в third-party в лице OpenSSL)?

С моей точки зрения, это всё функциональные тесты, и пофиг, что из них считать "юнитами". А как в остальном мире?
The God is real, unless declared integer.
Отредактировано 18.06.2021 9:44 netch80 . Предыдущая версия .
Re[10]: Тестирование бесполезно
От: Poopy Joe Бельгия  
Дата: 18.06.21 09:57
Оценка: +1
Здравствуйте, netch80, Вы писали:


N>Конечно, нет. Может, у тебя один тест, который проверяет, как main() разбирает аргументы, и он зелёный

Во, ты начинаешь что-то подозревать. Прикол в том, что это ничем не отличается ни от 1000, ни от 10000.

N>1) Разумность самих тестов (метода, набора тестовых данных), с точки зрения нахождения проблем реализации согласно задаче и выбранному методу.

И как ты проверяешь разумность?

N>2) Верификация кода (хотя бы визуальная) на то, что реализован действительно нужный подход (а не поставлен, грубо говоря, большой if на конкретные тестируемые случаи).

Жесть какая...

N>3) Достаточное покрытие нужного-по-ТЗ кода тестами (несмотря на всю условность этого понятия).

Достаточное это какое?

N>4) Доверие среде и библиотекам.

А нафига тогда все предыдущие?

N>Вот после этого можно говорить — не абсолютно, но с практически достаточной уверенностью — про отсутствие багов.

И че хоть раз такое происходило? Ну, только честно.

N>И да, в это я верю. Как-то практика показывает, что именно так и оно и работает

В стране с единорогами?

N>Были, где, грубо говоря, 90%. Сейчас крайне мало — но это потому, что ресурсов нет. А так я бы и сейчас добавил переменных.

Охотно верю, был демо проект, где 90% и реальный код, где их почти нет. Я ровно об этом.

N>Если ты используешь тесты ровно для этого — это твои личные ограничения.

Увы, не мои. Это ограничение самой методики. Вот честно, хотелось бы иметь волшебную технологию уровня "компилируется — в продакшн"

N>А почему ты в этом рассмотрении предполагаешь только внутренние кодовые тесты?

Потому что речь о ТDD. Впрочем, заказчика вообще никакие тесты не интересуют. Я, по-крайней мере, таких не видел.

N>Это ловится на других уровнях и другими методами.

Какими?

N>А кто только что писал про предыдущую спецификацию? Сам уже не помнишь, что писал?

Я вообще не понял, что ТЫ написал. Я либо впервые использовал слово спецификация, либо использовал его до этого. Оба утверждения твои и оба они не могут быть верными одновременно.

N>OK. Представим себе, что "спецификация" это "полное и точное ТЗ", и пойдём дальше. Так откуда взялась предыдущая спецификация?

I'm lost. Полное и точное ТЗ, это функциональные требования к системе, это функциональные тесты, в лучшем случае.
Спецификация о которой идет речь это спецификация на отдельные куски кода, которые ты покрываешь тестами. Представим, что теплое это мягкое и пойдем дальше.

N>Ну вот я выше и описал. Разница между "ничего не гарантируют" и "статистически гарантируют поиск >90% ошибок", по-твоему, важна или нет?

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

N>Сарказм понят, но не оценён. Нарвёшься на то, что будешь отказываться от доступных средств из-за гордыни.

От каких доступных средств я отказываюсь? От тестов? Это ты сам придумал.
От построения из них карго-культа? Так это ты нарвешься, думая, что они тебе чего-то там гарантируют.
Отредактировано 18.06.2021 9:59 Poopy Joe . Предыдущая версия .
Re[10]: Тестирование бесполезно
От: Sharov Россия  
Дата: 18.06.21 10:01
Оценка:
Здравствуйте, netch80, Вы писали:

PJ>>Задача тестов одна, я ее упоминал выше. Отслеживать изменение поведение кода при рефакторинге.

N>Если ты используешь тесты ровно для этого — это твои личные ограничения.

А для чего еще нужно использовать юнит-тесты кроме как "локально" корректности кода? Ловить
проблемы при рефакторинге или изменении BL.
Кодом людям нужно помогать!
Re[11]: Разработка через тестирование бесполезна
От: Sharov Россия  
Дата: 18.06.21 10:23
Оценка:
Здравствуйте, netch80, Вы писали:


N>Transport layer незамоканный отправляет в сеть и принимает; замоканный зовёт нужные коллбэки.

N>Уровень транзакций незамоканный общается с транспортным, замоканный дёргает вызовы некоего мока.
N>Ну и с третьим точно так же.
N>Если я тестирую диалоговый уровень — что например по получению "200 OK" произошёл переход состояния объекта Dialog из Trying или Early в Confirmed, и посылаю это как вызов processResponse() от транзакционного модуля, это юнит-тест?

Да.

N>А если я сделаю то же самое, сэмулировав сетевой ответ от транспорта (тогда у транзакционного его processIncoming() опознает ответ, заматчит транзакцию, найдёт коллбэк диалога в её состоянии и вызовет его), это ещё юнит-тест или уже интеграционный?


Я бы сказал да. Ну точно не интеграционный.

N>А если я реально пришлю UDP пакет в транспорт, это уже интеграционный тест или ещё нет?


Интеграционный тест. Проверяем все целиком, т.е. вполне реальное взаимодействие. Т.е. если провели
с сетевой картой, то тест упадет.

N>А если это будет TLS поверх TCP (расшифровка которого делается в third-party в лице OpenSSL)?


Зависит от, см. выше. Если хоть что-то замокано, то не интеграционный точно.

N>С моей точки зрения, это всё функциональные тесты, и пофиг, что из них считать "юнитами". А как в остальном мире?


Ну нет, есть все же разница. Речь об уровне изоляции. В остальном мире что-то вроде этого (я никак не прочитаю) --
https://martinfowler.com/articles/practical-test-pyramid.html
Кодом людям нужно помогать!
Re[11]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 10:27
Оценка:
Здравствуйте, Poopy Joe, Вы писали:

N>>Вот после этого можно говорить — не абсолютно, но с практически достаточной уверенностью — про отсутствие багов.

PJ>И че хоть раз такое происходило? Ну, только честно.

Постоянно происходит, честно.
Например, QA в очередном релизе отловил 20 багов; у кастомеров сработало ещё 10; перед этим запуском в Jenkins было поймано и исправлено 300-400.
Перед этим ещё 100 (народ достаточно ленив) поймано самими программистами, в варианте "вот я наверно это сломаю... пойду запущу сразу, не дожидаясь получасового прогона всех тестов".
Цифры меняются, соотношение примерно похоже на это.

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

N>>Ну вот я выше и описал. Разница между "ничего не гарантируют" и "статистически гарантируют поиск >90% ошибок", по-твоему, важна или нет?

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

Ну вот пока ты будешь так думать, будешь предельно непрактичен.
И я не зря "подпёр" полезность тестов условием верификации кода.

N>>И да, в это я верю. Как-то практика показывает, что именно так и оно и работает

PJ>В стране с единорогами?

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

N>>Конечно, нет. Может, у тебя один тест, который проверяет, как main() разбирает аргументы, и он зелёный

PJ>Во, ты начинаешь что-то подозревать. Прикол в том, что это ничем не отличается ни от 1000, ни от 10000.
N>>1) Разумность самих тестов (метода, набора тестовых данных), с точки зрения нахождения проблем реализации согласно задаче и выбранному методу.
PJ>И как ты проверяешь разумность?

По каждому случаю отдельно.
Вот пример (не мой): у процессора нет операции умножения, надо её сэмулировать. Делается вариант 16*16->16 с откидыванием старшей части. Знаем, что будет какой-то цикл по битам.
Добавляем тесты: 0*0 -> 0, 1*0 -> 0, 1*1 -> 1, 2*0 -> 0, 0*2 -> 0, 2*2 -> 4, 2*-2 -> -4, -2*2 -> -4, 2*2 -> 4.
Ещё парочку базовых, типа 137*73 -> 10001.
На переполнение: 256*256 -> 0, 257*257 -> 513, -32768*3 -> -32768...
Пара десятков таких тестов покроет и базовую функциональность, и маргинальные случаи, с запасом на все типовые алгоритмы.

N>>2) Верификация кода (хотя бы визуальная) на то, что реализован действительно нужный подход (а не поставлен, грубо говоря, большой if на конкретные тестируемые случаи).

PJ>Жесть какая...

Что удивляет-то? Никогда peer review не проходил? Ну, всё впереди.

N>>3) Достаточное покрытие нужного-по-ТЗ кода тестами (несмотря на всю условность этого понятия).

PJ>Достаточное это какое?

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

N>>4) Доверие среде и библиотекам.

PJ>А нафига тогда все предыдущие?

Ну мало ли. Вдруг в следующей версии починят? )

N>>Были, где, грубо говоря, 90%. Сейчас крайне мало — но это потому, что ресурсов нет. А так я бы и сейчас добавил переменных.

PJ>Охотно верю, был демо проект, где 90% и реальный код, где их почти нет. Я ровно об этом.

Это у тебя демо, а у меня был полностью реальный.

N>>Если ты используешь тесты ровно для этого — это твои личные ограничения.

PJ>Увы, не мои. Это ограничение самой методики. Вот честно, хотелось бы иметь волшебную технологию уровня "компилируется — в продакшн"

Ограничения у методики есть, но сильно дальше, чем ты их видишь.

N>>А почему ты в этом рассмотрении предполагаешь только внутренние кодовые тесты?

PJ>Потому что речь о ТDD.

Нет, не только.

PJ> Впрочем, заказчика вообще никакие тесты не интересуют. Я, по-крайней мере, таких не видел.


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

N>>Это ловится на других уровнях и другими методами.

PJ>Какими?

Да хоть ручной проверкой. Это уже не наша задача.

N>>А кто только что писал про предыдущую спецификацию? Сам уже не помнишь, что писал?

PJ>Я вообще не понял, что ТЫ написал. Я либо впервые использовал слово спецификация, либо использовал его до этого. Оба утверждения твои и оба они не могут быть верными одновременно.

Я про предыдущую спецификацию вроде не писал первый.

N>>OK. Представим себе, что "спецификация" это "полное и точное ТЗ", и пойдём дальше. Так откуда взялась предыдущая спецификация?

PJ>I'm lost. Полное и точное ТЗ, это функциональные требования к системе, это функциональные тесты, в лучшем случае.
PJ>Спецификация о которой идет речь это спецификация на отдельные куски кода, которые ты покрываешь тестами. Представим, что теплое это мягкое и пойдем дальше.

Ну у тебя почему-то ТЗ это сверху, а спецификация это снизу. Я не вижу причин так делить.

N>>Сарказм понят, но не оценён. Нарвёшься на то, что будешь отказываться от доступных средств из-за гордыни.

PJ>От каких доступных средств я отказываюсь? От тестов? Это ты сам придумал.
PJ>От построения из них карго-культа? Так это ты нарвешься, думая, что они тебе чего-то там гарантируют.

Я получаю с них реальную пользу — баги ловятся задолго до попадания к кастомеру. А ты можешь продолжать искать и требовать воздушные замки.
The God is real, unless declared integer.
Re[12]: Тестирование бесполезно
От: Poopy Joe Бельгия  
Дата: 18.06.21 12:36
Оценка:
Здравствуйте, netch80, Вы писали:

N>Постоянно происходит, честно.

Как это сочетается с следующим предложением?
N>Например, QA в очередном релизе отловил 20 багов; у кастомеров сработало ещё 10;

N> перед этим запуском в Jenkins было поймано и исправлено 300-400.

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

N>Цифры меняются, соотношение примерно похоже на это.

Ну, я хотя бы понял, что у вас называется "отсутствием багов". Оказалось, что просто общаемся из разных планов бытия.

N>Ну вот пока ты будешь так думать, будешь предельно непрактичен.

Возможно, зато у нас кастомеры не ловят в "безбаговых" продуктах по 10 багов + еще хрен знает сколько не пойманых.

N>Единорогов не впрягали, за неимением таковых.

Угу, у вас вместо них кастомеры.

N>Что удивляет-то? Никогда peer review не проходил? Ну, всё впереди.

Ты ща начал размером опыта давить что ли? Не стоит.
Я никогда не видел, чтобы ревью чего-то доказывало. Особенно уровня "у тебя тут if не хватает".

N>100% хотя бы одним тестом каждого куска кода основного пути выполнения.

Понятно, тесты ради тестов, покрытие, ради покрытия.

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

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

N>Нет, не только.

Ну может ты еще о чем-то своем, но я говорил о разработке через тестирование.

N>Ну я видел, и работал с. И ты не учитываешь внутреннего заказчика в продукте.

Нет конечно, им точно так же похрен на твои тесты.

N>Да хоть ручной проверкой. Это уже не наша задача.

Что не твоя задача? Качество? Тогда зачем париться с тестами?

N>Я про предыдущую спецификацию вроде не писал первый.

Слово спецификация впервые употребил ты. http://rsdn.org/forum/flame.comp/8032039.1
Автор: netch80
Дата: 18.06.21
Если ты тестами описываешь спецификацию, то новый тест спецификацию расширяет/меняет, поэтому старая она становится предыдущейю. Не бог весть какая логика. Дальше я твою мысль не понимаю вообще.

N>Ну у тебя почему-то ТЗ это сверху, а спецификация это снизу. Я не вижу причин так делить.

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

N>Я получаю с них реальную пользу — баги ловятся задолго до попадания к кастомеру. А ты можешь продолжать искать и требовать воздушные замки.

Ага, я вижу.
Re[13]: Тестирование бесполезно
От: netch80 Украина http://netch80.dreamwidth.org/
Дата: 18.06.21 12:54
Оценка: +1
Здравствуйте, Poopy Joe, Вы писали:

N>> перед этим запуском в Jenkins было поймано и исправлено 300-400.

PJ> Вам надо ваш процесс переименовать с разработки через тестирование, на разработку через багфиксы.
N>>Цифры меняются, соотношение примерно похоже на это.
PJ>Ну, я хотя бы понял, что у вас называется "отсутствием багов". Оказалось, что просто общаемся из разных планов бытия.

Это очень прикольно, учитывая, что 1) я никогда не говорил, что ведём "разработку через тестирование", 2) никогда не утверждал отсутствие багов как результат применения тестов.

С кем ты тут споришь — не знаю, но это не я. Кто там у тебя на твоём плане бытия — не в курсе.

На этом я прекращаю. Продолжение будет возможно с собеседником, который общается со мной, а не с неизвестными астральными проекциями.
The God is real, unless declared integer.
Re[14]: Тестирование бесполезно
От: Poopy Joe Бельгия  
Дата: 18.06.21 13:11
Оценка:
Здравствуйте, netch80, Вы писали:

N>Это очень прикольно, учитывая, что 1) я никогда не говорил, что ведём "разработку через тестирование", 2) никогда не утверждал отсутствие багов как результат применения тестов.


Для того, чтобы с достаточной уверенностью доверять результатам тестов, нужно:
1) Разумность самих тестов (метода, набора тестовых данных), с точки зрения нахождения проблем реализации согласно задаче и выбранному методу.
2) Верификация кода (хотя бы визуальная) на то, что реализован действительно нужный подход (а не поставлен, грубо говоря, большой if на конкретные тестируемые случаи).
3) Достаточное покрытие нужного-по-ТЗ кода тестами (несмотря на всю условность этого понятия).
4) Доверие среде и библиотекам.

Вот после этого можно говорить — не абсолютно, но с практически достаточной уверенностью — про отсутствие багов.


Погоди, перед тем как уйдешь, позови, пожалуйста, того, кто писал эту цитату с твоего аккаунта.
Отредактировано 18.06.2021 13:12 Poopy Joe . Предыдущая версия .
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.