/*
* 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.
*/
package org.apache.stanbol.enhancer.servicesapi;

import java.io.InputStream;
import java.util.concurrent.locks.ReadWriteLock;

import org.apache.clerezza.rdf.core.UriRef;
import org.apache.clerezza.rdf.core.access.LockableMGraph;

/**
 * A unit of content that Stanbol Enhancer can enhance.
 * <p>
 * Gives access to the binary content that
 * was registered, and the Graph that represents its metadata
 * (provided by client and/or generated).
 */
public interface ContentItem {

    /** The Uri of this ContentItem (either supplied by client or generated by Stanbol Enhancer) */
    UriRef getUri();

    /**
     * The binary content stream. Shortcut for
     * <code>{@link #getBlob()}{@link Blob#getStream() .getStream()}</code>
     * @return the InputStream
     */
    InputStream getStream();

    /**
     * The MimeType. Shortcut for
     * <code>{@link #getBlob()}{@link Blob#getMimeType() .getMimeType()}</code>.
     * @return the MimeType as string
     */
    String getMimeType();

    /**
     * Read/write lock used to synchronise access to the {@link #getMetadata()
     * metadata} and the content parts of this content item.<p>
     * The lock used by the {@link LockableMGraph#getLock()} MUST BE the same
     * as the lock returned by this Instance. This is to avoid deadlocks when
     * using a lock while iterating over the {@link #getMetadata() metadata} and
     * simultaneously accessing the content parts. In other words
     * calling <code> contentItem.getLock() == contentItem.getMetadata().getLock()</code>
     * MUST BE <code>true</code>
     *  
     * @return the lock used for the content parts and the {@link LockableMGraph}
     * containing the metadata of this content item.
     */
    ReadWriteLock getLock();
    
    /** Optional metadata */
    LockableMGraph getMetadata();
    
    /**
     * The main content of this content item
     * 
     * @return the blob at index 0
     */
    Blob getBlob();
    
    /**
     * A content item may consists of multiple parts, while the part with index 0 should always be a blob,
     * higher position may be used by Enhancer to story arbitrary objects, such objects can be used for 
     * accessing the precomputations of EnhancementEngines previous in the chain.
     * @throws NoSuchPartException if no part with the parsed index exists
     * @throws ClassCastException if the class of the part is not compatiple with
     * the requested class
     * @throws IllegalArgumentException if <code>null</code> is parsed as
     * clazz.
     */
    <T> T getPart(int index, Class<T> clazz) throws NoSuchPartException;
    
    /**
     * Each part of the content item has a URI. EnhancementEngines typically access parts by their Uri as the
     * position may vary depending on the chain.
     * @throws NoSuchPartException if no part with the parsed uri exists
     * @throws ClassCastException if the class of the part is not compatiple with
     * the requested class
     * @throws IllegalArgumentException if <code>null</code> is parsed as
     * uri or clazz.
     */
    <T> T getPart(UriRef uri, Class<T> clazz) throws NoSuchPartException;
    
    /**
     * Get the uri of the part at the specified index
     * @throws NoSuchPartException if no part with the parsed index exists
     */
    UriRef getPartUri(int index) throws NoSuchPartException;

    /**
     * Add a new part to this ContentItem
     * 
     * @param uriRef the URI of the part
     * @param object the part
     * @return the part replaced by the parsed object or <code>null</code> if
     * no part with the parsed URI was present
     * @throws IllegalArgumentException if <code>null</code> is parsed as
     * uriRef or object.
     */
    Object addPart(UriRef uriRef, Object object);
    
    /**
     * Removes a part - other than the main content part - from this ContentItem
     * @param index the index of the part to remove. NOTE that index '0' 
     * - the main content part - can NOT be removed!
     * @throws NoSuchPartException if no ContentPart with the parsed id exists
     * @throws IllegalArgumentException it the parsed index &lt; 0
     * @throws IllegalStateException if '0' is parsed as index. The index '0' 
     * - the main content part - can NOT be removed!
     */
    void removePart(int index);
    
    /**
     * Removes a part - other than the main content part - from this ContentItem
     * @param uriRef the uri of the part to remove. NOTE that the part with the
     * uri <code>{@link #getPartUri(int) getPartUri(0)}</code> - the main 
     * content part - can NOT be removed!
     * @throws NoSuchPartException if no ContentPart with the parsed uri exists
     * @throws IllegalArgumentException it the parsed uri is <code>null</code>
     * @throws IllegalStateException if the parsed uri is equals to
     * <code>{@link #getPartUri(int) getPartUri(0)}</code>. This uri refers to
     * the main content part. This part can NOT be removed by this method
     */
    void removePart(UriRef uriRef);
    
}
