This is an automated email from the ASF dual-hosted git repository.

martin_s pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/archiva.git

commit 56de9e590b8d040add03b99df2e221eeedde860e
Author: Martin Stockhammer <[email protected]>
AuthorDate: Sun May 3 11:34:31 2020 +0200

    Adding new item type for additional files that are not real artifacts
---
 .../archiva/repository/ItemDeleteStatus.java       | 101 ++++++++++
 .../repository/ManagedRepositoryContent.java       |  40 +++-
 .../archiva/repository/content/Artifact.java       |  60 +++---
 .../archiva/repository/content/ArtifactType.java   |   2 +-
 .../{ArtifactType.java => BaseDataItemTypes.java}  |   7 +-
 .../archiva/repository/content/DataItem.java       |  87 ++++++++
 .../{ArtifactType.java => DataItemType.java}       |   6 +-
 .../repository/content/base/ArchivaArtifact.java   |   5 +-
 .../repository/content/base/ArchivaDataItem.java   | 223 +++++++++++++++++++++
 .../content/base/builder/DataItemOptBuilder.java}  |  26 ++-
 .../base/builder/DataItemWithIdBuilder.java}       |  11 +-
 .../mock/ManagedRepositoryContentMock.java         |  14 ++
 .../scanner/mock/ManagedRepositoryContentMock.java |  13 ++
 13 files changed, 537 insertions(+), 58 deletions(-)

diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ItemDeleteStatus.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ItemDeleteStatus.java
new file mode 100644
index 0000000..321824d
--- /dev/null
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ItemDeleteStatus.java
@@ -0,0 +1,101 @@
+package org.apache.archiva.repository;
+
+/*
+ * 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.archiva.repository.content.Artifact;
+import org.apache.archiva.repository.content.ContentItem;
+import org.apache.archiva.repository.content.Namespace;
+import org.apache.archiva.repository.content.Project;
+import org.apache.archiva.repository.content.Version;
+
+/**
+ *
+ * Deletion status of a given item.
+ *
+ * @author Martin Stockhammer <[email protected]>
+ */
+public class ItemDeleteStatus
+{
+    public static final int OK = 0;
+    public static final int DELETION_FAILED = 1;
+    public static final int ITEM_NOT_FOUND = 2;
+    public static final int UNKNOWN = 128;
+
+    private ContentItem item;
+    private int status;
+    private Throwable exception;
+
+    public ItemDeleteStatus(ContentItem item) {
+        this.item = item;
+        this.status = OK;
+    }
+
+    public ItemDeleteStatus(ContentItem item, int status) {
+        this.item = item;
+        this.status = status;
+    }
+
+    public ItemDeleteStatus(ContentItem item, int status, Throwable e) {
+        this.item = item;
+        this.status = status;
+        this.exception = e;
+    }
+
+    public ContentItem getItem( )
+    {
+        return item;
+    }
+
+    public int getStatus( )
+    {
+        return status;
+    }
+
+    public Throwable getException( )
+    {
+        return exception;
+    }
+
+    public Class<? extends ContentItem> getItemType() {
+        if (item instanceof Namespace ) {
+            return Namespace.class;
+        } else if (item instanceof Project ) {
+            return Project.class;
+        } else if (item instanceof Version ) {
+            return Version.class;
+        } else if (item instanceof Artifact ) {
+            return Artifact.class;
+        } else {
+            return ContentItem.class;
+        }
+    }
+
+
+    public <U extends ContentItem> U adapt(Class<U> clazz) throws 
IllegalArgumentException {
+        if (clazz.isAssignableFrom( item.getClass() )) {
+            return (U) item;
+        } else {
+            throw new IllegalArgumentException( "Cannot convert instance of " 
+ item.getClass( ) + " to " + clazz );
+        }
+    }
+
+
+
+
+}
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ManagedRepositoryContent.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ManagedRepositoryContent.java
index e06f62e..a093c8a 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ManagedRepositoryContent.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/ManagedRepositoryContent.java
@@ -33,8 +33,10 @@ import org.apache.archiva.repository.content.Version;
 import org.apache.archiva.repository.storage.StorageAsset;
 
 import java.nio.file.Path;
+import java.util.BitSet;
 import java.util.List;
 import java.util.Set;
+import java.util.function.Consumer;
 import java.util.stream.Stream;
 
 /**
@@ -49,6 +51,27 @@ public interface ManagedRepositoryContent extends 
RepositoryContent
     /// *****************   New generation interface **********************
 
     /**
+     * Delete all items that match the given selector. The type and number of 
deleted items
+     * depend on the specific selector:
+     * <ul>
+     *     <li>namespace: the complete namespace is deleted (recursively if 
the recurse flag is set)</li>
+     *     <li>project: the complete project and all contained versions are 
deleted</li>
+     *     <li>version: the version inside the project is deleted (project is 
required)</li>
+     *     <li>artifactId: all artifacts that match the id (project and 
version are required)</li>
+     *     <li>artifactVersion: all artifacts that match the version (project 
and version are required)</li>
+     *     <li></li>
+     * </ul>
+     *
+     * @param selector the item selector that selects the artifacts to delete
+     * @param consumer a consumer of the items that will be called after 
deletion
+     * @returns the list of items that are deleted
+     * @throws ContentAccessException if the deletion was not possible or only 
partly successful, because the access
+     * to the artifacts failed
+     * @throws IllegalArgumentException if the selector does not specify valid 
artifacts to delete
+     */
+    void deleteAllItems( ItemSelector selector, Consumer<ItemDeleteStatus> 
consumer) throws ContentAccessException, IllegalArgumentException;
+
+    /**
      * Removes the specified content item and if the item is a container or 
directory,
      * all content stored under the given item.
      *
@@ -137,11 +160,11 @@ public interface ManagedRepositoryContent extends 
RepositoryContent
      *     <li>artifactId or projectId</li>
      * </ul>
      * If the coordinates do not provide enough information for selecting a 
artifact, a {@link IllegalArgumentException} will be thrown
-     * It depends on the repository type, what exactly is deleted for a given 
set of coordinates. Some repository type
+     * It depends on the repository type, what exactly is returned for a given 
set of coordinates. Some repository type
      * may have different required and optional coordinates. For further 
information please check the documentation for the
      * type specific implementations.
      *
-     * The following coordinates are optional and may further specify the 
artifact to delete.
+     * The following coordinates are optional and may further specify the 
artifact to return.
      * <ul>
      *     <li>classifier</li>
      *     <li>type</li>
@@ -188,6 +211,19 @@ public interface ManagedRepositoryContent extends 
RepositoryContent
      */
     Stream<? extends Artifact> newArtifactStream( ItemSelector selector) 
throws ContentAccessException;
 
+    /**
+     * Returns a stream of items that match the given selector. It may return 
a stream of mixed types,
+     * like namespaces, projects, versions and artifacts. It will not select a 
specific type.
+     * The selector can specify the '*' pattern for all fields.
+     * The returned elements will be provided by depth first.
+     *
+     * @param selector the item selector that specifies the items
+     * @return the stream of content items
+     * @throws ContentAccessException if the access to the underlying storage 
failed
+     * @throws IllegalArgumentException if a illegal coordinate combination 
was provided
+     */
+    Stream<? extends ContentItem> newItemStream(ItemSelector selector, boolean 
parallel) throws ContentAccessException, IllegalArgumentException;
+
 
     /**
      * Return the projects that are part of the given namespace.
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/Artifact.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/Artifact.java
index ce5a191..0bb7e84 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/Artifact.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/Artifact.java
@@ -34,7 +34,7 @@ import org.apache.archiva.model.ArtifactReference;
  *
  * @author Martin Stockhammer <[email protected]>
  */
-public interface Artifact extends ContentItem
+public interface Artifact extends DataItem
 {
 
     /**
@@ -45,6 +45,7 @@ public interface Artifact extends ContentItem
      *
      * @return the identifier of the artifact. Never returns <code>null</code> 
or empty string
      */
+    @Override
     String getId( );
 
     /**
@@ -83,10 +84,33 @@ public interface Artifact extends ContentItem
     String getClassifier( );
 
     /**
+     * This may be different from extension and gives the remainder that is 
used to build the file path from
+     * the artifact coordinates (namespace, id, version, classifier, type)
+     *
+     * @return the file name remainder
+     */
+    String getRemainder( );
+
+    /**
+     * Returns the type of the artifact
+     * @return
+     */
+    @Override
+    ArtifactType getDataType();
+
+    /**
+     * Returns a unique key
+     * @return
+     */
+    String toKey();
+
+
+    /**
      * Short cut for the file name. Should always return the same value as the 
artifact name.
      *
      * @return the name of the file
      */
+    @Override
     default String getFileName( )
     {
         return getAsset( ).getName( );
@@ -98,6 +122,7 @@ public interface Artifact extends ContentItem
      *
      * @return the file name extension
      */
+    @Override
     default String getExtension( )
     {
         final String name = getAsset( ).getName( );
@@ -112,33 +137,8 @@ public interface Artifact extends ContentItem
         }
     }
 
-    /**
-     * This may be different from extension and gives the remainder that is 
used to build the file path from
-     * the artifact coordinates (namespace, id, version, classifier, type)
-     *
-     * @return the file name remainder
-     */
-    String getRemainder( );
-
-    /**
-     * Should return the mime type of the artifact.
-     *
-     * @return the mime type of the artifact.
-     */
-    String getContentType( );
-
-    /**
-     * Returns the type of the artifact
-     * @return
-     */
-    ArtifactType getArtifactType();
-
-    /**
-     * Returns a unique key
-     * @return
-     */
-    String toKey();
-
-
-
+    default ContentItem getParent( )
+    {
+        return getVersion();
+    }
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
index 7e52765..b5df079 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
@@ -24,7 +24,7 @@ package org.apache.archiva.repository.content;
  *
  * @author Martin Stockhammer <[email protected]>
  */
-public interface ArtifactType
+public interface ArtifactType extends DataItemType
 {
     String name();
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/BaseDataItemTypes.java
similarity index 88%
copy from 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
copy to 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/BaseDataItemTypes.java
index 7e52765..1ed09d1 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/BaseDataItemTypes.java
@@ -19,12 +19,9 @@ package org.apache.archiva.repository.content;
  */
 
 /**
- *
- * Type of the artifact to distinguish different flavours.
- *
  * @author Martin Stockhammer <[email protected]>
  */
-public interface ArtifactType
+public enum BaseDataItemTypes implements DataItemType
 {
-    String name();
+    METADATA,UNKNOWN
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItem.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItem.java
new file mode 100644
index 0000000..32dc00e
--- /dev/null
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItem.java
@@ -0,0 +1,87 @@
+package org.apache.archiva.repository.content;
+
+/*
+ * 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.
+ */
+
+/**
+ *
+ * A data item is a item that is not a real artifact because it does not have
+ * a version, but is normally file based.
+ *
+ * @author Martin Stockhammer <[email protected]>
+ */
+public interface DataItem extends ContentItem
+{
+
+    /**
+     * Returns the parent of the data item
+     * @return the parent item, which is either a Version, Project or Namespace
+     */
+    ContentItem getParent( );
+
+    /**
+     * Returns the identifier of the data item.
+     * @return the identifier string
+     */
+    String getId( );
+
+    /**
+     * Returns the extension of the file. This method should always return the 
extension string after the last
+     * '.'-character.
+     *
+     * @return the file name extension
+     */
+    default String getExtension( )
+    {
+        final String name = getAsset( ).getName( );
+        final int idx = name.lastIndexOf( '.' )+1;
+        if ( idx > 0 )
+        {
+            return name.substring( idx );
+        }
+        else
+        {
+            return "";
+        }
+    }
+
+    /**
+     * Should return the mime type of the artifact.
+     *
+     * @return the mime type of the artifact.
+     */
+    String getContentType( );
+
+
+    /**
+     * Short cut for the file name. Should always return the same value as the 
artifact name.
+     *
+     * @return the name of the file
+     */
+    default String getFileName( )
+    {
+        return getAsset( ).getName( );
+    }
+
+    /**
+     * Returns the
+     * @return the type of the item
+     */
+    DataItemType getDataType();
+
+}
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItemType.java
similarity index 90%
copy from 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
copy to 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItemType.java
index 7e52765..a976851 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/DataItemType.java
@@ -19,12 +19,10 @@ package org.apache.archiva.repository.content;
  */
 
 /**
- *
- * Type of the artifact to distinguish different flavours.
- *
+ * The data item type
  * @author Martin Stockhammer <[email protected]>
  */
-public interface ArtifactType
+public interface DataItemType
 {
     String name();
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaArtifact.java
 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaArtifact.java
index cb210ac..26b0449 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaArtifact.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaArtifact.java
@@ -22,6 +22,8 @@ package org.apache.archiva.repository.content.base;
 import org.apache.archiva.repository.content.Artifact;
 import org.apache.archiva.repository.content.ArtifactType;
 import org.apache.archiva.repository.content.BaseArtifactTypes;
+import org.apache.archiva.repository.content.ContentItem;
+import org.apache.archiva.repository.content.DataItem;
 import org.apache.archiva.repository.content.Version;
 import org.apache.archiva.repository.content.base.builder.ArtifactOptBuilder;
 import 
org.apache.archiva.repository.content.base.builder.ArtifactVersionBuilder;
@@ -66,7 +68,6 @@ public class ArchivaArtifact extends ArchivaContentItem 
implements Artifact
 
     }
 
-
     @Override
     public String getId( )
     {
@@ -110,7 +111,7 @@ public class ArchivaArtifact extends ArchivaContentItem 
implements Artifact
     }
 
     @Override
-    public ArtifactType getArtifactType( )
+    public ArtifactType getDataType( )
     {
         return artifactType;
     }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaDataItem.java
 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaDataItem.java
new file mode 100644
index 0000000..cb13e18
--- /dev/null
+++ 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/ArchivaDataItem.java
@@ -0,0 +1,223 @@
+package org.apache.archiva.repository.content.base;
+
+/*
+ * 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.archiva.repository.content.BaseArtifactTypes;
+import org.apache.archiva.repository.content.BaseDataItemTypes;
+import org.apache.archiva.repository.content.ContentItem;
+import org.apache.archiva.repository.content.DataItem;
+import org.apache.archiva.repository.content.DataItemType;
+import org.apache.archiva.repository.content.base.builder.DataItemOptBuilder;
+import 
org.apache.archiva.repository.content.base.builder.DataItemWithIdBuilder;
+import org.apache.archiva.repository.storage.StorageAsset;
+import org.apache.commons.lang3.StringUtils;
+
+/**
+ * Base implementation of artifact.
+ * <p>
+ * You have to use the builder method {@link #withAsset(StorageAsset)} to 
create a instance.
+ * The build() method can be called after the required attributes are set.
+ * <p>
+ * Artifacts are equal if the following coordinates match:
+ * <ul>
+ *     <li>repository</li>
+ *     <li>asset</li>
+ *     <li>version</li>
+ *     <li>artifactId</li>
+ *     <li>artifactVersion</li>
+ *     <li>type</li>
+ *     <li>classifier</li>
+ *     <li>artifactType</li>
+ * </ul>
+ *
+ * @author Martin Stockhammer <[email protected]>
+ */
+public class ArchivaDataItem extends ArchivaContentItem implements DataItem
+{
+    private String id;
+    private ContentItem parent;
+    private String contentType;
+    private DataItemType dataItemType;
+
+    private ArchivaDataItem( )
+    {
+
+    }
+
+    @Override
+    public String getId( )
+    {
+        return id;
+    }
+
+    @Override
+    public ContentItem getParent( )
+    {
+        return parent;
+    }
+
+    @Override
+    public String getContentType( )
+    {
+        return contentType;
+    }
+
+    @Override
+    public DataItemType getDataType( )
+    {
+        return dataItemType;
+    }
+
+
+    /**
+     * Returns the builder for creating a new artifact instance. You have to 
fill the
+     * required attributes before the build() method is available.
+     *
+     * @param asset the storage asset representing the artifact
+     * @return a builder for creating new artifact instance
+     */
+    public static DataItemWithIdBuilder withAsset( StorageAsset asset )
+    {
+        return new Builder( ).withAsset( asset );
+    }
+
+
+    @Override
+    public boolean equals( Object o )
+    {
+        if ( this == o ) return true;
+        if ( o == null || getClass( ) != o.getClass( ) ) return false;
+        if ( !super.equals( o ) ) return false;
+
+        ArchivaDataItem that = (ArchivaDataItem) o;
+
+        if ( !id.equals( that.id ) ) return false;
+        if ( !parent.equals( that.parent ) ) return false;
+        return dataItemType.equals(that.dataItemType );
+    }
+
+    @Override
+    public int hashCode( )
+    {
+        int result = super.hashCode( );
+        result = 31 * result + id.hashCode( );
+        result = 31 * result + parent.hashCode( );
+        result = 31 * result + dataItemType.hashCode( );
+        return result;
+    }
+
+    @Override
+    public String toString( )
+    {
+        final StringBuilder sb = new StringBuilder( "ArchivaArtifact{" );
+        sb.append( "id='" ).append( id ).append( '\'' );
+        sb.append( ", parent=" ).append( parent );
+        sb.append( ", contentType='" ).append( contentType ).append( '\'' );
+        sb.append( ", artifactType=" ).append( dataItemType );
+        sb.append( '}' );
+        return sb.toString( );
+    }
+
+    public static String defaultString( String value )
+    {
+        if ( value == null )
+        {
+            return "";
+        }
+
+        return value.trim();
+    }
+
+    private static class Builder
+        extends ContentItemBuilder<ArchivaDataItem, DataItemOptBuilder, 
DataItemWithIdBuilder >
+        implements DataItemOptBuilder,DataItemWithIdBuilder
+    {
+
+        Builder( )
+        {
+            super( new ArchivaDataItem( ) );
+        }
+
+        @Override
+        protected DataItemOptBuilder getOptBuilder( )
+        {
+            return this;
+        }
+
+        @Override
+        protected DataItemWithIdBuilder getNextBuilder( )
+        {
+            return this;
+        }
+
+        @Override
+        public DataItemOptBuilder withParent( ContentItem parent )
+        {
+            if ( parent == null )
+            {
+                throw new IllegalArgumentException( "version may not be null" 
);
+            }
+            item.parent = parent;
+            super.setRepository( parent.getRepository( ) );
+            return this;
+        }
+
+        @Override
+        public DataItemOptBuilder withId( String id )
+        {
+            if ( StringUtils.isEmpty( id ) )
+            {
+                throw new IllegalArgumentException( "Artifact id may not be 
null or empty" );
+            }
+            item.id = id;
+            return this;
+        }
+
+
+        @Override
+        public DataItemOptBuilder withContentType( String contentType )
+        {
+            item.contentType = contentType;
+            return this;
+        }
+
+        @Override
+        public DataItemOptBuilder withDataType( DataItemType type )
+        {
+            item.dataItemType = type;
+            return this;
+        }
+
+        @Override
+        public ArchivaDataItem build( )
+        {
+            super.build( );
+            if ( item.contentType == null )
+            {
+                item.contentType = "";
+            }
+            if (item.dataItemType ==null) {
+                item.dataItemType = BaseDataItemTypes.UNKNOWN;
+            }
+
+            return item;
+        }
+    }
+}
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemOptBuilder.java
similarity index 54%
copy from 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
copy to 
archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemOptBuilder.java
index 7e52765..04da17d 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemOptBuilder.java
@@ -1,5 +1,3 @@
-package org.apache.archiva.repository.content;
-
 /*
  * Licensed to the Apache Software Foundation (ASF) under one
  * or more contributor license agreements.  See the NOTICE file
@@ -18,13 +16,27 @@ package org.apache.archiva.repository.content;
  * under the License.
  */
 
+package org.apache.archiva.repository.content.base.builder;
+
+import org.apache.archiva.repository.content.ArtifactType;
+import org.apache.archiva.repository.content.ContentItem;
+import org.apache.archiva.repository.content.DataItem;
+import org.apache.archiva.repository.content.DataItemType;
+import org.apache.archiva.repository.content.base.ArchivaArtifact;
+import org.apache.archiva.repository.content.base.ArchivaDataItem;
+
 /**
- *
- * Type of the artifact to distinguish different flavours.
- *
  * @author Martin Stockhammer <[email protected]>
  */
-public interface ArtifactType
+public interface DataItemOptBuilder
+    extends OptBuilder<ArchivaDataItem, DataItemOptBuilder>
 {
-    String name();
+
+    DataItemOptBuilder withParent( ContentItem parent );
+
+    DataItemOptBuilder withContentType( String contentType );
+
+    DataItemOptBuilder withDataType( DataItemType type );
+
+    ArchivaDataItem build( );
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemWithIdBuilder.java
similarity index 84%
copy from 
archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
copy to 
archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemWithIdBuilder.java
index 7e52765..1dfd1aa 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-api/src/main/java/org/apache/archiva/repository/content/ArtifactType.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-layer/src/main/java/org/apache/archiva/repository/content/base/builder/DataItemWithIdBuilder.java
@@ -1,5 +1,3 @@
-package org.apache.archiva.repository.content;
-
 /*
  * Licensed to the Apache Software Foundation (ASF) under one
  * or more contributor license agreements.  See the NOTICE file
@@ -18,13 +16,12 @@ package org.apache.archiva.repository.content;
  * under the License.
  */
 
+package org.apache.archiva.repository.content.base.builder;
+
 /**
- *
- * Type of the artifact to distinguish different flavours.
- *
  * @author Martin Stockhammer <[email protected]>
  */
-public interface ArtifactType
+public interface DataItemWithIdBuilder
 {
-    String name();
+    DataItemOptBuilder withId( String id );
 }
diff --git 
a/archiva-modules/archiva-base/archiva-repository-layer/src/test/java/org/apache/archiva/repository/mock/ManagedRepositoryContentMock.java
 
b/archiva-modules/archiva-base/archiva-repository-layer/src/test/java/org/apache/archiva/repository/mock/ManagedRepositoryContentMock.java
index 9f52b80..dfd7703 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-layer/src/test/java/org/apache/archiva/repository/mock/ManagedRepositoryContentMock.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-layer/src/test/java/org/apache/archiva/repository/mock/ManagedRepositoryContentMock.java
@@ -25,6 +25,7 @@ import org.apache.archiva.model.ProjectReference;
 import org.apache.archiva.model.VersionedReference;
 import org.apache.archiva.repository.ContentAccessException;
 import org.apache.archiva.repository.ContentNotFoundException;
+import org.apache.archiva.repository.ItemDeleteStatus;
 import org.apache.archiva.repository.LayoutException;
 import org.apache.archiva.repository.ManagedRepository;
 import org.apache.archiva.repository.ManagedRepositoryContent;
@@ -40,6 +41,7 @@ import org.springframework.stereotype.Service;
 
 import java.nio.file.Path;
 import java.util.List;
+import java.util.function.Consumer;
 import java.util.stream.Stream;
 
 /**
@@ -63,6 +65,12 @@ public class ManagedRepositoryContentMock implements 
ManagedRepositoryContent
     }
 
     @Override
+    public void deleteAllItems( ItemSelector selector, 
Consumer<ItemDeleteStatus> consumer ) throws ContentAccessException, 
IllegalArgumentException
+    {
+
+    }
+
+    @Override
     public void deleteItem( ContentItem item ) throws ItemNotFoundException, 
ContentAccessException
     {
 
@@ -126,6 +134,12 @@ public class ManagedRepositoryContentMock implements 
ManagedRepositoryContent
     }
 
     @Override
+    public Stream<? extends ContentItem> newItemStream( ItemSelector selector, 
boolean parallel ) throws ContentAccessException, IllegalArgumentException
+    {
+        return null;
+    }
+
+    @Override
     public List<? extends Project> getProjects( Namespace namespace ) throws 
ContentAccessException
     {
         return null;
diff --git 
a/archiva-modules/archiva-base/archiva-repository-scanner/src/test/java/org/apache/archiva/repository/scanner/mock/ManagedRepositoryContentMock.java
 
b/archiva-modules/archiva-base/archiva-repository-scanner/src/test/java/org/apache/archiva/repository/scanner/mock/ManagedRepositoryContentMock.java
index 22ab865..7bbf517 100644
--- 
a/archiva-modules/archiva-base/archiva-repository-scanner/src/test/java/org/apache/archiva/repository/scanner/mock/ManagedRepositoryContentMock.java
+++ 
b/archiva-modules/archiva-base/archiva-repository-scanner/src/test/java/org/apache/archiva/repository/scanner/mock/ManagedRepositoryContentMock.java
@@ -45,6 +45,7 @@ import java.nio.file.Paths;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
+import java.util.function.Consumer;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 import java.util.stream.Stream;
@@ -79,6 +80,12 @@ public class ManagedRepositoryContentMock implements 
ManagedRepositoryContent
     }
 
     @Override
+    public void deleteAllItems( ItemSelector selector, 
Consumer<ItemDeleteStatus> consumer ) throws ContentAccessException, 
IllegalArgumentException
+    {
+
+    }
+
+    @Override
     public void deleteItem( ContentItem item ) throws ItemNotFoundException, 
ContentAccessException
     {
 
@@ -127,6 +134,12 @@ public class ManagedRepositoryContentMock implements 
ManagedRepositoryContent
     }
 
     @Override
+    public Stream<? extends ContentItem> newItemStream( ItemSelector selector, 
boolean parallel ) throws ContentAccessException, IllegalArgumentException
+    {
+        return null;
+    }
+
+    @Override
     public List<? extends Project> getProjects( Namespace namespace ) throws 
ContentAccessException
     {
         return null;

Reply via email to