<< Modern CMake >> 2.4 translation project directory structure
This section is a bit beside the point. But I think this is a good way. I will tell you how to plan the project directory. This is based on the practice, but it will help you:
- Easy reading other projects in the same mode,
- Lead to conflict avoidance mode,
- Avoid confusion and make the building complicated.
First, if your project is called project
, contains a link library is called lib
, an executable file called app
, then your file directory structure should be similar to the following:
- project
- .gitignore
- README.md
- LICENCE.md
- CMakeLists.txt
- cmake
- FindSomeLib.cmake
- include
- project
- lib.hpp
- src
- CMakeLists.txt
- lib.cpp
- apps
- CMakeLists.txt
- app.cpp
- tests
- testlib.cpp
- docs
- Doxyfile.in
- extern
- googletest
- scripts
- helper.py
The name is not absolute; you often see on test/
vs. tests/
debate, the Applications folder may be called a different name (for projects only library does not exist). You'll see when there is python
a directory for python
binding, or a folder CMake, assistant to place CMake files, such as Find<library>.cmake
documents. But the main folder above are listed.
Pay attention to some very obvious things; CMakeLists.txt
files are placed in all of the source directory, respectively, but include
the directory does not. This is because you should be able to copy the include
directory to /usr/include
or similar places (except configuration header file, I will describe in another chapter), no additional files or cause any conflict. This is why include
there is a layer of directories project
reasons directory. Use add_subdirectory
to add contains CMakeLists.txt
a subdirectory files.
You often need a cmake
directory to place all constructed assistant module. This is your Find*.cmake
place files in the storage. A common set of helper files can be seen here github.com/CLIUtils/cmake .
In this way you can add this folder to the CMake path:
set(CMAKE_MODULE_PATH "${PROJECT_SOURCE_DIR}/cmake" ${CMAKE_MODULE_PATH})
Your extern
folder should contain only git submodules. This allows you to explicitly control dependent version of the item, and can be easily upgraded. For an example of adding sub-module, see "Testing" chapter.
In your .gitignore
, you should have something like this /build*
, so that users can create a build directory in the source directory, and build the project in these directories. Some packages prohibited from doing so, but it is likened to a building outside the real source of much better, because then you have to type each build different command-line for the package you build.
If you want to avoid building directly in the source folder, you can add the following lines to your CMakeLists.txt
near the top of the file:
### Require out-of-source builds
file(TO_CMAKE_PATH "${PROJECT_BINARY_DIR}/CMakeLists.txt" LOC_PATH)
if(EXISTS "${LOC_PATH}")
message(FATAL_ERROR "You cannot build in a source directory (or any directory with a CMakeLists.txt file). Please make a build subdirectory. Feel free to remove CMakeCache.txt and CMakeFiles.") endif()