Skip to content

Improve/standardize CMake config file creation #180

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
rpavlik opened this issue Feb 19, 2015 · 8 comments
Closed

Improve/standardize CMake config file creation #180

rpavlik opened this issue Feb 19, 2015 · 8 comments

Comments

@rpavlik
Copy link

rpavlik commented Feb 19, 2015

Spurred by Kitware/CMake#144

Basically, jsoncpp is generating the config file in an "old" or less-preferred way. I tried patching the Find module slated for inclusion in CMake 3.2.0 to be able to bootstrap itself from the config file, but the (somewhat hasty) pull request was (quite reasonably) denied because of dependence on implementation-specific details of exported targets.

Not sure exactly what needs to be done to improve this, but I'll be starting a thread on the CMake mailing list to follow up on that patch.

@cdunn2001
Copy link
Contributor

Ok. Let us know what you learn. I think we need to remain backward-compatible for older cmake for now, but it might be possible to includes "ifs" within the cmakefiles for that.

@bradking
Copy link
Contributor

The CMake manual contains an explanation of how to create packages:

http://www.cmake.org/cmake/help/v3.2/manual/cmake-packages.7.html#creating-packages

Directly creating a <pkg>Config.cmake file with install(EXPORT) was never the official or preferred way. Package configuration files have always been created with configure_file or similar approaches, and pre-dated CMake's ability to export/import targets. When install(EXPORT) was introduced then projects started using it to create a <pkg>Targets.cmake file (whose name is only a convention and has no meaning to CMake) and then loading it from the main <pkg>Config.cmake.

There should be no compatibility issue for supporting older CMake versions if you switch to creating a jsoncppTargets.cmake file with install(EXPORT) and providing jsoncppConfig.cmake as a file that includes it. Furthermore then the new jsoncppConfig.cmake file should provide other information. See the above link about creating packages. Version information should also be provided in a jsoncppConfigVersion.cmake. That will allow applications that do find_package(jsoncpp CONFIG) to check variables like jsoncpp_VERSION to see the version number.

@cdunn2001
Copy link
Contributor

Sounds great! Could one of you write the patch?

@bradking
Copy link
Contributor

@rpavlik, if you work on this you could also consider naming the files jsoncpp-config.cmake, jsoncpp-config-version.cmake, and jsoncpp-targets.cmake. The lower case name seems more in the style of jsoncpp. Also CMake's find_package command has long documented support for the <pkg>-config.cmake naming alternative so even older CMake versions will still find it there.

@bradking
Copy link
Contributor

As discussed in Kitware/CMake#144, CMake 3.2 will not distribute a FindJsonCpp module as originally planned because it may conflict with existing code that does find_package(jsoncpp) looking for the current jsoncppConfig.cmake file. However, the only way for a CMake project to find jsoncpp reliably without having a copy of FindJsonCpp is if jsoncpp consistently provides the package configuration files so that a plain find_package(jsoncpp) call will always have a file to find. This means it would have to be done unconditionally and by all the build systems (LLVM provides one both with CMake and with autotools, for example). Currently jsoncppConfig.cmake is provided only by the CMake build system for jsoncpp and only conditionally.

@cdunn2001
Copy link
Contributor

@fraillt
Copy link

fraillt commented Mar 23, 2018

I would like to add one thing, regarding exporting targets.
In modern cmake it is prefered to export targets to namespaces like this:

find_package(jsoncpp)
target_link_libraries(myexe PRIVATE JSONCPP::jsoncpp_lib_static)

with this syntax, cmake knows that JSONCPP::jsoncpp_lib_static is cmake target, ant not some arbitrary library, so if you mistype library name at cmake will detect it at configure time.

The change is realy small

IF(JSONCPP_WITH_CMAKE_PACKAGE)
        INSTALL(EXPORT jsoncpp
                NAMESPACE JSONCPP:: # <-- add this line, to export targets in namespace
                DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/jsoncpp
                FILE        jsoncppConfig.cmake)
ENDIF()

The problem is that, existing users after update should write
target_link_libraries( ... JSONCPP::jsoncpp_lib_static) instead of
target_link_libraries( ... jsoncpp_lib_static)

@cdunn2001
Copy link
Contributor

The problem is that, existing users after update should ...

That's a pretty big problem. cmake support is only legacy. We use and recommend meson. I'd hate to break old cmake users when new cmake users have a good alternative.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants