Conan 1.38 is already here and comes with lots of new features and some bug fixes. As we have explained in previous posts we are paving the way to Conan 2.0, so most of the new features have to do with that. We have added a new conanfile.dependencies model, using a dictionary that returns information about the dependencies and may be used both directly in the recipe or indirectly to create custom build integrations and generators. Also, now Conan profiles support jinja2 syntax which provides the ability to read environment variables, using platform information, and much more. We have added a new cmake_layout() layout helper to define a multi-platform CMake layout that will work for different generators (Ninja, Xcode, Visual Studio, Unix), and is multi-config. There is also a new --conf argument to provide command line support for the new conf system. Finally, we have added a new PkgConfigDeps generator that will replace the existing pkg_config generator in Conan 2.0.

New conanfile.dependencies model

Starting in 1.38, Conan recipes will provide access to their dependencies through the self.dependencies attribute. The main use is to create new build system integrations and is already extensively used by Conan generators like CMakeDeps or MSBuildDeps to generate the necessary files for the build. It is also possible to access conanfile.dependencies from the recipe like this:

class MypkgConan(ConanFile):
    name = "mypkg"
    version = "1.0"
    requires = "libwebsockets/4.2.0"

    def generate(self):
        libwebsockets = self.dependencies["libwebsockets"]
        self.output.info(f"{libwebsockets.ref.version}")
        self.output.info(f"{libwebsockets.ref.revision}")
        self.output.info(f"{libwebsockets.settings.arch}")
        self.output.info(f"{', '.join([dep.ref.name for dep in libwebsockets.dependencies.values()])}")

As you can see we access can get information about the Conan reference, settings, and even the information about the dependencies of a specific dependency. Please, note that this information is read-only and that it can only be used in methods called after the full dependency graph has been computed. For more details about this, please check the documentation.

This new model will also allow iterating the dependencies of a recipe in a dict-like fashion, the key of that dictionary will contain the specifiers of the relation between the current recipe and the dependency. At the moment it can tell us if the dependency is a direct requirement (through the direct property) or if it’s a build_require (returned by the build property). Based on these values there are some helper properties to iterate all the dependencies and filter the ones we want. For example, if you want to list all the “host” requirements for the dependency you could call to self.dependencies.host and get all direct and transitive requirements that are not build_require.

class MypkgConan(ConanFile):
    name = "mypkg"
    version = "1.0"
    requires = "libwebsockets/4.2.0"

    def generate(self):
        trans_deps = self.dependencies.host
        self.output.info(f"transitive deps: {', '.join([dep.ref.name for dep in trans_deps.values()])}")

The output would look like this:

mypkg/1.0: Calling generate()
mypkg/1.0: transitive deps: libwebsockets, openssl

Please refer to the Conan documentation for more details on what helper properties are available.

Support for jinja2 syntax in Conan profiles

After many users requested having more powerful profiles we made some exploratory attempts with different implementations and we have finally decided to experimentally provide Conan profiles to support jinja2 templating syntax. This provides Conan profiles with some very useful capabilities. The only thing to be done is to name the profile with the .jinja extension. Let’s see some of those capabilities:

  • Using environment variables in profiles. Python os module is added to the render context so we can read environment variables using pure Python syntax. Also, you can define variables for use later.

      {% set build_type = os.getenv("MY_BUILD_TYPE") %}
      [settings]
      build_type = {{ build_type }}
    
  • Access to platform information. Python platform module is also added to the render context so we could set settings depending on the operating system we are running Conan into.

      [settings]
      os = {{ {"Darwin": "Macos"}.get(platform.system(), platform.system()) }}
    
  • Access to the current profile directory using the variable profile_dir.

You have all the information related to this feature in the Conan Documentation.

New cmake_layout() layout helper

After releasing the new layout() method for conanfile.py in 1.37, for this release, we are adding a pre-defined layout helper for CMake. This layout will check the CMake generator and set the corresponding folders according to that. For example, for multi-configuration generators such as Visual Studio or Xcode, the folders will be the same irrespective of the build type, and the build system will manage the different build types inside that folder. However, for single-config generators like Unix Makefiles, different folders will be set for each different configuration.

Using this in a recipe is as simple as this:

from conan.tools.layout import cmake_layout

def layout(self):
    cmake_layout(self)

You can check the implementation of this helper in the documentation. If your layout differs for example in where the sources are you can override the default value like this:

def layout(self):
    cmake_layout(self)
    self.folders.source = "mysrcfolder"

Configuration [conf] support from the command line

Starting in Conan 1.38 you can also set new configuration values using the -c argument for some commands. Taking the example from the cmake_layout() described above it is very handy to change the CMake generator using the command line like this:

conan create . -c tools.cmake.cmaketoolchain:generator=Xcode

New PkgConfigDeps generator

Please also check the new PkgConfigDeps generator meant to substitute our “classic” pkg_config generator in Conan 2.0. It makes use of the new conanfile.dependencies model we talked about in the beginning of this post. Check the docs for more information on how to use it.



Besides the items listed above, there were some minor bug fixes you may wish to read about. If so, please refer to the changelog for the complete list.

We hope you enjoy this release, and look forward to your feedback