You can probably make use of "Typed Tests" or "Type-Parameterized Tests" here.
So for example, if you remove TEST_F(BaseTest, ACommonTest) {}
(since that's where you instantiate a BaseTest
rather than one derived from it), you can replace it with:
template <typename T>
class DerivedCommonTest : public BaseTest {
public:
DerivedCommonTest() : BaseTest() {}
virtual void SetUp() { BaseTest::SetUp(); }
};
typedef ::testing::Types<Foo, Bar> MyTypes;
TYPED_TEST_CASE(DerivedCommonTest, MyTypes);
TYPED_TEST(DerivedCommonTest, ACommonTest) {} // common test case
If you really wish to make BaseTest
non-instantiable, you could add a pure virtual function to it, and then implement it for each derived type:
class BaseTest : public ::testing::Test {
protected:
BaseTest() {} // constructor with args to setup members
virtual void SetUp() {} // sets up the internals
virtual void PureVirtual() = 0;
};
...
template <typename T>
class DerivedCommonTest : public BaseTest {
public:
DerivedCommonTest() : BaseTest() {}
virtual void SetUp() { BaseTest::SetUp(); }
virtual void PureVirtual() {}
};
...
class DerivedTest : public BaseTest {
public:
DerivedTest() : BaseTest(...) {} // default no args constructor
virtual void SetUp() { BaseTest::SetUp(); }
virtual void PureVirtual() {}
};