[MNG-3652] add support for configuring user agent across all HTTP wagons
Merged from: r678986, 678784 from maven-2.0.10-RC branch
git-svn-id: https://svn.apache.org/repos/asf/maven/artifact/trunk@679005 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/src/main/java/org/apache/maven/artifact/manager/DefaultWagonManager.java b/src/main/java/org/apache/maven/artifact/manager/DefaultWagonManager.java
index a77f7ff..a5dd09a 100644
--- a/src/main/java/org/apache/maven/artifact/manager/DefaultWagonManager.java
+++ b/src/main/java/org/apache/maven/artifact/manager/DefaultWagonManager.java
@@ -21,6 +21,7 @@
import java.io.File;
import java.io.IOException;
+import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.security.NoSuchAlgorithmException;
@@ -29,6 +30,7 @@
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
+import java.util.Properties;
import java.util.Set;
import org.apache.maven.artifact.Artifact;
@@ -57,19 +59,22 @@
import org.codehaus.plexus.component.configurator.ComponentConfigurator;
import org.codehaus.plexus.component.repository.exception.ComponentLifecycleException;
import org.codehaus.plexus.component.repository.exception.ComponentLookupException;
+import org.codehaus.plexus.configuration.PlexusConfiguration;
import org.codehaus.plexus.configuration.xml.XmlPlexusConfiguration;
import org.codehaus.plexus.context.Context;
import org.codehaus.plexus.context.ContextException;
import org.codehaus.plexus.logging.AbstractLogEnabled;
import org.codehaus.plexus.personality.plexus.lifecycle.phase.Contextualizable;
+import org.codehaus.plexus.personality.plexus.lifecycle.phase.Initializable;
+import org.codehaus.plexus.personality.plexus.lifecycle.phase.InitializationException;
import org.codehaus.plexus.util.FileUtils;
+import org.codehaus.plexus.util.IOUtil;
import org.codehaus.plexus.util.xml.Xpp3Dom;
/** @plexus.component */
public class DefaultWagonManager
extends AbstractLogEnabled
- implements WagonManager,
- Contextualizable
+ implements WagonManager, Contextualizable, Initializable
{
private static final String WILDCARD = "*";
@@ -80,6 +85,8 @@
/** have to match the CHECKSUM_IDS */
private static final String[] CHECKSUM_ALGORITHMS = {"MD5", "SHA-1"};
+ private static final String MAVEN_ARTIFACT_PROPERTIES = "META-INF/maven/org.apache.maven/maven-artifact/pom.properties";
+
private PlexusContainer container;
// TODO: proxies, authentication and mirrors are via settings, and should come in via an alternate method - perhaps
@@ -118,6 +125,8 @@
/** @plexus.requirement */
private UpdateCheckManager updateCheckManager;
+ private String httpUserAgent;
+
// TODO: this leaks the component in the public api - it is never released back to the container
public Wagon getWagon( Repository repository )
throws UnsupportedProtocolException, WagonConfigurationException
@@ -131,7 +140,7 @@
Wagon wagon = getWagon( protocol );
- configureWagon( wagon, repository.getId() );
+ configureWagon( wagon, repository.getId(), protocol );
return wagon;
}
@@ -1128,14 +1137,21 @@
ArtifactRepository repository )
throws WagonConfigurationException
{
- configureWagon( wagon, repository.getId() );
+ configureWagon( wagon, repository.getId(), repository.getProtocol() );
}
private void configureWagon( Wagon wagon,
- String repositoryId )
+ String repositoryId,
+ String protocol )
throws WagonConfigurationException
{
- if ( serverConfigurationMap.containsKey( repositoryId ) )
+ PlexusConfiguration config = (PlexusConfiguration) serverConfigurationMap.get( repositoryId );
+ if ( protocol.startsWith( "http" ) || protocol.startsWith( "dav" ) )
+ {
+ config = updateUserAgentForHttp( wagon, config );
+ }
+
+ if ( config != null )
{
ComponentConfigurator componentConfigurator = null;
@@ -1143,8 +1159,7 @@
{
componentConfigurator = new BasicComponentConfigurator();
- componentConfigurator.configureComponent( wagon,
- serverConfigurationMap.get( repositoryId ), container.getContainerRealm() );
+ componentConfigurator.configureComponent( wagon, config, container.getContainerRealm() );
}
catch ( ComponentConfigurationException e )
{
@@ -1168,6 +1183,59 @@
}
}
+ // TODO: Remove this, once the maven-shade-plugin 1.2 release is out, allowing configuration of httpHeaders in the components.xml
+ private PlexusConfiguration updateUserAgentForHttp( Wagon wagon, PlexusConfiguration config )
+ {
+ if ( config == null )
+ {
+ config = new XmlPlexusConfiguration( "configuration" );
+ }
+
+ if ( httpUserAgent != null )
+ {
+ try
+ {
+ wagon.getClass().getMethod( "setHttpHeaders", new Class[]{ Properties.class } );
+
+ PlexusConfiguration headerConfig = config.getChild( "httpHeaders", true );
+ PlexusConfiguration[] children = headerConfig.getChildren( "property" );
+ boolean found = false;
+ for ( int i = 0; i < children.length; i++ )
+ {
+ PlexusConfiguration c = children[i].getChild( "name", false );
+ if ( c != null && "User-Agent".equals( c.getValue( null ) ) )
+ {
+ found = true;
+ break;
+ }
+ }
+ if ( !found )
+ {
+ XmlPlexusConfiguration propertyConfig = new XmlPlexusConfiguration( "property" );
+ headerConfig.addChild( propertyConfig );
+
+ XmlPlexusConfiguration nameConfig = new XmlPlexusConfiguration( "name" );
+ nameConfig.setValue( "User-Agent" );
+ propertyConfig.addChild( nameConfig );
+
+ XmlPlexusConfiguration versionConfig = new XmlPlexusConfiguration( "value" );
+ versionConfig.setValue( httpUserAgent );
+ propertyConfig.addChild( versionConfig );
+ }
+ }
+ catch ( SecurityException e )
+ {
+ // forget it. this method is public, if it exists.
+ }
+ catch ( NoSuchMethodException e )
+ {
+ // forget it.
+ }
+ }
+
+ return config;
+ }
+
public void addConfiguration( String repositoryId,
Xpp3Dom configuration )
{
@@ -1195,4 +1263,58 @@
{
this.updateCheckManager = updateCheckManager;
}
+
+ // TODO: Remove this, once the maven-shade-plugin 1.2 release is out, allowing configuration of httpHeaders in the components.xml
+ public void initialize()
+ throws InitializationException
+ {
+ if ( httpUserAgent == null )
+ {
+ InputStream resourceAsStream = null;
+ try
+ {
+ Properties properties = new Properties();
+ resourceAsStream = getClass().getClassLoader().getResourceAsStream( MAVEN_ARTIFACT_PROPERTIES );
+
+ if ( resourceAsStream != null )
+ {
+ try
+ {
+ properties.load( resourceAsStream );
+
+ httpUserAgent =
+ "maven-artifact/" + properties.getProperty( "version" ) + " (Java "
+ + System.getProperty( "java.version" ) + "; " + System.getProperty( "os.name" ) + " "
+ + System.getProperty( "os.version" ) + ")";
+ }
+ catch ( IOException e )
+ {
+ getLogger().warn(
+ "Failed to load Maven artifact properties from:\n" + MAVEN_ARTIFACT_PROPERTIES
+ + "\n\nUser-Agent HTTP header may be incorrect for artifact resolution." );
+ }
+ }
+ }
+ finally
+ {
+ IOUtil.close( resourceAsStream );
+ }
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public void setHttpUserAgent( String userAgent )
+ {
+ this.httpUserAgent = userAgent;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public String getHttpUserAgent()
+ {
+ return httpUserAgent;
+ }
}