Модульное тестирование неэкспортированных классов в DLL - PullRequest
29 голосов
/ 31 марта 2011

Мы разрабатываем приложение на C ++ с использованием Visual Studio 2008 и модульное тестирование с использованием Boost.Test.На данный момент у нас есть отдельное решение, которое содержит наши модульные тесты.

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

У меня есть две идеи о том, как их можно тестировать:

  1. Экспорт всего
  2. Поместите тесты в DLL (тот же проект и решение) и используйте внешний бегун Boost.Test

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

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

Ответы [ 4 ]

15 голосов
/ 17 июня 2014

Расширяя ответ Тома Куарендона на этот вопрос , я использовал небольшой вариант ответа Саймона Стила:

  • Создайте тестовый проект (используя любую тестовую среду, которая вам нравится,Я использую CppUnit ).
  • В вашем test_case.cpp, #include <header/in/source/project.h>.
  • В свойствах тестового проекта:
    • В Linker-> Generalдобавьте $(IntDir) исходного проекта в каталоги дополнительных библиотек.
    • В Linker-> Input добавьте файлы .obj в дополнительные зависимости.
  • Добавитьзависимость от тестового проекта до исходного проекта в Project-> Project Dependencies.

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

4 голосов
/ 31 марта 2011

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

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

2 голосов
/ 25 августа 2015

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

Добавить новую конфигурацию сборки, например, «Отладка модульного тестирования», в проект DLL и изменить тип конфигурации на «Статическая библиотека»..lib "(" General "->" Тип конфигурации ").

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

Итак, преимущества этого решения:

  • низкая стоимость обслуживания
  • один проект DLL / статическая библиотека
  • не нужно вручную ссылаться на файлы .obj

Недостатки:

  • Дополнительные профили конфигурации) потребует некоторых изменений в вашей среде сборки (CI)
  • Увеличенное время компиляции

Обновление: в действительности мы использовали другой подход.

Мы добавили новые конфигурации «Test debug» / «Test release» для каждого имеющегося у нас проекта.

Для проектов .exe / .dll мы отключили исходный файл main.cpp от компиляции и заменили его на тот, которыйсоздает тестовую среду (например, gtest) и запускает все тесты, тесты находятся в отдельных файлах .cpp, которые также исключаются из компиляции в обычных конфигурациях (Release / Debug) и включены тольков тестовых конфигурациях.

Для проектов .lib у нас также есть новые конфигурации «Test debug» / «Test release», и мы преобразуем статическую библиотеку в файл .exe и предоставляем main.cpp, который создает экземпляр инфраструктуры тестирования и запускаеттесты и сами тесты.Связанные с тестом файлы исключаются из компиляции в конфигурациях выпуска / отладки.

0 голосов
/ 18 января 2013

Попробуйте создать определение, например, следующее, где все файлы будут включать:

#define EXPORTTESTING __declspec(dllexport)

И используйте его вместо dllexport, вот так:

class EXPORTTESTING Foo 
{
 ...
};

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...