2828import  org .gradle .api .attributes .java .TargetJvmEnvironment ;
2929import  org .gradle .api .model .ObjectFactory ;
3030import  org .gradle .api .provider .ListProperty ;
31+ import  org .gradle .api .provider .Property ;
3132
3233import  io .quarkus .gradle .tooling .dependency .DependencyUtils ;
3334import  io .quarkus .gradle .tooling .dependency .ExtensionDependency ;
@@ -169,22 +170,26 @@ public static void setCommonAttributes(AttributeContainer attrs, ObjectFactory o
169170     * @param project project 
170171     * @param mode launch mode 
171172     */ 
172-     public  static  void  addVariants (Project  project , LaunchMode  mode ) {
173-         new  QuarkusComponentVariants (project , mode ).configureAndAddVariants ();
173+     public  static  void  addVariants (Project  project , LaunchMode  mode ,
174+             Property <ManualPlatformSpec > manualPlatformConfig ) {
175+         new  QuarkusComponentVariants (project , mode , manualPlatformConfig ).configureAndAddVariants ();
174176    }
175177
176178    private  final  Attribute <String > quarkusDepAttr ;
177179    private  final  Project  project ;
180+     private  final  Property <ManualPlatformSpec > manualPlatformConfig ;
178181    private  final  Map <ArtifactKey , ProcessedDependency > processedDeps  = new  HashMap <>();
179182    private  final  Map <ArtifactKey , ConditionalDependency > allConditionalDeps  = new  HashMap <>();
180183    private  final  List <ConditionalDependencyVariant > dependencyVariantQueue  = new  ArrayList <>();
181184    private  final  Map <String , SatisfiedExtensionDeps > satisfiedExtensionDeps  = new  HashMap <>();
182185    private  final  LaunchMode  mode ;
183186    private  final  AtomicInteger  configCopyCounter  = new  AtomicInteger ();
184187
185-     private  QuarkusComponentVariants (Project  project , LaunchMode  mode ) {
188+     private  QuarkusComponentVariants (Project  project , LaunchMode  mode ,
189+             Property <ManualPlatformSpec > manualPlatformConfig ) {
186190        this .project  = project ;
187191        this .mode  = mode ;
192+         this .manualPlatformConfig  = manualPlatformConfig ;
188193        this .quarkusDepAttr  = getConditionalDependencyAttribute (project .getName (), mode );
189194        project .getDependencies ().getAttributesSchema ().attribute (quarkusDepAttr );
190195        project .getDependencies ().getAttributesSchema ().attribute (getDeploymentDependencyAttribute (project .getName (), mode ));
@@ -407,7 +412,10 @@ private void processDependency(ProcessedDependency parent,
407412    }
408413
409414    private  void  queueConditionalDependency (ProcessedDependency  parent , Dependency  dep ) {
410-         dependencyVariantQueue .add (new  ConditionalDependencyVariant (parent .extension , getOrCreateConditionalDep (dep )));
415+         var  conditionalDep  = getOrCreateConditionalDep (dep );
416+         if  (conditionalDep  != null ) {
417+             dependencyVariantQueue .add (new  ConditionalDependencyVariant (parent .extension , conditionalDep ));
418+         }
411419    }
412420
413421    private  ConditionalDependency  getOrCreateConditionalDep (Dependency  dep ) {
@@ -417,7 +425,7 @@ private ConditionalDependency getOrCreateConditionalDep(Dependency dep) {
417425    }
418426
419427    private  ResolvedArtifact  tryResolvingRelocationArtifact (Dependency  dep ) {
420-         final  Configuration  configForRelocated  = project . getConfigurations (). detachedConfiguration (dep ).setTransitive (true );
428+         final  Configuration  configForRelocated  = getDetachedWithExclusions (dep ).setTransitive (true );
421429        setConditionalAttributes (configForRelocated , project , mode );
422430
423431        var  firstLevelDeps  = configForRelocated .getResolvedConfiguration ().getFirstLevelModuleDependencies ();
@@ -447,8 +455,11 @@ private ResolvedArtifact tryResolvingRelocationArtifact(Dependency dep) {
447455        return  artifact ;
448456    }
449457
450-     private  ConditionalDependency  newConditionalDep (Dependency  dep ) {
451-         final  Configuration  config  = project .getConfigurations ().detachedConfiguration (dep ).setTransitive (false );
458+     private  ConditionalDependency  newConditionalDep (Dependency  originalDep ) {
459+         var  manualConfig  = manualPlatformConfig .get ();
460+         var  dep  = getConstrainedDep (originalDep , manualConfig .getConstraints ());
461+         final  Configuration  config  = getDetachedWithExclusions (dep ).setTransitive (false );
462+ 
452463        setConditionalAttributes (config , project , mode );
453464        ResolvedArtifact  resolvedArtifact  = null ;
454465
@@ -464,6 +475,11 @@ private ConditionalDependency newConditionalDep(Dependency dep) {
464475        }
465476
466477        if  (resolvedArtifact  == null ) {
478+             // check if that's due to exclude rules, and if yes, ignore 
479+             if  (isExplicitlyExcluded (dep )) {
480+                 project .getLogger ().info ("Conditional dependency {} ignored due to exclusion rule" , dep );
481+                 return  null ;
482+             }
467483            throw  new  RuntimeException (dep  + " did not resolve to any artifacts" );
468484        }
469485
@@ -474,6 +490,48 @@ private ConditionalDependency newConditionalDep(Dependency dep) {
474490
475491    }
476492
493+     private  boolean  isExplicitlyExcluded (Dependency  dep ) {
494+         return  manualPlatformConfig .get ().getExclusions ().stream ().anyMatch (rule  -> {
495+             rule .getGroup ();
496+             if  (!rule .getGroup ().equals (dep .getGroup ())) {
497+                 return  false ;
498+             }
499+             rule .getModule ();
500+             return  rule .getModule ().equals (dep .getName ());
501+         });
502+     }
503+ 
504+     private  Configuration  getDetachedWithExclusions (Dependency  dep ) {
505+         var  c  = project .getConfigurations ().detachedConfiguration (dep );
506+         manualPlatformConfig .get ().getExclusions ().forEach (rule  -> {
507+             Map <String , String > excludeProperties  = new  HashMap <>();
508+             excludeProperties .put ("group" , rule .getGroup ());
509+             excludeProperties .put ("module" , rule .getModule ());
510+             c .exclude (excludeProperties );
511+         });
512+         return  c ;
513+     }
514+ 
515+     private  Dependency  getConstrainedDep (Dependency  dep , Set <ManualPlatformSpec .Constraint > constraints ) {
516+         if  (constraints  == null  || constraints .isEmpty ()) {
517+             return  dep ;
518+         }
519+ 
520+         var  matchingConstraints  = constraints .stream ().filter (c  -> c .matches (dep )).toList ();
521+ 
522+         if  (matchingConstraints .isEmpty ()) {
523+             return  dep ;
524+         }
525+ 
526+         if  (matchingConstraints .size () > 1 ) {
527+             throw  new  RuntimeException ("Multiple matching constraints for "  + dep  + ": "  + matchingConstraints );
528+         }
529+ 
530+         var  c  = matchingConstraints .get (0 );
531+         return  project .getDependencies ().create (
532+                 dep .getGroup () + ":"  + dep .getName () + ":"  + c .getVersion ());
533+     }
534+ 
477535    private  class  ProcessedDependency  {
478536        private  final  ResolvedArtifact  artifact ;
479537        private  final  ExtensionDependency <?> extension ;
0 commit comments