mirror of https://github.com/apache/maven.git
[MNG-7160] Ability to customize core extensions classloaders (#616)
This commit is contained in:
parent
df38f1c079
commit
415eaf31de
|
@ -29,7 +29,7 @@ import javax.inject.Singleton;
|
|||
|
||||
import org.apache.maven.artifact.resolver.filter.ArtifactFilter;
|
||||
import org.apache.maven.artifact.resolver.filter.ExclusionSetFilter;
|
||||
import org.apache.maven.extension.internal.CoreExportsProvider;
|
||||
import org.apache.maven.extension.internal.CoreExports;
|
||||
|
||||
/**
|
||||
* @author Jason van Zyl
|
||||
|
@ -50,10 +50,10 @@ public class DefaultArtifactFilterManager
|
|||
|
||||
@Inject
|
||||
public DefaultArtifactFilterManager( List<ArtifactFilterManagerDelegate> delegates,
|
||||
CoreExportsProvider coreExports )
|
||||
CoreExports coreExports )
|
||||
{
|
||||
this.delegates = delegates;
|
||||
this.coreArtifacts = coreExports.get().getExportedArtifacts();
|
||||
this.coreArtifacts = coreExports.getExportedArtifacts();
|
||||
}
|
||||
|
||||
private synchronized Set<String> getExcludedArtifacts()
|
||||
|
|
|
@ -37,7 +37,7 @@ import javax.inject.Singleton;
|
|||
|
||||
import org.apache.maven.artifact.ArtifactUtils;
|
||||
import org.apache.maven.classrealm.ClassRealmRequest.RealmType;
|
||||
import org.apache.maven.extension.internal.CoreExportsProvider;
|
||||
import org.apache.maven.extension.internal.CoreExports;
|
||||
import org.apache.maven.model.Model;
|
||||
import org.apache.maven.model.Plugin;
|
||||
import org.codehaus.plexus.MutablePlexusContainer;
|
||||
|
@ -94,19 +94,19 @@ public class DefaultClassRealmManager
|
|||
@Inject
|
||||
public DefaultClassRealmManager( PlexusContainer container,
|
||||
List<ClassRealmManagerDelegate> delegates,
|
||||
CoreExportsProvider exports )
|
||||
CoreExports exports )
|
||||
{
|
||||
this.world = ( (MutablePlexusContainer) container ).getClassWorld();
|
||||
this.containerRealm = container.getContainerRealm();
|
||||
this.delegates = delegates;
|
||||
|
||||
Map<String, ClassLoader> foreignImports = exports.get().getExportedPackages();
|
||||
Map<String, ClassLoader> foreignImports = exports.getExportedPackages();
|
||||
|
||||
this.mavenApiRealm =
|
||||
createRealm( API_REALMID, RealmType.Core, null /* parent */, null /* parentImports */,
|
||||
foreignImports, null /* artifacts */ );
|
||||
|
||||
this.providedArtifacts = exports.get().getExportedArtifacts();
|
||||
this.providedArtifacts = exports.getExportedArtifacts();
|
||||
}
|
||||
|
||||
private ClassRealm newRealm( String id )
|
||||
|
|
|
@ -19,34 +19,34 @@ package org.apache.maven.extension.internal;
|
|||
* under the License.
|
||||
*/
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import javax.inject.Provider;
|
||||
import javax.inject.Singleton;
|
||||
|
||||
import org.codehaus.plexus.PlexusContainer;
|
||||
import org.eclipse.sisu.Nullable;
|
||||
|
||||
/**
|
||||
* CoreExportsProvider
|
||||
*/
|
||||
@Named
|
||||
@Singleton
|
||||
public class CoreExportsProvider
|
||||
public class CoreExportsProvider implements Provider<CoreExports>
|
||||
{
|
||||
|
||||
private final CoreExports exports;
|
||||
|
||||
@Inject
|
||||
public CoreExportsProvider( PlexusContainer container, @Nullable CoreExports exports )
|
||||
public CoreExportsProvider( PlexusContainer container )
|
||||
{
|
||||
if ( exports == null )
|
||||
{
|
||||
this.exports = new CoreExports( CoreExtensionEntry.discoverFrom( container.getContainerRealm() ) );
|
||||
this( new CoreExports( CoreExtensionEntry.discoverFrom( container.getContainerRealm() ) ) );
|
||||
}
|
||||
else
|
||||
|
||||
public CoreExportsProvider( CoreExports exports )
|
||||
{
|
||||
this.exports = exports;
|
||||
}
|
||||
this.exports = Objects.requireNonNull( exports );
|
||||
}
|
||||
|
||||
public CoreExports get()
|
||||
|
|
|
@ -175,7 +175,7 @@ under the License.
|
|||
<groupId>org.codehaus.modello</groupId>
|
||||
<artifactId>modello-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<version>1.0.0</version>
|
||||
<version>1.1.0</version>
|
||||
<models>
|
||||
<model>src/main/mdo/core-extensions.mdo</model>
|
||||
</models>
|
||||
|
|
|
@ -31,6 +31,7 @@ import javax.inject.Named;
|
|||
import org.apache.maven.RepositoryUtils;
|
||||
import org.apache.maven.cli.internal.extension.model.CoreExtension;
|
||||
import org.apache.maven.execution.MavenExecutionRequest;
|
||||
import org.apache.maven.extension.internal.CoreExports;
|
||||
import org.apache.maven.extension.internal.CoreExtensionEntry;
|
||||
import org.apache.maven.internal.aether.DefaultRepositorySystemSessionFactory;
|
||||
import org.apache.maven.model.Plugin;
|
||||
|
@ -60,12 +61,18 @@ import org.slf4j.LoggerFactory;
|
|||
@Named
|
||||
public class BootstrapCoreExtensionManager
|
||||
{
|
||||
public static final String STRATEGY_PARENT_FIRST = "parent-first";
|
||||
public static final String STRATEGY_PLUGIN = "plugin";
|
||||
public static final String STRATEGY_SELF_FIRST = "self-first";
|
||||
|
||||
private final Logger log = LoggerFactory.getLogger( getClass() );
|
||||
|
||||
private final DefaultPluginDependenciesResolver pluginDependenciesResolver;
|
||||
|
||||
private final DefaultRepositorySystemSessionFactory repositorySystemSessionFactory;
|
||||
|
||||
private final CoreExports coreExports;
|
||||
|
||||
private final ClassWorld classWorld;
|
||||
|
||||
private final ClassRealm parentRealm;
|
||||
|
@ -73,10 +80,12 @@ public class BootstrapCoreExtensionManager
|
|||
@Inject
|
||||
public BootstrapCoreExtensionManager( DefaultPluginDependenciesResolver pluginDependenciesResolver,
|
||||
DefaultRepositorySystemSessionFactory repositorySystemSessionFactory,
|
||||
CoreExports coreExports,
|
||||
PlexusContainer container )
|
||||
{
|
||||
this.pluginDependenciesResolver = pluginDependenciesResolver;
|
||||
this.repositorySystemSessionFactory = repositorySystemSessionFactory;
|
||||
this.coreExports = coreExports;
|
||||
this.classWorld = ( (DefaultPlexusContainer) container ).getClassWorld();
|
||||
this.parentRealm = container.getContainerRealm();
|
||||
}
|
||||
|
@ -121,15 +130,43 @@ public class BootstrapCoreExtensionManager
|
|||
{
|
||||
String realmId =
|
||||
"coreExtension>" + extension.getGroupId() + ":" + extension.getArtifactId() + ":" + extension.getVersion();
|
||||
ClassRealm realm = classWorld.newRealm( realmId, null );
|
||||
log.debug( "Populating class realm " + realm.getId() );
|
||||
final ClassRealm realm = classWorld.newRealm( realmId, null );
|
||||
Set<String> providedArtifacts = Collections.emptySet();
|
||||
String classLoadingStrategy = extension.getClassLoadingStrategy();
|
||||
if ( STRATEGY_PARENT_FIRST.equals( classLoadingStrategy ) )
|
||||
{
|
||||
realm.importFrom( parentRealm, "" );
|
||||
}
|
||||
else if ( STRATEGY_PLUGIN.equals( classLoadingStrategy ) )
|
||||
{
|
||||
coreExports.getExportedPackages().forEach( ( p, cl ) -> realm.importFrom( cl, p ) );
|
||||
providedArtifacts = coreExports.getExportedArtifacts();
|
||||
}
|
||||
else if ( STRATEGY_SELF_FIRST.equals( classLoadingStrategy ) )
|
||||
{
|
||||
realm.setParentRealm( parentRealm );
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new IllegalArgumentException( "Unsupported class-loading strategy '"
|
||||
+ classLoadingStrategy + "'. Supported values are: " + STRATEGY_PARENT_FIRST
|
||||
+ ", " + STRATEGY_PLUGIN + " and " + STRATEGY_SELF_FIRST );
|
||||
}
|
||||
log.debug( "Populating class realm {}", realm.getId() );
|
||||
for ( Artifact artifact : artifacts )
|
||||
{
|
||||
String id = artifact.getGroupId() + ":" + artifact.getArtifactId();
|
||||
if ( providedArtifacts.contains( id ) )
|
||||
{
|
||||
log.debug( " Excluded {}", id );
|
||||
}
|
||||
else
|
||||
{
|
||||
File file = artifact.getFile();
|
||||
log.debug( " Included " + file );
|
||||
log.debug( " Included {} located at {}", id, file );
|
||||
realm.addURL( file.toURI().toURL() );
|
||||
}
|
||||
}
|
||||
return CoreExtensionEntry.discoverFrom( realm, Collections.singleton( artifacts.get( 0 ).getFile() ) );
|
||||
}
|
||||
|
||||
|
|
|
@ -82,6 +82,14 @@
|
|||
<required>true</required>
|
||||
<type>String</type>
|
||||
</field>
|
||||
<field>
|
||||
<name>classLoadingStrategy</name>
|
||||
<description>The class loading strategy: 'self-first' (the default), 'parent-first' (loads classes from the parent, then from the extension) or 'plugin' (follows the rules from extensions defined as plugins).</description>
|
||||
<version>1.1.0+</version>
|
||||
<defaultValue>self-first</defaultValue>
|
||||
<required>false</required>
|
||||
<type>String</type>
|
||||
</field>
|
||||
</fields>
|
||||
<codeSegments>
|
||||
<codeSegment>
|
||||
|
|
Loading…
Reference in New Issue