Designing CMaize’s PackageManager Component

This page describes the design of the classes comprising CMaize’s PackageManager component.

What is the PackageManager Component?

Developers use CMaize to write the build system for their project. As part of that build system they state the dependencies which the project needs. The PackageManager component is responsible for actually making those dependencies available to the user, be it by finding already built versions, or by building them.

Why do we Need a PackageManager Component?

The need for package manager integrations was one of the high-level considerations behind CMaize (see package manager support). The PackageManager component is how CMaize addresses this consideration. It should be noted that traditional CMake can be seen as having an underlying package manager manager with find_package serving as the function for locating existing packages and the FetchContent and/or ExternalProject modules actually building and installing the packages.

PackageManager Considerations

finding packages

The design discussion in Overview of CMaize’s User API Design decided that the package manager would be responsible for finding packages that meet the specifications needed by the project. From the Designing CMaize’s CMaizeProject Component discussion it was decided that the specifications will be represented by PackageSpecification objects.

building packages

The design discussion in Overview of CMaize’s User API Design decided that the package manager would be responsible for building packages that the project depends on.

installing packages

Brought up in Designing CMaize’s C++ Target Classes, the package manager is responsible for installing the built packages.

CMake package manager

Historically, C++ build system maintainers have relied on CMake’s package managing capabilities. To be backwards compatible, CMaize must support CMake’s package manager. See CMake’s Package Manager for more details on how traditional CMake is used as a package manager.

extendable

Ultimately we want to leverage existing package managers outside the CMake ecosystem. The PackageManager component should be able to wrap other package managers aside from the CMake manager.

PackageManager Design

../../../_images/package_manager.png

Fig. 7 Overview of CMaize’s PackageManager component.

Fig. 7 provides an overview of the PackageManager component. Considerations finding packages, building packages, and installing packages are addressed by the abstract base class’s API. More specifically, each derived class is charged with implementing mechanisms for finding (find_installed), building (get_package), and installing (install_package) packages. The mechanisms for using CMake’s built in package manager are implemented by the CMakePackageManager class (consideration CMake package manager). Finally, we note that the extendable consideration is addressed by deriving new classes from the PackageManager base class.

Summary

finding packages

Finding installed packages is done via the find_installed method. Each derived class must implement it appropriately.

building packages

Obtaining and/or building a package is done by calling the get_package method. Again, the derived class is responsible for implementing it in a manner which is appropriate for the backend.

installing packages

Installing the package is abstracted away by the install_package method. Classes derived from PackageManager must implement the method appropriately.

CMake package manager

The first package manager implemented in CMaize is the CMake package manager, which is represented by the CMakePackageManager class. The CMakePackageManager class leverages CMake’s find_package function and the FetchContent module.

extendable

Extending the package manager component to additional package managers is straightforward and done by deriving new classes from PackageManager.