Время — деньги. Создание команды разработчиков программного обеспечения.

Глава 5. Инструментальные программы.

В компании NuMega мы использовали лишь те инструментальные программные средства, которые были жизненно необходимы для нашей работы и вписывались в наш стиль работы. Из всех доступных инструментов мы больше всего применяли и полагались на систему управления исходным кодом и систему устранения проблем и неисправностей (поиска «жучков»). Возможность приспосабливать эти продукты к нашим нуждам позволила ускорить работу — вся команда использовала их почти каждый день.

Средства управления исходным кодом.

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

О чём пойдёт речь.

Продукты по управлению исходным кодом хранят файлы с кодом, отслеживают их версии, управляют файлами, составляющими проект, и предоставляют следующие функции.

• Хранение файла и его прошлых, настоящих и будущих версий.

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

• Отслеживание истории изменений для каждого файла.

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

• Группирование файлов.

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

• Маркировка файлов, связанных с конкретным выпуском программного продукта.

Система управления исходным кодом позволит пользователям пометить определённые версии файлов всего проекта/подпроекта. Это позволяет чётко маркировать или идентифицировать файлы, составляющие определённый выпуск ПО.

• Блокировка и разблокировка файлов.

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

Что туда входит.

Удобное расположение всех файлов и информации, связанной с проектом — это страшная (но излечимая) головная боль при разработке ПО. В NuMega не было времени создавать обширную инфраструктуру или сложные процессы для поддержки грамотного документооборота. Поэтому мы решили просто поместить все файлы и документы проекта в систему управления исходным кодом. Это были:

• исходные файлы;

• файлы заголовков;

• файлы библиотек;

• сценарии компоновки;

• результаты компиляции;

• результаты компоновки;

• инструменты и файлы для установки программ;

• инструменты и файлы для тестирования;

• спецификации проекта;

• планы проекта (ПО, документации и тестирования);

• пользовательская документация;

• тестовые задания и сценарии;

• тестовые модули разработчиков.

Из собственного опыта

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

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

Зачем это нужно.

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

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

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

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

И последнее (но не менее ценное) преимущество — централизация файлов в системе управления исходным кодом обеспечивает простое резервное копирование всего проекта. Одной командой мы могли создать резервную копню или просто скопировать весь проект на другой диск или другую машину.

Каковы их технологические возможности.

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

• управление разработкой нескольких редакций продукта;

• управление разработкой нескольких версий одной редакции;

• применение общих компонентов, как в рамках одного, так и нескольких проектов компании;

• компоновка продукта на основе самого свежего набора файлов с исходным кодом (или на основе другого набора исходных файлов);

• поддержка локальных сборок для отдельных разработчиков.

Как ими управлять.

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

Мы использовали систему управления исходным кодом Visual Source Safe (VSS) компании Microsoft. Она предоставляет нужные нам основные функции, и у неё отличная цена — как раз для начинающего бизнеса. Хотя обсуждение VSS выходит за рамки этой книги, я расскажу о том, как мы приспособили этот продукт под наши нужды.

Основы структуры.

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

Структура и использование хранилища исходного кода.

Все файлы, используемые при разработке наших продуктов, были рассортированы по трём папкам:

• Product Name — для файлов, относящихся к продукту;

• Environment — для файлов среды разработки;

• Imports — для сторонних файлов.

Папка Product Name содержала создаваемые нами файлы, необходимые для сборки, тестирования и написания документации к продукту (табл. 5-1). В ней были подкаталоги Branch для каждого варианта, над которым мы работали. В подкаталоге Parts хранились стандартные и совместно используемые компоненты, включаемые в продукт. И, наконец, для каждой редакции продукта имелся подкаталог Product. В каждой папке Product содержались необходимые для продукта части. Чтобы эта структура работала, нужно строго соблюдать соглашения об именах и не нарушать структуру. Координация изменений в частях и продуктах также была критичной.

Табл. 5-1. Примерная структура папки «Product Name».

$/Product_Name/ — Файлы, относящиеся к продукту.

$/Product_Name/Branch/ — Различные направления в разработке.

$/Product_Name/Parts/ — Совместно используемые файлы, входящие в продукт.

$/Product_Name/Parts/Src/ — Исходный код для Parts (при необходимости совместно используется с/Products/Src).

$/Product_Name/Parts/Doc/ — Исходные файлы документации.

$/Product_Name/Parts/Help/ — Исходные файлы справочной системы.

$/Product_Name/Parts/Install/ — Исходный код программы установки.

$/Product_Name/Parts/Patch/ — Исходный код вставок.

$/Product_Name/Parts/Setup/ — Исходный код установщика.

$/Product_Name/Parts/Samples/ — Исходный код с примерами.

$/Product_Name/Parts/Tests/ — Исходный код тестов, тестовые задания и т.д.

$/Product_Name/Product/ — Редакции продукта Product Name (по одной папке на каждую редакцию).

$/Product_Name/Product/Output/ — Область для программ, созданных в других проектах.

$/Product_Name/Product/Src/ — Исходный код продукта (при необходимости совместно используется с /Parts/Src).

$/Product_Name/Product/Doc/ — Файлы документации к продукту (совместно используется с /Parts/Doc).

$/Product_Name/Product/Help/ — Файлы справочной системы продукта (совместно используется с /Parts/Help).

$/Product_Name/Product/Imports/ — Импорт (совместно используется с /Imports).

$/Product_Name/Product/Install/ — Файлы для установки продукта (используется с /Parts/Install).

$/Product_Name/Product/Samples/ — Примеры для продукта (совместно используется с /Parts/Samples).

$/Product_Name/Product/Tests/ — Тестовые задания, тестовые сценарии (совместно используется с /Parts/Tests).

Из собственного опыта

Когда я пришёл в NuMega, для одного из продуктов было создано три каталога по именам разработчиков: Frank, Bill и Matt. Так как каждый работал над своим собственным кодом, они могли вносить изменения, не повреждая чужих файлов. Однако там было мало общего кода (одна большая структура данных для основных подсистем). Но это работало! Дальше нам нужно было увеличить команду разработчиков, и мы уже не могли обойтись без системы управления исходным кодом. Такая система позволила усложнить проект, удерживая его под контролем. Без неё я просто не могу представить ПО для разработчиков.

В папке Environment ($/Env) хранятся файлы, используемые командой разработчиков, но не являющиеся частью конечного продукта. Это все, начиная с инструментов и утилит и заканчивая стандартами создания кода и шаблонами для проекта. Папка Environment содержит файлы среды, описывающие среду с точки зрения разработчика, а также с точки зрения тестирования и документации. В NuMega мы хотели создать общую среду для команд разработчиков, и потому для этой цели мы создали специальный раздел в хранилище исходного кода. Вот примерный список подкаталогов, которые могут быть в этом разделе хранилища исходного кода (табл. 5-2):

Табл. 5-2. Примерная структура папки Environment.

$/Env/Dev/ ПО среды разработки и инструментальных средств.

$/Env/Dev/Bin Исполняемые модули (подкаталог для каждого инструмента).

$/Env/Dev/Src Исходный код для этих инструментов (подкаталог для каждого).

$/Env/Dev/Doc Документация для этих инструментов (подкаталог для каждого).

$/Env/Dev/Etc Прочие файлы.

$/Env/Test/ Инструментальные средства и файлы для тестирования.

$/Env/Test/Bin Исполняемые модули.

$/Env/Test/Src Исходный код и документация для этих инструментов.

$/Env/Test/Doc Документация по среде тестирования.

$/Env/Test/Etc Прочие файлы.

$/Env/Documentation/ Документация по среде проекта.

$/Env/Documentation/Templates Шаблоны проекта, шаблоны документации и справочники по стилям.

$/Env/Documentation/Plans Планы и спецификации проекта, тестовых заданий и документации.

$/Env/Documentation/Process Технологические документы проекта.

$/Env/Etc Прочие файлы, не вошедшие в предыдущие категории.

В папке Imports ($/Imports) хранились файлы или наборы инструментов из сторонних продуктов (табл. 5-3). Сами сторонние продукты в этой папке не содержались, там были только библиотеки и заголовки. В результате в разделе Imports проводилось совсем немного изменений. Однако так как эта область использовалась для хранения различных версий сторонних продуктов, было очень важно не вносить никаких изменений без чёткого осмысления, полного тестирования и учёта связей с элементами, на которые эти изменения могли бы подействовать.

Табл. 5-3. Примерная структура папки Imports.

$/Imports/RogueWave Библиотеки и заголовки RogueWave.

$/Imports/ObjectSpace Библиотеки и заголовки ObjectSpace.

$/Imports/Visual С Результаты компиляции, библиотеки и заголовки Visual С.

$/Imports/Install Shield Библиотеки и заголовки Install Shield.

$/Imports/Прочие Папки для каждого инструмента или библиотеки сторонних производителей.

Компоновочная система.

В NuMega мы писали сценарий сборки продукта на выделенной «компоновочной машине». Сценарий должен был выбирать нужные для сборки продукта файлы из системы управления исходным кодом. Эта информация включала как сами средства компоновки, так и исходные файлы, библиотеки, заголовки и другие необходимые компоненты. Для ведения процесса компиляции мы выбрали Nmake — популярное средство управления компоновкой. Nmake сначала собирает все части продукта, а затей компонует окончательные исполняемые файлы продукта.

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

Надёжная автоматическая система компоновки — необходимое условие успешной разработки. Затраты времени и сил на то, чтобы заставить эту систему работать, своего стоят. Этот и другие вопросы применения технологического ПО обсуждаются в главе 7.

Устранение проблем и неисправностей.

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

О чём пойдёт речь.

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

Что туда входит.

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

Примечание.

Я бы не советовал писать собственные программы по устранению проблем и неисправностей, так как хватает различных коммерческих программных продуктов по разумным ценам. Например, Compuware/NuMega TrackRecord, PVCS Tracker, Rational ClearQuest и др. Хотя вам потребуется самим определить, какая из них отвечает вашим потребностям, я настоятельно рекомендую принять решение в пользу покупки. Ведь вы не обязаны тратить время на создание собственных инструментов, ваше дело — поставлять ПО.

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

Как это работает.

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

• текущее состояние проблемы: открытая или закрытая;

• дата возникновения, изменения и решения;

• текстовое описание проблемы;

• номер выпуска/сборки программы, в которой обнаружена проблема;

• имя человека, описавшего проблему:

• имя человека, работающего над проблемой в настоящее время;

• состояние проблемы: расследуется, требуется больше информации, ожидается внешнее событие, решена и т.д.;

• приоритет проблемы: низкий, средний, высокий;

• выпуск, в котором присутствует проблема;

• статут процедуры контроля качества;

• количество попыток неуспешного решения проблемы;

• список изменений к отчёту о проблеме или неисправности.

Посмотрим, как мы использовали ПО для устранения проблем и неисправностей в NuMega.

Из собственного опыта

Когда я начинал работать в NuMega, «жучки» и другие различные неисправности фиксировались на доске (если вообще фиксировались). Они оставались там до тех пор, пока не были исправлены, а затем их просто стирали. Когда доска заполнялась полностью, новые записи втискивали в уголок или, чтобы освободить место, стирали другие ошибки. Эта система работала для одного-двух человек, но истории работы над ошибками не было.

С ростом организации становилось очевидно, что нам требуется автоматизированное решение. Если бы мы в то время не перешли к нему, то не смогли бы успешно вырастить свою команду. Хотя поиск инструмента, способного решить наши проблемы, и не был сложен, способ его использования часто становился предметом спора. В конце концов мы выяснили, что для группы нашего размера куда важнее выполнять на «отлично» всего несколько функций, чем пытаться делать всё, что мы можем только представить.

Для всех ошибок — одно хранилище.

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

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

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

Управление изменениями.

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

Приоритеты на основе времени.

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

Рассмотрите включение поля «Исправить к дате» для установления приоритетов на основе критерия времени. Значения, помещаемые в это поле, могут браться на основе внутреннего графика выпуска проекта, например, здесь может быть указан определённый этап, бета-версия или кандидат на выпуск. Чтобы определиться с приоритетом, задайте себе вопросы: «эту проблему нужно решить к этапу 2 или бета-версии 1?», «Что, если мы выпустим продукт сейчас, а ошибку исправим в следующем выпуске?».

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

Проверяйте и исправляйте ошибки.

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

Используйте замечания по выпуску.

Когда мы сталкивались с неполадкой, которую следует описать в замечаниях по выпуску или файле Read Me, мы изменяли её статус на «Release Notes», но оставляли её открытой. В примечаниях по выпуску описываются известные проблемы, способы их обойти и информация, появившаяся в последний момент и не попавшая в официальную документацию. Когда наступал момент выпуска бета-версии или окончательной версии, было очень просто составить список проблем, о которых следует указать в замечаниях по выпуску. И только после того, как проблему разрешили, мы окончательно её закрывали.

Используйте стандартные запросы.

Чтобы осуществлять полноценный поиск по базе данных проекта, важно иметь набор стандартных запросов. Эти запросы должны использоваться совместно и быть доступны всем членам команды; важно, что у каждого будет одинаковая картина данных. Хотя частные запросы хороши для редких и особых требований, их не следует использовать для распределения заданий членам команды. Риск неправильного составления запроса или указания неиспользуемого более поля достаточно велик. В таблице представлены наиболее важные запросы.

Все открытые ошибки

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

Все открытые ошибки для конкретного этапа

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

Все открытые ошибки для конкретного человека

Позволяет каждому человеку просмотреть свой текущий список ошибок.

Все открытые ошибки для конкретного этапа и человека

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

Все открытые ошибки тестировщиков с полем «Контролю качества: проверить» = «Истина»

Позволяет команде просмотреть свой план тестирования.

Все открытые ошибки с полем «Предложения» = «Истина»

Позволяет менеджеру проекта и руководству пересмотреть текущие предложения по изменениям.

Другие способы применения.

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

Интенсивность возникновения и устранения ошибок.

Интенсивность возникновения — это мера того, сколько новых ошибок или неисправностей было обнаружено за определённый период времени. Интенсивность возникновения взлетает вверх в начале проекта, но с течением времени снижается. Интенсивность устранения — это мера того, сколько ошибок или неисправностей закрыто за определённый период времени. Она снижается по мере устранения ошибок. Ниже показана интенсивность возникновения и устранения ошибок — для проекта эти данные могут быть весьма полезны (рис. 5-1 и 5-2).

Время — деньги. Создание команды разработчиков программного обеспечения

Рис. 5-1. Интенсивность возникновения и устранения ошибок в начале проекта.

Время — деньги. Создание команды разработчиков программного обеспечения

Рис. 5-2. Интенсивность возникновения и устранения ошибок в моменты, когда проект близится к завершению определённого этапа.

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

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

Интенсивность устранения поможет вам определить эффективность обнаружения причин возникновения неполадки, а также примерный срок устранения ошибок, которые могут появиться в будущем. Скажем, если интенсивность устранения в течение двух последних недель составляла 10 ошибок в день, это может быть большим успехом. Если у вас 100 открытых ошибок, то вполне закономерно ожидать, что все они будут устранены приблизительно в течение следующих 10 дней. Эта цифра конечно же не точна (для исправления какой-нибудь неполадки может потребоваться и неделя), но она позволяет понять, чего вам следует ожидать при наличии большого количества оставшихся ошибок.

Количество изменений.

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

Счётчик неудачных исправлений.

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

Дополнительные средства.

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

Отладчики.

Одним из наиболее важных инструментов для наших разработчиков был разработанный NuMega Technologies невероятно мощный отладчик для Windows — SoftICE. Он загружается при запуске системы как драйвер устройства на уровне ядра и предоставляет беспрецедентные возможности управления и наблюдения за внутренними процессами приложения и операционной системы. Команда разработчиков часто использовала SoftICE для разрешения наиболее сложных проблем при отладке.

Средства анализа производительности и полноты.

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

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

Средства написания сценариев и автоматизации тестирования.

Так как наши планы тестирования требовали максимально возможной автоматизации, мы всегда интересовались инструментами, способными нам в этом помочь. Наиболее важными были средства написания сценариев (Perl, командные файлы DOS и т.п.) и средства автоматизации тестирования. В то время Visual Test был доступен по разумной цене и предлагался взыскательным тестировщикам и разработчикам. С его помощью мы тестировали пользовательский интерфейс, но в подавляющем большинстве мероприятий по автоматизации полагались на средства написания сценариев.

Из собственного опыта

Когда мы создавали группу разработки ПО, проверяющего исправность кода, члены команды не были до конца уверены в его значимости. Но с продвижением проекта, когда команда начала применять собственный продукт на собственном коде, стало ясно, что если разработчики блочно тестировали свой код с полнотой 80%, то качество продукта заметно повышалось.

Типичные проблемы и их решение.

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

Проблемы с инструментами.

• Отбор нужных инструментов.

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

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

• Смена инструментов на средине пути.

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

Проблемы управления исходным кодом.

• Структура проекта.

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

• Содержание.

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

• Конфликты ключевых файлов.

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

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

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

В большинстве систем управления исходным кодом поддерживается слияние файлов. Это позволяет совместить изменения в файлах. Хотя обычно эта функция работает правильно, не позволяйте операцию слияния проводить автоматически. Вы должны убедиться, что проверили все изменения, сделанные в файле. Если в нашей системе управления исходным кодом поддержка слияния реализована плохо, можете воспользоваться такими редакторами кода, как Visual Slick Edit и Code Write. Они помогут выявить различия визуально и проверить результат слияния перед его реальным осуществлением.

• Маркировка.

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

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

Из собственного опыта

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

Проблемы поиска ошибок и неисправностей.

• Целостность данных.

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

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

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