суббота, 30 июня 2018 г.

МОПС - сборщик мусора

МОПС = Метод Отложенного Поиска Смысла, Можно Обдумать После Спринта, Мобильная Организация Проверки Сомнений

Проанализировав свой стиль работы, могу предложить вам верные шаги для повышения эффективности тестировщика.
МОПС реализую через сбор скриншотов и последующее оформление багов и предложений.
Во время тестирования обязательно попадаются случайно-странные баги, на исследование, локализацию и оформление которых не планируется время во взятом в работу тесте. Поэтому с подозрительных мест моментально снимаю скриншоты с помощью виндовых ножниц или Picpick, помечаю маркером или просто пером спорные случаи и откладываю (сохраняю) картинку в особую папку. У каждого файла в имени: исследуемый продукт, билд и краткое имя основного бага. Папка со скриншотами имеет доступ из разных мест - комп с установленным продуктом, развёрнутая баг-трекинговая система, консультанту предоставляется быстрый линк на картинку. На протяжении теста приходит понимание о важности бага, локализуются тонкости или определяются предложения по модернизации. По окончании теста (после рабочего дня или спринта, поэтому имя файла конкретизируется билдом и кратким названием бага) выделяю время на актуализацию и оформление задач. После рассмотрения каждого скриншота его файл удаляется из папки временных багов, тем самым виден объём работ до окончания.

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

Общее время теста равно количеству опций (по  одной из каждого класса эквивалентности) помноженному на 2-5 минут в зависимости от скорости памяти оперативной (иногда достаточен перезапуск формы) и постоянной (обязателен перезапуск приложения).

Проверка внешнего вида формы настроек (размер и  расположение элементов, грамотность подписей) в тест о сохранении/восстановлении не входит. Поэтому все отклонения выравниваний, размерности шрифтов, цветовые сочетания, опечатки складируются в папку временных багов МОПС. Для таких мелких ошибок обычно достаточно виндовых ножниц, либо настраиваем приложение для снятия скриншотов на активное окно. Первый сохраняемый файл называем "КороткоеИмяПродукта_НомерБилда_КраткоеИмяБага". Все последующие скриншоты, используя возможности приложения, будут автоматически сохраняться в папку МОПС и нам лишь остаётся подправлять окончание в имени файла или увеличивать последовательно номер. Но более полезно менять "КраткоеИмяБага", поскольку на оформление и локализацию задач из папки МОПС обычно время выделяется из числа неоплачиваемого.
Логичность зависимостей опций между собой (например, шрифт в приложении использовать стандартный или индивидуальный; если настраиваемый, то опции формата должны быть доступны для изменений, иначе - только на просмотр) тоже не входит в наш изначальный тест. А поскольку нашим тестом проверяются все опции, то вполне возможно, что какие-то опции могут быть сгруппированы и включаться по глобальной выборке. Эти предложения откладываются в папку МОПС, поскольку требуют вмешательства со стороны консультантов, да и время теста на обсуждение не планировалось. Скриншоты в таких случаях более полезны со всего экрана, то есть запущенный PicPick (или иное приложение) настраиваем на снятие скриншотов всего рабочего стола.
Сопутствующие баги настроек иногда выявляются путём проверок синхронизаций (опция выставляется в форме настроек, а меняться может в пользовательской форме с прямым назначением: параметры принтера удобно корректировать перед самой печатью). Если пользовательская форма не имеет синхронизации с формой настроек, то такие баги, конечно же, не относятся к нашему изначальному тесту, но вполне их можно обнаружить при проверке восстановлений опций. Поэтому такие (чаще спорные моменты, которые программисты называют фичами) сомнительные моменты временно оформляем в папку МОПС. Старайтесь снять скриншот так, чтобы в его область попало сразу всё - и окно настроек, и пользовательская форма, либо воспользуйтесь видео-рекодером.

Шаги МОПСа:
- Создать папку с общим доступом:
-- для консультантов, аналитиков, программистов права на чтение. Не давайте пополнять им эту папку, иначе утонете в завалах;
-- к папке есть доступ из компа с тестируемым продуктом для создания файлов-скриншотов. Поскольку для тестируемых приложений обычно разворачивается виртуальная машина, то следует заранее продумывать её структуру, в том числе и доступ ко всем необходимым папкам, документам и вспомогательным приложениям (для снятия скриншотов должна работать клавиша PrtSc или копирование в буфер, для записи видео нужна специальная программа);
-- к папке есть доступ из системы контроля версий для редактирования, загрузки в баг-трекинговую систему, удаления использованных скриншотов.
- Во время проведения основного теста снимать скриншоты и складывать их в папку временных багов. Файлам давать имена с указанием продукта, билда, основного подозрительного момента.
- Актуализация, локализация и оформление выявленных спорных моментов проводятся по окончании теста, в конце рабочего дня (лучше на следующий день с утра) или спринта. Чем раньше будет выполнена эта работа, тем легче будет проводить локализацию, так как билд может смениться или подробности забудутся. Желательно проводить этот шаг в рабочее время, поскольку иногда требуется консультация других сотрудников, поэтому более лучшее время - утро следующего дня (как в поговорке "утро вечера мудренее" - проверено, локализация проходит быстрее на свежую голову). Поскольку МОПС - это метод организации работы тестировщика, то желательно руководителям запланировать время на работы по очистке папок МОПС для каждого сотрудника, в том числе и консультантов.
- Каждый использованный скриншот удаляется после актуализации и оформления. Полезные скриншоты отправляются в БТС с соответствующей корректировкой (удаляются лишние поля, добавляются пометки). Постепенное очищение папки временных багов показывает скорость вашей работы и даёт надежду на скорое её окончание, то есть мотивирует вас на достижение цели - чистота в папке временных багов ведёт к чистоте всего продукта.

Собаки мопсы - коротконогие, а шаги МОПСа позволяет по скорому тестировать и экономить рабочее время за счёт сокращения отвлеканий от основной идеи. Скарлетт О'Хара твердила: "Об этом я подумаю завтра" и не забивала голову лишними проблемами. Откладывайте актуализацию на завтра, но помечайте каждый момент, тогда ваше внимание не будет распыляться на временные препятствия, да и "всякие мелочи" не ускользнут от профессионала.

пятница, 29 июня 2018 г.

GDPR - доверяй и проверяй

Возврат к бюрократии или Сотрудник на доверии
(рубрика - Нюх на баги)

Европейское сообщество решилось на усовершенствование охраны данных. Теперь тестировщикам и сотрудникам отделов тех-поддержки необходимо в срочном порядке совершенствовать свои знания в области юриспруденции.
Начать обучение следует с самого документа - "General Data Protection Regulation (GDPR)".
В большей мере вопрос касается персональных, конфиденциальных данных. А есть ли в них различие? Что об этом думают эксперты? Читайте "Experts on the GDPR #3: What is personal data under the GDPR?".
С технической точки зрения эксперты определили облачные сервисы для защиты данных - "Experts on the GDPR #4. Storing encrypted personal data in the cloud: What is the most secure option?", "EU GDPR: соблюдение требований регуляторов в сфере облачных вычислений".
Какая же ответственность теперь будет у сотрудников техподдержки первого уровня и тестировщиков? Для техподдержки объектом пристального внимания становится информация о кастомерах, которую необходимо дифференцировать по территориальному признаку - индивидуальные данные от покупателей и поставщиков следует хранить и обновлять в рамках GDPR, компаньонов из других стран позволено обслуживать в прежнем режиме, только если они не связаны с европейцами. Было бы проще ко всем применить политику GDPR, но Вы уверены, что иные страны не имеют более жёстких условий? Поэтому техподдержка первого уровня - одно из самых важных звеньев в процессе фильтрации данных. Например, баг от пользователя должен храниться во внутренней системе компании разработки, а все контакты пользователя в независимой базе, вплоть до отдельного сервера. Получается, связующее звено "техподдержка" при этом несёт полную ответственность за линковку данных об исправляемом баге и пересылаемом отчёте пользователю. Тестировщику, оформляющему баг в базу при этом придётся унифицировать проблему, применяя переименование и аггрегацию для сокрытия данных от сторонних глаз. А Ваши базы контрагентов и задач готовы к такой конфиденциальности?
Создавая и тестируя базы данных в программном продукте, выпускаемом Вашей компанией, следует более тщательно контролировать простоту наименований таблиц и полей, связей реляционных баз и доступность их описания. В этом плане хороший пример в OEBS, где таблицы и поля имеют нелогичные наименования, в основном состоящие из цифр, что хорошо запутывает взломщиков. Также должны быть усилены тесты по способам и местам хранения данных - физические носители, облачные сервисы, удалённое управление с ограничением прав доступа и функций. При пересылке данных должны использоваться высоко-защищённые от несанкционированного доступа способы, а пересылаемые данные защифрованы в обязательном порядке. Также не менее важно проверять объём информации, присылаемой с отчётом о баге, чтобы в ней не хранилось что-либо, идентифицирующее пользователя продукта. Объём и содержимое пересылаемых данных необходимо проверять на актуальность, необходимость и достаточность, предотвращать скрытые пересылки (без ведома пользователя) паролей, IP-адресов, списков баз и прав доступа, прочих идентификаторов.
Список ответственных за сохранность данных не ограничивается техподдержкой. Компания, выпускающая десктопный продукт и продающая его через свой сайт, вполне может быть распределённой: например, зарегистрирована компания в США, разработчики и тестировщики фактически раскиданы по России и Украине, маркетологи разъезжают по всему миру, сервера с исходниками и данными пользователей могут быть распределены  по всему миру. Удобнее иметь сервера с исходным кодом и задачами поближе к группе разработки, а сервис продаж в Европе. Но при этом копия базы данных покупателей обязана быть у разработчика в оригинале, а не переименованная, поскольку могут быть проблемы, напрямую зависящие от комбинации исходных данных. Такие моменты прописаны в GDPR как доступ к данным по запросу "Art. 15 GDPR  Right of access by the data subject". О предварительных действиях компании разработки рассказано в "How to prepare for Data Access Requests under GDPR", "GDPR data access portal: Logging into the GDPR data access portal, Making a data access request, The data access request excel template, Making a data deletion request, Making a data change request, Making a consent change request".
Поскольку дело теперь уходит в юридическую область, которая верит только документам, то процесс тестирования и техподдержки становится более бюрократичным. Для чего компания обязана принять внутреннее соглашение и неукоснительно следовать ему. В противном случае, компания подвержена опасности разорения при утере данных пользователем Вашего продукта.

четверг, 28 июня 2018 г.

Ударный Тест

Ударное слово при Тест-дизайне
(рубрики ТТ = Театр и Тестировании, Нюх на баги)

Театральному мастерству много веков, тестирование же намного моложе. Многие приёмы актёрской профессии вполне применимы и к тестированию.
Основные понятия драматургии удобно использовать при планировании работы тестировщика, о чём подробнее будет рассказано позже. Этот мастер-класс нацелен на один из первичных шагов - тест-дизайн. Порою довольно сложно приступить к созданию тестовых случаев, особенно если продукт новый для Вас. Для составления полноценного списка тест-кейсов воспользуемся упражнением по актёрскому мастерству, когда ударения на словах в предложении меняются для разнообразия смысла фразы.
В русском языке имеются такие знаки препинания как "запятая" и "точка", в большинстве случаев ударным считается последнее слово перед запятой или точкой с поднятием интонации перед запятой и опусканием перед точкой, но обычно им является глагол. Для английского языка характерны порядок слов в предложении и отсутствие запятых, более привычные в русском. Поэтому основным ударным словом в английской речи получается какое-нибудь причастие, деепричастие. Но при художественном чтении, а особенно поэзии, ударным словом может быть любое слово из предложения. Для развития навыка театральные курсанты обычную фразу произносят на разные лады, меняют ударное слово, повышая звучание или протяжность гласных.
Пример:
ОТ топота копыт пыль по полю летит
от ТОПОТА копыт пыль по полю летит
от топота КОПЫТ пыль по полю летит
от топота копыт ПЫЛЬ по полю летит
от топота копыт пыль ПО ПОЛЮ летит
от топота копыт пыль по полю ЛЕТИТ
Произнесите фразу 6 раз с различными ударениями на выделенные слова.

По аналогии с вышеописанным упражнением составим тест-кейсы, исходя из текста (короткого и подробного) техзадания. Как принято в большинстве компаний, короткое наименование задачи отвечает на вопросы "Что? Где? Когда?", это упрощает задачу составления тест-кейсов.
Пример техзадачи:
Краткое описание: "Окно Windows Notepad не закрывается с новым (только-что созданным) текстом"
Подробное описание: "По кнопке 'x' (крестик в правом верхнем углу) не пустое окно Windows 10 Notepad не закрывается после благополучного закрытия диалога о сохранении файла, если оно было открыто для создания нового текстового файла."
Из краткого описания выделяем 4 тестируемые сущности:
- окно Windows Notepad;
- не закрывается;
- с новым (только-что созданным);
- текстом.

Тест-кейсы первой группы будут нацелены на воспроизведение аналогичной проблемы в иных текстовых редакторах (MS Word, Aditor, Notepad++ и другие редакторы, доступные на тестовом стенде) или приложениях со сходными функциями (набор или вставка текста, изображения, звука, видео данных из буфера).
Вторую группу тестов описываем на действия с окном: закрытие, открытие, переоткрытие, дублирование экшена вручную и автоматически. Общее правило: если используется глагол, то выпишите его известные синонимы и антонимы, по которым сформируйте тест.
Третью группу тестов формируем для новосозданных и ранее имевшихся файлов. Здесь же стоит проверить способы создания: ручной или рукописный набор, вставка из буфера, drag&drop, виртуальная клавиатура, специальные возможности пользователей с ограниченными возможностями, сканирование и иные новомодные примочки. 
И в четвёртой группе тестов проверяем типы данных: текст и иные символы, пустота и пробелы, двоичный код (исполняемые файлы, аудио-видео, иной не текстовый формат).

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

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

среда, 27 июня 2018 г.

Привычка кодить

Прогноз проблем по привычкам программиста
(рубрика - Нюх на баги)
Исходя из многолетнего опыта работы программистом, аналитиком-внедренцем, в тестировании и техподдержке могу заверить вас, что у каждого разработчика есть свой почерк написания кода. И не важно насколько строгие правила кодирования приняты в компании: кто-то играет с порядком параметров, кто-то с наименованиями объектов, кто-то с самописными или стандартными подпрограммами. Одно и тоже действие можно написать, используя стандартные функции (тогда тестировщикам заранее известны слабые места кода), а могут сочинить универсальный или сложно-запутанный код, от которого тестировщикам можно будет ждать всяких непредвиденных ситуаций.
Поэтому, чтоб тестирование не получалось всегда неожиданностью, ниже сопоставлены некоторые человеческие особенности с написанным программистом кодом. А именно, с самым распространённым действием – чаепитие или кофе-брейк. В зависимости от того, как программист готовится или завершает чайно-кофейную церемонию, родились связки с его фирменными ошибками. Когда же сфера IT перешла в удалённый режим, и команды стали распределёнными, естественно пропала возможность наблюдать за общением программиста со "своей кружкой". Но, оказалось, что по скриншоту рабочего стола тоже можно определить тип программиста.
В начале карьеры мои обязанности ограничивались программированием и техподдержкой. В те времена о тестировании вообще никто не говорил и не слышал, потому что сами программисты выполняли аналитику, кодирование, отладку, внедрение и поддержку. Но в силу того, что отпуска в своём большинстве давались полностью (вплоть до 40 рабочих дней), то кому-то приходилось замещать сотрудника в ответственные дни отчётов. В до-САПР-овские времена, когда не было "Галактика" или "Axapta", автоматизация предприятий проводилась собственными силами, а это значит весь код был самописным, без особых корпоративных стандартов. В то время легко было определить почерк кодера: кто-то давал переменным и объектам особенные имена (короткие, нелогичные, без привязки к функционалу), кто-то использовал особые конструкции или ранее-написанные собственные блоки. И если вдруг в отсутствии замещаемого сотрудника падал код, то заместителю поначалу приходилось тратить не мало времени на понимание такого легаси. Вспомните себя студентом, переписывающим пропущенные конспекты лекций от разных однокашников: не с первой страницы начинаешь бегло читать чужой почерк. Также и с легаси-кодом – не с первого блока кода понимаешь логику прописанных команд.
После перехода из универсальных программистов в разряд всемогущих тестировщиков в моём арсенале разнообразия почерков программистов стало больше. При чём сюда добавились и аналитики, и конечные пользователи, присылающие своё видение на проблемы продукта. Высоким словом "разработчик" в некоторых компаниях называют программиста, совмещающего роль с аналитикой. Поэтому, как продумаешь логику, так она и отработает в коде. В моём докладе о лёгкости тестирования кода с помощью утилит аудиторов кода уже говорилось об основных причинах самых заковыристых багов. Они-то и кроются в особенностях почерка кодировщика. А коль скоро характер программиста не перевоспитаешь, то и его фирменные баги вы сможете вылавливать в первую очередь. На счёт скорости обнадёживать вас не буду, но направления для поиска вам будут очевидны.
Итак, типы почерков программистов делю на 6 групп.
Чистюля (аккуратист, педант)
На его рабочем столе никогда не бывает ничего лишнего, весь минимальный набор (клавиатура, мышь, за редкостью чистый лист и карандаш) расставлен "под линеечку", ни пылинки-соринки, ничего мешающего рабочему процессу. Если говорить об иконках на рабочем столе операционной системы компа, то там могут быть лишь стандартные приложения, либо всё необходимое разнесено по папкам. Свою кружку моет сразу после чаепития и убирает на строго отведённое место в закрытом шкафу.
Исходя из описанного поведения, программист-чистюля привык писать код так, чтобы объём и логика кода строго соответствовали описанному заданию, все переменные после использования были очищены. Вроде бы всё должно быть прекрасно, но программист-педант опасен тем, что программа часто недостаточно обрабатывает исключения, не прописанные в ТЗ, либо умышленно опущенные из-за их стандартности, он же привык, что всё разложено по полочкам и ничего лишнего не мешает его взгляду. Перед использованием переменных программист-аккуратист забывает проверить их на корректность объявления и присвоения значений, он же привык, что его кружка всегда чистая. Поэтому код от программиста-чистюли надо проверять исследовательским методом на неописанные в ТЗ ситуации, нагрузочные и интеграционные тесты делать на передаваемые и входящие переменные. В качестве профилактики можно применять правило Code Review, результатом проверки которого является список параметров процедуры, использованных не по назначению.  
Хозяйчик запасливый
Его рабочий стол напоминает склад тысячи мелочей, ящики тумбочки еле закрываются от всего "очень нужного", вполне вероятно он оккупировал и рядом стоящий шкаф под свои полезняшки. Иконок на рабочем столе компьютера видимо-невидимо, разбросаны по всей площади и на первый взгляд в хаотичном порядке. Скорее всего кружку для кофе или чая он держит на своём же рабочем столе, чтоб она всегда была "под контролем", моет её тщательно перед чаепитием. В силу привычек, программист-хозяйчик пишет код "с запасом", программирует неописанное в ТЗ, но на его взгляд возможное при исполнении программы. Код запасливого программиста надо проверять на избыточность объявленных переменных, на достаточность алгоритмов без половинчатого кодирования единичных исключений. Код хозяйственного программиста может быть похож на "лапшу", поэтому в качестве профилактики надо применять оптимизацию блок-схем и сокращать запланированное ему время на написание кода.
Всезнайка
Ученость всезнайки видно по обилию литературы на столе, рабочий стол компьютера – это научный отдел всемирной библиотеки или линки на всевозможные новостные каналы. У него отдельные кружки и стаканы, бокалы для чая, кофе и прочих жидкостей. Их много, и все они разные. Исходя из жизненных пристрастий, код всезнайки заумен, изобилует сторонними библиотеками, возможна перестраховка в виде шифрования. Проверку стоит начинать с поиска "мёртвого" кода. Множество унифицированных вспомогательных функций можно единожды привести в соответствие, но их использование заумным программистом усугубляет интеграционные баги. Обязательной профилактикой для всезнайки служит публичный процесс Code Review, нагрузка по передаче знаний и умений сотрудникам всех отраслей, что позволяет ему понять причины собственных ошибок. Не ограничивайте свои тесты программы от Всезнайки только теорией от гуру, поскольку его сочинение может оказаться слишком навороченным. Пример о граничных значениях: обе функции определяют принадлежность значения к определённому числовому промежутку, но описанный способ матрицы можно применить только к функции "if_cycl" при тестировании "чёрным ящиком".


Рубаха-парень (общительный)
Любитель поболтать вместо кодирования опознаётся по количеству средств связи на рабочем столе. Это могут быть как различные виды телефонов, смартфонов, раций, так и иконки чатов, конференций, аудио-видео коммуникационных каналов. "Свой парень" предпочитает чайно-кофейные кружки из общей кухни, за которыми не надо следить и мыть. У общительного программиста вместо кода на первом месте коммуникации, поэтому программа может быть просто недописана, либо блоки после копи-паста недоправлены. В первую очередь продукт от ультра-разговорчивого программиста надо проверять на точное соответствие ТЗ в области полноты и законченности, каждый из новых пунктов проверять на корректность, не допуская частичной выборки классов эквивалентности. В качестве профилактики по недопущению им багов предлагается не отвлекать его от работы, а общение на нерабочие темы выносить только в перерывы.
Фантазёр жизнелюбивый, живчик
Радость жизни в код не впишешь, и по хаосу на рабочем столе его легко выявить. Среди иконок не мало игр. Кроме компьютера на столе бытовое множество вещей, будто дом или объект его увлечения переехал на работу. Разнообразные чайно-кофейные кружки, в том числе и чужие, можно найти не только на столе, но и в тумбочке, или на чужом столе. Он не замечает даже, когда меняет бокалы, стаканы на общественные или соседские. Это признаки (законы) общежития, и они отражаются в его коде в виде опечаток, обилия неоптимизированного кода, неочищенных переменных и параметров без присвоенных значений. Из-за лёгкого отношения программиста к жизни тестировщику нужно тщательно проводить регрессионные и нагрузочные тесты. Профилактикой может быть работа в паре с Чистюлей или Всезнайкой до момента, когда за него будут выполнять более 30-40% задач.
Пофигист (разгильдяй, тупокодер)
Бардак и грязь на столе, немытые кружки, минимум иконок – признаки тупокодера. Его код не низок, не высок, не узок, не широк, то есть на первый взгляд в точности соответствует ТЗ. Но опасайтесь недописанных блоков, недопроверенных опечаток, неучтённых исключений, незакрытых уязвимостей. Все виды и методы тестирования актуальны для кода от пофигиста. Растормошить его можно доверить любому увлечённому общим делом сотруднику.

Рекомендации по определению типов: смотрите когда и как тщательно программист моет кружку (до или после чае-кофе-пития), сколько их у него и в каком они состоянии, что ещё имеется на рабочем столе, изучите расположение иконок в его операционной системе. Проанализируйте баги и их причины, составьте таблицу в разрезе программистов. Обычное наблюдение даст вам понятие о почерке программиста: сопоставьте типы кодеров и их фирменные баги. Впоследствии можете начинать тестирование с фирменных багов, это ускорит Вашу работу и повысит качество продукта, потому что будете находить проблемы, казалось-бы не очевидные, но вполне вероятные на стороне конечного пользователя.
И ещё несколько подсказок.
Типы могут пересекаться в одном программисте, поэтому подглядывать за поведением кодера стоит регулярно, особенно перед передачей задачи на тестирование.
Не буду скрывать, к некоторым перечисленным типам относится и мой стиль кодирования.
Наиболее действенна профилактика багов, когда в неё вовлечены все сотрудники. Для этого можно на стендапах или ретроспективах выделять время для напоминалок, а сами правила формулировать в стишках, песенках, поговорках или анекдотах. Например, для забывающих очищать переменные упомяните лозунг "Уходя гасите свет" с расшифровкой о нагоревших киловаттах для пустоты. Также действенны публичные Code Review с привлечением тестировщиков в качестве слушателей. Такие собрания полноценно заменяют митинги о передаче знаний.
Надеюсь, у каждого из вас уже есть свой список типов программистов и их фирменных багов. Это хорошее подспорье для увеличения скорости проверки продуктов.

вторник, 26 июня 2018 г.

Нюх на баги - развитие тестировщика

Повышение профессионализма тестировщика традиционными методами

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

1. знание теории тестирования
Знаниями теории тестирования обладает выпускник общего курса о тестировании. Но теорию можно изучать и самостоятельно, без особых лекций. Литературы по теории тестирования на сегодняшний день не мало, новые знания аккумулируются и распространяются на конференциях, в блогах, форумах и чатах/соц.сетях. Но теория без практики – ничто, поэтому теоретик в тестировании может рассчитывать только на уровень "юниор". Уровень знаний в теории тестирования имеет градацию: общие понятия (ручное-автоматизированное, стадии тестирования, планирование-результаты) для desktop-web-mobile-hard/iot, соответствие качества по стандартам iso-9126 functionality-usability-load-law-maintainability-reliability-efficiency-portability. Владение теорией тестирования помогает быстрому вхождению новичка в любую команду разработки программного обеспечения. Теоретику тестирования проще формировать планы работ и выявлять узкие места продукта и процесса разработки.

2. владение методами проведения тестирования
Тестировщик-практик без знаний теории тестирования образуется из числа программистов и пользователей. Владение некоторыми, но полноценно, методами тестирования позволяет выявлять сложные места продукта без излишних затрат времени тестировщика, иных сотрудников, вспомогательных дорогостоящих средств. Узконаправленный специалист глубоко копает, поэтому можно быть спокойным за качество кода, если это бывший программист, и за качество функционала, если тестировщик выявился в среде пользователей. Однозначно, не существует тестировщика, равнозначно владеющего всеми методами проведения тестирования, поэтому не стоит надеяться на высоту профессионализма у отличника-теоретика всех методов. Практик одного или нескольких смежных методов тестирования (ручное-автоматизированное, code-functional, smoke-integrated, load-stress, usability-law) всегда имеется в списке кандидатов. Полезным может быть только узкий специалист, но владеющий несколькими методами. Развивать и увеличивать количество методов можно на курсах, самостоятельно, в рамках практики и текущей работы. Передача навыков более эффективна внутри команды путём проведения мастер-классов. В овладении методами и вспомогательными средствами тестирования нет ничего лучше специализированных курсов, вебинаров и сообществ. При подборе специалиста с глубоким знанием определённого метода тестирования руководителю необходимо чётко знать цель тестирования, какая область продукта вызывает максимум подозрений о провальности.

3. знание предназначения продукта
Профессионализм тестировщика повышается за счёт знаний и умений в области предназначения продукта. Если ПО предназначено для кассиров, то теория бухгалтерии и финансов помогает выявлять критические места не только готового приложения, но и на более раннем этапе разработки при составлении технического задания. Общение с пользователями, наличие и повышение знаний в области применимости конечного продукта способствует росту профессионализма тестировщика. Углубленное владение теорией или практикой предназначенности продукта – лёгкий пропуск в среду уникальных тестировщиков, потому что овладение методами и теорией тестирования – дело наживное. Бета-тестеры – первые претенденты на профессионалов. Полноценность хелпов и логичность интерфейса, корректность обработки данных и удобство использования, направления развития продукта и второй уровень техподдержки – всё во власти такого спеца.

4. знание архитектуры продукта
Широкое горизонтальное и вертикальное тестирование невозможно без понимания зависимостей модулей, настроек. Постигать архитектуру приложения можно несколькими способами: из хелпа продукта и документации разработок, из блок-схем программы, из диаграмм зависимостей модулей и данных, по мастер-классам или отчётам бизнес-аналитиков и программистов, во время исследовательского тестирования. Для применения знаний архитектуры продукта в его тестировании весьма не лишними будут знания общей теории тестирования. Велика полезность таких знаний и для аналитиков с разработчиками, поэтому обмен знаниями и опытом должен проходить в разнонаправленной команде. Критичность выявляемых проблем оправдывает затраты на изучение структуры приложения. Стоимость предотвращения архитектурных багов не сравнима с затратами на их исправление. Знания углубляются и развиваются только в конкретной команде разработки, но лёгкий уровень можно достигнуть при прямом использовании продукта.

5. знание языка кодирования
День тестировщика отмечается 9 сентября, когда была обнаружена букашка в процессе отладки программы. Тестировщики первого уровня тестирования – дебаггеры – выявляют проблемы на уровне кода. Прямые кандидаты в тестировщики кода – это программисты, но, благодаря наличию утилит аудита кода в среде разработки, в число дебаггеров могут входить обычные выпускники средней школы. Качество кода – исчислимая величина, правила кодирования стабильны, соответствие кода техническому заданию проверять просто и высоко-полезно. Синтаксис языка кодирования эффективно изучать на специализированных курсах, но затраты в таком случае могут превосходить скорость вхождения в проект, поэтому тестировщику можно использовать комментарии программистов в коде, обсуждения code review и другие совещания вместо учебников. Чисто-написанный изначально код обнуляет затраты на исправление багов.

6. вспомогательные продукты для проведения тестирования
Наличие утилит, облегчающих и ускоряющих работу – путь к успеху. Автоматизация, нагрузочное и стресс-тестирование реализуемы на сторонних приложениях. Логирование положительных и отрицательных действий – большая помощь тестировщику в локализации проблемы. Закупка компанией сторонних приложений окупается только при наличии готовых специалистов по их использованию. Помогалок больших и малых, сложных и простых, бесплатных и дорогих имеется в достаточном количестве на рынке и курсах тестировщиков. На чём остановить своё внимание зависит от направленности тестируемого продукта, одного уникального помощника всем тестировщикам пока не создали.

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


понедельник, 25 июня 2018 г.

ГКЧП-4 = ТТ-2 (Драматургия)

Оформление задачи по законам драматургии
(рубрики: ГдеКакЧтоПравить-4, Тестирование&Театр-2)

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

в Театре V в BTS
Название пьесы обязательно Краткое наименование задачи
Категория произведения (комедия-драма) обязательно Тип задачи: баг, улучшение, новшество
Действующие лица обязательно Продукт, модуль, функциональные объекты
Пролог опционально Предварительные действия: выставление настроек, создание БД, отсутствие автоматизации и др.
Экспозиция обязательно Сочетание опций и мест применения
Завязка обязательно Шаги для воспроизведения
Интриги, нарастание конфликта опционально Исключительные случаи, условия локализации проблемы
Кульминация обязательно Актуальный результат, текущее неверное положение дел
Развязка обязательно Ожидаемый результат
Эпилог опционально Преференции от внедрения, линкование сопутствующих и новых проблем

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


Ссылки по теме:
Тестирование = Критика ? (ГКЧП-3)
Issue review (ГКЧП-2)
ГКЧП - Где, Как, Что Править?
Суть-Содержание
AutoRN
Дорогие trivial-ы

воскресенье, 24 июня 2018 г.

Тестирование = Критика ? (ГКЧП-3)

Статья "Почему разработчики не могут быть хорошими тестировщиками?" (корректная ссылка на использованный оригинал "Why can’t developers be good testers?") и её обсуждения натолкнули на мысль, что роль тестировщика в команде разработки часто путают с понятием о критике.
Ниже приведён перевод статьи "There’s a human on the other side of your code review" (Tadas Antanavicius, Full-Stack Engineer @SolutionLoft), в  которой автор тоже путается в формулировке отчётов о проверке кода.

##############################
Человеческий фактор при проверке кода

Для большинства разработчиков программного обеспечения проверка кода является неотъемлемой частью жизни; но в достаточной ли мере мы разделяем жизнь и код?
Не углубляйтесь в персональность комментариев, они для инженера всего лишь один из способов донести свою мысль”.
Для меня эта цитата – один из советов начинающим программистам. Я сильно не задумывался над этим, но, по-моему, смысл в словах есть.
Поскольку я сам проверяю код и моя работа ежедневно проверяется, то эти строки опять и опять всплывают в моей памяти. И совет-то весьма прост, чтобы следовать ему. Но, меня волнует – а в чём же статус-кво?
О кодревью было уже много сказано и написано. “Это не только про ошибки, но более об индивидуальном понимании кода”, “мы о минимизации времени на проведение проверок”, “молодые разработчики учатся быстрее, когда их просят делать ревью”, и многое другое. Я хочу исследовать другой аспект анализа кода, который часто игнорируется: чем помогает (или мешает) проверка кода для поднятия духа товарищества, доверия, в обучении и прогрессе?
И с этой мыслью собрал горстку идей, которые мы можем реализовать для укрепления команды и повышения результатов её деятельности.
Поговори со мною, кодер
Повсеместно проверка кода начинается без обсуждения темы программистом и проверяющим. Но даже если задача имеет пояснения высокоуровневой архитектуры, то рецензент понятия не имеет, как и по каким причинам программист уложил полноценно идею в несколько файлов.
Буквально пять минут общения — персонально, по телефону или с помощью тексто-обменника (мессенджер, чат) — дают очевидное преимущество для производительности и качества. Как проверяющий, Вы лучше других оцените сочетаемость структуры файла не только с основными соображениями разработчика, но и с причудами или предположениями, которые он или она включили в код, а также выявите какие-то конкретные проблемные области, требующие Вашего усиленного внимания.
Кроме того, Вы даёте кодеру шанс обучить Вас, ревьювера, чему-то пока Вам неизвестному. Программист уделяет много времени коду, дотошно исследуя проблемные места. Прежде чем вторгаться в идеально созданное королевство кодировщика, чтобы осушить многочисленные болота, дайте ему возможность гордо провести Вас по этому изящному лабиринту.
Автоматизированные приложения разрушают межличностный контакт в зародыше
Дежурное решение для оптимизации проверок - автоматизация. Отладчики, непрерывная интеграция, автоматизированные тесты, метрики покрытия кода   —  несомненно всё это способствует повышению качества кода, уменьшению количества циклов обратной связи и снижению трат времени впустую.
Независимую критику предоставляет автоматизация, и этот факт пока ещё не оценён по достоинству.
Никому не нравится критика, и этот негатив усугубляется при прочтении большинства отчётов проверяющих. Напоминая Вашему коллеге использовать табуляцию вместо пробелов, разрозненный регистр вместо строчного, или реорганизовывать вкрапления файлов, вы не завоюете уважение офиса, даже если это действительно улучшит восстанавливаемость кода в своей основе.
Вы ничего не теряете, когда утилиты говорят за вас, и это не нарушит целостность кода. Поэтому не стесняйтесь расширять список задач для автоматизации, но не переходите грань межличностных отношений со своими товарищами пока не стало слишком поздно.
Отзыв о коде формулируйте кротко и ободряюще
Нет ничего более деморализующего для кодера, чем читать сухой, ничего не значащий комментарий “Этот алгоритм выполняет квадратичную функцию”.
Простой комментарий проверки кода, который сообщает “Сделайте X” или “X является неправильным”, сам по себе часто оказывается некорректным вопреки Вашим ожиданиям. И даже если это не так, и в текущий момент не соответствует вершине Вашего ума, но в конце концов разработчик имеет право заявить, что его решение сделать так, а не иначе – осознано и имеет объективные причины. По истечении дня разработки, даже приученный к Вашему стилю программист, будет раздражаться, если Вы не оцените его усилий, не предложите в обязательном порядке выход из положения, но высокомерно заявите о собственной значительности.
По крайней мере, предваряйте свои комментарии словом «пожалуйста». Формулируйте Ваши комментарии в виде вопроса: “А Вы учли выполнение X способом Y?” А если Ваша догадка по правде говоря субъективна, то найдите случай попросить: “Вы могли бы пояснить вот это мне?”, и скорее всего Вы узнаете что-то, доселе Вам не известное, или по крайней мере дадите разработчику возможность продумать этот момент более тщательно и найти лучшее решение самостоятельно.
Самое главное, Вы не приучите бояться проверок. Они не будут бояться пробовать решать проблему по-новому, потому что они будут счастливы обсудить с Вами применение и отдачу нового подхода. Они будут продолжать задумываться о “наилучшем коде”, а не о “том, что скажет проверяющий”.
Я понимаю, что мы, как инженеры, склонны к краткости и точности. Но сэкономленное на оптимизации время не стоит Ваших добрых отношений с сотрудниками.
Используйте время общения для обучения
Иногда быть скромным и воодушевляющим хорошо, но давайте заглянем на шаг вперед.
Студент находится по ту сторону Вашего анализа. В большинстве своём просто надеется на высоко- классность и одобрение рассматриваемого кода, но, если Вы собираетесь опровергнуть его надежды, то сделайте это с максимальной пользой его/её времени. Обоснуйте своё мнение. Обратитесь к документации, из которой нашли изящный прием, или к блогу, где Вы подчерпнули наиболее успешную практику.
Мало того, что это закрепит некоторые знания Вашего подопечного так, что Вам не придётся вылавливать те же ошибки в следующий раз, но и он/она начнёт уважать Вас больше, поскольку поймёт значимость отдачи каждого анализа кода, проводимого Вами.
Займите сторону наставника вместо остановки ошибок человеческого фактора в выпускаемом коде. И это окажется более полезным для всех вовлечённых в конфликт.
Когда что-то ломается - это только *Ваша* ошибка
Это непременно произойдёт. Вы одобрите анализ, код опубликуют, и … что-то рассыплется. Программист отчаянно будет править и минимизировать влияние пользователя, но ущерб нанесён. Кодер виноват, все в Вашей команде это знают, и это будет внутренним конфликтом до тех пор, пока это не дойдёт до умов всех членов команды.
Иной ход дела, когда вы вступаетесь за разработчика и берёте вину на себя.
Отказывайтесь до последнего от функции орала. У программиста уже достаточно напряга: исправление ошибки идёт под давлением, его имя прописано большими буквами в истории контроля версий рядом с тормозящим комитом, потратив много часов на сочинение кода он не мог предположить наличие этого бага.
И у Вас есть очень маленькая лазейка. Объявите, что это Ваша ошибка, Вы забыли рассмотреть крайний случай, но этого не случится в следующий раз. Посидите с программистом, чтобы исправить ошибку. В худшем случае Ваша команда придет к заключению, что это была ошибка вас обоих и оставит вас в покое. Но независимо от их мнения, Вы построите длительное взаимопонимание с разработчиком, которого Вы поддержали, и заслужите уважение босса, который пристально наблюдал за развитием ситуации.
Анализ кода не должен быть просто процессом, пунктиком для проставления галочки. Когда в деле учитывается человек, то путь, которым Вы достигли результат, имеет более высокое значение, нежели сам результат.
##############################

Надеюсь, должностные инструкции в Вашей компании однозначно отвечают на вопрос об "идентичности" тестирования и критики.
Критика базируется на трёх китах - похвали, поругай, предложи. Тестировщик оперирует фактами об актуальном состоянии программы, знает из ТЗ (техническое задание, описание фичи заказчиком) каким должен быть ожидаемый результат после определённых шагов, умеет (а в некоторых компаниях обязан) определить причины выявленной проблемы и пути её решения. Программист считает ошибку наполовину исправленной, если в описании указаны причины, а планировщик задач не поднимает BV (business value) багам без явных причин, чтоб не тратить время кодера на их поиск. Да, баг с расписанным ходом решения правится быстрее, но ведь это за счёт квалифицированности проверяющего, а не исправляющего.
Результат работы проверяющего - отчёт о состоянии программы - не входит в цикл художественных произведений, поэтому должен быть на техническом языке. В компании с выделенным отделом тестирования программист не ждёт вступительных слов "красивый код, но, пожалуйста, исправьте ..." в формулировке бага. Формулы Халстеда о наличии багов в любом коде определяют основную обязанность тестировщика, и об этом стоит помнить кодеру. А постоянная якобы дипломатичность в виде просьб о разъяснении достаточно быстро и надолго опускает эксперта до позиции "мальчика для битья". После одного признания вины за баг руководство и вся команда привыкает иметь всегда под рукой единственного грешника. Тем самым из высоко-квалифицированного специалиста тестировщик превращается в "мусорное ведро" - отдачи не ждут, но нечистоты есть куда поместить.
Тестировщик - такой же полноценный член команды, как и любой разработчик. Он - неотъемлемое звено в производственной цепочке, поэтому не стоит всю вину за провал скидывать на того, кто способствует улучшению продукта. Рядовой QC (quality checker) вырастает в эксперта по тестированию и самостоятельно обучаясь, но, изначально утерянное уважение к рангу проверяющих, команда не способна воспринимать должность тестировщика любого уровня как ровню разработчикам. Вероятно поэтому в Facebook и Microsoft тестировщиков нет, но есть инженеры по тестированию. Ценность профессии подтверждена.

Ссылки по теме:
Я бы в тестеры пошёл...
Качество и уважение
Командность
Им о нас
Каество кода одним числом

суббота, 23 июня 2018 г.

Issue review (ГКЧП-2)

В Agile команде оформлением задач занимаются все – QA (по совместительству - тестировщики, аналитики, техподдержка), PM (в теории – главный аналитик, а на деле – только регулятор работ), разработчики (в основном понятии слова их первоочередной обязанностью и является конкретизация условий задачи). А поскольку у каждого человека свой "почерк" (забывчивость правил и отсутствие знаний как признак индивидуальности), то на понимание задачи у программиста и тестировщика уходит не мало времени (см. "Дорогие trivial-ы"). Дабы ускорить общекомандное время разработки продукта нужна унификация оформления. Jira частично помогает автоматизировать процесс, но кроме обязательных полей ускоряют понимание и некоторые пользовательские поля.

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

Рассмотрим поля в Jira, заполняемые в команде Conquest Software Solutions при создании задач.

* Project Name. Корректность выбора продукта может проверять любой член команды, знающий все разрабатываемые продукты команды, чтобы идентичная задача была выполнена во всех глобальных и интеграционных модулях. Если вовремя не оформить задачу на все связанные продукты, то на доработку может потребоваться в несколько раз больше времени, нежели программист продумает один алгоритм для всех продуктов в едином скрипте.

* Issue Type. У тестировщиков постоянная дилема – баг или фича. От типа задачи зависят тексты заголовка и описания: для бага заголовок пишется в утвердительном наклонении (Проблема есть там-то при таких-то условиях), для новшества – в повелительном (Сделать что-то где-то по другому, новому). В зависимости от правильно выбранного типа задачи можно автоматизировать создание текста в поле Description. Проверка корректности поля Issue Type неразделима с проверкой полей Summary, Description. От типа задачи зависит список бэклога спринта: планирование новой версии в Conquest Software Solutions с помощью эдона Structure зависит только от объёма разработок, Project Manager при выполнении обязанностей scrum-master не включает ни старые, ни новые баги в план выпуска, эстимация фиксов багов не проводится и для публикации фикс-билда. В первую очередь тип задачи должен проверять на корректность Project Manager или Product Lead.

* Summary. Текст заголовка задачи надо проверять лингвисту, тем более, что его содержимое зависит от типа задачи, а чаще заменяет даже полное описание (Description). Текст должен быть в повелительном наклонении для предложений об усовершенствовании или новинок (Сделать что-то где-то иначе), и в утвердительном – для багов (Проблема такая-то есть там-то при таких-то условиях). Удобно создавать Summary беря за подсказку два правила "Что-Где-Когда" (в одном предложении вся суть) и "краткость – сестра таланта" (текст не должен быть более 5-7 слов и без знаков препинания). Единовременно человек запоминает не более 7 символов. Хорошим тоном у публицистов считается однозначность восприятия заголовка при отсутствии знаков препинания.

* Components. Список модулей, в которых проявляется баг или нужны дополнения, лучше других проверит сотрудник, кто проверяет и Project Name. Программисту дешевле составить сразу один алгоритм на все модули, нежели дорабатывать их после возврата задачи. Тестировщику тоже дешевле составить комплексный тест-план, зная полный список мест для интеграционной задачи.

* Affect Versions. Точное соответствие версии продукта, где был выявлен баг, а также наличие бага в текущей разрабатываемой версии сокращает время программисту для поиска причин ошибки или истории её появления. При составлении Release Notes по импрувам точный номер билда, отличный от текущего опубликованного, показывает временность предложения. Для техподдержки и QA точный номер билда, в котором импрува не было, сокращает время поиска билда, работавшего благополучно, без регрессии.

* Priority. Blocker-Critical-Major-Minor-Trivial. Каждая команда определяет свой список приоритетов. О смысловой нагрузке лучше договориться заранее, так как руководитель или заказчик понимают даже слово Blocker/Fatal по разному: кто-то блокером/фаталом считает лишь ту проблему, при которой продукт не запускается, а кому-то достаточно грамматической опечатки. Сочетание с Business Value и Issue Type проверяется старшим по продукту.

* Business Value. Пользовательское числовое поле, аналогично Severity. Со значениями обязательно договориться внутри команды. Старая BTS имела простую систему – от 0 до 99, новая была усложнена Project Manager: наивысший 10 может быть только у Blocker, Critical и в случае "пятиминутки" (см. "Дорогие trivial-ы" ) у Trivial; 11 разрешено давать Critial или Major, 12 как минимальное только для Major, Minor могут быть со значениями 13, 14, 15, и т.д.; Trivial в большинстве должны быть 15 и более. Логичнее и проще, конечно, основываться на обычных баллах от 0 до 100 или от 1 до 10(5). Но если выбрана сложная зависимость от Priority, то проверка на корректность оформления обязательна, и лучше от имени старшего программиста или заказчика.

* Environments. Не для всех задач нужны особые условия, но если их не упомянуть (продублировать) в собственном поле, то при кодировании и проверке тестировщиком будет перерасход времени. На этапе оформления задачи системное окружение лучше проверять разработчикам или системным аналитикам.

* Labels. Система пользовательских лейбл упрощает фильтрацию задач в Jira. Наличие или отсутствие особых лейбл при оформлении может быть тесно связано со значениями полей Affect Versions, Fix Versions, Priority, Business Value, Issue Type. Композицию этих полей следует модерировать в несколько стадий. Примеры лейбл:
actual (отмечаются задачи во время процесса актуализации после выпуска очередной версии, не может быть у новооформленной),
internal (задача с такой отметкой не входит в Release Notes, имеет невысокий приоритет проверки, содержимое нужно только для внутреннего использования командой),
fix_in_component (отметка об особенности правки, влияющей на множество иных модулей и продуктов, требует полного перечисления модулей/продуктов/скриптов с исправленным компонентом для полноценных интеграционных тестов),
fix_in_official (фикс должен войти в текущую опубликованную версию, лейбла помогает фильтровать задачи перед выпуском фикс-билда, фикс и тестирование проводятся в первую очередь, обязательно наличие последнего опубликованного билда в Affect Versions),
fix_in_previous (фикс должен войти в предыдущую опубликованную и до сих пор поддерживаемую версию, лейбла помогает фильтровать задачи перед выпуском фикс-билда, фикс и тестирование проводятся в первую очередь, обязательно наличие предыдущей версии в Affect Versions),
fix_in_rc (фикс должен войти в ближайшую публикуемую версию, лейбла помогает фильтровать задачи перед выпуском новой версии, фикс и тестирование проводятся в первую очередь, обязательно наличие планируемой версии в Fix Versions для импрувов),
non_actual (отмечаются задачи во время процесса актуализации после выпуска очередной версии, не может быть у новооформленной, признак для автозакрытия программистом или старшим по продукту),
rare (редкие задачи могут иметь только Minor или Trivial приоритет и Business Value не выше 15, фикс и тестирование в таком же низком приоритете, обязательно упоминание условий редкости в Description и Environments),
regression (проблемы, как следствие нововведений, должны исправляться в первую очередь, не может иметь Affect Versions равным опубликованным билдам без исходного импрува, обязательно наличие линков с исходным импрувом),
temporary (не может быть у новооформленной задачи, пометка нужна для отсеивания из Release Notes, промежуток между Affect Versions и Fix Versions не должен перекрывать опубликованные билды),
waiting_for_feedback (некоторые задачи невозможно полноценно оформить без подтверждения заказчика или какого-то специалиста, наличие лейблы оправдывает незапланированный Status).

* Status. Баги планирует оформитель задачи, импрувы – только скрам-мастер и добавляет их в Structure. Любой может проверить корректность оформления совокупности полей Status-Issue Type-Fix Versions-Structure и сообщить о проблемах оформителю или PM.

* Bug_Hunter. Пользовательское поле в помощь к Reporter и Creator. Не всякого пользователя продукта можно добавить в список для выбора в поле Reporter, поэтому строковое Bug_Hunter помогает отсеить задачи конечных пользователей. За оформление поля отвечает сотрудник тех.поддержки, если поле не пустое, то в Description или Comments указывается способ связи с клиентом или его контакты.

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

* Fix Versions. Трёхзначный номер версии (без билда, только [Major-Minor-Release]) оформляется для импрувов, входящих в бэклог выпуска. Новооформленные баги должны быть с пустым значением. Актуальность поля лежит в ответственности QA.

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

* Description. Один из самых важных параметров задачи необходимо проверять в несколько этапов. Для ускорения работы и унификации текстов в Conquest Software Solutions были настроены два шаблона Баг и Импрув с точным использованием заголовков, стилей и фонтов, межстрочных интервалов. Для срабатывания (автовставка текста в поле Description) шаблонов необходимо создавать задачу в два этапа: сначала выбрать Product, Issue Type, Components, напечатать что-нибудь в поле Summary, создать задачу в Jira, при этом якобы пустое поле Description автоматически будет оформлено шаблоном в зависимости от выбранного типа задачи:

 шаблон для типа BUG:

Introduction:

[Enter text of issue history. Optionally.]

User wrote:

{quote}

[Enter text from end-user. Optionally.]

{quote}

(OSD=[Enter OSD message number. Optionally.])

Steps to reproduce:

[List steps of actions. Mandatory.]

Actual result:

[Describe actual, detailed result of actions in product. Mandatory.]

Expected result:

[Describe the detailed expected result of actions in product. Mandatory.]

Notes:

[Explain additional information. Optionally.]
  шаблон для типов NEW FEATURE, IMPROVEMENT:

Introduction:

[Enter text of issue history. Optionally.]

User wrote:

{quote}

[Enter text from end-user. Optionally.]

{quote}

(OSD=[Enter OSD message number. Optionally.])

Resolutions:

[Describe the detailed expected result. Mandatory.]

Notes:

[Explain additional information. Optionally.]

При проверке на соответствие стандарту Project Manager отказывал в планировании импрувов, если не хватало пустой строки между абзацами или заголовок не был bold, либо банально удалял задачу и передавал оформление "дубликата" иному сотруднику без пояснения несовпадений с шаблоном и не принимая во внимание возможность смены типа задачи после её создания. Ещё один неудобный момент использования шаблонов заключается в автоматическом перевыборе Assignee в момент применения шаблона, но при этом в истории задачи логгируются изменения от имени автора шаблона.

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

На полноценность текста влияют многие поля: Product (задача может быть склонирована для нескольких продуктов), Issue Type (шаблон зависит от типа задачи), Summary (не должно быть логического противоречия в кратком и подробном описаниях), Affect Versions (в примечаниях указываются отличия версий), Attachments (наличие и соответствие имён упомянутых прикреплений), Components (нет необходимости дублировать модули в полном описании, но есть смысл перечислить затрагиваемые скрипты в комментариях для облегчения составления плана фикса и проверки), Environments (особые настройки желательно перечислять в блоке Notes), Labels (некоторые из лейбл требуют детализации), Bug_Hunter (если в поле есть ID конечного пользователя, то строка про номер OSD не может быть пустой в описании; к сожалению, поиск в текстах Jira подразумевает своё определённое совпадение символов, поэтому фильтр по задачам от юзеров сложный).

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

* Comments. Для новооформленной задачи комментарии не нужны, но проверяющий может указать имя оформителя или иного члена команды через символ "@" для более быстрого реагирования на замечания к описанию.

* Links. "Проверка одной задачи порождает как минимум две новые". У любого бага существует задача-импрув, породившая его. Даже отчёт от конечного пользователя не был бы создан, если бы не появилось что-то новое в продукте. Связь бага с породившим его импрувом – 50% помощи программисту для исправления. TestSession в режиме исполнения и функция клонирования линкуют автоматически. Список линков может быть расширен Jira-пользовательскими настройками, например, "Устаревшая задача + Отменяющая задача".

* TestSession. При подключенном плагине Capture в Jira появляется возможность более подробно описать и выполнить проверку фикса. Оформлением тест-сессии занимается тест-лид, расписывает тест-план и назначает тестировщика-исполнителя. Тест-сессия создаётся только для сложных задач, подразумевающих комплексное тестирование. Полноценность тест-плана проверяет Team Lead.

* Structure. По необъяснимому и упрямому желанию Project Manager в компании Conquest Software Solutions в Structure добавляются задачи только типов Improvement и New Feature. Каждая задача включается в бэклог при оформлении, а не при планировании ближайшей версии продукта. В бэклог задача добавляется до эстимации (оценки затрачиваемого времени) членами команды (аналитик-программист-тестировщик). Поэтому корректность оформления возложена только на самого PM, а для всех остальных членов команды оно всего лишь информативное.

* Due Date. Дата, к которой задача должна быть исполнена, напрямую зависит от планов (Status, Structure, Fix Versions). Заполнение поля производит планировщик бэклога, информация важна исполнителям (в Assignee выбирается только программист, у которого не всегда есть право публикации) и проверяющему исполнение (в Conquest Software Solutions не оформляются отдельные задачи для тестирования и публикации каждого импрува, не переназначаются Assignee, поскольку фактический объём работ тестировщиков никак не учитывается).

* TO-DO. Чек-лист для типа задачи Task. Необязательное к заполнению поле используется в основном для чек-листов выпуска билда, когда мелкие шаги задачи должны выполнять разные сотрудники (QA, DevOps, ..). Полноценность оформления желательно контролировать руководящему составу.

Why "issue review"?
Основная причина необходимости проверки новых задач в том, чтобы сократить время на последующую разработку – отвлекать оформителя от текущих дел более накладно в момент разработки, нежели по горячим следам в день оформления.

Как много времени и сил нужно на проверку? Если эффективно распределить обязанности, то не более 20-30 секунд на каждую задачу. Если всю проверку делать один раз в день/неделю, то "набитый глаз" позволяет ускорять процесс.

Позднее аккумулированный объём знаний ускоряет принятие решений сотрудниками техподдержки при определении причн проблем от пользователей, дальнейшая разработка новинок сразу учитывает имеющиеся нюансы. А в случае большой текучки кадров не приходится искать виновных в недооформленности, поскольку тонкости учтены заранее.
Наименование поля Project Manager, Заказчик Team Lead Лингвист Член команды
Affect Versions 1-2 сек
Assignee 3-5 сек
Attachments 1-2 сек
Bug_Hunter 1-2 сек
Business Value 3-5 сек
Comments 1-2 сек
Components 3-5 сек
Description 2 мин 10 сек
Due Date 1-2 сек
Environments 3-5 сек
Fix Versions 3-5 сек
Issue Type 1-2 сек
Labels 1-2 сек 1-2 сек
Links 3-5 сек
Priority 1-2 сек
Project Name 1-2 сек
Resolution 1-2 сек
Status 3-5 сек
Structure 3-5 сек
Summary 3-5 сек
TestSession 0 сек - 1 мин 3-5 сек
TO-DO 0 сек - 1 мин 3-5 сек
ИТОГО: 14-24 сек 7 сек - 2 мин 12 сек 2 мин 3-5 сек 30-56 сек

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

пятница, 22 июня 2018 г.

ГКЧП - Где, Как, Что Править?

Команда разрабатывает несколько десктопных продуктов с некоторыми едиными модулями, какие-то продукты являются как самостоятельными, так и частью других, собственный сайт для поддержки продуктов как самостоятельный продукт тоже имеет тесные связки с десктопными.
Самописная система ведения задач была удобна, но недостаточна для распределённой команды. Поэтому был выполнен переход на Jira. Каждому продукту было присвоено своё имя в BTS (Bug Tracking System), а несколько глобальных модулей (код исправляется в одном скрипте, а при компиляции каждого продукта исправления автоматически попадают в билды) были перенесены из старой BTS в новую в продукт Global Modules, также задачи по сайту были импортированы в отдельный продукт Jira.
В старой BTS возможно было использовать единый список версий продуктов, а для закрытия багов приписали небольшой интерфейс. В Jira, к сожалению, нет возможности использовать сквозной список версий продуктов, поэтому в продукте Global Modules приходится создавать дубликаты номеров билдов по каждому скомпилированному продукту (но этот утомительный ручной труд был автоматизирован спустя 3 года мучений).
Пока команда состояла из 7 программистов и одного тестировщика, то проблем с описанием и пониманием задач не случалось. Когда же команда разработчиков сменилась на 70% и вдвое увеличилась, то появилась необходимость расшифровывать устоявшиеся понятия и правила. А чтобы не тратить на каждую задачу драгоценное время старожил, создавались документы с описанием корпоративных правил. Для более быстрого и эффективного запоминания всех сложностей, придуманных PM, мной была предложена мнемоника.

ГКЧП
или Как Правильно Читать баГ/импрув?
Где, Как, Что Править?
ГДЕ
* Определяем продукты, в которых надо фиксить. Это видно из номера:
     Prod_1-[issuenumber] - только в Product_1;
     Prod_2-[issuenumber] - в Product_2 и может быть в Product_3;
     Prod_3-[issuenumber] - в Product_3 и скорее всего в Product_2;
     GM-[issuenumber] - в Product_1, Product_2, Product_3 и может быть на сайте;
     WEB-[issuenumber] - на сайте и может в Product_1, Product_2, Product_3
* Определяем модуль или функционал, как часть продукта. Это видно из поля Component.
* Определяем список версий, в которых нужно внести исправления. Для этого на сайте смотрим номер текущей версии (Support -> Release History -> [ProductName]) и сравниваем его с номером билда, в котором выявлен баг/импрув. Это видно по значению поля Affect Versions. Если баг/импрув из числа GM, то номер Affects Versions префиксован кратким наименованием продукта. Если номер версии совпадает с точностью до релиза, то правку вносим только в текущие поддерживаемую и разрабатываемую. Если версия отлична по Мажору/Минору, то сверяемся в поле Label по наличию значений FIX_IN_PREV_VER и/или FIX_IN_OFFICIAL_VER.
* О том, нужен ли фикс в предыдущей версии или в будущей-разрабатываемой версии говорит поле Label со значениями FIX_IN_PREV_VER и/или FIX_IN_OFFICIAL_VER.

ЧТО
* Определяем объём работ по совокупности значений полей Summary, Description, Attachments. Обычно структура Description нижеследующая:
     [Шаг / Модуль]
     [Пункт / Страница]
     [Что не так?]
     [При каких условиях?]
     Как должно быть?]
         example:
         [Шаги примера]

* Пояснительный скриншот или лог бага, или длинный пример хранится в поле Attachments (атач).
* У кого уточнить детали бага/импрува видно из полей BUG_HUNTER или Reporter.

ПРАВИТЬ/ПРОВЕРЯТЬ
* Если фикс был возвращен на доработку, то в поле Comments имеется причина.
* Проверять фикс надо как с default настройками, так и с описанными в Description или Environment.


четверг, 21 июня 2018 г.

ТнаТ

Тестировщик на техподдержке (ТнаТ) или Слуга на все четыре стороны

Кто есть тестировщик на техподдержке? Сотрудники техподдержки первого, второго уровня (бывшие аналитики, бета-тестеры) обязаны досконально знать продукт, чтобы максимально быстро дать ответ пользователю. Третий уровень техподдержки - программисты - знают код продукта, то есть его внутренности. Тестировщики знакомы с продуктом как со стороны пользователя, так и со стороны кодеров. К тому же у тестировщиков выше уровень грамотности, что является важным фактором при оформлении ответов пользователям и задач в баг-трекинговую систему. Поэтому на первый уровень техподдержки обычно ставят тестировщиков, иногда аналитиков. Но поскольку у тестировщиков есть ещё и знания кодирования, то тестировщик на должности техподдержки получается более дешёвым сотрудником.
Общепринято считать, что тестировщик и сотрудник техподдержки должны в первую очередь защищать сторону пользователя, то есть быть адвокатом юзера. ТнаТ должен уметь общаться с пользователем наравне - грамотно, но не заумно; на доступном для обеих сторон языке; о пользовательских нуждах, воплощённых в коде. Любой отчёт пользователя приходится рассматривать как критичный баг, убеждать кодеров и руководство в необходимости правки. Программисты, как всегда, ведут разъяснительные беседы о новшествах, которые плохо описаны в аннотации к билду, поэтому юзер считает фичи багами.
Соглашусь, что напору проггеров сложно противостоять, и вскоре мнение тестировщика склоняется в сторону фичи, а не бага. Но при этом техподдержке приходится вуалировать или откровенно врать пользователю о явном баге, который по мнению аналитиков и программистов тянет на фичу. Выясняя подробности отчёта юзера, сотрудник техподдержки оказывает неоценимую услугу аналитику и программисту, облегчая им работу, или, попросту говоря, работает вместо них: переформулирует вопросы с кодерского языка на юзерский и ответы обратно, уговаривает пользователя принять ошибку за новшество. Вот и первая ступень борьбы ТнаТ с совестью. В моей практике было не мало примеров, когда программист заменял логичное "два плюс два" по задаче от аналитика "два и два" в более быстрое по мнению кодера "дважды два". При этом результат в большинстве случаев не менялся, но никакое предупреждение пользователя в продукт или аннотацию к билду не включали сотрудники, выпускавшие билд. Когда пользователь обнаруживал такое несовпадение, то непременно репортил его как баг, а то и отказывался от продукта с заявлением о возврате потраченных им средств. Баг ли это или рефакторинг, промах  разработчиков или выпускавших билд - решение принимал всегда шеф не в пользу тестировщиков и техподдержки.
Но как ни печально, далее ещё сложнее, поскольку врать приходится ради денег фирмы. Ложь для собственной единоличной наживы совесть позволяет оправдать. А групповой обман подпадает под уголовную статью второй-третьей частей, то есть более сильную. Отдел маркетинга проводит опросы, собирает статистику, распространяет рекламу. Вся информация в оба конца проходит через руки ТнаТ, который группирует её по контрагентам, анализирует при исследовании проблемы, передаёт часть маркетологу, часть аналитику и программисту, часть руководству. Конечно, из настроек продукта ТнаТ может вычленить много полезного для локализации бага, но вместе с этим приходится пропускать (с 25 мая 2018 года шифровать, маскировать и фильтровать в рамках GDPR) индивидуальную инфу. Некоторые ошибки тесно связаны с персональными данными, но у ТнаТ не всегда есть право распространять инфу третьим лицам, которыми вполне можно считать кодировщиков. Итого, сначала ТнаТ шлёт рекламу пользователю с обещаниями всяческих плюшек, а чуть позже ему же приходится оправдываться в их отсутствии или иной реализации, при этом быть политкорректным настолько, чтобы фирма не потеряла свои финансы. Но виноватыми в этой ситуации остаются сами же ТнаТ, как в глазах пользователя (ТнаТ - лицо компании), так и по мнению руководства, для которого за успех продукта поощряются программисты, а за провал наказываются тестировщики. Для избежания подобных проблем ТнаТ должно быть позволительно влиять продукт: участвовать в планировании спринта (особенно если реклама обещает новшества к определённому сроку), проверять аннотацию (Release Notes) к выпуску, тесно сотрудничать с финансовым отделом для ограничения распространения спама о скидках или регулярных платежах за техподдержку. Тогда ТнаТ может проявить всю свою политкорректность в переписке с пользователем не споря с собственной совестью.
Ну, и самый тёмный угол - это соблюдение законов, которые подчас могут противоречить друг другу. Например, корпоративная этика, минимизирующая бюрократизм, и закон о сохранности персональных данных, обязывающий логировать передачу индивидуальной информации. ТнаТ тяжело удерживаться на своём месте и не противоречить сотрудникам фирмы, поскольку маркетолог, программист и пользователь как лебедь, рак и щука тянут продукт в свои стороны. А ТнаТ вынужден меж этих огней ещё и соблюдать законность, политкорректность и дружелюбность в общении пользователя и фирмы. Сотруднику техподдержки бывает очень сложно убедить руководство не обманывать пользователя для соблюдения законности: предупреждать об объёме собираемой и пересылаемой в фирму индивидуальной информации пользователя; отвечать за обещанное рекламой и фактически поставленное продуктом в рамках лицензионного соглашения; скрывать от пользователя конкретику работы фирмы в рамках соглашения о нераспространении внутрикорпоративной информации и подробно описывать шаги группы разработки для спокойствия пользователя.
Миссия ТнаТ не легка. При переходе на должность сотрудника техподдержки непременно подтяните свои знания в области юриспруденции, психологии, грамотности (русский или английский язык переписки с пользователями) и дикции (для случаев аудио-связи), наряду с отличным знанием продукта.

среда, 20 июня 2018 г.

Качество кода одним числом

Maintainability Index – величина качества кода

Качество продукта, согласно ISO-9126, состоит из 6 частей (см. Рис.1 "ISO-9126").
Рис.1 "ISO-9126"
Из этих же шести пунктов (см. Рис.1 "ISO-9126") строится и качество кода, которое можно измерить для любого языка программирования. К сожалению, идеального кода не существует и добиться невозможно, как и КПД-100%.
Одна из простейших метрик – количество параметров, которое рекомендуют не более 7: 5 входящих, 2 на выход. Особое место занимают глобальные переменные, наличие которых усложняет код.
Более сложно качество кода вычисляется по формулам, только одна из которых "цикломатическая сложность" пока принята институтом стандартов. Когда научному миру удастся доказать полезность и значимость остальных формул, тестировщики смогут официально ориентироваться на эти лимиты.
Формула расчёта Maintainability Index была выведена достаточно давно Доном Колеманом, Паулем Оманом и Джеком Хегмейстером. Она имеет несколько вариаций для различных языков программирования. Фактически, польза индекса "ремонтопригодности" не только в оценке готового кода, но по этой величине вполне можно спрогнозировать устойчивость кода с учётом будущих исправлений.
Согласно формулам (см. Рис.2 "Две формулы подсчёта количества багов в юните", где TNOpr – общее количество операторов, TNOpd – общее количество операндов, DNOpr – количество уникальных операторов, DNOpd  – количество уникальных операндов) Мариуса Халстеда, если код состоит хотя бы из одного оператора и операнда, то величина багов в этом коде уже не нулевая.
Рис.2 "Две формулы подсчёта количества багов в юните"
Если оценить обе формулы (см. Рис.2 "Две формулы подсчёта количества багов в юните") через их графики, то очевидно, что количество багов в новом и исправленном коде будет нулевым только в "пустой" подпрограмме.
 
Рис.3 "График и формула подсчёта новых багов"
На рисунке 3 "График и формула подсчёта новых багов" верхняя формула для расчёта прогнозируемых багов минимизирована по количеству операторов (1 шт) и операндов (2 шт). Количество багов смотрим по оси Y, количество операторов и операндов (только целые числа) смотрим по оси X. Поскольку рабочей подпрограммы без операторов и операндов не существует, то по графику убеждаемся, что количество багов резко уходит в бесконечность только при нулевых значениях операторов и операндов [0..1], количество багов растёт плавно (y>0 при x>1). 
 
 Рис.4 "График и формула подсчёта недавних багов"
Минимизировав вторую формулу (см. Рис.2 "Две формулы подсчёта количества багов в юните") для расчёта недавних багов и приняв один оператор на пару операторов, получаем по-сути аналогичный график (см. Рис.4 "График и формула подсчёта недавних багов"), когда количество багов равномерно растёт по оси Y и не может быть отрицательным, так как в рабочем коде должен быть хотя бы один оператор и операнд, то есть значения по оси X рассматриваются только целочисленные, начиная с 1.
Итак, мы убедились, что в любом коде всегда есть баги. А об их серьёзности можно судить по величине Maintainability Index (MI).

Из чего же складывается величина качества кода?
Максимальная формула учитывает значения Сложности Халстеда, Цикломатической Сложности, значимые Строки кода и объём Комментариев:
MI = 171 - 5.2 * ln(HV) - 0.23 * CC - 16.2 * ln (LOC) + 50 * sin(sqrt(2.4 * COM)), где HV – сложность Халстеда, CC – цикломатическая сложность, LOC – количество строк кода, COM – объём комментариев в коде.
Укороченная формула не учитывает объём комментариев:
MI = 171 - 5.2 * ln(HV) - 0.23 * CC - 16.2 * ln (LOC)
Компилируемые языки программирования "не отвлекаются" на комментарии, поэтому для них (например, Си) вполне очевидно использование укороченной формулы. А языки-интерпретаторы (например, SQL) корректнее оценивать по полной формуле, так как комментарии внутри цикла в некоторых языках могут замедлять исполнение программы, поскольку на вычленение незначимых строк тоже нужно время.
Пределы индекса принято рассматривать по следующей таблице (см. Рис.5 "Лимиты Maintainability Index"):
- подпрограмма требует немедленного исправления, если MI упал меньше 65;
- подпрограмму желательно исправить, если MI больше или равен 65, но меньше 85;
- подпрограмма не нуждается в исправлении, если MI равен или больше 85.
Исходя из формулы абсолютное максимальное значение Maintainability Index равно 221 (171-0-0-0+50), но оно не достижимо ни при каком содержимом сорсника.
Рис.5 "Лимиты Maintainability Index"
Об истории лимитов MI можно почитать в статье.

Итак, чем больше индекс, тем лучше код. Рассмотрим способы повышения индекса важности кода.
Более скорый способ увеличения индекса исходя из формулы первой модели "MI = 171 - 5.2 * ln(HV) - 0.23 * CC - 16.2 * ln (LOC) + 50 * sin(sqrt(2.4 * COM))" возможен за счёт увеличения объёма комментариев, так как индекс в формуле – наибольшее положительное число "50". Объём комментариев зависит от функции синуса, которая колеблется в пределах [-1..1]. Но поскольку объём комментариев можно исчислять двумя способами – как процент или долю, а значение синуса может быть и отрицательным, то необходимо выяснить оптимальные пределы комментариев. Для этого рассмотрим график функции "y(x)= 50 * sin(sqrt(2.4 * x))" на отрезках [0..100] (при исчислении комментариев в процентах) и [0..1] (при исчислении комментариев в долях от общего кода).
Рис.6 "График комментариев в процентах"
На графике (см. Рис.6 "График комментариев в процентах"), построенном по формуле "y(x)= 50 * sin(sqrt(2.4 * x))", по оси X имеем процентное соотношение комментариев к строкам кода, а по оси Y – величину для расчёта Maintainability Index. 1-2% или 25-26% или 83-84% комментариев дадут желаемый максимум (y=50), 0% или 4% или 17% или 37% или 66% комментариев абсолютно не влияют на Maintainability Index (y=0), 9% или 50-51% комментариев самым сильным образом (y=-50) отрицательно влияют на индекс ремонтопригодности. При этом MI может стать и отрицательной величиной. 
Рис.7 "График комментариев в долях"
На графике (см. Рис.7 "График комментариев в долях"), построенном по формуле "y(x)= 50 * sin(sqrt(2.4 * x))", по оси X имеем долевое соотношение комментариев к строкам кода, а по оси Y – величину для расчёта Maintainability Index. График показывает, что 3-4 комментированные строки кода из 10 рассматриваемых (или каждая третья) максимально помогают увеличить MI, то есть являются самым полезным соотношением.
Итак, если MI упал ниже 65, то по-быстрому его поднять можно вставкой комментариев в каждую третью строку.
Примечания:
- полезность/качество комментариев не рассчитывается формулой, поэтому не стоит забывать, что просто закомментированный код – это не полезные примечания;
- при добавлении комментариев соответственно увеличится и общее количество строк кода.

Шаг второй по повышению индекса устойчивости подпрограммы – снизить количество строк кода, потому что в формуле "MI = 171 - 5.2 * ln(HV) - 0.23 * CC - 16.2 * ln (LOC)" наибольший отрицательный индекс "16.2" у величины строк. На графике (см. Рис.8 "График и формула строк кода") видно, например, что 4500 строк уменьшат индекс на 136 пунктов из 171 возможного по формуле. Количество строк в подпрограмме определяется по спецсимволам текста, поэтому парсер обмануть не получится обычным размещением команд в одну строку файла. Единственный вариант – оптимизация кода за счёт объединения и выноса идентичных блоков кода в самостоятельные функции, которые будут рассматриваться как отдельные подпрограммы.
Примечания:
- не забывайте, что при этом увеличится количество параметров и скорее всего даже глобальных;
- блок-схемы, flowchart или UML диаграммы помогают вычленить повторяющиеся блоки хода подпрограммы.
 
 Рис.8 "График и формула строк кода"
Если пойти от обратного и принять в формуле MI(<=65) максимальные значения HV(=1000), CC(=10) и комментариев (sin[X]=1), то в одном юните желательно иметь не более 1500 строк (см. Рис.9 "График максимального количества строк кода и формула с учётом комментариев").
 Рис.9 "График максимального количества строк кода и формула с учётом комментариев"
То есть по формуле Maintainability Index с учётом комментариев мы вывели лимит для оптимального количества строк в подпрограмме: LOC<1500 mi="">=65.
Для формулы второй модели (без учёта комментариев) смотрите рисунок 10 "График максимального количества строк кода и формула без учёта комментариев".
 Рис.10 "График максимального количества строк кода и формула без учёта комментариев"
График по оси Y показывает MI, а LOC по оси X. Из чего следует, что в юните без комментариев для стабильно-устойчивого кода нужно иметь менее 50 строк (см. Рис.11 "Увеличенный график максимального количества строк кода для формулы без учёта комментариев").
 
 Рис.11 "Увеличенный график максимального количества строк кода для формулы без учёта комментариев"
Об иных подробностях строк кода читайте в статье "Source lines of code".

Третий шаг по повышению MI – это снижение сложности Халстеда из части "5.2 * ln(HV)". Максимальная величина Халстеда – 1000. Исходя из этого на графике (см. Рис.12 "График и формула Halstead Volume в рамках MI") видно, что сложность Халстеда максимально может уменьшить индекс ремонтопригодности на 36 пунктов.
 
 Рис.12 "График и формула Halstead Volume в рамках MI"
Все величины Халстеда рассчитываются по операторам и операндам. Напомню, что в выражении "a+b" оператором является плюс, а операндами – переменные "a" и "b". Длина программы по Халстеду – это сумма всех операторов и всех операндов. Словарь юнита он определил как сумму уникальных операторов и операндов. А помножив длину программы на логарифм словаря, Халстед получил объём подпрограммы (или ещё эту величину называют сложностью Халстеда):
HV = ( TNOpr + TNOpd ) * log2 ( DNOpr + DNOpd ),
где TNOpr – общее количество операторов, TNOpd – общее количество операндов, DNOpr – количество уникальных операторов, DNOpd  – количество уникальных операндов. Более подробно о величинах Халстеда читайте в статье "Halstead complexity measures".
Если принять, что на один оператор приходится два операнда, то график функции HV будет приблизительно, как на рисунке 13 "График и функция сложности Халстеда".
 Рис.13 "График и функция сложности Халстеда"
По оси Y смотрим значение HV, а по оси X выбираем количество операторов. Максимальному значению HV=1000 соответствует 45 операторов, и соответственно около 90 операндов (~ два операнда на один оператор).
Для увеличения MI до 65 и выше надо уменьшать HV, то есть количество операторов и операндов. В коде (см. пример на рисунке 14 "Пример сложных и простых вычислений") можно множество простых операций объединить в одну сложную. Это как в начальной школе по арифметике при имеющемся решении задачи в три-четыре действия выполнить расчёт одним действием.
 Рис.14 "Пример сложных и простых вычислений"
На скриншоте из ClearSQL (см. Рис.15 "Пример упрощения кода по HV, MI") показана разница в значениях HV для сложной "hv_1" и простой "hv_2" подпрограмм.
 Рис.15 "Пример упрощения кода по HV, MI"
Уменьшая количество операторов и операндов в коде снижается сложность Халстеда (HV), и как следствие увеличивается (улучшается) индекс ремонтопригодности (MI).

Четвёртый шаг по улучшению MI – снижение цикломатической сложности.
Томас Дж.Маккейб вывел формулу цикломатической сложности юнита как разность рёбер (edges) и узлов (junctions) с добавлением удвоенного количества компонент связности (coherences):
CC = EdgesJunctions + 2*Coherences
Максимальное значение величины Маккейба утверждено Американским Национальным Институтом Стандартов и Технологий (NIST), равно 10, но последнее время расширяют до 15. Нам тестировщикам это значение говорит о необходимом количестве юнит-тестов. Более подробно о цикломатической сложности читайте в статье "Cyclomatic complexity". Цикломатическая сложность снижает индекс ремонтопригодности максимально на 2-3 пункта, поэтому её рассматриваем в последнюю очередь. График (см. Рис.16 "График и формула цикломатической сложности в рамках MI") показывает часть "0.23 * CC" из формулы MI.
 
 Рис.16 "График и формула цикломатической сложности в рамках MI"
По оси X берём целочисленное значение Cyclomatic Complexity (max=10 or 15), по оси Y видим объём снижения (коэффициент – отрицательная величина "-0.23") MI.
Для улучшения MI нужно уменьшать CC, то есть "выпрямлять" ход программы. Но учтите, что иногда сложные условия (композиция нескольких AND и OR) рассчитывается как одно, то есть уменьшается количество узлов и рёбер, следовательно и само значение CC будет меньше.
Рис.17 "Пример кода цикломатической сложности"
В примере (см. Рис.17 "Пример кода цикломатической сложности") процедура threeinone имеет одно сложное условие (CC=4 или CC=2), а процедура oneinthree – три простых условия (СС=4 всегда).

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

Полезные ссылки:
* Качественный анализ программного модуля на основе метрик кода
* Don M. Coleman, Dan Ash, Bruce Lowther, Paul W. Oman. Using Metrics to Evaluate Software System Maintainability. IEEE Computer 27(8), 1994, pp. 44-49.
* Paul Omand and Jack Hagemeister. “Metrics for assessing a software system’s maintainability”. Proceedings International Conference on Software Mainatenance (ICSM), 1992, pp 337-344.
* Paul W. Oman, Jack R. Hagemeister: Construction and testing of polynomials predicting software maintainability. Journal of Systems and Software 24(3), 1994, pp. 251-266.
* The Maintainability Index was introduced at the International Conference on Software Maintenance in 1992
* To date, MI is included in Visual Studio (since 2007), in the recent (2012) JSComplexity and Radon metrics reporters for Javascript and Python, and in older metric tool suites such as verifysoft.
* Think Twice Before Using the Maintainability Index
* P. Oman
* J. Hagemeister