package org.yacos.web.author.controller;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.ArrayList;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.validation.BindException;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.ModelAndViewDefiningException;
import org.springframework.web.servlet.mvc.SimpleFormController;
import org.springframework.web.servlet.view.RedirectView;
import org.yacos.core.article.Article;
import org.yacos.core.article.IArticleManager;
import org.yacos.core.conferences.Conference;
import org.yacos.core.users.User;
import org.yacos.web.author.form.FormSubmission;
import org.yacos.web.system.session.SessionService;

public class SArticleController extends SimpleFormController {

	/** Logger for this class and subclasses */
	protected final Log logger = LogFactory.getLog(getClass());

	private IArticleManager articleManager;
	private String downloadDirPath;

	public ModelAndView onSubmit(HttpServletRequest request,
			HttpServletResponse response, Object command, BindException errors)
	throws ServletException, IllegalStateException {

		// Fetching conference
		Conference conf = SessionService.getInstance().getCurrentConference();
		// Fetching user
		User user = SessionService.getInstance().getCurrentUser();

		String title = ((FormSubmission) command).getTitle();
		String theme = ((FormSubmission) command).getTheme();
		String abstractText = ((FormSubmission) command).getAbstractText();

		ArrayList<String> listSecondaryAuthor = new ArrayList<String>();
		// Removes null entries from the list
		for(String sAuthor : ((FormSubmission) command).getListe()){
			if(sAuthor != null){
				listSecondaryAuthor.add(sAuthor);
			}
		}

		String action = request.getParameter("action");
		if (action == null || action.equals(""))
		{

			String nomFile="";

			try {
				MultipartFile file = ((FormSubmission) command).getFile();
				if (file == null || file.isEmpty()) {
					errors.rejectValue("file", "form.submitArticle.noFile");
					try {
						return showForm(request, response, errors);
					} catch (Exception e) {
						e.printStackTrace();
					}
				}
				else {

					// Creates the article
					Article newArticle = articleManager.addArticle(
							title, theme, abstractText, nomFile, user.getLogin(),
							listSecondaryAuthor, Article.State.SUBMITED, conf.getId());

					if(newArticle==null){
						errors.reject("article.errors.didNotSave");
						try {
							return showForm(request, response, errors);
						} catch (Exception e) {
							e.printStackTrace();
						}
					}

					byte b[] = file.getBytes();

					String path = "conference"+conf.getId()+"/";
					(new File(downloadDirPath+path)).mkdirs();
					path += newArticle.getId()+"_"+file.getOriginalFilename();
					File uploadedFile = new File(downloadDirPath+path);

					FileOutputStream fos = new FileOutputStream(uploadedFile);

					fos.write(b);
					fos.close();

					newArticle.setURL_article(path);
					articleManager.updateArticle(newArticle);
				}
			}
			catch (FileNotFoundException e) {
				System.out.println(e);
			} catch (IOException e) {
				System.out.println(e);
			}

			// The role author might have been added, refresh the credentials
			SessionService.getInstance().refreshAuthentication();
		}
		else if (action.equals("modify")) {
			String articleID = request.getParameter("articleID");

			try {
				Integer id = new Integer(articleID);

				// TODO : vérifier que l'id de l'article appartient ŕ l'auteur... vive les GET...

				Article old = articleManager.getArticle(id);
				old.setTitle(title);
				old.setTopic(theme);
				old.setSecondaryAuthors(listSecondaryAuthor);
				old.setAbstractText(abstractText);

				MultipartFile file = ((FormSubmission) command).getFile();
				if (file == null || file.isEmpty()) {
					articleManager.updateArticle(old);
				}
				else {
					byte b[] = file.getBytes();

					String path = "conference"+conf.getId()+"/";
					(new File(downloadDirPath+path)).mkdirs();
					path += old.getId()+"_"+file.getOriginalFilename();
					File uploadedFile = new File(downloadDirPath+path);

					FileOutputStream fos = new FileOutputStream(uploadedFile);

					fos.write(b);
					fos.close();

					old.setURL_article(path);
					articleManager.updateArticle(old);
				}
			} catch (NumberFormatException e) {
				throw new ModelAndViewDefiningException(new ModelAndView("404error"));
			} catch (FileNotFoundException e) {
				System.out.println(e);
			} catch (IOException e) {
				System.out.println(e);
			}

		}
		else {
			throw new ModelAndViewDefiningException(new ModelAndView("404error"));
		}

		return new ModelAndView(new RedirectView(getSuccessView()));
	}

	protected Object formBackingObject(HttpServletRequest request) throws ModelAndViewDefiningException {
		String action = request.getParameter("action");
		if (action == null || action.equals(""))
		{
			FormSubmission myArticle = new FormSubmission();
			return myArticle;
		}
		else if (action.equals("modify")) {

			String articleID = request.getParameter("articleID");

			try {
				Integer id = new Integer(articleID);

				// TODO : vérifier que l'id de l'article appartient ŕ l'auteur... vive les GET...

				Article a = articleManager.getArticle(id);

				if (a == null)
					throw new ModelAndViewDefiningException(new ModelAndView("denied", "message", getMessageSourceAccessor().getMessage("submission.modify.denied")));

				FormSubmission myArticle = new FormSubmission();				
				
				myArticle.setAbstractText(a.getAbstractText());
				myArticle.setTitle(a.getTitle());
				//myArticle.setListe(a.getSecondaryAuthors());
				myArticle.setTheme(a.getTopic());

				request.getSession().setAttribute("listSecondaryAuthors", a.getSecondaryAuthors());

				return myArticle;

			}
			catch (NumberFormatException e) {
				throw new ModelAndViewDefiningException(new ModelAndView("404error"));
			}

		}
		else {
			throw new ModelAndViewDefiningException(new ModelAndView("404error"));
		}


	}

	public IArticleManager getArticleManager() {
		return articleManager;
	}

	public void setArticleManager(IArticleManager articleManager) {
		this.articleManager = articleManager;
	}

	public String getDownloadDirPath() {
		return downloadDirPath;
	}

	public void setDownloadDirPath(String downloadDirPath) {
		this.downloadDirPath = downloadDirPath;
	}
}