package gr.uoa.di.web.utils.ep;

import eu.dnetlib.domain.data.Document;
import eu.dnetlib.domain.functionality.UserProfile;
import gr.uoa.di.web.utils.ep.domain.Entity;
import gr.uoa.di.web.utils.ep.domain.Graph;
import gr.uoa.di.web.utils.ep.domain.Node;
import gr.uoa.di.web.utils.ep.domain.RelatedNode;
import gr.uoa.di.web.utils.ep.domain.Relation;
import gr.uoa.di.web.utils.search.DocumentPage;

import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * This interface describes a manager for enhanced publications.
 * @author thanos
 *
 */
public interface EPManager {
	/**
	 * Get the available entities.
	 * @return a set containing the available entities
	 * @throws EPManagerException if any errors occur
	 */
	public Set<Entity> getEntities() throws EPManagerException;
	
	/**
	 * Get the available relations.
	 * @return a set containing the available relations
	 * @throws EPManagerException if any errors occur
	 */
	public Set<Relation> getRelations() throws EPManagerException;
	
	/**
	 * Get the dropbox contents of a user
	 * @param userProfile the user to get dropbox contents of
	 * @return a set containing the documents of the user
	 * @throws EPManagerException if any errors occur
	 */
	public Set<Map<String, List<String>>> getDropboxContents(UserProfile userProfile) throws EPManagerException;
	
	/**
	 * Get a graph by its root node id.
	 * @param rootId the id of the root node
	 * @return a graph containing all the ancestors of the root node, its immediate parents and the edges connecting them or null if no such root node exists
	 * @throws EPManagerException if any errors occur
	 */
	public Graph getGraph(String rootId) throws EPManagerException;
	
	/**
	 * Save a graph.
	 * @param userProfile the user profile of the user attempting to save the graph
	 * @param rootId the id of the root node  
	 * @param commands the commands to execute in order to save the graph
	 * @return the (possibly) new id of the root node
	 * @throws EPManagerException if any errors occur
	 */
	public void saveGraph(UserProfile userProfile, String [] commands) throws EPManagerException;
	
	/**
	 * Save an enhanced publication.
	 * @param userProfile the user profile of the user that requests the creation
	 * @param creator the creator of the enhanced publication (if null or empty will be the aforementioned user)
	 * @param description the description of the enhanced publication
	 * @param language the language of the enhanced publication
	 * @param subject the subject of the enhanced publication
	 * @param title the title of the enhanced publication
	 * @param ePrintId the id of the e-Print of the enhanced publication
	 * @param nonEPrintIds the ids of the other contents (non-e-Prints) of the enhanced publication
	 * @return the id of the created enhanced publication
	 * @throws EPManagerException if any errors occur
	 */
	public String saveEnhancedPublication(UserProfile userProfile, String description, String language, String subject, String title, String ePrintId, Set<String> nonEPrintIds) throws EPManagerException;
	
	/**
	 * Save an aggregation object.
	 * @param userProfile the user profile of the user that requests the creation
	 * @param creator the creator of the aggregation object (if null or empty will be the aforementioned user)
	 * @param description the description of the aggregation object
	 * @param language the language of the aggregation object
	 * @param subject the subject of the aggregation object
	 * @param title the title of the aggregation object
	 * @param contentIds the ids of the contents of the aggregation object
	 * @return the id of the created aggregation object
	 * @throws EPManagerException if any errors occur
	 */
	public String saveAggregationObject(UserProfile userProfile, String description, String language, String subject, String title, Set<String> contentIds) throws EPManagerException;
	
	/**
	 * Get available enhanced publications.
	 * @param pageSize the page size to use
	 * @param pageNumber the number of the page to fetch
	 * @return a document page containing the corresponding subset of available enhanced publications 
	 * @throws EPManagerException if any errors occur
	 */
	public DocumentPage getEnhancedPublications(int pageSize, int pageNumber) throws EPManagerException;
	
	/**
	 * Get an existing enhanced publication.
	 * @param id the id of the enhanced publication to fetch
	 * @return the enhanced publication with this id or null if none is found
	 * @throws EPManagerException if any errors occur
	 */
	public Document getEnhancedPublication(String id) throws EPManagerException;
	
	/**
	 * Get an existing node.
	 * @param id the id of the node to fetch
	 * @return the node with the given id or null if none is found
	 * @throws EPManagerException if any errors occur
	 */
	public Node getNode(String id) throws EPManagerException;
	
	/**
	 * Get the parents of a node.	
	 * @param node the node to fetch parents of
	 * @return a set containing all the parents as related nodes
	 * @throws EPManagerException if any errors occur
	 */
	public Set<RelatedNode> getParents(Node node) throws EPManagerException;
	
	/**
	 * Get the children of a node.
	 * @param node the node to fetch children of
	 * @return a set containing all the children as related nodes
	 * @throws EPManagerException if any errors occur
	 */
	public Set<RelatedNode> getChildren(Node node) throws EPManagerException;
}