Merged
Conversation
…egateComponentEntries
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
This PR brings a number of improvements to the CGP Presets feature, and adds better support on OOP-like inheritance on presets.
Inheritance
Presets can now inherit from each other a short hand
: ParentPresetnotation. Behind the scene, thecgp_preset!macro is re-expanded multiple times to callParentPreset::with_components!to inherit the component delegation from the parent preset.Example:
In the above example,
PresetBwill delegateFooComponentandBarComponenttoPresetA::Provider.Overrides
When inheriting presets, the
overridekeyword can be specified in the child preset entry to override/exclude the component from the parent preset. This allows a preset to be customized with minimal code duplication, by specifying only the components to be overridden. This can also be used to resolve the diamond inheritance problem, with the child preset overriding any conflicting presets from the parents.Example:
In the above example,
PresetBoverrides theBarComponentfromPresetA, and replaces it withCustomProvider.Limitations of Override
Note that due to limitations of Rust macros, the override would only work based on exact identifier matches as seen by the preset macros, not by the original name or the import path.
Hence, the override may behave in unexpected ways, if it involves re-naming, or if multiple modules define components with the same name identifier.
Generic Presets
The
cgp_preset!macro can now work with presets containing generic parameters. It is now also possible to include generic parameters inside the preset delegate entries, similar todelegate_components!.Minimal Preset Re-exports (Breaking Changes)
The re-exports from preset modules have been reduced to only expose the component name identifiers. Before, the preset bulk re-exports everything that was imported from the module that contains
cgp_preset!, which could pollute the import scope in the child presets.With this changes, the original
Preset::re_exportsmodule is made private, with a newPreset::componentsmodule that re-exports only the component name identifiers. Note that the originalPreset::re_exportsis still required, as the macro cannot keep track of whether a component name identifier originates from the child preset, or from one of the parent presets. Hence, we usePreset::re_exportsto combine everything first, then buildPreset::componentsto re-export fromPreset::re_exports.Removal of
DelegatesToPresetTrait (Breaking Changes)We have removed the derivation of
DelegatesToPresettrait incgp_preset!. Originally, this trait could be used to check whether a child provider has delegated all of the preset's components to the given preset provider. However, challenges arise when either the preset or the entries contain generic parameters, with the macro generating code with incorrect generic bindings.we have removed the trait to simplify the implementation of
cgp_preset!. Furthermore, there isn't much need for theDelegatesToPresetanymore, with the newIsProviderFortrait helping to improve debugging of CGP-related errors.Examples
For more examples of how the new presets work, check out the test examples in the
cgp-testcrate.Note that preset is an advanced concept in CGP that is yet to be formally introduced in our book. More updates will be coming very soon.