summaryrefslogtreecommitdiffstats
path: root/archiva-reporting
diff options
context:
space:
mode:
authorJoakim Erdfelt <joakime@apache.org>2007-03-22 21:16:24 +0000
committerJoakim Erdfelt <joakime@apache.org>2007-03-22 21:16:24 +0000
commitf5ede06188f2f82e92703c46a7d2aedb6f26ef6e (patch)
treecac03d5d47e8e5294e04d8c7db4fd23782c39e96 /archiva-reporting
parent0b4c3be0dc1d3b40539fc32d109f8494de0eabab (diff)
downloadarchiva-f5ede06188f2f82e92703c46a7d2aedb6f26ef6e.tar.gz
archiva-f5ede06188f2f82e92703c46a7d2aedb6f26ef6e.zip
Setting up reporting infrastructure
git-svn-id: https://svn.apache.org/repos/asf/maven/archiva/branches/archiva-jpox-database-refactor@521474 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'archiva-reporting')
-rwxr-xr-xarchiva-reporting/archiva-report-manager/pom.xml176
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/ReportingException.java50
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractJdoDatabase.java237
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractResultsDatabase.java80
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabase.java282
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabase.java209
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ReportingDatabase.java124
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/AbstractReportGroup.java82
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/DefaultReportGroup.java66
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/OldArtifactReportGroup.java65
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/ReportGroup.java78
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/ArtifactResultsKey.java158
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/MetadataResultsKey.java126
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ArtifactReportProcessor.java34
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessor.java344
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumArtifactReportProcessor.java110
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumMetadataReportProcessor.java110
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessor.java167
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessor.java143
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessor.java107
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessor.java250
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/MetadataReportProcessor.java33
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessor.java100
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessor.java191
-rw-r--r--archiva-reporting/archiva-report-manager/src/main/mdo/reporting.mdo337
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AbstractRepositoryReportsTestCase.java154
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AllTests.java45
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/AllTests.java20
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabaseTest.java171
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabaseTest.java113
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ReportingDatabaseTest.java55
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/AllTests.java24
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessorTest.java454
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessorTest.java303
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.java150
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessorTest.java82
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessorTest.java227
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.java99
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.java170
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AbstractChecksumArtifactReporterTestCase.java287
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AllTests.java45
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumArtifactReporterTest.java79
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumMetadataReporterTest.java135
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/DefaultArtifactReporterTest.java390
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-sources.jarbin0 -> 45568 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.tar.gzbin0 -> 45568 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.zipbin0 -> 45568 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.jarbin0 -> 45568 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.pom25
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-2/artifactId-1.0-alpha-2.pom25
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/maven-metadata.xml31
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-20050611.202024-1.pom19
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-SNAPSHOT.pom19
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/groupId/unexpectedfile.xml22
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/maven-metadata.xml25
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/artifactId/1.0-alpha-3/artifactId-1.0-alpha-3.pom28
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.jarbin0 -> 11720 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.pom46
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/note.txt4
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.jarbin0 -> 78476 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.pom105
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/note.txt3
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.jarbin0 -> 7591 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.pom34
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/note.txt4
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.jarbin0 -> 104615 bytes
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.pom72
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/note.txt4
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/resources/META-INF/plexus/components.xml9
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/resources/log4j.properties10
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.xml47
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.xml38
-rw-r--r--archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.xml39
73 files changed, 7271 insertions, 0 deletions
diff --git a/archiva-reporting/archiva-report-manager/pom.xml b/archiva-reporting/archiva-report-manager/pom.xml
new file mode 100755
index 000000000..9d02313dc
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/pom.xml
@@ -0,0 +1,176 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <groupId>org.apache.maven.archiva</groupId>
+ <artifactId>archiva</artifactId>
+ <version>1.0-SNAPSHOT</version>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <artifactId>archiva-reports-standard</artifactId>
+ <name>Archiva Standard Reports</name>
+ <dependencies>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-utils</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-container-default</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact-manager</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-model</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-repository-metadata</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven.wagon</groupId>
+ <artifactId>wagon-provider-api</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven.archiva</groupId>
+ <artifactId>archiva-repository-layer</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven.archiva</groupId>
+ <artifactId>archiva-indexer</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven.archiva</groupId>
+ <artifactId>archiva-discoverer</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>commons-lang</groupId>
+ <artifactId>commons-lang</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>commons-io</groupId>
+ <artifactId>commons-io</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-jdo2</artifactId>
+ <version>1.0-alpha-8</version>
+ <exclusions>
+ <exclusion>
+ <groupId>xerces</groupId>
+ <artifactId>xercesImpl</artifactId>
+ </exclusion>
+ <exclusion>
+ <groupId>xerces</groupId>
+ <artifactId>xmlParserAPIs</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
+ <dependency>
+ <groupId>jpox</groupId>
+ <artifactId>jpox</artifactId>
+ <version>1.1.6</version>
+ <scope>compile</scope>
+ <exclusions>
+ <!-- targeting JDK 1.4 we don't need this -->
+ <exclusion>
+ <groupId>javax.sql</groupId>
+ <artifactId>jdbc-stdext</artifactId>
+ </exclusion>
+ </exclusions>
+ </dependency>
+ <!-- TEST DEPS -->
+ <dependency>
+ <groupId>hsqldb</groupId>
+ <artifactId>hsqldb</artifactId>
+ <version>1.7.3.3</version>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.codehaus.modello</groupId>
+ <artifactId>modello-maven-plugin</artifactId>
+ <version>1.0-alpha-15-SNAPSHOT</version>
+ <configuration>
+ <version>1.0.0</version>
+ <packageWithVersion>false</packageWithVersion>
+ <model>src/main/mdo/reporting.mdo</model>
+ </configuration>
+ <executions>
+ <execution>
+ <id>modello-java</id>
+ <goals>
+ <goal>java</goal>
+ <goal>jpox-metadata-class</goal>
+ <!--
+ <goal>xpp3-writer</goal>
+ <goal>xpp3-reader</goal>
+ -->
+ </goals>
+ </execution>
+ <execution>
+ <id>jpox-jdo-mapping</id>
+ <goals>
+ <goal>jpox-jdo-mapping</goal>
+ </goals>
+ <configuration>
+ <outputDirectory>${basedir}/target/classes/org/apache/maven/archiva/reporting/model/</outputDirectory>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>jpox-maven-plugin</artifactId>
+ <version>1.1.6</version>
+ <executions>
+ <execution>
+ <goals>
+ <goal>enhance</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>cobertura-maven-plugin</artifactId>
+ <configuration>
+ <instrumentation>
+ <!-- exclude generated -->
+ <excludes>
+ <exclude>org/apache/maven/archiva/reporting/model/**</exclude>
+ </excludes>
+ </instrumentation>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/ReportingException.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/ReportingException.java
new file mode 100644
index 000000000..2854befa7
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/ReportingException.java
@@ -0,0 +1,50 @@
+package org.apache.maven.archiva.reporting;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+/**
+ * ReportingException
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class ReportingException
+ extends Exception
+{
+
+ public ReportingException()
+ {
+ }
+
+ public ReportingException( String message )
+ {
+ super( message );
+ }
+
+ public ReportingException( Throwable cause )
+ {
+ super( cause );
+ }
+
+ public ReportingException( String message, Throwable cause )
+ {
+ super( message, cause );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractJdoDatabase.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractJdoDatabase.java
new file mode 100644
index 000000000..f474ef664
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractJdoDatabase.java
@@ -0,0 +1,237 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.codehaus.plexus.jdo.JdoFactory;
+import org.codehaus.plexus.personality.plexus.lifecycle.phase.Initializable;
+import org.codehaus.plexus.personality.plexus.lifecycle.phase.InitializationException;
+
+import java.util.List;
+
+import javax.jdo.Extent;
+import javax.jdo.JDOException;
+import javax.jdo.JDOHelper;
+import javax.jdo.JDOObjectNotFoundException;
+import javax.jdo.JDOUserException;
+import javax.jdo.PersistenceManager;
+import javax.jdo.PersistenceManagerFactory;
+import javax.jdo.Query;
+import javax.jdo.Transaction;
+
+/**
+ * AbstractJdoResults - Base class for all JDO related results.
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public abstract class AbstractJdoDatabase
+ implements Initializable
+{
+ /**
+ * @plexus.requirement role-hint="archiva"
+ */
+ private JdoFactory jdoFactory;
+
+ private PersistenceManagerFactory pmf;
+
+ // -------------------------------------------------------------------
+ // JPOX / JDO Specifics.
+ // -------------------------------------------------------------------
+
+ protected List getAllObjects( Class clazz, String ordering )
+ {
+ PersistenceManager pm = getPersistenceManager();
+ Transaction tx = pm.currentTransaction();
+
+ try
+ {
+ tx.begin();
+
+ Extent extent = pm.getExtent( clazz, true );
+
+ Query query = pm.newQuery( extent );
+
+ if ( ordering != null )
+ {
+ query.setOrdering( ordering );
+ }
+
+// for ( Iterator i = fetchGroups.iterator(); i.hasNext(); )
+// {
+// pm.getFetchPlan().addGroup( (String) i.next() );
+// }
+
+ List result = (List) query.execute();
+
+ result = (List) pm.detachCopyAll( result );
+
+ tx.commit();
+
+ return result;
+ }
+ finally
+ {
+ rollbackIfActive( tx );
+ }
+ }
+
+ protected Object getObjectByKey( Class clazz, Object key )
+ throws JDOObjectNotFoundException, JDOException
+ {
+ if ( key == null )
+ {
+ throw new JDOException( "Unable to get object from jdo using null key." );
+ }
+
+ PersistenceManager pm = getPersistenceManager();
+ Transaction tx = pm.currentTransaction();
+
+ try
+ {
+ tx.begin();
+
+ // if ( fetchGroup != null )
+ // {
+ // pm.getFetchPlan().addGroup( fetchGroup );
+ // }
+
+ Object objectId = pm.newObjectIdInstance( clazz, key.toString() );
+
+ Object object = pm.getObjectById( objectId );
+
+ object = pm.detachCopy( object );
+
+ tx.commit();
+
+ return object;
+ }
+ finally
+ {
+ rollbackIfActive( tx );
+ }
+ }
+
+ public void initialize()
+ throws InitializationException
+ {
+ pmf = jdoFactory.getPersistenceManagerFactory();
+ }
+
+ protected void removeObject( Object o )
+ {
+ PersistenceManager pm = getPersistenceManager();
+ Transaction tx = pm.currentTransaction();
+
+ try
+ {
+ tx.begin();
+
+ o = pm.getObjectById( pm.getObjectId( o ) );
+
+ pm.deletePersistent( o );
+
+ tx.commit();
+ }
+ finally
+ {
+ rollbackIfActive( tx );
+ }
+ }
+
+ protected Object saveObject( Object object )
+ {
+ return saveObject( object, null );
+ }
+
+ protected Object saveObject( Object object, String fetchGroups[] )
+ throws JDOException
+ {
+ PersistenceManager pm = getPersistenceManager();
+ Transaction tx = pm.currentTransaction();
+
+ try
+ {
+ tx.begin();
+
+ if ( ( JDOHelper.getObjectId( object ) != null ) && !JDOHelper.isDetached( object ) )
+ {
+ throw new JDOException( "Existing object is not detached: " + object );
+ }
+
+ if ( fetchGroups != null )
+ {
+ for ( int i = 0; i >= fetchGroups.length; i++ )
+ {
+ pm.getFetchPlan().addGroup( fetchGroups[i] );
+ }
+ }
+
+ pm.makePersistent( object );
+
+ object = pm.detachCopy( object );
+
+ tx.commit();
+
+ return object;
+ }
+ finally
+ {
+ rollbackIfActive( tx );
+ }
+ }
+
+ protected PersistenceManager getPersistenceManager()
+ {
+ PersistenceManager pm = pmf.getPersistenceManager();
+
+ pm.getFetchPlan().setMaxFetchDepth( -1 );
+
+ return pm;
+ }
+
+ protected static void closePersistenceManager( PersistenceManager pm )
+ {
+ try
+ {
+ pm.close();
+ }
+ catch ( JDOUserException e )
+ {
+ // ignore
+ }
+ }
+
+ protected static void rollbackIfActive( Transaction tx )
+ {
+ PersistenceManager pm = tx.getPersistenceManager();
+
+ try
+ {
+ if ( tx.isActive() )
+ {
+ tx.rollback();
+ }
+ }
+ finally
+ {
+ closePersistenceManager( pm );
+ }
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractResultsDatabase.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractResultsDatabase.java
new file mode 100644
index 000000000..26fbeff45
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/AbstractResultsDatabase.java
@@ -0,0 +1,80 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.model.ResultReason;
+
+/**
+ * AbstractResultsDatabase
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public abstract class AbstractResultsDatabase
+ extends AbstractJdoDatabase
+{
+ /**
+ * <p>
+ * Get the number of failures in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of failures in the database.
+ */
+ public abstract int getNumFailures();
+
+ /**
+ * <p>
+ * Get the number of warnings in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of warnings in the database.
+ */
+ public abstract int getNumWarnings();
+
+ /**
+ * <p>
+ * Get the number of notices in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of notices in the database.
+ */
+ public abstract int getNumNotices();
+
+ protected static ResultReason createResultReason( String processor, String problem, String reason )
+ {
+ ResultReason result = new ResultReason();
+ result.setProcessor( processor );
+ result.setProblem( problem );
+ result.setReason( reason );
+ return result;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabase.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabase.java
new file mode 100644
index 000000000..791b56bf8
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabase.java
@@ -0,0 +1,282 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.archiva.reporting.model.ArtifactResultsKey;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.jdo.JDOObjectNotFoundException;
+import javax.jdo.PersistenceManager;
+import javax.jdo.Query;
+import javax.jdo.Transaction;
+
+/**
+ * ArtifactResultsDatabase - Database of ArtifactResults.
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase"
+ */
+public class ArtifactResultsDatabase
+ extends AbstractResultsDatabase
+{
+ // -------------------------------------------------------------------
+ // ArtifactResults methods.
+ // -------------------------------------------------------------------
+
+ public static final String ROLE = ArtifactResultsDatabase.class.getName();
+
+ public void addFailure( Artifact artifact, String processor, String problem, String reason )
+ {
+ ArtifactResults results = getArtifactResults( artifact );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getFailures().contains( result ) )
+ {
+ results.addFailure( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void addNotice( Artifact artifact, String processor, String problem, String reason )
+ {
+ ArtifactResults results = getArtifactResults( artifact );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getNotices().contains( result ) )
+ {
+ results.addNotice( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void addWarning( Artifact artifact, String processor, String problem, String reason )
+ {
+ ArtifactResults results = getArtifactResults( artifact );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getWarnings().contains( result ) )
+ {
+ results.addWarning( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void clearResults( ArtifactResults results )
+ {
+ results.getFailures().clear();
+ results.getWarnings().clear();
+ results.getNotices().clear();
+
+ saveObject( results );
+ }
+
+ public List getAllArtifactResults()
+ {
+ return getAllObjects( ArtifactResults.class, null );
+ }
+
+ public Iterator getIterator()
+ {
+ List allartifacts = getAllArtifactResults();
+ if ( allartifacts == null )
+ {
+ return Collections.EMPTY_LIST.iterator();
+ }
+
+ return allartifacts.iterator();
+ }
+
+ public List findArtifactResults( String groupId, String artifactId, String version )
+ {
+ PersistenceManager pm = getPersistenceManager();
+ Transaction tx = pm.currentTransaction();
+
+ try
+ {
+ tx.begin();
+
+ Query query = pm.newQuery( "javax.jdo.query.JDOQL", "SELECT FROM " + ArtifactResults.class.getName()
+ + " WHERE groupId == findGroupId && " + " artifactId == findArtifactId && "
+ + " version == findVersionId" );
+ query.declareParameters( "String findGroupId, String findArtifactId, String findVersionId" );
+ query.setOrdering( "findArtifactId ascending" );
+
+ List result = (List) query.execute( groupId, artifactId, version );
+
+ result = (List) pm.detachCopyAll( result );
+
+ tx.commit();
+
+ return result;
+ }
+ finally
+ {
+ rollbackIfActive( tx );
+ }
+ }
+
+ public void remove( ArtifactResults results )
+ {
+ removeObject( results );
+ }
+
+ public void remove( Artifact artifact )
+ {
+ try
+ {
+ ArtifactResults results = lookupArtifactResults( artifact );
+ remove( results );
+ }
+ catch ( JDOObjectNotFoundException e )
+ {
+ // nothing to do.
+ }
+ }
+
+ /**
+ * Get an {@link ArtifactResults} from the store.
+ * If the store does not have one, create it.
+ *
+ * Equivalent to calling {@link #lookupArtifactResults(Artifact)} then if
+ * not found, using {@link #createArtifactResults(Artifact)}.
+ *
+ * @param artifact the artifact information
+ * @return the ArtifactResults object (may not be in database yet, so don't forget to {@link #saveObject(Object)})
+ * @see #lookupArtifactResults(Artifact)
+ * @see #createArtifactResults(Artifact)
+ */
+ public ArtifactResults getArtifactResults( Artifact artifact )
+ {
+ ArtifactResults results;
+
+ try
+ {
+ results = lookupArtifactResults( artifact );
+ }
+ catch ( JDOObjectNotFoundException e )
+ {
+ results = createArtifactResults( artifact );
+ }
+
+ return results;
+ }
+
+ /**
+ * Create a new {@link ArtifactResults} object from the provided Artifact information.
+ *
+ * @param artifact the artifact information.
+ * @return the new {@link ArtifactResults} object.
+ * @see #getArtifactResults(Artifact)
+ * @see #lookupArtifactResults(Artifact)
+ */
+ private ArtifactResults createArtifactResults( Artifact artifact )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The ArtifactResults object has a complex primary key consisting of groupId, artifactId, version,
+ * type, classifier.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ ArtifactResults results = new ArtifactResults();
+ results.setGroupId( StringUtils.defaultString( artifact.getGroupId() ) );
+ results.setArtifactId( StringUtils.defaultString( artifact.getArtifactId() ) );
+ results.setVersion( StringUtils.defaultString( artifact.getVersion() ) );
+ results.setArtifactType( StringUtils.defaultString( artifact.getType() ) );
+ results.setClassifier( StringUtils.defaultString( artifact.getClassifier() ) );
+
+ return results;
+ }
+
+ /**
+ * Lookup the {@link ArtifactResults} in the JDO store from the information in
+ * the provided Artifact.
+ *
+ * @param artifact the artifact information.
+ * @return the previously saved {@link ArtifactResults} from the JDO store.
+ * @throws JDOObjectNotFoundException if the {@link ArtifactResults} are not found.
+ * @see #getArtifactResults(Artifact)
+ * @see #createArtifactResults(Artifact)
+ */
+ private ArtifactResults lookupArtifactResults( Artifact artifact )
+ throws JDOObjectNotFoundException
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The ArtifactResults object has a complex primary key consisting of groupId, artifactId, version,
+ * type, classifier.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ ArtifactResultsKey key = new ArtifactResultsKey();
+ key.groupId = StringUtils.defaultString( artifact.getGroupId() );
+ key.artifactId = StringUtils.defaultString( artifact.getArtifactId() );
+ key.version = StringUtils.defaultString( artifact.getVersion() );
+ key.artifactType = StringUtils.defaultString( artifact.getType() );
+ key.classifier = StringUtils.defaultString( artifact.getClassifier() );
+
+ return (ArtifactResults) getObjectByKey( ArtifactResults.class, key );
+ }
+
+ public int getNumFailures()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ ArtifactResults results = (ArtifactResults) it.next();
+ count += results.getFailures().size();
+ }
+ return count;
+ }
+
+ public int getNumNotices()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ ArtifactResults results = (ArtifactResults) it.next();
+ count += results.getNotices().size();
+ }
+ return count;
+ }
+
+ public int getNumWarnings()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ ArtifactResults results = (ArtifactResults) it.next();
+ count += results.getWarnings().size();
+ }
+ return count;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabase.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabase.java
new file mode 100644
index 000000000..934cc6941
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabase.java
@@ -0,0 +1,209 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.maven.archiva.reporting.model.MetadataResults;
+import org.apache.maven.archiva.reporting.model.MetadataResultsKey;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.jdo.JDOObjectNotFoundException;
+
+/**
+ * MetadataResultsDatabase
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.database.MetadataResultsDatabase"
+ */
+public class MetadataResultsDatabase
+ extends AbstractResultsDatabase
+{
+ public static final String ROLE = MetadataResultsDatabase.class.getName();
+
+ public void addFailure( RepositoryMetadata metadata, String processor, String problem, String reason )
+ {
+ MetadataResults results = getMetadataResults( metadata );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getFailures().contains( result ) )
+ {
+ results.addFailure( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void addWarning( RepositoryMetadata metadata, String processor, String problem, String reason )
+ {
+ MetadataResults results = getMetadataResults( metadata );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getWarnings().contains( result ) )
+ {
+ results.addWarning( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void addNotice( RepositoryMetadata metadata, String processor, String problem, String reason )
+ {
+ MetadataResults results = getMetadataResults( metadata );
+ ResultReason result = createResultReason( processor, problem, reason );
+
+ if ( !results.getNotices().contains( result ) )
+ {
+ results.addNotice( result );
+ }
+
+ saveObject( results );
+ }
+
+ public void clearResults( MetadataResults results )
+ {
+ results.getFailures().clear();
+ results.getWarnings().clear();
+ results.getNotices().clear();
+
+ saveObject( results );
+ }
+
+ public List getAllMetadataResults()
+ {
+ return getAllObjects( MetadataResults.class, null );
+ }
+
+ public Iterator getIterator()
+ {
+ List allmetadatas = getAllMetadataResults();
+ if ( allmetadatas == null )
+ {
+ return Collections.EMPTY_LIST.iterator();
+ }
+
+ return allmetadatas.iterator();
+ }
+
+ public void remove( MetadataResults results )
+ {
+ removeObject( results );
+ }
+
+ public void remove( RepositoryMetadata metadata )
+ {
+ try
+ {
+ MetadataResults results = lookupMetadataResults( metadata );
+ remove( results );
+ }
+ catch ( JDOObjectNotFoundException e )
+ {
+ // nothing to do.
+ }
+ }
+
+ public MetadataResults getMetadataResults( RepositoryMetadata metadata )
+ {
+ MetadataResults results;
+
+ try
+ {
+ results = lookupMetadataResults( metadata );
+ }
+ catch ( JDOObjectNotFoundException e )
+ {
+ results = createMetadataResults( metadata );
+ }
+
+ return results;
+ }
+
+ private MetadataResults createMetadataResults( RepositoryMetadata metadata )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The MetadataResults object has a complex primary key consisting of groupId, artifactId, and version.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ MetadataResults results = new MetadataResults();
+ results.setGroupId( StringUtils.defaultString( metadata.getGroupId() ) );
+ results.setArtifactId( StringUtils.defaultString( metadata.getArtifactId() ) );
+ results.setVersion( StringUtils.defaultString( metadata.getBaseVersion() ) );
+
+ return results;
+ }
+
+ private MetadataResults lookupMetadataResults( RepositoryMetadata metadata )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The MetadataResults object has a complex primary key consisting of groupId, artifactId, and version.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ MetadataResultsKey key = new MetadataResultsKey();
+ key.groupId = StringUtils.defaultString( metadata.getGroupId(), "" );
+ key.artifactId = StringUtils.defaultString( metadata.getArtifactId(), "" );
+ key.version = StringUtils.defaultString( metadata.getBaseVersion(), "" );
+
+ return (MetadataResults) getObjectByKey( MetadataResults.class, key );
+ }
+
+ public int getNumFailures()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ MetadataResults results = (MetadataResults) it.next();
+ count += results.getFailures().size();
+ }
+ return count;
+ }
+
+ public int getNumNotices()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ MetadataResults results = (MetadataResults) it.next();
+ count += results.getNotices().size();
+ }
+ return count;
+ }
+
+ public int getNumWarnings()
+ {
+ int count = 0;
+ for ( Iterator it = getIterator(); it.hasNext(); )
+ {
+ MetadataResults results = (MetadataResults) it.next();
+ count += results.getWarnings().size();
+ }
+ return count;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ReportingDatabase.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ReportingDatabase.java
new file mode 100644
index 000000000..4dd2430a5
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/database/ReportingDatabase.java
@@ -0,0 +1,124 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.Iterator;
+
+/**
+ * The Main Reporting Database.
+ *
+ * @todo i18n, including message formatting and parameterisation
+ * @plexus.component role="org.apache.maven.archiva.reporting.database.ReportingDatabase"
+ */
+public class ReportingDatabase
+{
+ public static final String ROLE = ReportingDatabase.class.getName();
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase artifactDatabase;
+
+ /**
+ * @plexus.requirement
+ */
+ private MetadataResultsDatabase metadataDatabase;
+
+ public Iterator getArtifactIterator()
+ {
+ return artifactDatabase.getIterator();
+ }
+
+ public Iterator getMetadataIterator()
+ {
+ return metadataDatabase.getIterator();
+ }
+
+ public void clear()
+ {
+ }
+
+ /**
+ * <p>
+ * Get the number of failures in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of failures in the database.
+ */
+ public int getNumFailures()
+ {
+ int count = 0;
+ count += artifactDatabase.getNumFailures();
+ count += metadataDatabase.getNumFailures();
+ return count;
+ }
+
+ /**
+ * <p>
+ * Get the number of notices in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of notices in the database.
+ */
+ public int getNumNotices()
+ {
+ int count = 0;
+ count += artifactDatabase.getNumNotices();
+ count += metadataDatabase.getNumNotices();
+ return count;
+ }
+
+ /**
+ * <p>
+ * Get the number of warnings in the database.
+ * </p>
+ *
+ * <p>
+ * <b>WARNING:</b> This is a very resource intensive request. Use sparingly.
+ * </p>
+ *
+ * @return the number of warnings in the database.
+ */
+ public int getNumWarnings()
+ {
+ int count = 0;
+ count += artifactDatabase.getNumWarnings();
+ count += metadataDatabase.getNumWarnings();
+ return count;
+ }
+
+ public ArtifactResultsDatabase getArtifactDatabase()
+ {
+ return artifactDatabase;
+ }
+
+ public MetadataResultsDatabase getMetadataDatabase()
+ {
+ return metadataDatabase;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/AbstractReportGroup.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/AbstractReportGroup.java
new file mode 100644
index 000000000..4e5acdddb
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/AbstractReportGroup.java
@@ -0,0 +1,82 @@
+package org.apache.maven.archiva.reporting.group;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor;
+import org.apache.maven.archiva.reporting.processor.MetadataReportProcessor;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.model.Model;
+
+import java.util.Iterator;
+import java.util.Map;
+
+/**
+ * Basic functionality for all report groups.
+ */
+public abstract class AbstractReportGroup
+ implements ReportGroup
+{
+ /**
+ * @plexus.requirement role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor"
+ */
+ private Map artifactReports;
+
+ /**
+ * @plexus.requirement role="org.apache.maven.archiva.reporting.processor.MetadataReportProcessor"
+ */
+ private Map metadataReports;
+
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ for ( Iterator i = artifactReports.entrySet().iterator(); i.hasNext(); )
+ {
+ Map.Entry entry = (Map.Entry) i.next();
+
+ if ( includeReport( (String) entry.getKey() ) )
+ {
+ ArtifactReportProcessor report = (ArtifactReportProcessor) entry.getValue();
+
+ report.processArtifact( artifact, model );
+ }
+ }
+ }
+
+ public void processMetadata( RepositoryMetadata repositoryMetadata, ArtifactRepository repository )
+ {
+ for ( Iterator i = metadataReports.entrySet().iterator(); i.hasNext(); )
+ {
+ Map.Entry entry = (Map.Entry) i.next();
+
+ if ( includeReport( (String) entry.getKey() ) )
+ {
+ MetadataReportProcessor report = (MetadataReportProcessor) entry.getValue();
+
+ report.processMetadata( repositoryMetadata, repository );
+ }
+ }
+ }
+
+ public String toString()
+ {
+ return getName();
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/DefaultReportGroup.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/DefaultReportGroup.java
new file mode 100644
index 000000000..58b8e2f63
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/DefaultReportGroup.java
@@ -0,0 +1,66 @@
+package org.apache.maven.archiva.reporting.group;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+/**
+ * The default report set, for repository health.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.group.ReportGroup"
+ * role-hint="health"
+ * @todo could these report groups be assembled dynamically by configuration rather than as explicit components? eg, reportGroup.addReport( ARP ), reportGroup.addReport( MRP )
+ */
+public class DefaultReportGroup
+ extends AbstractReportGroup
+{
+ /**
+ * Role hints of the reports to include in this set.
+ */
+ private static final Map reports = new LinkedHashMap();
+
+ static
+ {
+ reports.put( "checksum", "Checksum Problems" );
+ reports.put( "dependency", "Dependency Problems" );
+ // TODO re-enable duplicate, once a way to populate the index is determined!
+// reports.put( "duplicate", "Duplicate Artifact Problems" );
+ reports.put( "invalid-pom", "POM Problems" );
+ reports.put( "bad-metadata", "Metadata Problems" );
+ reports.put( "checksum-metadata", "Metadata Checksum Problems" );
+ reports.put( "artifact-location", "Artifact Location Problems" );
+ }
+
+ public boolean includeReport( String key )
+ {
+ return reports.containsKey( key );
+ }
+
+ public Map getReports()
+ {
+ return reports;
+ }
+
+ public String getName()
+ {
+ return "Repository Health";
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/OldArtifactReportGroup.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/OldArtifactReportGroup.java
new file mode 100644
index 000000000..d8ccc6fab
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/OldArtifactReportGroup.java
@@ -0,0 +1,65 @@
+package org.apache.maven.archiva.reporting.group;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+/**
+ * The report set for finding old artifacts (both snapshot and release)
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.group.ReportGroup" role-hint="old-artifact"
+ */
+public class OldArtifactReportGroup
+ extends AbstractReportGroup
+{
+ /**
+ * Role hints of the reports to include in this set.
+ *
+ * @todo implement these report processors!
+ */
+ private static final Map reports = new LinkedHashMap();
+
+ static
+ {
+ reports.put( "old-artifact", "Old Artifacts" );
+ reports.put( "old-snapshot-artifact", "Old Snapshot Artifacts" );
+ }
+
+ public boolean includeReport( String key )
+ {
+ return reports.containsKey( key );
+ }
+
+ public Map getReports()
+ {
+ return reports;
+ }
+
+ public String getFilename()
+ {
+ return "old-artifacts-report.xml";
+ }
+
+ public String getName()
+ {
+ return "Old Artifacts";
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/ReportGroup.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/ReportGroup.java
new file mode 100644
index 000000000..fa34b2233
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/group/ReportGroup.java
@@ -0,0 +1,78 @@
+package org.apache.maven.archiva.reporting.group;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.model.Model;
+
+import java.util.Map;
+
+/**
+ * A grouping or report processors for execution as a visible report from the web interface - eg, "health",
+ * "old artifacts", etc.
+ */
+public interface ReportGroup
+{
+ /**
+ * Plexus component role.
+ */
+ String ROLE = ReportGroup.class.getName();
+
+ /**
+ * Run any artifact related reports in the report set.
+ *
+ * @param artifact the artifact to process
+ * @param model the POM associated with the artifact to process
+ */
+ void processArtifact( Artifact artifact, Model model );
+
+ /**
+ * Run any metadata related reports in the report set.
+ *
+ * @param repositoryMetadata the metadata to process
+ * @param repository the repository the metadata is located in
+ */
+ void processMetadata( RepositoryMetadata repositoryMetadata, ArtifactRepository repository );
+
+ /**
+ * Whether a report with the given role hint is included in this report set.
+ *
+ * @param key the report role hint.
+ * @return whether the report is included
+ */
+ boolean includeReport( String key );
+
+ /**
+ * Get the report processors in this set. The map is keyed by the report's role hint, and the value is it's
+ * display name.
+ *
+ * @return the reports
+ */
+ Map getReports();
+
+ /**
+ * Get the user-friendly name of this report.
+ *
+ * @return the report name
+ */
+ String getName();
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/ArtifactResultsKey.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/ArtifactResultsKey.java
new file mode 100644
index 000000000..d41e119b2
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/ArtifactResultsKey.java
@@ -0,0 +1,158 @@
+package org.apache.maven.archiva.reporting.model;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+
+import java.io.Serializable;
+
+/**
+ * ArtifactResultsKey - used by jpox for application identity for the {@link ArtifactResults} object and table.
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class ArtifactResultsKey
+ implements Serializable
+{
+ public String groupId = "";
+
+ public String artifactId = "";
+
+ public String version = "";
+
+ public String artifactType = "";
+
+ public String classifier = "";
+
+ public ArtifactResultsKey()
+ {
+ /* do nothing */
+ }
+
+ public ArtifactResultsKey( String key )
+ {
+ String parts[] = StringUtils.splitPreserveAllTokens( key, ':' );
+ groupId = parts[0];
+ artifactId = parts[1];
+ version = parts[2];
+ artifactType = parts[3];
+ classifier = parts[4];
+ }
+
+ public String toString()
+ {
+ return StringUtils.join( new String[] { groupId, artifactId, version, artifactType, classifier }, ':' );
+ }
+
+ public int hashCode()
+ {
+ final int PRIME = 31;
+ int result = 1;
+ result = PRIME * result + ( ( groupId == null ) ? 0 : groupId.hashCode() );
+ result = PRIME * result + ( ( artifactId == null ) ? 0 : artifactId.hashCode() );
+ result = PRIME * result + ( ( version == null ) ? 0 : version.hashCode() );
+ result = PRIME * result + ( ( artifactType == null ) ? 0 : artifactType.hashCode() );
+ result = PRIME * result + ( ( classifier == null ) ? 0 : classifier.hashCode() );
+ return result;
+ }
+
+ public boolean equals( Object obj )
+ {
+ if ( this == obj )
+ {
+ return true;
+ }
+
+ if ( obj == null )
+ {
+ return false;
+ }
+
+ if ( getClass() != obj.getClass() )
+ {
+ return false;
+ }
+
+ final ArtifactResultsKey other = (ArtifactResultsKey) obj;
+
+ if ( groupId == null )
+ {
+ if ( other.groupId != null )
+ {
+ return false;
+ }
+ }
+ else if ( !groupId.equals( other.groupId ) )
+ {
+ return false;
+ }
+
+ if ( artifactId == null )
+ {
+ if ( other.artifactId != null )
+ {
+ return false;
+ }
+ }
+ else if ( !artifactId.equals( other.artifactId ) )
+ {
+ return false;
+ }
+
+ if ( version == null )
+ {
+ if ( other.version != null )
+ {
+ return false;
+ }
+ }
+ else if ( !version.equals( other.version ) )
+ {
+ return false;
+ }
+
+ if ( artifactType == null )
+ {
+ if ( other.artifactType != null )
+ {
+ return false;
+ }
+ }
+ else if ( !artifactType.equals( other.artifactType ) )
+ {
+ return false;
+ }
+
+ if ( classifier == null )
+ {
+ if ( other.classifier != null )
+ {
+ return false;
+ }
+ }
+ else if ( !classifier.equals( other.classifier ) )
+ {
+ return false;
+ }
+
+ return true;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/MetadataResultsKey.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/MetadataResultsKey.java
new file mode 100644
index 000000000..aeaff3bde
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/model/MetadataResultsKey.java
@@ -0,0 +1,126 @@
+package org.apache.maven.archiva.reporting.model;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+
+import java.io.Serializable;
+
+/**
+ * MetadataResultsKey - used by jpox for application identity for the {@link MetadataResults} object and table.
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class MetadataResultsKey
+ implements Serializable
+{
+ public String groupId = "";
+
+ public String artifactId = "";
+
+ public String version = "";
+
+ public MetadataResultsKey()
+ {
+ /* do nothing */
+ }
+
+ public MetadataResultsKey( String key )
+ {
+ String parts[] = StringUtils.splitPreserveAllTokens( key, ':' );
+ groupId = parts[0];
+ artifactId = parts[1];
+ version = parts[2];
+ }
+
+ public String toString()
+ {
+ return StringUtils.join( new String[] { groupId, artifactId, version }, ':' );
+ }
+
+ public int hashCode()
+ {
+ final int PRIME = 31;
+ int result = 1;
+ result = PRIME * result + ( ( groupId == null ) ? 0 : groupId.hashCode() );
+ result = PRIME * result + ( ( artifactId == null ) ? 0 : artifactId.hashCode() );
+ result = PRIME * result + ( ( version == null ) ? 0 : version.hashCode() );
+ return result;
+ }
+
+ public boolean equals( Object obj )
+ {
+ if ( this == obj )
+ {
+ return true;
+ }
+
+ if ( obj == null )
+ {
+ return false;
+ }
+
+ if ( getClass() != obj.getClass() )
+ {
+ return false;
+ }
+
+ final ArtifactResultsKey other = (ArtifactResultsKey) obj;
+
+ if ( groupId == null )
+ {
+ if ( other.groupId != null )
+ {
+ return false;
+ }
+ }
+ else if ( !groupId.equals( other.groupId ) )
+ {
+ return false;
+ }
+
+ if ( artifactId == null )
+ {
+ if ( other.artifactId != null )
+ {
+ return false;
+ }
+ }
+ else if ( !artifactId.equals( other.artifactId ) )
+ {
+ return false;
+ }
+
+ if ( version == null )
+ {
+ if ( other.version != null )
+ {
+ return false;
+ }
+ }
+ else if ( !version.equals( other.version ) )
+ {
+ return false;
+ }
+
+ return true;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ArtifactReportProcessor.java
new file mode 100644
index 000000000..52e63c5e7
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ArtifactReportProcessor.java
@@ -0,0 +1,34 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.model.Model;
+
+/**
+ * This interface will be called by the main system for each artifact as it is discovered. This is how each of the
+ * different types of reports are implemented.
+ */
+public interface ArtifactReportProcessor
+{
+ String ROLE = ArtifactReportProcessor.class.getName();
+
+ void processArtifact( Artifact artifact, Model model );
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessor.java
new file mode 100644
index 000000000..04a31af7e
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessor.java
@@ -0,0 +1,344 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.maven.archiva.layer.RepositoryQueryLayer;
+import org.apache.maven.archiva.layer.RepositoryQueryLayerFactory;
+import org.apache.maven.archiva.reporting.database.MetadataResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.metadata.Plugin;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.Snapshot;
+import org.apache.maven.artifact.repository.metadata.Versioning;
+import org.codehaus.plexus.util.FileUtils;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * This class will report on bad metadata files. These include invalid version declarations and incomplete version
+ * information inside the metadata file. Plugin metadata will be checked for validity of the latest plugin artifacts.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.MetadataReportProcessor" role-hint="bad-metadata"
+ */
+public class BadMetadataReportProcessor
+ implements MetadataReportProcessor
+{
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactFactory artifactFactory;
+
+ /**
+ * @plexus.requirement
+ */
+ private RepositoryQueryLayerFactory repositoryQueryLayerFactory;
+
+ /**
+ * @plexus.requirement
+ */
+ private MetadataResultsDatabase database;
+
+ private static final String ROLE_HINT = "bad-metadata";
+
+ /**
+ * Process the metadata encountered in the repository and report all errors found, if any.
+ *
+ * @param metadata the metadata to be processed.
+ * @param repository the repository where the metadata was encountered
+ * @param reporter the ReportingDatabase to receive processing results
+ */
+ public void processMetadata( RepositoryMetadata metadata, ArtifactRepository repository )
+ {
+ if ( metadata.storedInGroupDirectory() )
+ {
+ try
+ {
+ checkPluginMetadata( metadata, repository );
+ }
+ catch ( IOException e )
+ {
+ addWarning( metadata, null, "Error getting plugin artifact directories versions: " + e );
+ }
+ }
+ else
+ {
+ Versioning versioning = metadata.getMetadata().getVersioning();
+ boolean found = false;
+ if ( versioning != null )
+ {
+ String lastUpdated = versioning.getLastUpdated();
+ if ( lastUpdated != null && lastUpdated.length() != 0 )
+ {
+ found = true;
+ }
+ }
+ if ( !found )
+ {
+ addFailure( metadata, "missing-last-updated", "Missing lastUpdated element inside the metadata." );
+ }
+
+ if ( metadata.storedInArtifactVersionDirectory() )
+ {
+ checkSnapshotMetadata( metadata, repository );
+ }
+ else
+ {
+ checkMetadataVersions( metadata, repository );
+
+ try
+ {
+ checkRepositoryVersions( metadata, repository );
+ }
+ catch ( IOException e )
+ {
+ String reason = "Error getting plugin artifact directories versions: " + e;
+ addWarning( metadata, null, reason );
+ }
+ }
+ }
+ }
+
+ private void addWarning( RepositoryMetadata metadata, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addWarning( metadata, ROLE_HINT, problem, reason );
+ }
+
+ /**
+ * Method for processing a GroupRepositoryMetadata
+ *
+ * @param metadata the metadata to be processed.
+ * @param repository the repository where the metadata was encountered
+ * @param reporter the ReportingDatabase to receive processing results
+ */
+ private void checkPluginMetadata( RepositoryMetadata metadata, ArtifactRepository repository )
+ throws IOException
+ {
+ File metadataDir = new File( repository.getBasedir(), repository.pathOfRemoteRepositoryMetadata( metadata ) )
+ .getParentFile();
+ List pluginDirs = getArtifactIdFiles( metadataDir );
+
+ Map prefixes = new HashMap();
+ for ( Iterator plugins = metadata.getMetadata().getPlugins().iterator(); plugins.hasNext(); )
+ {
+ Plugin plugin = (Plugin) plugins.next();
+
+ String artifactId = plugin.getArtifactId();
+ if ( artifactId == null || artifactId.length() == 0 )
+ {
+ addFailure( metadata, "missing-artifact-id:" + plugin.getPrefix(),
+ "Missing or empty artifactId in group metadata for plugin " + plugin.getPrefix() );
+ }
+
+ String prefix = plugin.getPrefix();
+ if ( prefix == null || prefix.length() == 0 )
+ {
+ addFailure( metadata, "missing-plugin-prefix:" + artifactId,
+ "Missing or empty plugin prefix for artifactId " + artifactId + "." );
+ }
+ else
+ {
+ if ( prefixes.containsKey( prefix ) )
+ {
+ addFailure( metadata, "duplicate-plugin-prefix:" + prefix, "Duplicate plugin prefix found: "
+ + prefix + "." );
+ }
+ else
+ {
+ prefixes.put( prefix, plugin );
+ }
+ }
+
+ if ( artifactId != null && artifactId.length() > 0 )
+ {
+ File pluginDir = new File( metadataDir, artifactId );
+ if ( !pluginDirs.contains( pluginDir ) )
+ {
+ addFailure( metadata, "missing-plugin-from-repository:" + artifactId, "Metadata plugin "
+ + artifactId + " not found in the repository" );
+ }
+ else
+ {
+ pluginDirs.remove( pluginDir );
+ }
+ }
+ }
+
+ if ( pluginDirs.size() > 0 )
+ {
+ for ( Iterator plugins = pluginDirs.iterator(); plugins.hasNext(); )
+ {
+ File plugin = (File) plugins.next();
+ addFailure( metadata, "missing-plugin-from-metadata:" + plugin.getName(), "Plugin " + plugin.getName()
+ + " is present in the repository but " + "missing in the metadata." );
+ }
+ }
+ }
+
+ /**
+ * Method for processing a SnapshotArtifactRepository
+ *
+ * @param metadata the metadata to be processed.
+ * @param repository the repository where the metadata was encountered
+ * @param reporter the ReportingDatabase to receive processing results
+ */
+ private void checkSnapshotMetadata( RepositoryMetadata metadata, ArtifactRepository repository )
+ {
+ RepositoryQueryLayer repositoryQueryLayer = repositoryQueryLayerFactory.createRepositoryQueryLayer( repository );
+
+ Versioning versioning = metadata.getMetadata().getVersioning();
+ if ( versioning != null )
+ {
+ Snapshot snapshot = versioning.getSnapshot();
+
+ String version = StringUtils.replace( metadata.getBaseVersion(), Artifact.SNAPSHOT_VERSION, snapshot
+ .getTimestamp()
+ + "-" + snapshot.getBuildNumber() );
+ Artifact artifact = artifactFactory.createProjectArtifact( metadata.getGroupId(), metadata.getArtifactId(),
+ version );
+ artifact.isSnapshot(); // trigger baseVersion correction
+
+ if ( !repositoryQueryLayer.containsArtifact( artifact ) )
+ {
+ addFailure( metadata, "missing-snapshot-artifact-from-repository:" + version, "Snapshot artifact "
+ + version + " does not exist." );
+ }
+ }
+ }
+
+ /**
+ * Method for validating the versions declared inside an ArtifactRepositoryMetadata
+ *
+ * @param metadata the metadata to be processed.
+ * @param repository the repository where the metadata was encountered
+ * @param reporter the ReportingDatabase to receive processing results
+ */
+ private void checkMetadataVersions( RepositoryMetadata metadata, ArtifactRepository repository )
+ {
+ RepositoryQueryLayer repositoryQueryLayer = repositoryQueryLayerFactory.createRepositoryQueryLayer( repository );
+
+ Versioning versioning = metadata.getMetadata().getVersioning();
+ if ( versioning != null )
+ {
+ for ( Iterator versions = versioning.getVersions().iterator(); versions.hasNext(); )
+ {
+ String version = (String) versions.next();
+
+ Artifact artifact = artifactFactory.createProjectArtifact( metadata.getGroupId(), metadata
+ .getArtifactId(), version );
+
+ if ( !repositoryQueryLayer.containsArtifact( artifact ) )
+ {
+ addFailure( metadata, "missing-artifact-from-repository:" + version, "Artifact version " + version
+ + " is present in metadata but " + "missing in the repository." );
+ }
+ }
+ }
+ }
+
+ /**
+ * Searches the artifact repository directory for all versions and verifies that all of them are listed in the
+ * ArtifactRepositoryMetadata
+ *
+ * @param metadata the metadata to be processed.
+ * @param repository the repository where the metadata was encountered
+ * @param reporter the ReportingDatabase to receive processing results
+ * @throws java.io.IOException if there is a problem reading from the file system
+ */
+ private void checkRepositoryVersions( RepositoryMetadata metadata, ArtifactRepository repository )
+ throws IOException
+ {
+ Versioning versioning = metadata.getMetadata().getVersioning();
+ List metadataVersions = versioning != null ? versioning.getVersions() : Collections.EMPTY_LIST;
+ File versionsDir = new File( repository.getBasedir(), repository.pathOfRemoteRepositoryMetadata( metadata ) )
+ .getParentFile();
+
+ // TODO: I don't know how this condition can happen, but it was seen on the main repository.
+ // Avoid hard failure
+ if ( versionsDir.exists() )
+ {
+ List versions = FileUtils.getFileNames( versionsDir, "*/*.pom", null, false );
+ for ( Iterator i = versions.iterator(); i.hasNext(); )
+ {
+ File path = new File( (String) i.next() );
+ String version = path.getParentFile().getName();
+ if ( !metadataVersions.contains( version ) )
+ {
+ addFailure( metadata, "missing-artifact-from-metadata:" + version, "Artifact version " + version
+ + " found in the repository but " + "missing in the metadata." );
+ }
+ }
+ }
+ else
+ {
+ addFailure( metadata, null, "Metadata's directory did not exist: " + versionsDir );
+ }
+ }
+
+ /**
+ * Used to gather artifactIds from a groupId directory.
+ *
+ * @param groupIdDir the directory of the group
+ * @return the list of artifact ID File objects for each directory
+ * @throws IOException if there was a failure to read the directories
+ */
+ private List getArtifactIdFiles( File groupIdDir )
+ throws IOException
+ {
+ List artifactIdFiles = new ArrayList();
+
+ File[] files = groupIdDir.listFiles();
+ if ( files != null )
+ {
+ for ( Iterator i = Arrays.asList( files ).iterator(); i.hasNext(); )
+ {
+ File artifactDir = (File) i.next();
+
+ if ( artifactDir.isDirectory() )
+ {
+ List versions = FileUtils.getFileNames( artifactDir, "*/*.pom", null, false );
+ if ( versions.size() > 0 )
+ {
+ artifactIdFiles.add( artifactDir );
+ }
+ }
+ }
+ }
+
+ return artifactIdFiles;
+ }
+
+ private void addFailure( RepositoryMetadata metadata, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( metadata, ROLE_HINT, problem, reason );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumArtifactReportProcessor.java
new file mode 100644
index 000000000..8bd5e141f
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumArtifactReportProcessor.java
@@ -0,0 +1,110 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.FileUtils;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+import org.codehaus.plexus.digest.Digester;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.File;
+import java.io.IOException;
+
+/**
+ * This class reports invalid and mismatched checksums of artifacts and metadata files.
+ * It validates MD5 and SHA-1 checksums.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="checksum"
+ */
+public class ChecksumArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ /**
+ * @plexus.requirement role-hint="sha1"
+ */
+ private Digester sha1Digester;
+
+ /**
+ * @plexus.requirement role-hint="md5"
+ */
+ private Digester md5Digester;
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ private static final String ROLE_HINT = "checksum";
+
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException(
+ "Can't process repository '" + repository.getUrl() + "'. Only file based repositories are supported" );
+ }
+
+ //check if checksum files exist
+ String path = repository.pathOf( artifact );
+ File file = new File( repository.getBasedir(), path );
+
+ // TODO: make md5 configurable
+// verifyChecksum( repository, path + ".md5", file, md5Digester, reporter, artifact );
+ verifyChecksum( repository, path + ".sha1", file, sha1Digester, artifact );
+ }
+
+ private void verifyChecksum( ArtifactRepository repository, String path, File file, Digester digester,
+ Artifact artifact )
+ {
+ File checksumFile = new File( repository.getBasedir(), path );
+ if ( checksumFile.exists() )
+ {
+ try
+ {
+ digester.verify( file, FileUtils.readFileToString( checksumFile, null ) );
+ }
+ catch ( DigesterException e )
+ {
+ addFailure( artifact, "checksum-wrong", e.getMessage() );
+ }
+ catch ( IOException e )
+ {
+ addFailure( artifact, "checksum-io-exception", "Read file error: " + e.getMessage() );
+ }
+ }
+ else
+ {
+ addFailure( artifact, "checksum-missing",
+ digester.getAlgorithm() + " checksum file does not exist." );
+ }
+ }
+
+ private void addFailure( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( artifact, ROLE_HINT, problem, reason );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumMetadataReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumMetadataReportProcessor.java
new file mode 100644
index 000000000..84313dc52
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/ChecksumMetadataReportProcessor.java
@@ -0,0 +1,110 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.FileUtils;
+import org.apache.maven.archiva.reporting.database.MetadataResultsDatabase;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.codehaus.plexus.digest.Digester;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.File;
+import java.io.IOException;
+
+/**
+ * This class reports invalid and mismatched checksums of artifacts and metadata files.
+ * It validates MD5 and SHA-1 checksums.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.MetadataReportProcessor" role-hint="checksum-metadata"
+ */
+public class ChecksumMetadataReportProcessor
+ implements MetadataReportProcessor
+{
+ /**
+ * @plexus.requirement role-hint="sha1"
+ */
+ private Digester sha1Digester;
+
+ /**
+ * @plexus.requirement role-hint="md5"
+ */
+ private Digester md5Digester;
+
+ /**
+ * @plexus.requirement
+ */
+ private MetadataResultsDatabase database;
+
+ private static final String ROLE_HINT = "checksum-metadata";
+
+ /**
+ * Validate the checksums of the metadata. Get the metadata file from the
+ * repository then validate the checksum.
+ */
+ public void processMetadata( RepositoryMetadata metadata, ArtifactRepository repository )
+ {
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException( "Can't process repository '" + repository.getUrl()
+ + "'. Only file based repositories are supported" );
+ }
+
+ //check if checksum files exist
+ String path = repository.pathOfRemoteRepositoryMetadata( metadata );
+ File file = new File( repository.getBasedir(), path );
+
+ verifyChecksum( repository, path + ".md5", file, md5Digester, metadata );
+ verifyChecksum( repository, path + ".sha1", file, sha1Digester, metadata );
+ }
+
+ private void verifyChecksum( ArtifactRepository repository, String path, File file, Digester digester,
+ RepositoryMetadata metadata )
+ {
+ File checksumFile = new File( repository.getBasedir(), path );
+ if ( checksumFile.exists() )
+ {
+ try
+ {
+ digester.verify( file, FileUtils.readFileToString( checksumFile, null ) );
+ }
+ catch ( DigesterException e )
+ {
+ addFailure( metadata, "checksum-wrong", e.getMessage() );
+ }
+ catch ( IOException e )
+ {
+ addFailure( metadata, "checksum-io-exception", "Read file error: " + e.getMessage() );
+ }
+ }
+ else
+ {
+ addFailure( metadata, "checksum-missing", digester.getAlgorithm() + " checksum file does not exist." );
+ }
+ }
+
+ private void addFailure( RepositoryMetadata metadata, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( metadata, ROLE_HINT, problem, reason );
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessor.java
new file mode 100644
index 000000000..049767c2d
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessor.java
@@ -0,0 +1,167 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.layer.RepositoryQueryLayer;
+import org.apache.maven.archiva.layer.RepositoryQueryLayerFactory;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.versioning.InvalidVersionSpecificationException;
+import org.apache.maven.artifact.versioning.VersionRange;
+import org.apache.maven.model.Dependency;
+import org.apache.maven.model.Model;
+
+import java.text.MessageFormat;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="dependency"
+ */
+public class DependencyArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactFactory artifactFactory;
+
+ /**
+ * @plexus.requirement
+ */
+ private RepositoryQueryLayerFactory layerFactory;
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ private static final String POM = "pom";
+
+ private static final String ROLE_HINT = "dependency";
+
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ RepositoryQueryLayer queryLayer = layerFactory.createRepositoryQueryLayer( artifact.getRepository() );
+ if ( !queryLayer.containsArtifact( artifact ) )
+ {
+ // TODO: is this even possible?
+ addFailure( artifact, "missing-artifact", "Artifact does not exist in the repository" );
+ }
+
+ if ( model != null && POM.equals( artifact.getType() ) )
+ {
+ List dependencies = model.getDependencies();
+ processDependencies( dependencies, queryLayer, artifact );
+ }
+ }
+
+ private void addFailure( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( artifact, ROLE_HINT, problem, reason );
+ }
+
+ private void processDependencies( List dependencies, RepositoryQueryLayer repositoryQueryLayer,
+ Artifact sourceArtifact )
+ {
+ if ( dependencies.size() > 0 )
+ {
+ Iterator iterator = dependencies.iterator();
+ while ( iterator.hasNext() )
+ {
+ Dependency dependency = (Dependency) iterator.next();
+
+ try
+ {
+ Artifact artifact = createArtifact( dependency );
+
+ // TODO: handle ranges properly. We should instead be mapping out all the artifacts in the
+ // repository and mapping out the graph
+
+ if ( artifact.getVersion() == null )
+ {
+ // it was a range, for now presume it exists
+ continue;
+ }
+
+ if ( !repositoryQueryLayer.containsArtifact( artifact ) )
+ {
+ String reason = MessageFormat
+ .format( "Artifact''s dependency {0} does not exist in the repository",
+ new String[] { getDependencyString( dependency ) } );
+ addFailure( sourceArtifact, "missing-dependency:" + getDependencyKey( dependency ), reason );
+ }
+ }
+ catch ( InvalidVersionSpecificationException e )
+ {
+ String reason = MessageFormat.format( "Artifact''s dependency {0} contains an invalid version {1}",
+ new String[] {
+ getDependencyString( dependency ),
+ dependency.getVersion() } );
+ addFailure( sourceArtifact, "bad-version:" + getDependencyKey( dependency ), reason );
+ }
+ }
+ }
+ }
+
+ private String getDependencyKey( Dependency dependency )
+ {
+ String str = dependency.getGroupId();
+ str += ":" + dependency.getArtifactId();
+ str += ":" + dependency.getVersion();
+ str += ":" + dependency.getType();
+ if ( dependency.getClassifier() != null )
+ {
+ str += ":" + dependency.getClassifier();
+ }
+ return str;
+ }
+
+ static String getDependencyString( Dependency dependency )
+ {
+ String str = "(group=" + dependency.getGroupId();
+ str += ", artifact=" + dependency.getArtifactId();
+ str += ", version=" + dependency.getVersion();
+ str += ", type=" + dependency.getType();
+ if ( dependency.getClassifier() != null )
+ {
+ str += ", classifier=" + dependency.getClassifier();
+ }
+ str += ")";
+ return str;
+ }
+
+ private Artifact createArtifact( Dependency dependency )
+ throws InvalidVersionSpecificationException
+ {
+ VersionRange spec = VersionRange.createFromVersionSpec( dependency.getVersion() );
+
+ if ( spec == null )
+ {
+ throw new InvalidVersionSpecificationException( "Dependency version was null" );
+ }
+
+ return artifactFactory.createDependencyArtifact( dependency.getGroupId(), dependency.getArtifactId(), spec,
+ dependency.getType(), dependency.getClassifier(), dependency
+ .getScope() );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessor.java
new file mode 100644
index 000000000..fc0e626a0
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessor.java
@@ -0,0 +1,143 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.lucene.index.Term;
+import org.apache.lucene.search.TermQuery;
+import org.apache.maven.archiva.indexer.RepositoryArtifactIndex;
+import org.apache.maven.archiva.indexer.RepositoryArtifactIndexFactory;
+import org.apache.maven.archiva.indexer.RepositoryIndexSearchException;
+import org.apache.maven.archiva.indexer.lucene.LuceneQuery;
+import org.apache.maven.archiva.indexer.record.StandardArtifactIndexRecord;
+import org.apache.maven.archiva.indexer.record.StandardIndexRecordFields;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+import org.codehaus.plexus.digest.Digester;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.File;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Validates an artifact file for duplicates within the same groupId based from what's available in a repository index.
+ *
+ * @author Edwin Punzalan
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="duplicate"
+ */
+public class DuplicateArtifactFileReportProcessor
+ implements ArtifactReportProcessor
+{
+ /**
+ * @plexus.requirement role-hint="md5"
+ */
+ private Digester digester;
+
+ /**
+ * @plexus.requirement
+ */
+ private RepositoryArtifactIndexFactory indexFactory;
+
+ /**
+ * @plexus.configuration
+ */
+ private String indexDirectory;
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ private static final String ROLE_HINT = "duplicate";
+
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+ if ( artifact.getFile() != null )
+ {
+ System.out.println( "indexDirectory = " + indexDirectory );
+
+ File indexDirectoryFile = new File( indexDirectory );
+
+ RepositoryArtifactIndex index = indexFactory.createStandardIndex( indexDirectoryFile );
+
+ String checksum = null;
+ try
+ {
+ checksum = digester.calc( artifact.getFile() );
+ }
+ catch ( DigesterException e )
+ {
+ addWarning( artifact, "cant-checksum", "Unable to generate checksum for " + artifact.getFile() + ": " + e );
+ }
+
+ if ( checksum != null )
+ {
+ try
+ {
+ List results = index
+ .search( new LuceneQuery( new TermQuery( new Term( StandardIndexRecordFields.MD5, checksum
+ .toLowerCase() ) ) ) );
+
+ if ( !results.isEmpty() )
+ {
+ for ( Iterator i = results.iterator(); i.hasNext(); )
+ {
+ StandardArtifactIndexRecord result = (StandardArtifactIndexRecord) i.next();
+
+ //make sure it is not the same artifact
+ if ( !result.getFilename().equals( repository.pathOf( artifact ) ) )
+ {
+ //report only duplicates from the same groupId
+ String groupId = artifact.getGroupId();
+ if ( groupId.equals( result.getGroupId() ) )
+ {
+ addFailure( artifact, "duplicate", "Found duplicate for " + artifact.getId() );
+ }
+ }
+ }
+ }
+ }
+ catch ( RepositoryIndexSearchException e )
+ {
+ addWarning( artifact, null, "Failed to search in index" + e );
+ }
+ }
+ }
+ else
+ {
+ addWarning( artifact, null, "Artifact file is null" );
+ }
+ }
+
+ private void addFailure( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( artifact, ROLE_HINT, problem, reason );
+ }
+
+ private void addWarning( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addWarning( artifact, ROLE_HINT, problem, reason );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessor.java
new file mode 100644
index 000000000..05977be86
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessor.java
@@ -0,0 +1,107 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.IOUtils;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
+import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
+
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.Reader;
+
+/**
+ * This class validates well-formedness of pom xml file.
+ *
+ * @todo nice to have this a specific, tested report - however it is likely to double up with project building exceptions from IndexerTask. Resolve [!]
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="invalid-pom"
+ */
+public class InvalidPomArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ private static final String ROLE_HINT = "invalid-pom";
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ /**
+ * @param artifact The pom xml file to be validated, passed as an artifact object.
+ * @param reporter The artifact reporter object.
+ */
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException( "Can't process repository '" + repository.getUrl()
+ + "'. Only file based repositories are supported" );
+ }
+
+ if ( "pom".equals( artifact.getType().toLowerCase() ) )
+ {
+ File f = new File( repository.getBasedir(), repository.pathOf( artifact ) );
+
+ if ( !f.exists() )
+ {
+ addFailure( artifact, "pom-missing", "POM not found." );
+ }
+ else
+ {
+ Reader reader = null;
+
+ MavenXpp3Reader pomReader = new MavenXpp3Reader();
+
+ try
+ {
+ reader = new FileReader( f );
+ pomReader.read( reader );
+ }
+ catch ( XmlPullParserException e )
+ {
+ addFailure( artifact, "pom-parse-exception",
+ "The pom xml file is not well-formed. Error while parsing: " + e.getMessage() );
+ }
+ catch ( IOException e )
+ {
+ addFailure( artifact, "pom-io-exception", "Error while reading the pom xml file: " + e.getMessage() );
+ }
+ finally
+ {
+ IOUtils.closeQuietly( reader );
+ }
+ }
+ }
+ }
+
+ private void addFailure( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( artifact, ROLE_HINT, problem, reason );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessor.java
new file mode 100644
index 000000000..cc68ea9d6
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessor.java
@@ -0,0 +1,250 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.IOUtils;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.handler.DefaultArtifactHandler;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
+import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Set;
+import java.util.jar.JarEntry;
+import java.util.jar.JarFile;
+
+/**
+ * Validate the location of the artifact based on the values indicated
+ * in its pom (both the pom packaged with the artifact & the pom in the
+ * file system).
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="artifact-location"
+ */
+public class LocationArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactFactory artifactFactory;
+
+ // TODO: share with other code with the same
+ private static final Set JAR_FILE_TYPES = new HashSet( Arrays.asList( new String[] {
+ "jar",
+ "war",
+ "par",
+ "ejb",
+ "ear",
+ "rar",
+ "sar" } ) );
+
+ /**
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ private static final String POM = "pom";
+
+ private static final String ROLE_HINT = "artifact-location";
+
+ /**
+ * Check whether the artifact is in its proper location. The location of the artifact
+ * is validated first against the groupId, artifactId and versionId in the specified model
+ * object (pom in the file system). Then unpack the artifact (jar file) and get the model (pom)
+ * included in the package. If a model exists inside the package, then check if the artifact's
+ * location is valid based on the location specified in the pom. Check if the both the location
+ * specified in the file system pom and in the pom included in the package is the same.
+ */
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException( "Can't process repository '" + repository.getUrl()
+ + "'. Only file based repositories are supported" );
+ }
+
+ adjustDistributionArtifactHandler( artifact );
+
+ String artifactPath = repository.pathOf( artifact );
+
+ if ( model != null )
+ {
+ // only check if it is a standalone POM, or an artifact other than a POM
+ // ie, don't check the location of the POM for another artifact matches that of the artifact
+ if ( !POM.equals( artifact.getType() ) || POM.equals( model.getPackaging() ) )
+ {
+ //check if the artifact is located in its proper location based on the info
+ //specified in the model object/pom
+ Artifact modelArtifact = artifactFactory.createArtifactWithClassifier( model.getGroupId(), model
+ .getArtifactId(), model.getVersion(), artifact.getType(), artifact.getClassifier() );
+
+ adjustDistributionArtifactHandler( modelArtifact );
+ String modelPath = repository.pathOf( modelArtifact );
+ if ( !modelPath.equals( artifactPath ) )
+ {
+ addFailure( artifact, "repository-pom-location",
+ "The artifact is out of place. It does not match the specified location in the repository pom: "
+ + modelPath );
+ }
+ }
+ }
+
+ // get the location of the artifact itself
+ File file = new File( repository.getBasedir(), artifactPath );
+
+ if ( file.exists() )
+ {
+ if ( JAR_FILE_TYPES.contains( artifact.getType() ) )
+ {
+ //unpack the artifact (using the groupId, artifactId & version specified in the artifact object itself
+ //check if the pom is included in the package
+ Model extractedModel = readArtifactModel( file, artifact );
+
+ if ( extractedModel != null )
+ {
+ Artifact extractedArtifact = artifactFactory.createBuildArtifact( extractedModel.getGroupId(),
+ extractedModel.getArtifactId(),
+ extractedModel.getVersion(),
+ extractedModel.getPackaging() );
+ if ( !repository.pathOf( extractedArtifact ).equals( artifactPath ) )
+ {
+ addFailure( artifact, "packaged-pom-location",
+ "The artifact is out of place. It does not match the specified location in the packaged pom." );
+ }
+ }
+ }
+ }
+ else
+ {
+ addFailure( artifact, "missing-artifact", "The artifact file [" + file + "] cannot be found for metadata." );
+ }
+ }
+
+ private void addFailure( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addFailure( artifact, ROLE_HINT, problem, reason );
+ }
+
+ private static void adjustDistributionArtifactHandler( Artifact artifact )
+ {
+ // need to tweak these as they aren't currently in the known type converters. TODO - add them in Maven
+ if ( "distribution-zip".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "zip" ) );
+ }
+ else if ( "distribution-tgz".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "tar.gz" ) );
+ }
+ }
+
+ private Model readArtifactModel( File file, Artifact artifact )
+ {
+ Model model = null;
+
+ JarFile jar = null;
+ try
+ {
+ jar = new JarFile( file );
+
+ //Get the entry and its input stream.
+ JarEntry entry = jar.getJarEntry( "META-INF/maven/" + artifact.getGroupId() + "/"
+ + artifact.getArtifactId() + "/pom.xml" );
+
+ // If the entry is not null, extract it.
+ if ( entry != null )
+ {
+ model = readModel( jar.getInputStream( entry ) );
+
+ if ( model.getGroupId() == null )
+ {
+ model.setGroupId( model.getParent().getGroupId() );
+ }
+ if ( model.getVersion() == null )
+ {
+ model.setVersion( model.getParent().getVersion() );
+ }
+ }
+ }
+ catch ( IOException e )
+ {
+ addWarning( artifact, "Unable to read artifact to extract model: " + e );
+ }
+ catch ( XmlPullParserException e )
+ {
+ addWarning( artifact, "Unable to parse extracted model: " + e );
+ }
+ finally
+ {
+ if ( jar != null )
+ {
+ //noinspection UnusedCatchParameter
+ try
+ {
+ jar.close();
+ }
+ catch ( IOException e )
+ {
+ // ignore
+ }
+ }
+ }
+ return model;
+ }
+
+ private void addWarning( Artifact artifact, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addWarning( artifact, ROLE_HINT, "bad-location", reason );
+ }
+
+ private Model readModel( InputStream entryStream )
+ throws IOException, XmlPullParserException
+ {
+ Reader isReader = new InputStreamReader( entryStream );
+
+ Model model;
+ try
+ {
+ MavenXpp3Reader pomReader = new MavenXpp3Reader();
+ model = pomReader.read( isReader );
+ }
+ finally
+ {
+ IOUtils.closeQuietly( isReader );
+ }
+ return model;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/MetadataReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/MetadataReportProcessor.java
new file mode 100644
index 000000000..ad8465028
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/MetadataReportProcessor.java
@@ -0,0 +1,33 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+
+/**
+ * This interface is called by the main system for each piece of metadata as it is discovered.
+ */
+public interface MetadataReportProcessor
+{
+ String ROLE = MetadataReportProcessor.class.getName();
+
+ void processMetadata( RepositoryMetadata metadata, ArtifactRepository repository );
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessor.java
new file mode 100644
index 000000000..b5f0817cb
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessor.java
@@ -0,0 +1,100 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.handler.DefaultArtifactHandler;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+
+import java.io.File;
+
+/**
+ * Find artifacts in the repository that are considered old.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="old-artifact"
+ * @todo make this configurable from the web interface
+ */
+public class OldArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ private static final String ROLE_HINT = "old-artifact";
+
+ /**
+ * The maximum age of an artifact before it is reported old, specified in seconds. The default is 1 year.
+ *
+ * @plexus.configuration default-value="31536000"
+ */
+ private int maxAge;
+
+ /**
+ * TODO: Must create an 'Old Artifact' database.
+ * TODO: Base this off of an artifact table query instead.
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ public void processArtifact( Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException(
+ "Can't process repository '" + repository.getUrl() + "'. Only file based repositories are supported" );
+ }
+
+ adjustDistributionArtifactHandler( artifact );
+
+ String artifactPath = repository.pathOf( artifact );
+
+ //get the location of the artifact itself
+ File file = new File( repository.getBasedir(), artifactPath );
+
+ if ( file.exists() )
+ {
+ if ( System.currentTimeMillis() - file.lastModified() > maxAge * 1000 )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addNotice( artifact, ROLE_HINT, "old-artifact",
+ "The artifact is older than the maximum age of " + maxAge + " seconds." );
+ }
+ }
+ else
+ {
+ throw new IllegalStateException( "Couldn't find artifact " + file );
+ }
+ }
+
+ private static void adjustDistributionArtifactHandler( Artifact artifact )
+ {
+ // need to tweak these as they aren't currently in the known type converters. TODO - add them in Maven
+ if ( "distribution-zip".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "zip" ) );
+ }
+ else if ( "distribution-tgz".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "tar.gz" ) );
+ }
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessor.java b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessor.java
new file mode 100644
index 000000000..02c2cecb0
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessor.java
@@ -0,0 +1,191 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.handler.DefaultArtifactHandler;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.model.Model;
+
+import java.io.File;
+import java.io.FilenameFilter;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.regex.Matcher;
+
+/**
+ * Find snapshot artifacts in the repository that are considered old.
+ *
+ * @plexus.component role="org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor" role-hint="old-snapshot-artifact"
+ * @todo make this configurable from the web interface
+ */
+public class OldSnapshotArtifactReportProcessor
+ implements ArtifactReportProcessor
+{
+ private static final String ROLE_HINT = "old-snapshot-artifact";
+
+ /**
+ * The maximum age of an artifact before it is reported old, specified in seconds. The default is 1 year.
+ *
+ * @plexus.configuration default-value="31536000"
+ */
+ private int maxAge;
+
+ /**
+ * The maximum number of snapshots to retain within a given version. The default is 0, which keeps all snapshots
+ * that are within the age limits.
+ *
+ * @plexus.configuration default-value="0"
+ */
+ private int maxSnapshots;
+
+ /**
+ * TODO: Must create an 'Old Artifact' database.
+ * TODO: Base this off of an artifact table query instead.
+ * @plexus.requirement
+ */
+ private ArtifactResultsDatabase database;
+
+ public void processArtifact( final Artifact artifact, Model model )
+ {
+ ArtifactRepository repository = artifact.getRepository();
+
+ if ( !"file".equals( repository.getProtocol() ) )
+ {
+ // We can't check other types of URLs yet. Need to use Wagon, with an exists() method.
+ throw new UnsupportedOperationException( "Can't process repository '" + repository.getUrl()
+ + "'. Only file based repositories are supported" );
+ }
+
+ adjustDistributionArtifactHandler( artifact );
+
+ String artifactPath = repository.pathOf( artifact );
+
+ //get the location of the artifact itself
+ File file = new File( repository.getBasedir(), artifactPath );
+
+ if ( file.exists() )
+ {
+ if ( artifact.isSnapshot() )
+ {
+ Matcher m = Artifact.VERSION_FILE_PATTERN.matcher( artifact.getVersion() );
+ if ( m.matches() )
+ {
+ long timestamp;
+ try
+ {
+ timestamp = new SimpleDateFormat( "yyyyMMdd.HHmmss" ).parse( m.group( 2 ) ).getTime();
+ }
+ catch ( ParseException e )
+ {
+ throw new IllegalStateException(
+ "Shouldn't match timestamp pattern and not be able to parse it: "
+ + m.group( 2 ) );
+ }
+
+ if ( System.currentTimeMillis() - timestamp > maxAge * 1000 )
+ {
+ addNotice( artifact, "snapshot-expired-time", "The artifact is older than the maximum age of "
+ + maxAge + " seconds." );
+ }
+ else if ( maxSnapshots > 0 )
+ {
+ File[] files = file.getParentFile().listFiles( new FilenameFilter()
+ {
+ public boolean accept( File file, String string )
+ {
+ return string.startsWith( artifact.getArtifactId() + "-" )
+ && string.endsWith( "." + artifact.getArtifactHandler().getExtension() );
+ }
+ } );
+
+ List/*<Integer>*/buildNumbers = new ArrayList();
+ Integer currentBuild = null;
+ for ( Iterator i = Arrays.asList( files ).iterator(); i.hasNext(); )
+ {
+ File f = (File) i.next();
+
+ // trim to version
+ int startIndex = artifact.getArtifactId().length() + 1;
+ int extensionLength = artifact.getArtifactHandler().getExtension().length() + 1;
+ int endIndex = f.getName().length() - extensionLength;
+ String name = f.getName().substring( startIndex, endIndex );
+
+ Matcher matcher = Artifact.VERSION_FILE_PATTERN.matcher( name );
+
+ if ( matcher.matches() )
+ {
+ Integer buildNumber = Integer.valueOf( matcher.group( 3 ) );
+
+ buildNumbers.add( buildNumber );
+ if ( name.equals( artifact.getVersion() ) )
+ {
+ currentBuild = buildNumber;
+ }
+ }
+ }
+
+ // Prune back to expired build numbers
+ Collections.sort( buildNumbers );
+ for ( int i = 0; i < maxSnapshots && !buildNumbers.isEmpty(); i++ )
+ {
+ buildNumbers.remove( buildNumbers.size() - 1 );
+ }
+
+ if ( buildNumbers.contains( currentBuild ) )
+ {
+ addNotice( artifact, "snapshot-expired-count",
+ "The artifact is older than the maximum number of retained snapshot builds." );
+ }
+ }
+ }
+ }
+ }
+ else
+ {
+ throw new IllegalStateException( "Couldn't find artifact " + file );
+ }
+ }
+
+ private void addNotice( Artifact artifact, String problem, String reason )
+ {
+ // TODO: reason could be an i18n key derived from the processor and the problem ID and the
+ database.addNotice( artifact, ROLE_HINT, problem, reason );
+ }
+
+ private static void adjustDistributionArtifactHandler( Artifact artifact )
+ {
+ // need to tweak these as they aren't currently in the known type converters. TODO - add them in Maven
+ if ( "distribution-zip".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "zip" ) );
+ }
+ else if ( "distribution-tgz".equals( artifact.getType() ) )
+ {
+ artifact.setArtifactHandler( new DefaultArtifactHandler( "tar.gz" ) );
+ }
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/main/mdo/reporting.mdo b/archiva-reporting/archiva-report-manager/src/main/mdo/reporting.mdo
new file mode 100644
index 000000000..37ebd5615
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/main/mdo/reporting.mdo
@@ -0,0 +1,337 @@
+<?xml version="1.0" ?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<model>
+ <id>reporting</id>
+ <name>Reporting</name>
+ <description>
+ Storage database for reporting results in the repository.
+ </description>
+ <defaults>
+ <default>
+ <key>package</key>
+ <value>org.apache.maven.archiva.reporting.model</value>
+ </default>
+ </defaults>
+ <classes>
+ <class rootElement="true" xml.tagName="reporting" stash.storable="false">
+ <name>Reporting</name>
+ <version>1.0.0</version>
+ <fields>
+ <field>
+ <name>artifacts</name>
+ <version>1.0.0</version>
+ <association>
+ <type>ArtifactResults</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field>
+ <name>metadata</name>
+ <version>1.0.0</version>
+ <association>
+ <type>MetadataResults</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ </fields>
+ </class>
+ <class stash.storable="true"
+ jpox.use-identifiers-as-primary-key="true"
+ jpox.identity-type="application"
+ jpox.identity-class="ArtifactResultsKey">
+ <name>ArtifactResults</name>
+ <version>1.0.0</version>
+ <fields>
+ <field xml.attribute="true"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>groupId</name>
+ <identity>true</identity>
+ <version>1.0.0</version>
+ <type>String</type>
+ <required>true</required>
+ <description>
+ The group ID of the artifact in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>artifactId</name>
+ <version>1.0.0</version>
+ <identity>true</identity>
+ <type>String</type>
+ <required>true</required>
+ <description>
+ The artifact ID of the artifact in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>version</name>
+ <version>1.0.0</version>
+ <identity>true</identity>
+ <type>String</type>
+ <required>true</required>
+ <description>
+ The version of the artifact in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>artifactType</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <identity>true</identity>
+ <required>true</required>
+ <description>
+ The type of the artifact in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.nullValue="none"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>classifier</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <identity>true</identity>
+ <description>
+ The classifier of the artifact in the result.
+ </description>
+ </field>
+ <field>
+ <name>failures</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field>
+ <name>warnings</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field>
+ <name>notices</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ </fields>
+ </class>
+ <class stash.storable="true"
+ jpox.use-identifiers-as-primary-key="true"
+ jpox.identity-type="application"
+ jpox.identity-class="MetadataResultsKey">
+ <name>MetadataResults</name>
+ <version>1.0.0</version>
+ <fields>
+ <field xml.attribute="true"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>groupId</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <required>true</required>
+ <identity>true</identity>
+ <description>
+ The group ID of the metadata in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.nullValue="none"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>artifactId</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <identity>true</identity>
+ <description>
+ The artifact ID of the metadata in the result.
+ </description>
+ </field>
+ <field xml.attribute="true"
+ jpox.nullValue="none"
+ jpox.primary-key="true"
+ jpox.value-strategy="off"
+ jpox.persistence-modifier="persistent">
+ <name>version</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <identity>true</identity>
+ <description>
+ The version of the metadata in the result.
+ </description>
+ </field>
+ <field>
+ <name>failures</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field>
+ <name>warnings</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field>
+ <name>notices</name>
+ <version>1.0.0</version>
+ <association stash.part="true"
+ jpox.join="true"
+ java.init="field"
+ jpox.dependent="true"
+ java.generate-break="false"
+ java.generate-create="false">
+ <type>ResultReason</type>
+ <multiplicity>*</multiplicity>
+ </association>
+ </field>
+ <field xml.attribute="true">
+ <name>lastModified</name>
+ <version>1.0.0</version>
+ <type>long</type>
+ <identity>true</identity>
+ <description>
+ The time that the metadata was last modified.
+ </description>
+ </field>
+ </fields>
+ </class>
+ <class stash.storable="true">
+ <name>ResultReason</name>
+ <version>1.0.0</version>
+ <fields>
+ <field xml.attribute="true">
+ <name>reason</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <description>
+ The reason given for the result.
+ </description>
+ <required>true</required>
+ </field>
+ <field xml.attribute="true">
+ <name>processor</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <description>
+ The processor identifier for the report that triggered the problem. This matches the role-hint of a report
+ processor.
+ </description>
+ <required>true</required>
+ </field>
+ <field xml.attribute="true">
+ <name>problem</name>
+ <version>1.0.0</version>
+ <type>String</type>
+ <description>
+ The problem identifier for the problem that occurred. This is so that the processor can identify how to
+ fix the problem. It may be null if it cannot be fixed automatically.
+ </description>
+ </field>
+ </fields>
+
+ <codeSegments>
+ <codeSegment>
+ <version>1.0.0</version>
+ <code><![CDATA[
+ public boolean equals( Object obj )
+ {
+ if ( obj instanceof ResultReason )
+ {
+ if ( this == obj )
+ {
+ return true;
+ }
+ ResultReason rhs = (ResultReason) obj;
+ return new org.apache.commons.lang.builder.EqualsBuilder()
+ .append( problem, rhs.problem )
+ .append( processor, rhs.processor )
+ .append( reason, rhs.reason )
+ .isEquals();
+ }
+ return false;
+ }
+
+ public int hashCode()
+ {
+ return new org.apache.commons.lang.builder.HashCodeBuilder( 19, 43 )
+ .append( getReason() )
+ .append( getProcessor() )
+ .append( getProblem() )
+ .toHashCode();
+ }
+ ]]></code>
+ </codeSegment>
+ </codeSegments>
+
+ </class>
+ </classes>
+</model>
+
+
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AbstractRepositoryReportsTestCase.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AbstractRepositoryReportsTestCase.java
new file mode 100644
index 000000000..a0d6894ba
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AbstractRepositoryReportsTestCase.java
@@ -0,0 +1,154 @@
+package org.apache.maven.archiva.reporting;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.repository.ArtifactRepository;
+import org.apache.maven.artifact.repository.ArtifactRepositoryFactory;
+import org.apache.maven.artifact.repository.layout.ArtifactRepositoryLayout;
+import org.codehaus.plexus.PlexusTestCase;
+import org.codehaus.plexus.jdo.DefaultConfigurableJdoFactory;
+import org.codehaus.plexus.jdo.JdoFactory;
+import org.jpox.SchemaTool;
+
+import java.io.File;
+import java.net.URL;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Properties;
+
+import javax.jdo.PersistenceManager;
+import javax.jdo.PersistenceManagerFactory;
+
+/**
+ *
+ */
+public abstract class AbstractRepositoryReportsTestCase
+ extends PlexusTestCase
+{
+ /**
+ * This should only be used for the few that can't use the query layer.
+ */
+ protected ArtifactRepository repository;
+
+ private ArtifactFactory artifactFactory;
+
+ private ArtifactRepositoryFactory factory;
+
+ private ArtifactRepositoryLayout layout;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ setupJdoFactory();
+
+ File repositoryDirectory = getTestFile( "src/test/repository" );
+
+ factory = (ArtifactRepositoryFactory) lookup( ArtifactRepositoryFactory.ROLE );
+ layout = (ArtifactRepositoryLayout) lookup( ArtifactRepositoryLayout.ROLE, "default" );
+
+ repository = factory.createArtifactRepository( "repository", repositoryDirectory.toURL().toString(), layout,
+ null, null );
+ artifactFactory = (ArtifactFactory) lookup( ArtifactFactory.ROLE );
+ }
+
+ protected void setupJdoFactory()
+ throws Exception
+ {
+ DefaultConfigurableJdoFactory jdoFactory = (DefaultConfigurableJdoFactory) lookup( JdoFactory.ROLE, "archiva" );
+
+ jdoFactory.setPersistenceManagerFactoryClass( "org.jpox.PersistenceManagerFactoryImpl" ); //$NON-NLS-1$
+
+ jdoFactory.setDriverName( "org.hsqldb.jdbcDriver" ); //$NON-NLS-1$
+
+ jdoFactory.setUrl( "jdbc:hsqldb:mem:" + getName() ); //$NON-NLS-1$
+
+ jdoFactory.setUserName( "sa" ); //$NON-NLS-1$
+
+ jdoFactory.setPassword( "" ); //$NON-NLS-1$
+
+ jdoFactory.setProperty( "org.jpox.transactionIsolation", "READ_UNCOMMITTED" ); //$NON-NLS-1$ //$NON-NLS-2$
+
+ jdoFactory.setProperty( "org.jpox.poid.transactionIsolation", "READ_UNCOMMITTED" ); //$NON-NLS-1$ //$NON-NLS-2$
+
+ jdoFactory.setProperty( "org.jpox.autoCreateSchema", "true" ); //$NON-NLS-1$ //$NON-NLS-2$
+
+ jdoFactory.setProperty( "javax.jdo.PersistenceManagerFactoryClass", "org.jpox.PersistenceManagerFactoryImpl" );
+
+ Properties properties = jdoFactory.getProperties();
+
+ for ( Iterator it = properties.entrySet().iterator(); it.hasNext(); )
+ {
+ Map.Entry entry = (Map.Entry) it.next();
+
+ System.setProperty( (String) entry.getKey(), (String) entry.getValue() );
+ }
+
+ SchemaTool.createSchemaTables( new URL[] { getClass()
+ .getResource( "/org/apache/maven/archiva/reporting/model/package.jdo" ) }, new URL[] {}, null, false, null ); //$NON-NLS-1$
+
+ PersistenceManagerFactory pmf = jdoFactory.getPersistenceManagerFactory();
+
+ assertNotNull( pmf );
+
+ PersistenceManager pm = pmf.getPersistenceManager();
+
+ pm.close();
+ }
+
+ protected Artifact createArtifactFromRepository( File repository, String groupId, String artifactId, String version )
+ throws Exception
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( groupId, artifactId, version, "jar" );
+
+ artifact.setRepository( factory.createArtifactRepository( "repository", repository.toURL().toString(), layout,
+ null, null ) );
+
+ artifact.isSnapshot();
+
+ return artifact;
+ }
+
+ protected Artifact createArtifact( String groupId, String artifactId, String version )
+ {
+ return createArtifact( groupId, artifactId, version, "jar" );
+ }
+
+ protected Artifact createArtifact( String groupId, String artifactId, String version, String type )
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( groupId, artifactId, version, type );
+ artifact.setRepository( repository );
+ artifact.isSnapshot();
+ return artifact;
+ }
+
+ protected Artifact createArtifactWithClassifier( String groupId, String artifactId, String version, String type,
+ String classifier )
+ {
+ Artifact artifact = artifactFactory.createArtifactWithClassifier( groupId, artifactId, version, type,
+ classifier );
+ artifact.setRepository( repository );
+ return artifact;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AllTests.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AllTests.java
new file mode 100644
index 000000000..7894f3b81
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/AllTests.java
@@ -0,0 +1,45 @@
+package org.apache.maven.archiva.reporting;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * AllTests - Used to Aide in IDE based development.
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class AllTests
+{
+
+ public static Test suite()
+ {
+ TestSuite suite = new TestSuite( "Test for org.apache.maven.archiva.reporting.*" );
+ //$JUnit-BEGIN$
+ suite.addTest( org.apache.maven.archiva.reporting.database.AllTests.suite() );
+ suite.addTest( org.apache.maven.archiva.reporting.processor.AllTests.suite() );
+ suite.addTest( org.apache.maven.archiva.reporting.reporter.AllTests.suite() );
+ //$JUnit-END$
+ return suite;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/AllTests.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/AllTests.java
new file mode 100644
index 000000000..3e331465a
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/AllTests.java
@@ -0,0 +1,20 @@
+package org.apache.maven.archiva.reporting.database;
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+public class AllTests
+{
+
+ public static Test suite()
+ {
+ TestSuite suite = new TestSuite( "Test for org.apache.maven.archiva.reporting.database" );
+ //$JUnit-BEGIN$
+ suite.addTestSuite( ArtifactResultsDatabaseTest.class );
+ suite.addTestSuite( MetadataResultsDatabaseTest.class );
+ suite.addTestSuite( ReportingDatabaseTest.class );
+ //$JUnit-END$
+ return suite;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabaseTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabaseTest.java
new file mode 100644
index 000000000..7b816c643
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ArtifactResultsDatabaseTest.java
@@ -0,0 +1,171 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.DefaultArtifact;
+import org.apache.maven.artifact.versioning.VersionRange;
+
+import java.util.List;
+
+/**
+ * ArtifactResultsDatabaseTest
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class ArtifactResultsDatabaseTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private Artifact artifact;
+
+ private String processor, problem, reason;
+
+ private ArtifactResultsDatabase database;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+
+ artifact = new DefaultArtifact( "group", "artifact", VersionRange.createFromVersion( "1.0" ), "scope", "type",
+ "classifier", null );
+ processor = "processor";
+ problem = "problem";
+ reason = "reason";
+ }
+
+ protected void tearDown()
+ throws Exception
+ {
+ release( database );
+
+ super.tearDown();
+ }
+
+ public void testAddNoticeArtifactStringStringString()
+ {
+ database.addNotice( artifact, processor, problem, reason );
+ ArtifactResults artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumNotices() );
+ assertEquals( 1, artifactResults.getNotices().size() );
+
+ database.addNotice( artifact, processor, problem, reason );
+ artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumNotices() );
+ assertEquals( 1, artifactResults.getNotices().size() );
+ }
+
+ public void testAddWarningArtifactStringStringString()
+ {
+ database.addWarning( artifact, processor, problem, reason );
+ ArtifactResults artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumWarnings() );
+ assertEquals( 1, artifactResults.getWarnings().size() );
+
+ database.addWarning( artifact, processor, problem, reason );
+ artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumWarnings() );
+ assertEquals( 1, artifactResults.getWarnings().size() );
+ }
+
+ public void testAddFailureArtifactStringStringString()
+ {
+ database.addFailure( artifact, processor, problem, reason );
+ ArtifactResults artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 1, artifactResults.getFailures().size() );
+
+ database.addFailure( artifact, processor, problem, reason );
+ artifactResults = database.getArtifactResults( artifact );
+
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 1, artifactResults.getFailures().size() );
+ }
+
+ public void testFindArtifactResults()
+ {
+ String groupId = "org.test.group";
+
+ Artifact bar = createArtifact( "org.bar", "bar", "2.0" );
+ Artifact foo = createArtifact( groupId, "foo", "1.0" );
+ Artifact fooSources = createArtifactWithClassifier( groupId, "foo", "1.0", "jar", "sources" );
+ Artifact fooJavadoc = createArtifactWithClassifier( groupId, "foo", "1.0", "jar", "javadoc" );
+
+ database.addFailure( bar, processor, problem, "A reason that should not be found." );
+
+ String testprocessor = "test-processor";
+ String testproblem = "test-problem";
+
+ database.addFailure( foo, testprocessor, testproblem, "Test Reason on main jar." );
+ database.addFailure( foo, testprocessor, testproblem, "Someone mistook this for an actual reason." );
+ database.addWarning( foo, testprocessor, testproblem, "Congrats you have a test reason." );
+
+ database.addFailure( fooSources, testprocessor, testproblem, "Sources do not seem to match classes." );
+ database.addWarning( fooJavadoc, testprocessor, testproblem, "Javadoc content makes no sense." );
+
+ ArtifactResults artifactResults = database.getArtifactResults( foo );
+
+ assertEquals( 4, database.getNumFailures() );
+ assertEquals( 2, artifactResults.getFailures().size() );
+
+ List hits = database.findArtifactResults( groupId, "foo", "1.0" );
+ assertNotNull( hits );
+
+// for ( Iterator it = hits.iterator(); it.hasNext(); )
+// {
+// ArtifactResults result = (ArtifactResults) it.next();
+// System.out.println( " result: " + result.getGroupId() + ":" + result.getArtifactId() + ":"
+// + result.getVersion() + ":" + result.getClassifier() + ":" + result.getType() );
+//
+// for ( Iterator itmsgs = result.getFailures().iterator(); itmsgs.hasNext(); )
+// {
+// Result res = (Result) itmsgs.next();
+// String msg = (String) res.getReason();
+// System.out.println( " failure: " + msg );
+// }
+//
+// for ( Iterator itmsgs = result.getWarnings().iterator(); itmsgs.hasNext(); )
+// {
+// Result res = (Result) itmsgs.next();
+// String msg = (String) res.getReason();
+// System.out.println( " warning: " + msg );
+// }
+//
+// for ( Iterator itmsgs = result.getNotices().iterator(); itmsgs.hasNext(); )
+// {
+// Result res = (Result) itmsgs.next();
+// String msg = (String) res.getReason();
+// System.out.println( " notice: " + msg );
+// }
+// }
+
+ assertEquals( "Should find 3 artifacts", 3, hits.size() ); // 3 artifacts
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabaseTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabaseTest.java
new file mode 100644
index 000000000..acee25334
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/MetadataResultsDatabaseTest.java
@@ -0,0 +1,113 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.model.MetadataResults;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.DefaultArtifact;
+import org.apache.maven.artifact.repository.metadata.ArtifactRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.artifact.versioning.VersionRange;
+
+/**
+ * MetadataResultsDatabaseTest
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class MetadataResultsDatabaseTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private MetadataResultsDatabase database;
+
+ private RepositoryMetadata metadata;
+
+ private String processor, problem, reason;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ database = (MetadataResultsDatabase) lookup( MetadataResultsDatabase.ROLE );
+
+ Artifact artifact = new DefaultArtifact( "group", "artifact", VersionRange.createFromVersion( "1.0" ), "scope",
+ "type", "classifier", null );
+ metadata = new ArtifactRepositoryMetadata( artifact );
+
+ processor = "processor";
+ problem = "problem";
+ reason = "reason";
+ }
+
+ protected void tearDown()
+ throws Exception
+ {
+ release( database );
+
+ super.tearDown();
+ }
+
+ public void testAddNoticeRepositoryMetadataStringStringString()
+ {
+ database.addNotice( metadata, processor, problem, reason );
+ MetadataResults metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumNotices() );
+ assertEquals( 1, metadataResults.getNotices().size() );
+
+ database.addNotice( metadata, processor, problem, reason );
+ metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumNotices() );
+ assertEquals( 1, metadataResults.getNotices().size() );
+ }
+
+ public void testAddWarningRepositoryMetadataStringStringString()
+ {
+ database.addWarning( metadata, processor, problem, reason );
+ MetadataResults metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumWarnings() );
+ assertEquals( 1, metadataResults.getWarnings().size() );
+
+ database.addWarning( metadata, processor, problem, reason );
+ metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumWarnings() );
+ assertEquals( 1, metadataResults.getWarnings().size() );
+ }
+
+ public void testAddFailureRepositoryMetadataStringStringString()
+ {
+ database.addFailure( metadata, processor, problem, reason );
+ MetadataResults metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 1, metadataResults.getFailures().size() );
+
+ database.addFailure( metadata, processor, problem, reason );
+ metadataResults = database.getMetadataResults( metadata );
+
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 1, metadataResults.getFailures().size() );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ReportingDatabaseTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ReportingDatabaseTest.java
new file mode 100644
index 000000000..e03d59c4f
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/database/ReportingDatabaseTest.java
@@ -0,0 +1,55 @@
+package org.apache.maven.archiva.reporting.database;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+
+/**
+ * Test for {@link ReportingDatabase}.
+ *
+ * @author <a href="mailto:carlos@apache.org">Carlos Sanchez</a>
+ * @version $Id$
+ */
+public class ReportingDatabaseTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ReportingDatabase database;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+ database = (ReportingDatabase) lookup( ReportingDatabase.ROLE );
+ }
+
+ protected void tearDown()
+ throws Exception
+ {
+ release( database );
+ super.tearDown();
+ }
+
+ public void testLookup()
+ {
+ assertNotNull( "database should not be null.", database );
+ assertNotNull( "database.artifactDatabase should not be null.", database.getArtifactDatabase() );
+ assertNotNull( "database.metadataDatabase should not be null.", database.getMetadataDatabase() );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/AllTests.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/AllTests.java
new file mode 100644
index 000000000..953cb4c66
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/AllTests.java
@@ -0,0 +1,24 @@
+package org.apache.maven.archiva.reporting.processor;
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+public class AllTests
+{
+
+ public static Test suite()
+ {
+ TestSuite suite = new TestSuite( "Test for org.apache.maven.archiva.reporting.processor" );
+ //$JUnit-BEGIN$
+ suite.addTestSuite( LocationArtifactReportProcessorTest.class );
+ suite.addTestSuite( DuplicateArtifactFileReportProcessorTest.class );
+ suite.addTestSuite( OldSnapshotArtifactReportProcessorTest.class );
+ suite.addTestSuite( DependencyArtifactReportProcessorTest.class );
+ suite.addTestSuite( OldArtifactReportProcessorTest.class );
+ suite.addTestSuite( InvalidPomArtifactReportProcessorTest.class );
+ suite.addTestSuite( BadMetadataReportProcessorTest.class );
+ //$JUnit-END$
+ return suite;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessorTest.java
new file mode 100644
index 000000000..fb9ff2581
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/BadMetadataReportProcessorTest.java
@@ -0,0 +1,454 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.MetadataResultsDatabase;
+import org.apache.maven.archiva.reporting.model.MetadataResults;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.repository.metadata.ArtifactRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.GroupRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.Plugin;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.Snapshot;
+import org.apache.maven.artifact.repository.metadata.SnapshotArtifactRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.Versioning;
+
+import java.util.Iterator;
+
+/**
+ * BadMetadataReportProcessorTest
+ *
+ * @version $Id$
+ */
+public class BadMetadataReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ArtifactFactory artifactFactory;
+
+ private MetadataReportProcessor badMetadataReportProcessor;
+
+ private MetadataResultsDatabase database;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ artifactFactory = (ArtifactFactory) lookup( ArtifactFactory.ROLE );
+
+ database = (MetadataResultsDatabase) lookup( MetadataResultsDatabase.ROLE );
+
+ badMetadataReportProcessor = (MetadataReportProcessor) lookup( MetadataReportProcessor.ROLE, "bad-metadata" );
+ }
+
+ protected void tearDown()
+ throws Exception
+ {
+ release( artifactFactory );
+ release( badMetadataReportProcessor );
+ super.tearDown();
+ }
+
+ public void testMetadataMissingLastUpdated()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.addVersion( "1.0-alpha-2" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( metadata, results );
+ assertEquals( "check reason", "Missing lastUpdated element inside the metadata.", result.getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testMetadataMissingVersioning()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, null );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ assertMetadata( metadata, results );
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( "check reason", "Missing lastUpdated element inside the metadata.", result.getReason() );
+ result = (ResultReason) failures.next();
+ boolean alpha1First = false;
+ if ( result.getReason().indexOf( "alpha-1" ) > 0 )
+ {
+ alpha1First = true;
+ }
+ if ( alpha1First )
+ {
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-1 found in the repository but missing in the metadata.", result
+ .getReason() );
+ }
+ else
+ {
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-2 found in the repository but missing in the metadata.", result
+ .getReason() );
+ }
+ result = (ResultReason) failures.next();
+ if ( !alpha1First )
+ {
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-1 found in the repository but missing in the metadata.", result
+ .getReason() );
+ }
+ else
+ {
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-2 found in the repository but missing in the metadata.", result
+ .getReason() );
+ }
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testSnapshotMetadataMissingVersioning()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "snapshot-artifact",
+ "1.0-alpha-1-SNAPSHOT", "type" );
+
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ assertMetadata( metadata, results );
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( "check reason", "Missing lastUpdated element inside the metadata.", result.getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testMetadataValidVersions()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.addVersion( "1.0-alpha-2" );
+ versioning.setLastUpdated( "20050611.202020" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertFalse( "check there are no failures", failures.hasNext() );
+ }
+
+ public void testMetadataMissingADirectory()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.setLastUpdated( "20050611.202020" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( metadata, results );
+ // TODO: should be more robust
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-2 found in the repository but missing in the metadata.", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testMetadataInvalidArtifactVersion()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.addVersion( "1.0-alpha-2" );
+ versioning.addVersion( "1.0-alpha-3" );
+ versioning.setLastUpdated( "20050611.202020" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( metadata, results );
+ // TODO: should be more robust
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-3 is present in metadata but missing in the repository.", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testMoreThanOneMetadataVersionErrors()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.addVersion( "1.0-alpha-3" );
+ versioning.setLastUpdated( "20050611.202020" );
+
+ RepositoryMetadata metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( metadata, results );
+ // TODO: should be more robust
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-3 is present in metadata but missing in the repository.", result
+ .getReason() );
+ assertTrue( "check there is a 2nd failure", failures.hasNext() );
+ result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason",
+ "Artifact version 1.0-alpha-2 found in the repository but missing in the metadata.", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testValidPluginMetadata()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", "default" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "snapshot-artifact", "default2" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertFalse( "check there are no failures", failures.hasNext() );
+ }
+
+ public void testMissingMetadataPlugin()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", "default" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "snapshot-artifact", "default2" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "missing-plugin", "default3" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Metadata plugin missing-plugin not found in the repository", result.getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testIncompletePluginMetadata()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", "default" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Plugin snapshot-artifact is present in the repository but "
+ + "missing in the metadata.", result.getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testInvalidPluginArtifactId()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", "default" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "snapshot-artifact", "default2" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( null, "default3" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "", "default4" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Missing or empty artifactId in group metadata for plugin default3", result
+ .getReason() );
+ assertTrue( "check there is a 2nd failure", failures.hasNext() );
+ result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Missing or empty artifactId in group metadata for plugin default4", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testInvalidPluginPrefix()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", null ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "snapshot-artifact", "" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Missing or empty plugin prefix for artifactId artifactId.", result.getReason() );
+ assertTrue( "check there is a 2nd failure", failures.hasNext() );
+ result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Missing or empty plugin prefix for artifactId snapshot-artifact.", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testDuplicatePluginPrefixes()
+ {
+ RepositoryMetadata metadata = new GroupRepositoryMetadata( "groupId" );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "artifactId", "default" ) );
+ metadata.getMetadata().addPlugin( createMetadataPlugin( "snapshot-artifact", "default" ) );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ // TODO: should be more robust
+ assertEquals( "check reason", "Duplicate plugin prefix found: default.", result.getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ public void testValidSnapshotMetadata()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "snapshot-artifact",
+ "1.0-alpha-1-SNAPSHOT", "type" );
+
+ Snapshot snapshot = new Snapshot();
+ snapshot.setBuildNumber( 1 );
+ snapshot.setTimestamp( "20050611.202024" );
+
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact, snapshot );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertFalse( "check there are no failures", failures.hasNext() );
+ }
+
+ public void testInvalidSnapshotMetadata()
+ {
+ Artifact artifact = artifactFactory.createBuildArtifact( "groupId", "snapshot-artifact",
+ "1.0-alpha-1-SNAPSHOT", "type" );
+
+ Snapshot snapshot = new Snapshot();
+ snapshot.setBuildNumber( 2 );
+ snapshot.setTimestamp( "20050611.202024" );
+
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact, snapshot );
+
+ badMetadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( metadata, results );
+ // TODO: should be more robust
+ assertEquals( "check reason", "Snapshot artifact 1.0-alpha-1-20050611.202024-2 does not exist.", result
+ .getReason() );
+ assertFalse( "check no more failures", failures.hasNext() );
+ }
+
+ private static void assertMetadata( RepositoryMetadata metadata, MetadataResults results )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The MetadataResults object has a complex primary key consisting of groupId, artifactId, and version.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+ assertEquals( "check metadata", StringUtils.defaultString( metadata.getGroupId() ), results.getGroupId() );
+ assertEquals( "check metadata", StringUtils.defaultString( metadata.getArtifactId() ), results.getArtifactId() );
+ assertEquals( "check metadata", StringUtils.defaultString( metadata.getBaseVersion() ), results.getVersion() );
+ }
+
+ private Plugin createMetadataPlugin( String artifactId, String prefix )
+ {
+ Plugin plugin = new Plugin();
+ plugin.setArtifactId( artifactId );
+ plugin.setName( artifactId );
+ plugin.setPrefix( prefix );
+ return plugin;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessorTest.java
new file mode 100644
index 000000000..a1598edaf
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DependencyArtifactReportProcessorTest.java
@@ -0,0 +1,303 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.model.Dependency;
+import org.apache.maven.model.Model;
+
+import java.util.Iterator;
+
+/**
+ *
+ */
+public class DependencyArtifactReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private static final String VALID_GROUP_ID = "groupId";
+
+ private static final String VALID_ARTIFACT_ID = "artifactId";
+
+ private static final String VALID_VERSION = "1.0-alpha-1";
+
+ private ArtifactResultsDatabase database;
+
+ private Model model;
+
+ private ArtifactReportProcessor processor;
+
+ private ArtifactFactory artifactFactory;
+
+ private static final String INVALID = "invalid";
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+ model = new Model();
+ artifactFactory = (ArtifactFactory) lookup( ArtifactFactory.ROLE );
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ processor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "dependency" );
+ }
+
+ public void testArtifactFoundButNoDirectDependencies()
+ {
+ Artifact artifact = createValidArtifact();
+ processor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ }
+
+ private Artifact createValidArtifact()
+ {
+ Artifact projectArtifact = artifactFactory.createProjectArtifact( VALID_GROUP_ID, VALID_ARTIFACT_ID,
+ VALID_VERSION );
+ projectArtifact.setRepository( repository );
+ return projectArtifact;
+ }
+
+ public void testArtifactNotFound()
+ {
+ Artifact artifact = artifactFactory.createProjectArtifact( INVALID, INVALID, INVALID );
+ artifact.setRepository( repository );
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( "Artifact does not exist in the repository", result.getReason() );
+ }
+
+ public void testValidArtifactWithNullDependency()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createValidDependency();
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ }
+
+ private Dependency createValidDependency()
+ {
+ return createDependency( VALID_GROUP_ID, VALID_ARTIFACT_ID, VALID_VERSION );
+ }
+
+ public void testValidArtifactWithValidSingleDependency()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createValidDependency();
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ }
+
+ public void testValidArtifactWithValidMultipleDependencies()
+ {
+ Dependency dependency = createValidDependency();
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+
+ Artifact artifact = createValidArtifact();
+ processor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ }
+
+ public void testValidArtifactWithAnInvalidDependency()
+ {
+ Dependency dependency = createValidDependency();
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( dependency );
+ model.addDependency( createDependency( INVALID, INVALID, INVALID ) );
+
+ Artifact artifact = createValidArtifact();
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyNotFoundMessage( createDependency( INVALID, INVALID, INVALID ) ), result.getReason() );
+ }
+
+ public void testValidArtifactWithInvalidDependencyGroupId()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( INVALID, VALID_ARTIFACT_ID, VALID_VERSION );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyNotFoundMessage( dependency ), result.getReason() );
+ }
+
+ private Dependency createDependency( String o, String valid, String s )
+ {
+ Dependency dependency = new Dependency();
+ dependency.setGroupId( o );
+ dependency.setArtifactId( valid );
+ dependency.setVersion( s );
+ return dependency;
+ }
+
+ public void testValidArtifactWithInvalidDependencyArtifactId()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( VALID_GROUP_ID, INVALID, VALID_VERSION );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyNotFoundMessage( dependency ), result.getReason() );
+ }
+
+ public void testValidArtifactWithIncorrectDependencyVersion()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( VALID_GROUP_ID, VALID_ARTIFACT_ID, INVALID );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyNotFoundMessage( dependency ), result.getReason() );
+ }
+
+ public void testValidArtifactWithInvalidDependencyVersion()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( VALID_GROUP_ID, VALID_ARTIFACT_ID, "[" );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyVersionInvalidMessage( dependency, "[" ), result.getReason() );
+ }
+
+ public void testValidArtifactWithInvalidDependencyVersionRange()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( VALID_GROUP_ID, VALID_ARTIFACT_ID, "[1.0,)" );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+ }
+
+ public void testValidArtifactWithMissingDependencyVersion()
+ {
+ Artifact artifact = createValidArtifact();
+
+ Dependency dependency = createDependency( VALID_GROUP_ID, VALID_ARTIFACT_ID, null );
+ model.addDependency( dependency );
+
+ processor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( 0, database.getNumNotices() );
+
+ Iterator failures = database.getIterator();
+ ArtifactResults results = (ArtifactResults) failures.next();
+ assertFalse( failures.hasNext() );
+ failures = results.getFailures().iterator();
+ ResultReason result = (ResultReason) failures.next();
+ assertEquals( getDependencyVersionInvalidMessage( dependency, null ), result.getReason() );
+ }
+
+ private String getDependencyVersionInvalidMessage( Dependency dependency, String version )
+ {
+ return "Artifact's dependency " + getDependencyString( dependency ) + " contains an invalid version " + version;
+ }
+
+ private static String getDependencyString( Dependency dependency )
+ {
+ return DependencyArtifactReportProcessor.getDependencyString( dependency );
+ }
+
+ private String getDependencyNotFoundMessage( Dependency dependency )
+ {
+ return "Artifact's dependency " + getDependencyString( dependency ) + " does not exist in the repository";
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.java
new file mode 100644
index 000000000..6ab299a5c
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.java
@@ -0,0 +1,150 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.FileUtils;
+import org.apache.maven.archiva.indexer.RepositoryArtifactIndex;
+import org.apache.maven.archiva.indexer.RepositoryArtifactIndexFactory;
+import org.apache.maven.archiva.indexer.record.RepositoryIndexRecordFactory;
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.model.Model;
+
+import java.io.File;
+import java.util.Collections;
+
+/**
+ * @author Edwin Punzalan
+ */
+public class DuplicateArtifactFileReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private Artifact artifact;
+
+ private Model model;
+
+ private ArtifactReportProcessor processor;
+
+ private ArtifactFactory artifactFactory;
+
+ File indexDirectory;
+
+ private ArtifactResultsDatabase database;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ indexDirectory = getTestFile( "target/indexDirectory" );
+ FileUtils.deleteDirectory( indexDirectory );
+
+ artifactFactory = (ArtifactFactory) lookup( ArtifactFactory.ROLE );
+
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+
+ artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "1.0-alpha-1", "jar" );
+
+ model = new Model();
+
+ RepositoryArtifactIndexFactory factory =
+ (RepositoryArtifactIndexFactory) lookup( RepositoryArtifactIndexFactory.ROLE, "lucene" );
+
+ RepositoryArtifactIndex index = factory.createStandardIndex( indexDirectory );
+
+ RepositoryIndexRecordFactory recordFactory =
+ (RepositoryIndexRecordFactory) lookup( RepositoryIndexRecordFactory.ROLE, "standard" );
+
+ index.indexRecords( Collections.singletonList( recordFactory.createRecord( artifact ) ) );
+
+ processor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "duplicate" );
+ }
+
+ public void testNullArtifactFile()
+ throws Exception
+ {
+ artifact.setFile( null );
+
+ processor.processArtifact( artifact, model );
+
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ assertEquals( "Check warnings", 1, database.getNumWarnings() );
+ assertEquals( "Check no failures", 0, database.getNumFailures() );
+ }
+
+ public void testSuccessOnAlreadyIndexedArtifact()
+ throws Exception
+ {
+ processor.processArtifact( artifact, model );
+
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ assertEquals( "Check warnings", 0, database.getNumWarnings() );
+ assertEquals( "Check no failures", 0, database.getNumFailures() );
+ }
+
+ public void testSuccessOnDifferentGroupId()
+ throws Exception
+ {
+ artifact.setGroupId( "different.groupId" );
+ processor.processArtifact( artifact, model );
+
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ assertEquals( "Check warnings", 0, database.getNumWarnings() );
+ assertEquals( "Check no failures", 0, database.getNumFailures() );
+ }
+
+ public void testSuccessOnNewArtifact()
+ throws Exception
+ {
+ Artifact newArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "1.0-alpha-1", "pom" );
+
+ processor.processArtifact( newArtifact, model );
+
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ assertEquals( "Check warnings", 0, database.getNumWarnings() );
+ assertEquals( "Check no failures", 0, database.getNumFailures() );
+ }
+
+ public void testFailure()
+ throws Exception
+ {
+ Artifact duplicate = createArtifact( artifact.getGroupId(), "snapshot-artifact", "1.0-alpha-1-SNAPSHOT",
+ artifact.getVersion(), artifact.getType() );
+ duplicate.setFile( artifact.getFile() );
+
+ processor.processArtifact( duplicate, model );
+
+ assertEquals( "Check warnings", 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ assertEquals( "Check no failures", 1, database.getNumFailures() );
+ }
+
+ private Artifact createArtifact( String groupId, String artifactId, String baseVersion, String version,
+ String type )
+ {
+ Artifact artifact = artifactFactory.createArtifact( groupId, artifactId, version, null, type );
+ artifact.setBaseVersion( baseVersion );
+ artifact.setRepository( repository );
+ artifact.setFile( new File( repository.getBasedir(), repository.pathOf( artifact ) ) );
+ return artifact;
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessorTest.java
new file mode 100644
index 000000000..f37bd20ac
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/InvalidPomArtifactReportProcessorTest.java
@@ -0,0 +1,82 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+
+/**
+ * This class tests the InvalidPomArtifactReportProcessor class.
+ */
+public class InvalidPomArtifactReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private ArtifactResultsDatabase database;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "invalid-pom" );
+ }
+
+ /**
+ * Test the InvalidPomArtifactReportProcessor when the artifact is an invalid pom.
+ */
+ public void testInvalidPomArtifactReportProcessorFailure()
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "artifactId", "1.0-alpha-3", "pom" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 1, database.getNumFailures() );
+ }
+
+
+ /**
+ * Test the InvalidPomArtifactReportProcessor when the artifact is a valid pom.
+ */
+ public void testInvalidPomArtifactReportProcessorSuccess()
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-2", "pom" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+
+ /**
+ * Test the InvalidPomArtifactReportProcessor when the artifact is not a pom.
+ */
+ public void testNotAPomArtifactReportProcessorSuccess()
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "jar" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessorTest.java
new file mode 100644
index 000000000..134295cb9
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/LocationArtifactReportProcessorTest.java
@@ -0,0 +1,227 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.model.Model;
+import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
+import org.codehaus.plexus.util.xml.pull.XmlPullParserException;
+
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.Reader;
+
+/**
+ * This class tests the LocationArtifactReportProcessor.
+ */
+public class LocationArtifactReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private ArtifactResultsDatabase database;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "artifact-location" );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact's physical location matches the location specified
+ * both in the file system pom and in the pom included in the package.
+ */
+ public void testPackagedPomLocationArtifactReporterSuccess()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "maven-model", "2.0" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is in the location specified in the
+ * file system pom (but the jar file does not have a pom included in its package).
+ */
+ public void testLocationArtifactReporterSuccess()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1" );
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is in the location specified in the
+ * file system pom, but the pom itself is passed in.
+ */
+ public void testLocationArtifactReporterSuccessPom()
+ throws IOException, XmlPullParserException
+ {
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( pomArtifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is in the location specified in the
+ * file system pom, with a classifier.
+ */
+ public void testLocationArtifactReporterSuccessClassifier()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "java-source" );
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is in the location specified in the
+ * file system pom, with a classifier.
+ */
+ public void testLocationArtifactReporterSuccessZip()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact =
+ createArtifactWithClassifier( "groupId", "artifactId", "1.0-alpha-1", "distribution-zip", "src" );
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is in the location specified in the
+ * file system pom, with a classifier.
+ */
+ public void testLocationArtifactReporterSuccessTgz()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact =
+ createArtifactWithClassifier( "groupId", "artifactId", "1.0-alpha-1", "distribution-tgz", "src" );
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact is not in the location specified
+ * in the file system pom.
+ */
+ public void testLocationArtifactReporterFailure()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-2" );
+ Artifact pomArtifact = createArtifact( "groupId", "artifactId", "1.0-alpha-2", "pom" );
+
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+
+ assertEquals( 1, database.getNumFailures() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact's physical location does not match the
+ * location in the file system pom but instead matches the specified location in the packaged pom.
+ */
+ public void testFsPomArtifactMatchFailure()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "maven-archiver", "2.0" );
+
+ Artifact pomArtifact = createArtifact( "org.apache.maven", "maven-archiver", "2.0", "pom" );
+ Model model = readPom( repository.pathOf( pomArtifact ) );
+ artifactReportProcessor.processArtifact( artifact, model );
+ assertEquals( 1, database.getNumFailures() );
+ }
+
+ private Model readPom( String path )
+ throws IOException, XmlPullParserException
+ {
+ Reader reader = new FileReader( new File( repository.getBasedir(), path ) );
+ Model model = new MavenXpp3Reader().read( reader );
+ // hokey inheritence to avoid some errors right now
+ if ( model.getGroupId() == null )
+ {
+ model.setGroupId( model.getParent().getGroupId() );
+ }
+ if ( model.getVersion() == null )
+ {
+ model.setVersion( model.getParent().getVersion() );
+ }
+ return model;
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact's physical location does not match the
+ * location specified in the packaged pom but matches the location specified in the file system pom.
+ */
+ public void testPkgPomArtifactMatchFailure()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "maven-monitor", "2.1" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 1, database.getNumFailures() );
+ }
+
+ /**
+ * Test the LocationArtifactReporter when the artifact's physical location does not match both the
+ * location specified in the packaged pom and the location specified in the file system pom.
+ */
+ public void testBothPomArtifactMatchFailure()
+ throws IOException, XmlPullParserException
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "maven-project", "2.1" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 1, database.getNumFailures() );
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.java
new file mode 100644
index 000000000..affabb19b
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.java
@@ -0,0 +1,99 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+import org.codehaus.plexus.util.FileUtils;
+
+import java.io.File;
+import java.util.Iterator;
+
+/**
+ * This class tests the OldArtifactReportProcessor.
+ */
+public class OldArtifactReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private ArtifactResultsDatabase database;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "old-artifact" );
+ }
+
+ public void testOldArtifact()
+ {
+ Artifact artifact = createArtifact( "org.apache.maven", "maven-model", "2.0" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check notices", 1, database.getNumNotices() );
+ ArtifactResults results = (ArtifactResults) database.getIterator().next();
+ assertEquals( artifact.getArtifactId(), results.getArtifactId() );
+ assertEquals( artifact.getGroupId(), results.getGroupId() );
+ assertEquals( artifact.getVersion(), results.getVersion() );
+ assertEquals( 1, results.getNotices().size() );
+ Iterator i = results.getNotices().iterator();
+ ResultReason result = (ResultReason) i.next();
+ assertEquals( "old-artifact", result.getProcessor() );
+ }
+
+ public void testNewArtifact()
+ throws Exception
+ {
+ File repository = getTestFile( "target/test-repository" );
+
+ FileUtils.copyDirectoryStructure( getTestFile( "src/test/repository/groupId" ),
+ new File( repository, "groupId" ) );
+
+ Artifact artifact = createArtifactFromRepository( repository, "groupId", "artifactId", "1.0-alpha-1" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ public void testMissingArtifact()
+ throws Exception
+ {
+ Artifact artifact = createArtifact( "foo", "bar", "XP" );
+
+ try
+ {
+ artifactReportProcessor.processArtifact( artifact, null );
+ fail( "Should not have passed" );
+ }
+ catch ( IllegalStateException e )
+ {
+ assertTrue( true );
+ }
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.java
new file mode 100644
index 000000000..440b63149
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.java
@@ -0,0 +1,170 @@
+package org.apache.maven.archiva.reporting.processor;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.FileUtils;
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+
+import java.io.File;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.Iterator;
+
+/**
+ * This class tests the OldArtifactReportProcessor.
+ */
+public class OldSnapshotArtifactReportProcessorTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private ArtifactResultsDatabase database;
+
+ private File tempRepository;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE,
+ "old-snapshot-artifact" );
+
+ tempRepository = getTestFile( "target/test-repository" );
+ FileUtils.deleteDirectory( tempRepository );
+ }
+
+ public void testOldSnapshotArtifact()
+ {
+ Artifact artifact = createArtifact( "groupId", "snapshot-artifact", "1.0-alpha-1-20050611.202024-1", "pom" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check notices", 1, database.getNumNotices() );
+ Iterator artifactIterator = database.getIterator();
+ assertArtifactResults( artifactIterator, artifact );
+ }
+
+ private static void assertArtifactResults( Iterator artifactIterator, Artifact artifact )
+ {
+ ArtifactResults results = (ArtifactResults) artifactIterator.next();
+ assertEquals( artifact.getArtifactId(), results.getArtifactId() );
+ assertEquals( artifact.getGroupId(), results.getGroupId() );
+ assertEquals( artifact.getVersion(), results.getVersion() );
+ assertFalse( artifact.getVersion().indexOf( "SNAPSHOT" ) >= 0 );
+ assertEquals( 1, results.getNotices().size() );
+ Iterator i = results.getNotices().iterator();
+ ResultReason result = (ResultReason) i.next();
+ assertEquals( "old-snapshot-artifact", result.getProcessor() );
+ }
+
+ public void testSNAPSHOTArtifact()
+ {
+ Artifact artifact = createArtifact( "groupId", "snapshot-artifact", "1.0-alpha-1-SNAPSHOT", "pom" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ public void testNonSnapshotArtifact()
+ {
+ Artifact artifact = createArtifact( "groupId", "artifactId", "1.0-alpha-1" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ public void testNewSnapshotArtifact()
+ throws Exception
+ {
+ File repository = getTestFile( "target/test-repository" );
+
+ File dir = new File( repository, "groupId/artifactId/1.0-alpha-1-SNAPSHOT" );
+ dir.mkdirs();
+
+ String date = new SimpleDateFormat( "yyyyMMdd.HHmmss" ).format( new Date() );
+ FileUtils.writeStringToFile( new File( dir, "artifactId-1.0-alpha-1-" + date + "-1.jar" ), "foo", null );
+
+ Artifact artifact = createArtifactFromRepository( repository, "groupId", "artifactId", "1.0-alpha-1-" + date
+ + "-1" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check no notices", 0, database.getNumNotices() );
+ }
+
+ public void testTooManySnapshotArtifact()
+ throws Exception
+ {
+ File dir = new File( tempRepository, "groupId/artifactId/1.0-alpha-1-SNAPSHOT" );
+ dir.mkdirs();
+
+ String date = new SimpleDateFormat( "yyyyMMdd.HHmmss" ).format( new Date() );
+ for ( int i = 1; i <= 5; i++ )
+ {
+ FileUtils.writeStringToFile( new File( dir, "artifactId-1.0-alpha-1-" + date + "-" + i + ".jar" ), "foo",
+ null );
+ }
+
+ for ( int i = 1; i <= 5; i++ )
+ {
+ Artifact artifact = createArtifactFromRepository( tempRepository, "groupId", "artifactId", "1.0-alpha-1-"
+ + date + "-" + i );
+ artifactReportProcessor.processArtifact( artifact, null );
+ }
+
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "Check notices", 3, database.getNumNotices() );
+ Iterator artifactIterator = database.getIterator();
+ for ( int i = 1; i <= 3; i++ )
+ {
+ String version = "1.0-alpha-1-" + date + "-" + i;
+ Artifact artifact = createArtifactFromRepository( tempRepository, "groupId", "artifactId", version );
+ assertArtifactResults( artifactIterator, artifact );
+ }
+ }
+
+ public void testMissingArtifact()
+ throws Exception
+ {
+ Artifact artifact = createArtifact( "foo", "bar", "XP" );
+
+ try
+ {
+ artifactReportProcessor.processArtifact( artifact, null );
+ fail( "Should not have passed" );
+ }
+ catch ( IllegalStateException e )
+ {
+ assertTrue( true );
+ }
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AbstractChecksumArtifactReporterTestCase.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AbstractChecksumArtifactReporterTestCase.java
new file mode 100644
index 000000000..3fd30bcdd
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AbstractChecksumArtifactReporterTestCase.java
@@ -0,0 +1,287 @@
+package org.apache.maven.archiva.reporting.reporter;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.io.FileUtils;
+import org.apache.commons.io.IOUtils;
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.codehaus.plexus.digest.Digester;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.BufferedOutputStream;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.io.OutputStreamWriter;
+import java.util.jar.JarEntry;
+import java.util.jar.JarOutputStream;
+
+/**
+ * This class creates the artifact and metadata files used for testing the ChecksumArtifactReportProcessor.
+ * It is extended by ChecksumArtifactReporterTest class.
+ */
+public abstract class AbstractChecksumArtifactReporterTestCase
+ extends AbstractRepositoryReportsTestCase
+{
+ private static final String[] validArtifactChecksumJars = {"validArtifact-1.0"};
+
+ private static final String[] invalidArtifactChecksumJars = {"invalidArtifact-1.0"};
+
+ private static final String metadataChecksumFilename = "maven-metadata";
+
+ private Digester sha1Digest;
+
+ private Digester md5Digest;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ sha1Digest = (Digester) lookup( Digester.ROLE, "sha1" );
+ md5Digest = (Digester) lookup( Digester.ROLE, "md5" );
+ }
+
+ /**
+ * Create checksum files.
+ *
+ * @param type The type of checksum file to be created.
+ */
+ protected void createChecksumFile( String type )
+ throws DigesterException, IOException
+ {
+ //loop through the valid artifact names..
+ if ( "VALID".equals( type ) )
+ {
+ for ( int i = 0; i < validArtifactChecksumJars.length; i++ )
+ {
+ writeChecksumFile( "checksumTest/", validArtifactChecksumJars[i], "jar", true );
+ }
+ }
+ else if ( "INVALID".equals( type ) )
+ {
+ for ( int i = 0; i < invalidArtifactChecksumJars.length; i++ )
+ {
+ writeChecksumFile( "checksumTest/", invalidArtifactChecksumJars[i], "jar", false );
+ }
+ }
+ }
+
+ /**
+ * Create checksum files for metadata.
+ *
+ * @param type The type of checksum to be created. (Valid or invalid)
+ */
+ protected void createMetadataFile( String type )
+ throws DigesterException, IOException
+ {
+ //loop through the valid artifact names..
+ if ( "VALID".equals( type ) )
+ {
+ writeMetadataFile( "checksumTest/validArtifact/1.0/", metadataChecksumFilename, "xml", true );
+ writeMetadataFile( "checksumTest/validArtifact/", metadataChecksumFilename, "xml", true );
+ writeMetadataFile( "checksumTest/", metadataChecksumFilename, "xml", true );
+ }
+ else if ( "INVALID".equals( type ) )
+ {
+ writeMetadataFile( "checksumTest/invalidArtifact/1.0/", metadataChecksumFilename, "xml", false );
+ }
+ }
+
+ /**
+ * Create artifact together with its checksums.
+ *
+ * @param relativePath The groupId
+ * @param filename The filename of the artifact to be created.
+ * @param type The file type (JAR)
+ * @param isValid Indicates whether the checksum to be created is valid or not.
+ */
+ private void writeChecksumFile( String relativePath, String filename, String type, boolean isValid )
+ throws IOException, DigesterException
+ {
+ //Initialize variables for creating jar files
+ String repoUrl = repository.getBasedir();
+
+ String dirs = filename.replace( '-', '/' );
+ //create the group level directory of the artifact
+ File dirFiles = new File( repoUrl + relativePath + dirs );
+
+ if ( dirFiles.mkdirs() )
+ {
+ // create a jar file
+ String path = repoUrl + relativePath + dirs + "/" + filename + "." + type;
+ FileOutputStream f = new FileOutputStream( path );
+ JarOutputStream out = new JarOutputStream( new BufferedOutputStream( f ) );
+
+ // jar sample.txt
+ String filename1 = repoUrl + relativePath + dirs + "/sample.txt";
+ createSampleFile( filename1 );
+
+ BufferedReader in = new BufferedReader( new FileReader( filename1 ) );
+ out.putNextEntry( new JarEntry( filename1 ) );
+ IOUtils.copy( in, out );
+ in.close();
+ out.close();
+
+ //Create md5 and sha-1 checksum files..
+
+ File file = new File( path + ".md5" );
+ OutputStream os = new FileOutputStream( file );
+ OutputStreamWriter osw = new OutputStreamWriter( os );
+ String sum = md5Digest.calc( new File( path ) );
+ if ( !isValid )
+ {
+ osw.write( sum + "1" );
+ }
+ else
+ {
+ osw.write( sum );
+ }
+ osw.close();
+
+ file = new File( path + ".sha1" );
+ os = new FileOutputStream( file );
+ osw = new OutputStreamWriter( os );
+ String sha1sum = sha1Digest.calc( new File( path ) );
+ if ( !isValid )
+ {
+ osw.write( sha1sum + "2" );
+ }
+ else
+ {
+ osw.write( sha1sum );
+ }
+ osw.close();
+ }
+ }
+
+ /**
+ * Create metadata file together with its checksums.
+ *
+ * @param relativePath The groupId
+ * @param filename The filename of the artifact to be created.
+ * @param type The file type (JAR)
+ * @param isValid Indicates whether the checksum to be created is valid or not.
+ */
+ private void writeMetadataFile( String relativePath, String filename, String type, boolean isValid )
+ throws IOException, DigesterException
+ {
+ //create checksum for the metadata file..
+ String repoUrl = repository.getBasedir();
+ String url = repository.getBasedir() + "/" + filename + "." + type;
+
+ String path = repoUrl + relativePath + filename + "." + type;
+ FileUtils.copyFile( new File( url ), new File( path ) );
+
+ //Create md5 and sha-1 checksum files..
+ File file = new File( path + ".md5" );
+ OutputStream os = new FileOutputStream( file );
+ OutputStreamWriter osw = new OutputStreamWriter( os );
+ String md5sum = md5Digest.calc( new File( path ) );
+ if ( !isValid )
+ {
+ osw.write( md5sum + "1" );
+ }
+ else
+ {
+ osw.write( md5sum );
+ }
+ osw.close();
+
+ file = new File( path + ".sha1" );
+ os = new FileOutputStream( file );
+ osw = new OutputStreamWriter( os );
+ String sha1sum = sha1Digest.calc( new File( path ) );
+ if ( !isValid )
+ {
+ osw.write( sha1sum + "2" );
+ }
+ else
+ {
+ osw.write( sha1sum );
+ }
+ osw.close();
+ }
+
+ /**
+ * Create the sample file that will be included in the jar.
+ *
+ * @param filename
+ */
+ private void createSampleFile( String filename )
+ throws IOException
+ {
+ File file = new File( filename );
+ OutputStream os = new FileOutputStream( file );
+ OutputStreamWriter osw = new OutputStreamWriter( os );
+ osw.write( "This is the content of the sample file that will be included in the jar file." );
+ osw.close();
+ }
+
+ /**
+ * Delete the test directory created in the repository.
+ *
+ * @param dir The directory to be deleted.
+ */
+ protected void deleteTestDirectory( File dir )
+ {
+ try
+ {
+ FileUtils.deleteDirectory( dir );
+ }
+ catch ( IOException e )
+ {
+ // ignore
+ }
+ }
+
+ private void deleteFile( String filename )
+ {
+ File f = new File( filename );
+ f.delete();
+ }
+
+ protected void deleteChecksumFiles( String type )
+ {
+ //delete valid checksum files of artifacts created
+ for ( int i = 0; i < validArtifactChecksumJars.length; i++ )
+ {
+ deleteFile( repository.getBasedir() + "checksumTest/" + validArtifactChecksumJars[i].replace( '-', '/' ) +
+ "/" + validArtifactChecksumJars[i] + "." + type + ".md5" );
+
+ deleteFile( repository.getBasedir() + "checksumTest/" + validArtifactChecksumJars[i].replace( '-', '/' ) +
+ "/" + validArtifactChecksumJars[i] + "." + type + ".sha1" );
+ }
+
+ //delete valid checksum files of metadata file
+ for ( int i = 0; i < validArtifactChecksumJars.length; i++ )
+ {
+ deleteFile( repository.getBasedir() + "checksumTest/" + validArtifactChecksumJars[i].replace( '-', '/' ) +
+ "/" + metadataChecksumFilename + ".xml.md5" );
+
+ deleteFile( repository.getBasedir() + "checksumTest/" + validArtifactChecksumJars[i].replace( '-', '/' ) +
+ "/" + metadataChecksumFilename + ".xml.sha1" );
+ }
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AllTests.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AllTests.java
new file mode 100644
index 000000000..b9bffef7b
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/AllTests.java
@@ -0,0 +1,45 @@
+package org.apache.maven.archiva.reporting.reporter;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
+/**
+ * AllTests
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class AllTests
+{
+
+ public static Test suite()
+ {
+ TestSuite suite = new TestSuite( "Test for org.apache.maven.archiva.reporting.reporter" );
+ //$JUnit-BEGIN$
+ suite.addTestSuite( DefaultArtifactReporterTest.class );
+ suite.addTestSuite( ChecksumMetadataReporterTest.class );
+ suite.addTestSuite( ChecksumArtifactReporterTest.class );
+ //$JUnit-END$
+ return suite;
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumArtifactReporterTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumArtifactReporterTest.java
new file mode 100644
index 000000000..3fc9acd0b
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumArtifactReporterTest.java
@@ -0,0 +1,79 @@
+package org.apache.maven.archiva.reporting.reporter;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor;
+import org.apache.maven.artifact.Artifact;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.IOException;
+
+/**
+ * This class tests the ChecksumArtifactReportProcessor.
+ * It extends the AbstractChecksumArtifactReporterTestCase class.
+ */
+public class ChecksumArtifactReporterTest
+ extends AbstractChecksumArtifactReporterTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private ArtifactResultsDatabase database;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "checksum" );
+ database = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ }
+
+ /**
+ * Test the ChecksumArtifactReportProcessor when the checksum files are valid.
+ */
+ public void testChecksumArtifactReporterSuccess()
+ throws DigesterException, IOException
+ {
+ createChecksumFile( "VALID" );
+ createChecksumFile( "INVALID" );
+
+ Artifact artifact = createArtifact( "checksumTest", "validArtifact", "1.0" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 0, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+ }
+
+ /**
+ * Test the ChecksumArtifactReportProcessor when the checksum files are invalid.
+ */
+ public void testChecksumArtifactReporterFailed()
+ {
+ String s = "invalidArtifact";
+ String s1 = "1.0";
+ Artifact artifact = createArtifact( "checksumTest", s, s1 );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 1, database.getNumFailures() );
+ assertEquals( 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+ }
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumMetadataReporterTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumMetadataReporterTest.java
new file mode 100644
index 000000000..6cd358321
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/ChecksumMetadataReporterTest.java
@@ -0,0 +1,135 @@
+package org.apache.maven.archiva.reporting.reporter;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase;
+import org.apache.maven.archiva.reporting.database.MetadataResultsDatabase;
+import org.apache.maven.archiva.reporting.model.MetadataResults;
+import org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor;
+import org.apache.maven.archiva.reporting.processor.MetadataReportProcessor;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.repository.metadata.ArtifactRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.GroupRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.SnapshotArtifactRepositoryMetadata;
+import org.codehaus.plexus.digest.DigesterException;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Iterator;
+
+/**
+ * ChecksumMetadataReporterTest
+ *
+ * @author <a href="mailto:joakim@erdfelt.com">Joakim Erdfelt</a>
+ * @version $Id$
+ */
+public class ChecksumMetadataReporterTest
+ extends AbstractChecksumArtifactReporterTestCase
+{
+ private ArtifactReportProcessor artifactReportProcessor;
+
+ private MetadataReportProcessor metadataReportProcessor;
+
+ private MetadataResultsDatabase database;
+
+ private ArtifactResultsDatabase artifactsDatabase;
+
+ public void setUp()
+ throws Exception
+ {
+ super.setUp();
+ metadataReportProcessor = (MetadataReportProcessor) lookup( MetadataReportProcessor.ROLE, "checksum-metadata" );
+ artifactReportProcessor = (ArtifactReportProcessor) lookup( ArtifactReportProcessor.ROLE, "checksum" );
+ database = (MetadataResultsDatabase) lookup( MetadataResultsDatabase.ROLE );
+ artifactsDatabase = (ArtifactResultsDatabase) lookup( ArtifactResultsDatabase.ROLE );
+ }
+
+ /**
+ * Test the valid checksum of a metadata file.
+ * The reportingDatabase should report 2 success validation.
+ */
+ public void testChecksumMetadataReporterSuccess()
+ throws DigesterException, IOException
+ {
+ createMetadataFile( "VALID" );
+ createMetadataFile( "INVALID" );
+
+ Artifact artifact = createArtifact( "checksumTest", "validArtifact", "1.0" );
+
+ //Version level metadata
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact );
+ metadataReportProcessor.processMetadata( metadata, repository );
+
+ //Artifact level metadata
+ metadata = new ArtifactRepositoryMetadata( artifact );
+ metadataReportProcessor.processMetadata( metadata, repository );
+
+ //Group level metadata
+ metadata = new GroupRepositoryMetadata( "checksumTest" );
+ metadataReportProcessor.processMetadata( metadata, repository );
+ }
+
+ /**
+ * Test the corrupted checksum of a metadata file.
+ * The reportingDatabase must report 2 failures.
+ */
+ public void testChecksumMetadataReporterFailure()
+ {
+ Artifact artifact = createArtifact( "checksumTest", "invalidArtifact", "1.0" );
+
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact );
+ metadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ }
+
+ /**
+ * Test the conditional when the checksum files of the artifact & metadata do not exist.
+ */
+ public void testChecksumFilesDoNotExist()
+ throws DigesterException, IOException
+ {
+ createChecksumFile( "VALID" );
+ createMetadataFile( "VALID" );
+ deleteChecksumFiles( "jar" );
+
+ Artifact artifact = createArtifact( "checksumTest", "validArtifact", "1.0" );
+
+ artifactReportProcessor.processArtifact( artifact, null );
+ assertEquals( 1, artifactsDatabase.getNumFailures() );
+
+ RepositoryMetadata metadata = new SnapshotArtifactRepositoryMetadata( artifact );
+ metadataReportProcessor.processMetadata( metadata, repository );
+
+ Iterator failures = database.getIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+
+ deleteTestDirectory( new File( repository.getBasedir() + "checksumTest" ) );
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/DefaultArtifactReporterTest.java b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/DefaultArtifactReporterTest.java
new file mode 100644
index 000000000..7d91d6f19
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/java/org/apache/maven/archiva/reporting/reporter/DefaultArtifactReporterTest.java
@@ -0,0 +1,390 @@
+package org.apache.maven.archiva.reporting.reporter;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.maven.archiva.reporting.AbstractRepositoryReportsTestCase;
+import org.apache.maven.archiva.reporting.database.ReportingDatabase;
+import org.apache.maven.archiva.reporting.model.ArtifactResults;
+import org.apache.maven.archiva.reporting.model.MetadataResults;
+import org.apache.maven.archiva.reporting.model.ResultReason;
+import org.apache.maven.artifact.Artifact;
+import org.apache.maven.artifact.factory.ArtifactFactory;
+import org.apache.maven.artifact.repository.metadata.ArtifactRepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.RepositoryMetadata;
+import org.apache.maven.artifact.repository.metadata.Versioning;
+
+import java.util.Iterator;
+
+/**
+ * DefaultArtifactReporterTest
+ *
+ * @version $Id$
+ */
+public class DefaultArtifactReporterTest
+ extends AbstractRepositoryReportsTestCase
+{
+ private ReportingDatabase database;
+
+ private RepositoryMetadata metadata;
+
+ private static final String PROCESSOR = "processor";
+
+ private static final String PROBLEM = "problem";
+
+ private Artifact artifact;
+
+ protected void setUp()
+ throws Exception
+ {
+ super.setUp();
+
+ database = (ReportingDatabase) lookup( ReportingDatabase.ROLE );
+
+ ArtifactFactory artifactFactory = (ArtifactFactory) lookup( ArtifactFactory.ROLE );
+
+ artifact = artifactFactory.createBuildArtifact( "groupId", "artifactId", "1.0-alpha-1", "type" );
+
+ Versioning versioning = new Versioning();
+ versioning.addVersion( "1.0-alpha-1" );
+ versioning.addVersion( "1.0-alpha-2" );
+
+ metadata = new ArtifactRepositoryMetadata( artifact, versioning );
+ }
+
+ public void testEmptyArtifactReporter()
+ {
+ assertEquals( "No failures", 0, database.getNumFailures() );
+ assertEquals( "No warnings", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+ assertFalse( "No artifact failures", database.getArtifactIterator().hasNext() );
+ assertFalse( "No metadata failures", database.getMetadataIterator().hasNext() );
+ }
+
+ public void testMetadataSingleFailure()
+ {
+ database.getMetadataDatabase().addFailure( metadata, PROCESSOR, PROBLEM, "Single Failure Reason" );
+ assertEquals( "failures count", 1, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator failures = database.getMetadataIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "Single Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more failures", failures.hasNext() );
+ }
+
+ private void assertMetadata( MetadataResults result )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The MetadataResults object has a complex primary key consisting of groupId, artifactId, and version.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ assertEquals( "check failure cause", StringUtils.defaultString( metadata.getGroupId() ), result.getGroupId() );
+ assertEquals( "check failure cause", StringUtils.defaultString( metadata.getArtifactId() ), result
+ .getArtifactId() );
+ assertEquals( "check failure cause", StringUtils.defaultString( metadata.getBaseVersion() ), result
+ .getVersion() );
+ }
+
+ public void testMetadataMultipleFailures()
+ {
+ database.getMetadataDatabase().addFailure( metadata, PROCESSOR, PROBLEM, "First Failure Reason" );
+ database.getMetadataDatabase().addFailure( metadata, PROCESSOR, PROBLEM, "Second Failure Reason" );
+ assertEquals( "failures count", 2, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator failures = database.getMetadataIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ MetadataResults results = (MetadataResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "First Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd failure", failures.hasNext() );
+ result = (ResultReason) failures.next();
+ assertEquals( "check failure reason", "Second Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more failures", failures.hasNext() );
+ }
+
+ public void testMetadataSingleWarning()
+ {
+ database.getMetadataDatabase().addWarning( metadata, PROCESSOR, PROBLEM, "Single Warning Message" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 1, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator warnings = database.getMetadataIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ MetadataResults results = (MetadataResults) warnings.next();
+ warnings = results.getWarnings().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "Single Warning Message", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testMetadataMultipleWarnings()
+ {
+ database.getMetadataDatabase().addWarning( metadata, PROCESSOR, PROBLEM, "First Warning" );
+ database.getMetadataDatabase().addWarning( metadata, PROCESSOR, PROBLEM, "Second Warning" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 2, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator warnings = database.getMetadataIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ MetadataResults results = (MetadataResults) warnings.next();
+ warnings = results.getWarnings().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "First Warning", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd warning", warnings.hasNext() );
+ result = (ResultReason) warnings.next();
+ assertEquals( "check failure reason", "Second Warning", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testMetadataSingleNotice()
+ {
+ database.getMetadataDatabase().addNotice( metadata, PROCESSOR, PROBLEM, "Single Notice Message" );
+ assertEquals( "failure count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check notices", 1, database.getNumNotices() );
+
+ Iterator warnings = database.getMetadataIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ MetadataResults results = (MetadataResults) warnings.next();
+ warnings = results.getNotices().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "Single Notice Message", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testMetadataMultipleNotices()
+ {
+ database.getMetadataDatabase().addNotice( metadata, PROCESSOR, PROBLEM, "First Notice" );
+ database.getMetadataDatabase().addNotice( metadata, PROCESSOR, PROBLEM, "Second Notice" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 2, database.getNumNotices() );
+
+ Iterator warnings = database.getMetadataIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ MetadataResults results = (MetadataResults) warnings.next();
+ warnings = results.getNotices().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertMetadata( results );
+ assertEquals( "check failure reason", "First Notice", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd warning", warnings.hasNext() );
+ result = (ResultReason) warnings.next();
+ assertEquals( "check failure reason", "Second Notice", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testArtifactSingleFailure()
+ {
+ database.getArtifactDatabase().addFailure( artifact, PROCESSOR, PROBLEM, "Single Failure Reason" );
+ assertEquals( "failures count", 1, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator failures = database.getArtifactIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ArtifactResults results = (ArtifactResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "Single Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more failures", failures.hasNext() );
+ }
+
+ private void assertArtifact( ArtifactResults results )
+ {
+ /* The funky StringUtils.defaultString() is used because of database constraints.
+ * The ArtifactResults object has a complex primary key consisting of groupId, artifactId, version,
+ * type, classifier.
+ * This also means that none of those fields may be null. however, that doesn't eliminate the
+ * ability to have an empty string in place of a null.
+ */
+
+ assertEquals( "check failure cause", StringUtils.defaultString( artifact.getGroupId() ), results.getGroupId() );
+ assertEquals( "check failure cause", StringUtils.defaultString( artifact.getArtifactId() ), results
+ .getArtifactId() );
+ assertEquals( "check failure cause", StringUtils.defaultString( artifact.getVersion() ), results.getVersion() );
+ assertEquals( "check failure cause", StringUtils.defaultString( artifact.getClassifier() ), results
+ .getClassifier() );
+ assertEquals( "check failure cause", StringUtils.defaultString( artifact.getType() ), results.getArtifactType() );
+ }
+
+ public void testArtifactMultipleFailures()
+ {
+ database.getArtifactDatabase().addFailure( artifact, PROCESSOR, PROBLEM, "First Failure Reason" );
+ database.getArtifactDatabase().addFailure( artifact, PROCESSOR, PROBLEM, "Second Failure Reason" );
+ assertEquals( "failures count", 2, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator failures = database.getArtifactIterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ArtifactResults results = (ArtifactResults) failures.next();
+ failures = results.getFailures().iterator();
+ assertTrue( "check there is a failure", failures.hasNext() );
+ ResultReason result = (ResultReason) failures.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "First Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd failure", failures.hasNext() );
+ result = (ResultReason) failures.next();
+ assertEquals( "check failure reason", "Second Failure Reason", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more failures", failures.hasNext() );
+ }
+
+ public void testArtifactSingleWarning()
+ {
+ database.getArtifactDatabase().addWarning( artifact, PROCESSOR, PROBLEM, "Single Warning Message" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 1, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator warnings = database.getArtifactIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ArtifactResults results = (ArtifactResults) warnings.next();
+ warnings = results.getWarnings().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "Single Warning Message", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testArtifactMultipleWarnings()
+ {
+ database.getArtifactDatabase().addWarning( artifact, PROCESSOR, PROBLEM, "First Warning" );
+ database.getArtifactDatabase().addWarning( artifact, PROCESSOR, PROBLEM, "Second Warning" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 2, database.getNumWarnings() );
+ assertEquals( "check no notices", 0, database.getNumNotices() );
+
+ Iterator warnings = database.getArtifactIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ArtifactResults results = (ArtifactResults) warnings.next();
+ warnings = results.getWarnings().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "First Warning", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd warning", warnings.hasNext() );
+ result = (ResultReason) warnings.next();
+ assertEquals( "check failure reason", "Second Warning", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testArtifactSingleNotice()
+ {
+ database.getArtifactDatabase().addNotice( artifact, PROCESSOR, PROBLEM, "Single Notice Message" );
+ assertEquals( "failure count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check notices", 1, database.getNumNotices() );
+
+ Iterator warnings = database.getArtifactIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ArtifactResults results = (ArtifactResults) warnings.next();
+ warnings = results.getNotices().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "Single Notice Message", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+ public void testArtifactMultipleNotices()
+ {
+ database.getArtifactDatabase().addNotice( artifact, PROCESSOR, PROBLEM, "First Notice" );
+ database.getArtifactDatabase().addNotice( artifact, PROCESSOR, PROBLEM, "Second Notice" );
+ assertEquals( "warnings count", 0, database.getNumFailures() );
+ assertEquals( "warnings count", 0, database.getNumWarnings() );
+ assertEquals( "check no notices", 2, database.getNumNotices() );
+
+ Iterator warnings = database.getArtifactIterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ArtifactResults results = (ArtifactResults) warnings.next();
+ warnings = results.getNotices().iterator();
+ assertTrue( "check there is a failure", warnings.hasNext() );
+ ResultReason result = (ResultReason) warnings.next();
+ assertArtifact( results );
+ assertEquals( "check failure reason", "First Notice", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertTrue( "must have 2nd warning", warnings.hasNext() );
+ result = (ResultReason) warnings.next();
+ assertEquals( "check failure reason", "Second Notice", result.getReason() );
+ assertEquals( "check failure parameters", PROCESSOR, result.getProcessor() );
+ assertEquals( "check failure parameters", PROBLEM, result.getProblem() );
+ assertFalse( "no more warnings", warnings.hasNext() );
+ }
+
+}
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-sources.jar b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-sources.jar
new file mode 100644
index 000000000..c2ea777c1
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-sources.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.tar.gz b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.tar.gz
new file mode 100644
index 000000000..c2ea777c1
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.tar.gz
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.zip b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.zip
new file mode 100644
index 000000000..c2ea777c1
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1-src.zip
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.jar b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.jar
new file mode 100644
index 000000000..c2ea777c1
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.pom b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.pom
new file mode 100644
index 000000000..a987f03ec
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-1/artifactId-1.0-alpha-1.pom
@@ -0,0 +1,25 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>groupId</groupId>
+ <artifactId>artifactId</artifactId>
+ <version>1.0-alpha-1</version>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-2/artifactId-1.0-alpha-2.pom b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-2/artifactId-1.0-alpha-2.pom
new file mode 100644
index 000000000..0ccf1e4d6
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/1.0-alpha-2/artifactId-1.0-alpha-2.pom
@@ -0,0 +1,25 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>groupId</groupId>
+ <artifactId>artifactId</artifactId>
+ <version>1.0-alpha-2</version>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/maven-metadata.xml b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/maven-metadata.xml
new file mode 100644
index 000000000..1438715d6
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/artifactId/maven-metadata.xml
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<metadata>
+ <groupId>groupId</groupId>
+ <artifactId>artifactId</artifactId>
+ <version>1.0-alpha-1</version>
+ <versioning>
+ <versions>
+ <version>1.0-alpha-1</version>
+ <version>1.0-alpha-2</version>
+ </versions>
+ </versioning>
+</metadata>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-20050611.202024-1.pom b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-20050611.202024-1.pom
new file mode 100644
index 000000000..cf613e847
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-20050611.202024-1.pom
@@ -0,0 +1,19 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-SNAPSHOT.pom b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-SNAPSHOT.pom
new file mode 100644
index 000000000..cf613e847
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/snapshot-artifact/1.0-alpha-1-SNAPSHOT/snapshot-artifact-1.0-alpha-1-SNAPSHOT.pom
@@ -0,0 +1,19 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/groupId/unexpectedfile.xml b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/unexpectedfile.xml
new file mode 100644
index 000000000..f7eed850d
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/groupId/unexpectedfile.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+This file is here to make sure that it will not be processed during unit
+ test. \ No newline at end of file
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/maven-metadata.xml b/archiva-reporting/archiva-report-manager/src/test/repository/maven-metadata.xml
new file mode 100644
index 000000000..51674bd11
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/maven-metadata.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<metadata>
+ <groupId>checksumTest</groupId>
+ <artifactId>invalidArtifact</artifactId>
+ <version>1.0</version>
+</metadata>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/artifactId/1.0-alpha-3/artifactId-1.0-alpha-3.pom b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/artifactId/1.0-alpha-3/artifactId-1.0-alpha-3.pom
new file mode 100644
index 000000000..2b163a4a4
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/artifactId/1.0-alpha-3/artifactId-1.0-alpha-3.pom
@@ -0,0 +1,28 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>artifactId</artifactId>
+ <version>1.0-alpha-3</version>
+ <build>
+ <plugins>
+ </build>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.jar b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.jar
new file mode 100644
index 000000000..2acfe605d
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.pom b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.pom
new file mode 100644
index 000000000..19df850af
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/maven-archiver-2.0.pom
@@ -0,0 +1,46 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <groupId>org.apache.maven</groupId>
+ <modelVersion>4.0.0</modelVersion>
+ <artifactId>maven-archiver</artifactId>
+ <name>Maven Archiver</name>
+ <version>2.1</version>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-project</artifactId>
+ <version>2.0</version>
+ </dependency>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-archiver</artifactId>
+ <version>1.0-alpha-3</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact</artifactId>
+ <version>2.0</version>
+ </dependency>
+ </dependencies>
+ <distributionManagement>
+ <status>deployed</status>
+ </distributionManagement>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/note.txt b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/note.txt
new file mode 100644
index 000000000..bc218ba95
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-archiver/2.0/note.txt
@@ -0,0 +1,4 @@
+- The artifact location does not match the location specified in the file system, but
+ matches the location specified in the pom included in the package.
+- The groupId, artifactId and version of the pom in the file system does not match
+ the groupId, artifactId and version of the pom included in the package.
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.jar b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.jar
new file mode 100644
index 000000000..d6820d6fe
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.pom b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.pom
new file mode 100644
index 000000000..76ca28cbc
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/maven-model-2.0.pom
@@ -0,0 +1,105 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <parent>
+ <artifactId>maven</artifactId>
+ <groupId>org.apache.maven</groupId>
+ <version>2.0</version>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-model</artifactId>
+ <name>Maven Model</name>
+ <version>2.0</version>
+ <description>Maven Model</description>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.codehaus.modello</groupId>
+ <artifactId>modello-maven-plugin</artifactId>
+ <executions>
+ <execution>
+ <goals>
+ <goal>xpp3-writer</goal>
+ <goal>java</goal>
+ <goal>xpp3-reader</goal>
+ <goal>xsd</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <version>4.0.0</version>
+ <model>maven.mdo</model>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+ <profiles>
+ <profile>
+ <id>all-models</id>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.codehaus.modello</groupId>
+ <artifactId>modello-maven-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>v3</id>
+ <goals>
+ <goal>xpp3-writer</goal>
+ <goal>java</goal>
+ <goal>xpp3-reader</goal>
+ <goal>xsd</goal>
+ </goals>
+ <configuration>
+ <version>3.0.0</version>
+ <packageWithVersion>true</packageWithVersion>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <executions>
+ <execution>
+ <phase>package</phase>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ <configuration>
+ <classifier>all</classifier>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+ </profile>
+ </profiles>
+ <dependencies>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-utils</artifactId>
+ </dependency>
+ </dependencies>
+ <distributionManagement>
+ <status>deployed</status>
+ </distributionManagement>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/note.txt b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/note.txt
new file mode 100644
index 000000000..13b46ec93
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-model/2.0/note.txt
@@ -0,0 +1,3 @@
+- The artifact is located in the proper location.
+- The groupId, artifactId and version of the pom in the file system matches
+ the groupId, artifactId and version of the pom included in the package.
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.jar b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.jar
new file mode 100644
index 000000000..c499d94ff
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.pom b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.pom
new file mode 100644
index 000000000..ade99a426
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/maven-monitor-2.1.pom
@@ -0,0 +1,34 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <parent>
+ <artifactId>maven</artifactId>
+ <groupId>org.apache.maven</groupId>
+ <version>2.1</version>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-monitor</artifactId>
+ <name>Maven Monitor</name>
+ <version>2.1</version>
+ <distributionManagement>
+ <status>deployed</status>
+ </distributionManagement>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/note.txt b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/note.txt
new file mode 100644
index 000000000..796d100b0
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-monitor/2.1/note.txt
@@ -0,0 +1,4 @@
+- The artifact location matches the location specified in the file system, but
+ does not match the location specified in the pom included in the package.
+- The groupId, artifactId and version of the pom in the file system does not match
+ the groupId, artifactId and version of the pom included in the package.
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.jar b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.jar
new file mode 100644
index 000000000..efeb8d456
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.jar
Binary files differ
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.pom b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.pom
new file mode 100644
index 000000000..83749b0b0
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/maven-project-2.1.pom
@@ -0,0 +1,72 @@
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<project>
+ <parent>
+ <artifactId>maven</artifactId>
+ <groupId>org.apache.maven</groupId>
+ <version>2.0</version>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <artifactId>maven-project</artifactId>
+ <name>Maven Project Builder</name>
+ <version>2.0</version>
+ <description>This library is used to not only read Maven project object model files, but to assemble inheritence
+ and to retrieve remote models as required.
+ </description>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact-test</artifactId>
+ <version>2.0</version>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-profile</artifactId>
+ <version>2.0</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-model</artifactId>
+ <version>2.0</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact-manager</artifactId>
+ <version>2.0</version>
+ </dependency>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-utils</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-artifact</artifactId>
+ <version>2.0</version>
+ </dependency>
+ <dependency>
+ <groupId>org.codehaus.plexus</groupId>
+ <artifactId>plexus-container-default</artifactId>
+ </dependency>
+ </dependencies>
+ <distributionManagement>
+ <status>deployed</status>
+ </distributionManagement>
+</project>
diff --git a/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/note.txt b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/note.txt
new file mode 100644
index 000000000..38aefadac
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/repository/org/apache/maven/maven-project/2.1/note.txt
@@ -0,0 +1,4 @@
+- The artifact location does not match both the location specified in the file system pom
+ and in the pom included in the package.
+- The groupId, artifactId and version of the pom in the file system does not match
+ the groupId, artifactId and version of the pom included in the package.
diff --git a/archiva-reporting/archiva-report-manager/src/test/resources/META-INF/plexus/components.xml b/archiva-reporting/archiva-report-manager/src/test/resources/META-INF/plexus/components.xml
new file mode 100644
index 000000000..6e2700539
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/resources/META-INF/plexus/components.xml
@@ -0,0 +1,9 @@
+<component-set>
+ <components>
+ <component>
+ <role>org.codehaus.plexus.jdo.JdoFactory</role>
+ <role-hint>archiva</role-hint>
+ <implementation>org.codehaus.plexus.jdo.DefaultConfigurableJdoFactory</implementation>
+ </component>
+ </components>
+</component-set>
diff --git a/archiva-reporting/archiva-report-manager/src/test/resources/log4j.properties b/archiva-reporting/archiva-report-manager/src/test/resources/log4j.properties
new file mode 100644
index 000000000..9b2c26ade
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/resources/log4j.properties
@@ -0,0 +1,10 @@
+# Set root logger level to DEBUG and its only appender to A1.
+log4j.rootLogger=WARN, A1
+
+# A1 is set to be a ConsoleAppender.
+log4j.appender.A1=org.apache.log4j.ConsoleAppender
+
+# A1 uses PatternLayout.
+log4j.appender.A1.layout=org.apache.log4j.PatternLayout
+log4j.appender.A1.layout.ConversionPattern=%-4r [%t] %-5p %c %x - %m%n
+
diff --git a/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.xml b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.xml
new file mode 100644
index 000000000..5ae012392
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/DuplicateArtifactFileReportProcessorTest.xml
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<component-set>
+ <components>
+ <component>
+ <role>org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor</role>
+ <role-hint>duplicate</role-hint>
+ <implementation>org.apache.maven.archiva.reporting.processor.DuplicateArtifactFileReportProcessor</implementation>
+ <requirements>
+ <requirement>
+ <role>org.codehaus.plexus.digest.Digester</role>
+ <role-hint>md5</role-hint>
+ <field-name>digester</field-name>
+ </requirement>
+ <requirement>
+ <role>org.apache.maven.archiva.indexer.RepositoryArtifactIndexFactory</role>
+ <field-name>indexFactory</field-name>
+ </requirement>
+ <requirement>
+ <role>org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase</role>
+ <field-name>database</field-name>
+ </requirement>
+ </requirements>
+ <configuration>
+ <indexDirectory>${basedir}/target/indexDirectory</indexDirectory>
+ </configuration>
+ </component>
+ </components>
+</component-set> \ No newline at end of file
diff --git a/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.xml b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.xml
new file mode 100644
index 000000000..016361e9b
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldArtifactReportProcessorTest.xml
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<component-set>
+ <components>
+ <component>
+ <role>org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor</role>
+ <role-hint>old-artifact</role-hint>
+ <implementation>org.apache.maven.archiva.reporting.processor.OldArtifactReportProcessor</implementation>
+ <requirements>
+ <requirement>
+ <role>org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase</role>
+ <field-name>database</field-name>
+ </requirement>
+ </requirements>
+ <configuration>
+ <maxAge>10</maxAge>
+ </configuration>
+ </component>
+ </components>
+</component-set> \ No newline at end of file
diff --git a/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.xml b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.xml
new file mode 100644
index 000000000..779aa8c24
--- /dev/null
+++ b/archiva-reporting/archiva-report-manager/src/test/resources/org/apache/maven/archiva/reporting/processor/OldSnapshotArtifactReportProcessorTest.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<!--
+ ~ Licensed to the Apache Software Foundation (ASF) under one
+ ~ or more contributor license agreements. See the NOTICE file
+ ~ distributed with this work for additional information
+ ~ regarding copyright ownership. The ASF licenses this file
+ ~ to you under the Apache License, Version 2.0 (the
+ ~ "License"); you may not use this file except in compliance
+ ~ with the License. You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing,
+ ~ software distributed under the License is distributed on an
+ ~ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ ~ KIND, either express or implied. See the License for the
+ ~ specific language governing permissions and limitations
+ ~ under the License.
+ -->
+
+<component-set>
+ <components>
+ <component>
+ <role>org.apache.maven.archiva.reporting.processor.ArtifactReportProcessor</role>
+ <role-hint>old-snapshot-artifact</role-hint>
+ <implementation>org.apache.maven.archiva.reporting.processor.OldSnapshotArtifactReportProcessor</implementation>
+ <requirements>
+ <requirement>
+ <role>org.apache.maven.archiva.reporting.database.ArtifactResultsDatabase</role>
+ <field-name>database</field-name>
+ </requirement>
+ </requirements>
+ <configuration>
+ <maxAge>3600</maxAge>
+ <maxSnapshots>2</maxSnapshots>
+ </configuration>
+ </component>
+ </components>
+</component-set> \ No newline at end of file