如何在Linux上将googleTest设置为共享库

103

Debian不再提供gTest的任何预编译包,他们建议您将框架集成到项目的makefile中。但我想保持我的makefile干净整洁。我该如何像早期版本(<1.6.0)那样设置gTest,以便可以链接到库?


2
顺便说一下,gtest的构建是使用autotools管理的,因此标准的“./configure && make && make install”工作流程应该可以正常工作。我不确定这是否值得发布,因为它与从源代码编译许多其他软件包没有什么区别。 - Shawn Chin
7
我猜并不是所有的用户都像你这么有经验。我最近从Windows转到Linux,如果在StackOverflow上能找到类似的东西,我会很开心的。 - ManuelSchneid3r
3
请注意,Google建议您不要构建库,而是将GTest代码包含在您的项目中。请参见https://code.google.com/p/googletest/wiki/FAQ#Why_is_it_not_recommended_to_install_a_pre-compiled_copy_of_Goog,但不要改变原来的意思。 - Mawg says reinstate Monica
1
@Mawg提供的链接已经失效(维基已删除),它似乎可以工作,但是指向的页面不再是相关话题(相当令人困惑)。我能找到的最好的替代品是这些构建说明:https://github.com/google/googletest/blob/master/googletest/README.md, 但是那只解释了如何使用cmake构建。对于autotools,我发现以下答案效果最好:https://dev59.com/vVsV5IYBdhLWcg3wngCy#36000856 - Carlo Wood
哇!!!那真是奇怪!!!感谢指出。 - Mawg says reinstate Monica
显示剩余2条评论
14个回答

160

在开始之前,请确保您已经阅读并理解了Google的这个说明!本教程使使用gtest变得容易,但可能会引入讨厌的错误

1. 获取googletest框架

wget https://github.com/google/googletest/archive/release-1.8.0.tar.gz

或者通过手动获取。我不会维护这个小教程,所以如果你发现链接已经过期,请随意编辑它。

2. 解压并构建Google测试

tar xf release-1.8.0.tar.gz
cd googletest-release-1.8.0
cmake -DBUILD_SHARED_LIBS=ON .
make

3. 在您的系统上“安装”头文件和库文件。

这一步可能因发行版而异,因此请确保将头文件和库文件复制到正确的目录中。我通过检查Debian以前的gtest库的位置来完成此操作。但我相信有更好的方法来做到这一点。

sudo cp -a googletest/include/gtest /usr/include
sudo cp -a googlemock/gtest/libgtest_main.so googlemock/gtest/libgtest.so /usr/lib/

# The easiest/best way:
make install  # Note: before v1.11 this can be dangerous and is not supported

4. 更新链接器缓存

...并检查GNU链接器是否知道这些库

sudo ldconfig -v | grep gtest

如果输出看起来像这样:
libgtest.so.0 -> libgtest.so.0.0.0
libgtest_main.so.0 -> libgtest_main.so.0.0.0

然后一切都很好。

gTestframework现在已经可以使用了。只需不要忘记通过设置-lgtest作为链接器标志将您的项目与库链接起来,如果您没有编写自己的测试main()例程,则可以选择使用显式的-lgtest_main标志。

从这里开始,您可能想查看Google的Googletest Primer文档以及关于该框架的旧文档,以了解其工作原理。祝您编码愉快!

编辑: 这也适用于OS X!请参阅{{link3:“如何在OS X上正确设置googleTest”}}


2
有没有make install目标,可以代替手动复制库和头文件? - Shawn Chin
16
makefile 的输出中提到:"'make install' 是危险且不被支持的。请查看 README 以了解如何将 Google Test 集成到您的构建系统中,而不是使用该命令。" - ManuelSchneid3r
4
您的帖子已经过时,请勿误导他人。sudo cp -a libgtest_main.so libgtest.so /usr/lib/已不再适用。该文件甚至不存在于此。 - Schütze
你的解决方案对我没用。正确的 ldconfig 输出没有显示出来。sudo make install 对我有用。 - Maxxik CZ
从1.11开始,只需运行make install,这在>=debian10上可用。 - jaques-sam
显示剩余6条评论

45

我来为Ubuntu用户具体解答这个问题。首先,需要安装gtest开发包。

sudo apt-get install libgtest-dev
请注意,此软件包仅安装源代码文件。您需要自行编译代码以创建必要的库文件。这些源代码文件应位于/usr/src/gtest目录下。转到此文件夹并使用cmake编译库。
sudo apt-get install cmake # install cmake
cd /usr/src/gtest
sudo mkdir build
cd build
sudo cmake ..
sudo make
sudo make install

现在,如果要编译使用gtest的程序,您需要将其与以下内容链接:

-lgtest -lgtest_main -lpthread

这个方法在我的 Ubuntu 14.04LTS 上完美地运行。


1
实际上,您不必手动复制库,Makefile 中有一个目标可以完成此操作。您只需按照以下步骤执行即可: sudo apt-get install cmake # 安装cmake cd /usr/src/gtest sudo cmake CMakeLists.txt sudo make install 这样就应该构建并复制到 /usr/local/lib/。 - Alexander Zinovyev
1
当我执行“sudo make install”时,我收到“make: *** No rule to make target 'install'. Stop.”的错误提示。@AlexanderZinovyev - m4l490n
2
"sudo make install" 在 Ubuntu 18.04 上运行正常,但在 Ubuntu 16.04 上无法运行。 - Ahmed Nassar
1
@AhmedNassar:“sudo make install”和“sudo cp *.a /usr/lib”做的事情是一样的。因此,如果在生成的Makefile中没有安装选项,您只需手动复制它们。 - amritkrs
不需要手动执行 sudo cp *.a /usr/lib,只需使用 sudo make install 替换即可。 - lingjiankong
我必须使用“-lgtest -lgtest_main -lpthread”进行编译才能使其正常工作。 - Ibrahim Mohamed

28

由于常规的“make install”已被删除,而我又不使用cmake,因此我花了一些时间才弄清楚这个问题。这是我的经验分享。在工作中,我没有Linux的root访问权限,因此我将Google测试框架安装在我的主目录下:~/usr/gtest/

如果要将包安装在~/usr/gtest/作为共享库,并附带示例构建,请使用以下命令:

$ mkdir ~/temp
$ cd ~/temp
$ unzip gtest-1.7.0.zip 
$ cd gtest-1.7.0
$ mkdir mybuild
$ cd mybuild
$ cmake -DBUILD_SHARED_LIBS=ON -Dgtest_build_samples=ON -G"Unix Makefiles" ..
$ make
$ cp -r ../include/gtest ~/usr/gtest/include/
$ cp lib*.so ~/usr/gtest/lib

为了验证安装,请使用以下test.c作为简单测试示例:

    #include <gtest/gtest.h>
    TEST(MathTest, TwoPlusTwoEqualsFour) {
        EXPECT_EQ(2 + 2, 4);
    }

    int main(int argc, char **argv) {
        ::testing::InitGoogleTest( &argc, argv );
        return RUN_ALL_TESTS();
    }

编译方法:

    $ export GTEST_HOME=~/usr/gtest
    $ export LD_LIBRARY_PATH=$GTEST_HOME/lib:$LD_LIBRARY_PATH
    $ g++ -I $GTEST_HOME/include -L $GTEST_HOME/lib -lgtest -lgtest_main -lpthread test.cpp 

1
最后一行出现错误:/usr/bin/ld: /tmp/cczG727X.o: 对符号“_ZN7testing4TestC2Ev”未定义的引用。我通过将test.cpp放在库之前来解决这个问题。即:g++ test.cpp -I $GTEST_HOME/include -L $GTEST_HOME/lib -lgtest -lgtest_main -lpthread - user9869932
如果链接到 gtest_main (lgtest_main),则在测试文件中无需定义自己的 main - Gino Mempin

11
如果您正在使用CMake,可以使用ExternalProject_Add来完成。如所述,这避免了您需要在代码库或其他地方安装gtest源代码的情况。gtest将自动下载并在构建树中构建。

3

Debian/Ubuntu 更新

Google Mock(包名称:google-mock)和 Google Test(包名称:libgtest-dev)已经合并,新的包名为 googletest。为了向后兼容,两个旧名称仍然可用,但现在它们都依赖于新的包 googletest

因此,要从软件包库获取您的库,您可以执行以下操作:

sudo apt-get install googletest -y
cd /usr/src/googletest
sudo mkdir build
cd build
sudo cmake ..
sudo make
sudo cp googlemock/*.a googlemock/gtest/*.a /usr/lib

之后,您可以链接 -lgmock(或链接-lgmock_main如果您不使用自定义的主方法),以及-lpthread。至少在我这里,这已足够使用 Google Test。

如果您想要最新版本的Google Test,请从github上下载。之后,步骤类似:

git clone https://github.com/google/googletest
cd googletest
sudo mkdir build
cd build
sudo cmake ..
sudo make
sudo cp lib/*.a /usr/lib

正如您所看到的,创建库的路径已经改变。请注意,新路径可能很快就会对软件包仓库有效。

您可以使用sudo make install来代替手动复制库。目前它是可用的,但要注意过去它并不总是有效的。此外,当使用此命令时,您无法控制目标位置,您可能不希望污染/usr/lib目录。


1
我对这种情况也感到失望,最终我自己为此创建了Ubuntu源代码包。这些源代码包允许您轻松生成二进制包。它们基于此帖子发布时最新的gtest和gmock源代码。 Google Test DEB源代码包 Google Mock DEB源代码包 要构建二进制包,请执行以下操作:
tar -xzvf gtest-1.7.0.tar.gz
cd gtest-1.7.0
dpkg-source -x gtest_1.7.0-1.dsc
cd gtest-1.7.0
dpkg-buildpackage

如果有必要,它会告诉您需要一些先决包,这种情况下,您只需要使用apt-get install安装它们。此外,构建好的.deb二进制软件包应该位于父目录中。

对于GMock,过程是相同的。

顺便提一句,虽然不特定于我的源代码包,但在将gtest链接到单元测试时,请确保先包含gtest (https://bbs.archlinux.org/viewtopic.php?id=156639)。这似乎是一个常见的坑点。


你的包在我尝试编译时给了我错误。有什么原因吗?这是我的日志test.cpp:(.text+0x57): undefined reference to testing::Message::Message()' test.cpp:(.text+0x84): undefined reference to testing::internal::AssertHelper::AssertHelper(testing::TestPartResult::Type, char const*, int, char const*)' test.cpp:(.text+0x97): undefined reference to `testing::internal::AssertHelper::operator=(testing::Message const&) const' ...它太长了,我无法发布整个内容。我在全新的Ubuntu 14.04 VM中完成了这项工作,因此除了必要的依赖项之外,没有安装其他任何内容。 - ddelnano
@ddelnano 嗯,我也遇到了这个小问题。显然,共享库的顺序很重要。在将 gtest 链接到单元测试时,请尝试先包含 gtest 再包含其他库。 当我遇到这个问题时,这个链接为我解决了它:https://bbs.archlinux.org/viewtopic.php?id=156639 - Nick Weedon
@ddelnano,如果你的测试套件没有定义“main”,那么不要忘记链接“gtest_main”。 - Nick Weedon
我没有包含任何其他库。这是我文件中所有的内容:#include TEST(MathTest, TwoPlusTwoEqualsFour) { EXPECT_EQ(2 + 2, 4); } int main(int argc, char **argv) { ::testing::InitGoogleTest( &argc, argv ); return RUN_ALL_TESTS(); } - ddelnano
没事,我在发完评论之后才读这篇博客文章。现在终于能正常工作了! - ddelnano

1
下面的方法可以避免手动操作 /usr/lib 目录,同时对你的 CMakeLists.txt 文件的更改要求最小。它还可以让你的软件包管理器干净地卸载 libgtest-dev
其思想是当你通过软件包管理器获取 libgtest-dev 包时,将库文件复制到你的项目中,并在 CMake 中链接这些库文件。
sudo apt install libgtest-dev

源代码存储在位置/usr/src/googletest

您只需将CMakeLists.txt指向该目录,以便它可以找到必要的依赖项

只需将FindGTest替换为add_subdirectory(/usr/src/googletest gtest)

最终,应该是这个样子

add_subdirectory(/usr/src/googletest gtest)
target_link_libraries(your_executable gtest)

1
这篇来自askubuntu的回答对我很有用。与其他选项相比,似乎更简单且不容易出错,因为它使用包libgtest-dev获取源代码并从那里构建:https://askubuntu.com/questions/145887/why-no-library-files-installed-for-google-test?answertab=votes#tab-top 请参考该回答,但作为快捷方式,我也提供了以下步骤:
sudo apt-get install -y libgtest-dev
sudo apt-get install -y cmake
cd /usr/src/gtest
sudo cmake .
sudo make
sudo mv libg* /usr/lib/

之后,我可以顺利构建依赖于gtest的项目。


1

如果有人像我昨天(2016-06-22)遇到了同样的问题,并且之前发布的方法也没有成功 - 在 Lubuntu 14.04 上,使用以下命令链对我有效:

git clone https://github.com/google/googletest
cd googletest
cmake -DBUILD_SHARED_LIBS=ON .
make
cd googlemock
sudo cp ./libgmock_main.so ./gtest/libgtest.so gtest/libgtest_main.so ./libgmock.so /usr/lib/
sudo ldconfig

1

这将构建并安装 gtest 和 gmock 1.7.0:

mkdir /tmp/googleTestMock
tar -xvf googletest-release-1.7.0.tar.gz -C /tmp/googleTestMock
tar -xvf googlemock-release-1.7.0.tar.gz -C /tmp/googleTestMock
cd /tmp/googleTestMock
mv googletest-release-1.7.0 gtest
cd googlemock-release-1.7.0
cmake -DBUILD_SHARED_LIBS=ON .
make -j$(nproc)
sudo cp -a include/gmock /usr/include
sudo cp -a libgmock.so libgmock_main.so /usr/lib/
sudo cp -a ../gtest/include/gtest /usr/include
sudo cp -a gtest/libgtest.so gtest/libgtest_main.so /usr/lib/
sudo ldconfig

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接