conan-io / cmake-conan

CMake wrapper for conan C and C++ package manager
MIT License
825 stars 250 forks source link

[question][dev2] How to prevent CMakeUserPresets.json/CMakePresets.json from being generated? #484

Open hwhsu1231 opened 1 year ago

hwhsu1231 commented 1 year ago

Problem Description

I tried to write my own CMakePresets.json specifying -DCMAKE_PROJECT_TOP_LEVEL_INCLUDES=conan_provider.cmake to simplify the step of configuring the project.

Click to expand CMakePresets.json ```json { "version": 4, "cmakeMinimumRequired": { "major": 3, "minor": 23, "patch": 0 }, "configurePresets": [ { "name": "win32-msvc16-x64-ninja-debug", "displayName": "Windows MSVC16 x64 (Ninja) Debug", "description": "Using MSVC16 x64 compilers with \"Ninja\" generator on Windows - Debug", "generator": "Ninja", "toolset": { "value": "v142,host=x64", "strategy": "external" }, "architecture": { "value": "x64", "strategy": "external" }, "binaryDir": "${sourceDir}/build/${presetName}", "cacheVariables": { "CMAKE_C_COMPILER": "cl.exe", "CMAKE_CXX_COMPILER": "cl.exe", "CMAKE_BUILD_TYPE": "Debug", "CMAKE_PROJECT_TOP_LEVEL_INCLUDES": "${sourceDir}/conan_provider.cmake" } } ], "buildPresets": [ { "name": "win32-msvc16-x64-ninja-debug", "displayName": "Build - Debug", "configurePreset": "win32-msvc16-x64-ninja-debug" } ] } ```

However, I found that there will be a CMakeUserPresets.json in the root directory and a CMakePresets.json inside the build directory generated by conan install command.

image

Since the original design of Conan 2.0 is to first run conan and then cmake, it seems that Conan 2.0 will generate CMakePresets.json/CMakeUserPresets.json for us to configure our CMake project. However, I think that I won't need these generated files when using cmake-conan because the starting point is cmake now. Therefore, I wondered:

How to prevent CMakeUserPresets.json/CMakePresets.json from being generated?

when consuming the packages.

Version and Environment

Steps to reproduce

  1. Extract the following archived file.

    cmake-conan-provider.zip

  2. Call vcvarsall.bat x64 to initialize the MSVC env:

    vcvarsall.bat x64
  3. Run the following cmake command to configure the porject:

    cmake --preset win32-msvc16-x64-ninja-debug

Logs

Click to expand logs ```cmd D:\Test\cmake-conan-provider>vcvarsall.bat x64 ********************************************************************** ** Visual Studio 2019 Developer Command Prompt v16.11.23 ** Copyright (c) 2021 Microsoft Corporation ********************************************************************** [vcvarsall.bat] Environment initialized for: 'x64' D:\Test\cmake-conan-provider>cmake --preset win32-msvc16-x64-ninja-debug Preset CMake variables: CMAKE_BUILD_TYPE="Debug" CMAKE_CXX_COMPILER="cl.exe" CMAKE_C_COMPILER="cl.exe" CMAKE_PROJECT_TOP_LEVEL_INCLUDES="D:/Test/cmake-conan-provider/conan_provider.cmake" -- The C compiler identification is MSVC 19.29.30147.0 -- The CXX compiler identification is MSVC 19.29.30147.0 -- Detecting C compiler ABI info -- Detecting C compiler ABI info - done -- Check for working C compiler: C:/Program Files (x86)/Microsoft Visual Studio/2019/Community/VC/Tools/MSVC/14.29.30133/bin/Hostx64/x64/cl.exe - skipped -- Detecting C compile features -- Detecting C compile features - done -- Detecting CXX compiler ABI info -- Detecting CXX compiler ABI info - done -- Check for working CXX compiler: C:/Program Files (x86)/Microsoft Visual Studio/2019/Community/VC/Tools/MSVC/14.29.30133/bin/Hostx64/x64/cl.exe - skipped -- Detecting CXX compile features -- Detecting CXX compile features - done ========== cmake-conan-provider ========== -- CMake-conan: first find_package() found. Installing dependencies with Conan -- Conan-cmake: Checking if a default profile exists D:\.conan2\home\profiles\default -- Conan-cmake: cmake_system_name=Windows -- Conan-cmake: CMake compiler=MSVC -- Conan-cmake: CMake cmpiler version=19.29.30147.0 -- Conan-cmake: [settings] compiler=msvc -- Conan-cmake: [settings] compiler.version=192 -- Conan-cmake: Creating profile D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug/conan_host_profile -- Conan-cmake: Profile: include(default) [settings] os=Windows compiler=msvc compiler.version=192 build_type=Debug [conf] tools.cmake.cmaketoolchain:generator=Ninja -- CMake-conan: Installing single configuration Debug -- CMake-conan: conan install D:/Test/cmake-conan-provider -of=D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug/conan -pr;D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug/conan_host_profile;--build=missing;-g;CMakeDeps ======== Input profiles ======== Profile host: [settings] arch=x86_64 build_type=Debug compiler=msvc compiler.cppstd=14 compiler.runtime=dynamic compiler.runtime_type=Debug compiler.version=192 os=Windows [conf] tools.cmake.cmaketoolchain:generator=Ninja Profile build: [settings] arch=x86_64 build_type=Release compiler=msvc compiler.cppstd=14 compiler.runtime=dynamic compiler.runtime_type=Release compiler.version=193 os=Windows ======== Computing dependency graph ======== Graph root conanfile.py: D:/Test/cmake-conan-provider\conanfile.py Requirements fmt/8.1.1#e63eae266b23cf3d7f3e0dfe33d1f7e9 - Cache ======== Computing necessary packages ======== Requirements fmt/8.1.1#e63eae266b23cf3d7f3e0dfe33d1f7e9:a6b1a9b5962f3f69ca4f26a80d8d82e9ba1fabe7#f1762e8333d32db4225378e23e3b4070 - Cache ======== Installing packages ======== fmt/8.1.1: Already installed! (1 of 1) WARN: Usage of deprecated Conan 1.X features that will be removed in Conan 2.X: WARN: 'cpp_info.names' used in: fmt/8.1.1 ======== Finalizing install (deploy, generators) ======== conanfile.py: Writing generators to D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug/conan conanfile.py: Generator 'CMakeToolchain' calling 'generate()' conanfile.py: CMakeToolchain generated: conan_toolchain.cmake conanfile.py: Preset 'conan-debug' added to CMakePresets.json. Invoke it manually using 'cmake --preset conan-debug' conanfile.py: If your CMake version is not compatible with CMakePresets (<3.19) call cmake like: 'cmake -G Ninja -DCMAKE_TOOLCHAIN_FILE=D:\Test\cmake-conan-provider\build\win32-msvc16-x64-ninja-debug\conan\conan_toolchain.cmake -DCMAKE_POLICY_DEFAULT_CMP0091=NEW -DCMAKE_BUILD_TYPE=Debug' conanfile.py: CMakeToolchain generated: CMakePresets.json conanfile.py: CMakeToolchain generated: ..\..\..\CMakeUserPresets.json conanfile.py: Generator 'CMakeDeps' calling 'generate()' conanfile.py: Generating aggregated env files conanfile.py: Generated aggregated env files: ['conanbuild.bat', 'conanrun.bat'] Install finished succesfully -- CMake-conan: CONAN_GENERATORS_FOLDER=D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug/conan -- Conan: Component target declared 'fmt::fmt' -- Configuring done -- Generating done -- Build files have been written to: D:/Test/cmake-conan-provider/build/win32-msvc16-x64-ninja-debug ```
hwhsu1231 commented 1 year ago

According to the Conan2 Docs of CMakeToolchian and cmake_layout,

when using CMakeToolchain generator.

The cause seems to be that conan install command searches the recipe in ${CMAKE_SOURCE_DIR}, which contains our CMakeLists.txt. Therefore, CMakeUserPresets.json will be generated in the source root directory:

https://github.com/conan-io/cmake-conan/blob/c389ff91274d2cc3805c61b4be1dc763d017528d/conan_support.cmake#L140-L145

Since CMakePresets.json is generated inside the CMake's build directory, I think it's fine. However, CMakeUserPresets.json is generated in the CMake's source root directory, which might interfere the cmake-presets detection supported by some IDEs.

How about:

  1. Copy the recipe from ${CMAKE_SOURCE_DIR} into ${CMAKE_BINARY_DIR}.
  2. And then conan install command searches the copy of recipe in the ${CMAKE_BINARY_DIR}.

So that CMakeUserPresets.json won't be generated?

saukijan commented 1 year ago

@hwhsu1231 I was wondering the same thing (in our case it IS messing with cmake configurations when we do not want to), do you have a workaround to disable the CMakeUserPresets.json configuration? (Apart from creating an empty CMakeUserPresets.json?)

memsharded commented 1 year ago

@hwhsu1231 I was wondering the same thing (in our case it IS messing with cmake configurations when we do not want to), do you have a workaround to disable the CMakeUserPresets.json configuration? (Apart from creating an empty CMakeUserPresets.json?)

I'd like to know a bit more, what kind of messing is causing. Is it an IDE-integration thing?

There is a way to disable it in the recipe:

def generate(self):
      tc = CMakeToolchain(self)
      tc.user_presets_path = False
      tc.generate()
hwhsu1231 commented 1 year ago

After researching for a while, I think the generation of CMakeUserPresets.json would not make the Git repository messy.

According to the CMake Documentation:

For example, if a project is using Git, CMakePresets.json may be tracked, and CMakeUserPresets.json should be added to the .gitignore.

In other words, unless we forgot to add CMakeUserPresets.json to .gitignore, the CMakeUserPresets.json generated in the root directory by Conan would not be pushed to the Git repository.

@memsharded - However, I want to confirm whether there is a way for Conan to disable the generation of CMakeUserPresets.json through CLI parameters, rather than modifying the recipe?

There is a way to disable it in the recipe:

def generate(self):
      tc = CMakeToolchain(self)
      tc.user_presets_path = False
      tc.generate()
sburton84 commented 2 weeks ago

I'll second that it would be useful to have a way of disabling this on the command-line. My use-case is that I want this generated when running non-Docker builds, as it's used by my IDE, but want to disable it when I run a Docker build, as it adds an entry that is invalid outside of Docker. I suppose I could add an option to my recipe, so I can disable this with a -o argument, if that's the only way, but that seems like a misuse of options...