Encapsulate the required provider logic in RequiredProviders class.
For now, only for aspects, but eventually expand to Attribute's
mandatory providers as well.
--
PiperOrigin-RevId: 144063369
MOS_MIGRATED_REVID=144063369
diff --git a/src/main/java/com/google/devtools/build/lib/packages/AspectDefinition.java b/src/main/java/com/google/devtools/build/lib/packages/AspectDefinition.java
index 18cd2eb..92f6d0c 100644
--- a/src/main/java/com/google/devtools/build/lib/packages/AspectDefinition.java
+++ b/src/main/java/com/google/devtools/build/lib/packages/AspectDefinition.java
@@ -56,8 +56,7 @@
public final class AspectDefinition {
private final AspectClass aspectClass;
- private final ImmutableList<ImmutableSet<Class<?>>> requiredProviderSets;
- private final ImmutableList<ImmutableSet<String>> requiredProviderNameSets;
+ private final RequiredProviders requiredProviders;
private final ImmutableMap<String, Attribute> attributes;
private final PropagationFunction attributeAspects;
@Nullable private final ConfigurationFragmentPolicy configurationFragmentPolicy;
@@ -68,23 +67,16 @@
private AspectDefinition(
AspectClass aspectClass,
- ImmutableList<ImmutableSet<Class<?>>> requiredProviderSets,
+ RequiredProviders requiredProviders,
ImmutableMap<String, Attribute> attributes,
PropagationFunction attributeAspects,
@Nullable ConfigurationFragmentPolicy configurationFragmentPolicy) {
this.aspectClass = aspectClass;
- this.requiredProviderSets = requiredProviderSets;
+ this.requiredProviders = requiredProviders;
this.attributes = attributes;
this.attributeAspects = attributeAspects;
this.configurationFragmentPolicy = configurationFragmentPolicy;
-
- ImmutableList.Builder<ImmutableSet<String>> requiredProviderNameSetsBuilder =
- new ImmutableList.Builder<>();
- for (ImmutableSet<Class<?>> requiredProviderSet : requiredProviderSets) {
- requiredProviderNameSetsBuilder.add(toStringSet(requiredProviderSet));
- }
- this.requiredProviderNameSets = requiredProviderNameSetsBuilder.build();
}
public String getName() {
@@ -105,34 +97,14 @@
}
/**
- * Returns the list of {@link com.google.devtools.build.lib.analysis.TransitiveInfoProvider}
- * sets. All required providers from at least one set must be present on a configured target so
- * that this aspect can be applied to it.
+ * Returns {@link RequiredProviders} that a configured target must have so that
+ * this aspect can be applied to it.
*
- * <p>We cannot refer to that class here due to our dependency structure, so this returns a set
- * of unconstrained class objects.
- *
- * <p>If a configured target does not have a required provider, the aspect is silently not created
- * for it.
+ * <p>If a configured target does not satisfy required providers, the aspect is
+ * silently not created for it.
*/
- public ImmutableList<ImmutableSet<Class<?>>> getRequiredProviders() {
- return requiredProviderSets;
- }
-
- /**
- * Returns the list of class name sets of
- * {@link com.google.devtools.build.lib.analysis.TransitiveInfoProvider}. All required providers
- * from at least one set must be present on a configured target so that this aspect can be applied
- * to it.
- *
- * <p>This set is a mirror of the set returned by {@link #getRequiredProviders}, but contains the
- * names of the classes rather than the class objects themselves.
- *
- * <p>If a configured target does not have a required provider, the aspect is silently not created
- * for it.
- */
- public ImmutableList<ImmutableSet<String>> getRequiredProviderNames() {
- return requiredProviderNameSets;
+ public RequiredProviders getRequiredProviders() {
+ return requiredProviders;
}
/**
@@ -176,31 +148,15 @@
for (Aspect candidateClass : attribute.getAspects(from)) {
// Check if target satisfies condition for this aspect (has to provide all required
// TransitiveInfoProviders)
- if (!advertisedProviders.canHaveAnyProvider()) {
- ImmutableList<ImmutableSet<Class<?>>> providerNamesList =
- candidateClass.getDefinition().getRequiredProviders();
-
- for (ImmutableSet<Class<?>> providerNames : providerNamesList) {
- if (advertisedProviders.getNativeProviders().containsAll(providerNames)) {
- addAllAttributesOfAspect(from, result, candidateClass, dependencyFilter);
- break;
- }
- }
- } else {
+ RequiredProviders requiredProviders =
+ candidateClass.getDefinition().getRequiredProviders();
+ if (requiredProviders.isSatisfiedBy(advertisedProviders)) {
addAllAttributesOfAspect(from, result, candidateClass, dependencyFilter);
}
}
return ImmutableMultimap.copyOf(result);
}
- private static ImmutableSet<String> toStringSet(ImmutableSet<Class<?>> classes) {
- ImmutableSet.Builder<String> classStrings = new ImmutableSet.Builder<>();
- for (Class<?> clazz : classes) {
- classStrings.add(clazz.getName());
- }
- return classStrings.build();
- }
-
@Nullable
private static Label maybeGetRepositoryRelativeLabel(Rule from, @Nullable Label label) {
return label == null ? null : from.getLabel().resolveRepositoryRelative(label);
@@ -246,7 +202,7 @@
public static final class Builder {
private final AspectClass aspectClass;
private final Map<String, Attribute> attributes = new LinkedHashMap<>();
- private ImmutableList<ImmutableSet<Class<?>>> requiredProviderSets = ImmutableList.of();
+ private RequiredProviders.Builder requiredProviders = RequiredProviders.acceptAnyBuilder();
private final Multimap<String, AspectClass> attributeAspects = LinkedHashMultimap.create();
private ImmutableCollection<AspectClass> allAttributesAspects = null;
private final ConfigurationFragmentPolicy.Builder configurationFragmentPolicy =
@@ -261,12 +217,9 @@
* from at least one set of required providers.
*/
public Builder requireProviderSets(Iterable<? extends Set<Class<?>>> providerSets) {
- ImmutableList.Builder<ImmutableSet<Class<?>>> requiredProviderSetsBuilder =
- ImmutableList.builder();
- for (Iterable<Class<?>> providerSet : providerSets) {
- requiredProviderSetsBuilder.add(ImmutableSet.copyOf(providerSet));
+ for (Set<Class<?>> providerSet : providerSets) {
+ requiredProviders.addNativeSet(ImmutableSet.copyOf(providerSet));
}
- requiredProviderSets = requiredProviderSetsBuilder.build();
return this;
}
@@ -274,8 +227,8 @@
* Asserts that this aspect can only be evaluated for rules that supply all of the specified
* providers.
*/
- public Builder requireProviders(Class<?>... requiredProviders) {
- requireProviderSets(ImmutableList.of(ImmutableSet.copyOf(requiredProviders)));
+ public Builder requireProviders(Class<?>... providers) {
+ requiredProviders.addNativeSet(ImmutableSet.copyOf(providers));
return this;
}
@@ -445,15 +398,7 @@
* <p>The builder object is reusable afterwards.
*/
public AspectDefinition build() {
- // If there is no required provider set, we still need to at least provide one empty set of
- // providers. We consider this case specially because aspects with no required providers
- // should match all rules, and having an empty set faciliates the matching logic.
- ImmutableList<ImmutableSet<Class<?>>> requiredProviders =
- requiredProviderSets.isEmpty()
- ? ImmutableList.of(ImmutableSet.<Class<?>>of())
- : requiredProviderSets;
-
- return new AspectDefinition(aspectClass, ImmutableList.copyOf(requiredProviders),
+ return new AspectDefinition(aspectClass, requiredProviders.build(),
ImmutableMap.copyOf(attributes),
allAttributesAspects != null
? new AllAttributesPropagationFunction(allAttributesAspects)