Dealing with CMake FetchContent

Is there already some generic way of dealing with fetchContent from CMake? So far, I was usually able to patch the projects and provide the required dependencies by hand but things have started to become transitive now where dependencies themselves start to have their own series of dependencies managed using fetchContent. This is starting to become a real hassle that probably needs to be solved in a somewhat generic way.

CMake seems to support setting a dependency provider on the high-level (Using Dependencies Guide — CMake 3.28.3 Documentation) which might be the way forward here. Though, given the lack of a global lockfile in CMake (like, e.g. Rust has) this still requires one run to capture all the dependencies.

Is anyone already working on solving this in a somewhat generic way?

5 Likes

I wrote some Nix code that extracts FetchContent declarations from a CMakeLists.txt file, defines derivations for them, and sets the CMake variables for FetchContent to use the nix-provided copy. The FetchContent declarations have the repo url, git hash, and name, so I just also add a comment with the hash. For an example of the CMake variables, passing -DFETCHCONTENT_SOURCE_DIR_hello=/nix/store/...-hello/ would override FetchContent declarations for hello (case-insensitve, the last part of variable is lowercased).

This does not solve the dependencies of dependencies problem (though I’m of the opinion that dependencies shouldn’t be in the business of locking deps for consumers…).

With IFD, it might be possible to write a derivation that extracts all the definitions, and produces the info for generating CMake flags for all the dependencies, including transitive ones.

1 Like

@accelbread, have you put the translation code you wrote somewhere? I’d like to use it, too.

1 Like

Seems its made it into a public repo, so heres a link: https://github.com/FreeRTOS/Labs-Project-ota-example-for-aws-iot-core/blob/c2fac602462395213e6011c47e1c9b5e81313795/flake.nix#L43

1 Like

The generic solution to this issue is to convince upstream to use FetchContent_Declare with FIND_PACKAGE_ARGS, so that FetchContent_MakeAvailable short-circuits if we provide it a ready dependency from Nixpkgs (vcpkg, debian, etc). This also requires a reasonably up-to-date cmake version

3 Likes

I created an approach that can deal with this and not require individual patching per project. Not sure if this is clean enough for Nixpkgs, but I will use it for personal projects. Works very well for CMake and might actually cover quite some additional use-cases.

1 Like