2 releases
0.1.1 | Nov 28, 2024 |
---|---|
0.1.0 | Nov 27, 2024 |
#602 in Configuration
281 downloads per month
27KB
351 lines
featurecomb
Define feature groups and enforce relations between Cargo features from your manifest
Documentation
The documentation is available on docs.rs.
Example
In
examples/featurecomb-example/featurecomb-example-dependent/Cargo.toml
try enabling/disabling the various features of
examples/featurecomb-example/featurecomb-example-lib
.
Run cargo run
in examples/featurecomb-example
to check the effect.
Licensed
Copyright 2024 AudaciousAxiom
This project is licensed under MPL-2.0, except for the featurecomb-schema
crate which is licensed under MIT OR Apache-2.0.
lib.rs
:
featurecomb allows you to define groups of Cargo features and define different kinds of relations between features and these feature groups from your crate's manifest, and enforce them at compile time.
Installation
Simply add featurecomb
as a dependency to your crate.
Usage
Define feature groups and feature relations in your manifest metadata
table
as explained below, and use the #[featurecomb::comb]
attribute macro in
your crate top module to have these checked automatically at compile time.
How it works
featurecomb generates compile-time checks using #[cfg]
-gated compile_error!
statements
so that the requirements defined are checked by the compiler.
Feature groups
Feature groups are defined in the [package.metadata.feature-groups]
table.
They do not live in the same namespace as features, i.e., feature groups can be named the same
as existing features and will not conflict with them.
Marking features as mutually exclusive: $group.xor
Features of a group can be marked as mutually exclusive using the xor
table:
#
[package.metadata.feature-groups]
openssl.xor = { features = ["native-openssl", "vendored-openssl"] }
Performance note: the number of generated checks increases quadratically with the number of features in the group.
Requiring exactly one feature: $group.exactly-one
When features of a group are mutually exclusive but one must always be enabled, the
exactly-one
table is to be used instead:
#
[package.metadata.feature-groups]
llvm-version.exactly-one = { features = ["llvm-16", "llvm-17", "llvm-18"] }
Performance note: the number of generated checks increases quadratically with the number of features in the group.
Defining a feature group with no relations
A feature group can also be defined without enforcing any relations between the features of that group:
#
[package.metadata.feature-groups]
ip-version = { features = ["ipv4", "ipv6"] }
This is useful so that the group can be required by a feature, to express an "at least one" relation.
Features
Feature relations are defined in the [package.metadata.feature-groups.features]
table.
They define relations for features already existing in the standard
[features]
table.
Requiring groups and features: $feature.requires
The requires
table on a feature requires that the features and features groups listed be
enabled when that feature is enabled:
#
[package.metadata.feature-groups.features]
tls.requires = { groups = ["openssl", "tls-version"] }
#
[package.metadata.feature-groups.features]
usb-hid.requires = { features = ["usb"] }
It is possible to use the groups
and features
keys at the same time, in which case all
features and feature groups listed are required.
Example
See the examples
directory in the repository, which contains a playground to try out the
following example:
#
[package.metadata.feature-groups]
ip-version = { features = ["ipv4", "ipv6"] }
llvm-version.exactly-one = { features = ["llvm-16", "llvm-17", "llvm-18"] }
openssl.xor = { features = ["native-openssl", "vendored-openssl"] }
tls-version = { features = ["tls-12", "tls-13"] }
[package.metadata.feature-groups.features]
tls.requires = { groups = ["openssl", "tls-version"] }
usb-hid.requires = { features = ["usb"] }
[features]
ipv4 = []
ipv6 = []
llvm-16 = []
llvm-17 = []
llvm-18 = []
usb = []
usb-hid = []
tls = []
tls-12 = []
tls-13 = []
native-openssl = []
vendored-openssl = []
Compatibility
The error messages generated by this crate should not be considered stable.
Dependencies
~2.4–3MB
~64K SLoC