package com.capgemini.reports.common.scheduling.controller;

import java.io.IOException;
import java.util.List;

import javax.ejb.EJB;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.capgemini.reports.database.HibernateUtil;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.json.JSONObject;
import org.quartz.SchedulerException;

import com.capgemini.framework.teamcenter.exceptions.KurtException;
import com.capgemini.reports.common.ServletMessageHelper;
import com.capgemini.reports.database.manager.MngReport;
import com.capgemini.reports.database.manager.MngReport.RunningReportEntry;
import com.capgemini.reports.quartz.SchedulerServer;
import com.capgemini.reports.quartz.SchedulerServer.JobExecution;

import lombok.extern.slf4j.Slf4j;

/**
 * A {@link HttpServlet} that reads data from the DB and Quartz to retrieve queue status, then forwards the data t oa JSP for pretty-printing.
 */
@Slf4j
@WebServlet("/queueReader")
public class QueueReaderServlet extends HttpServlet {
  private static final long serialVersionUID = -1471984298116642565L;

  // Output attribute keys
  private static final String KEY_REPORTS_IN_QUARTZ = "quartzJobList";
  private static final String KEY_REPORTS_IN_QUEUE = "waitingReports";

  private static final String CONTENT_TYPE_JSON = "application/json";
  private static final String FORMATTING_JSP_URL = "/frames/queue.jsp";

  @EJB
  SchedulerServer quartz;

  @Override
  protected void doPost(final HttpServletRequest request, final HttpServletResponse response) throws ServletException, IOException {
    // Parse server request parameters
    try {
      perform(request, response);
      JSONObject successMessage = ServletMessageHelper.successMessage("success");
      response.setContentType(CONTENT_TYPE_JSON);
      response.getWriter().write(successMessage.toString());
    }
    catch (SchedulerException e) {
      // A nice error message will be sent to the user to tell him what he did wrong
      log.error(e.getMessage(), e);
      response.setContentType(CONTENT_TYPE_JSON);
      response.getWriter().write(ServletMessageHelper.errorMessage(new KurtException("Unable to post a message", e)).toString());
    }
  }

  @Override
  protected void doGet(final HttpServletRequest request, final HttpServletResponse response) throws ServletException, IOException {
    doPost(request, response);
  }

  private void perform(final HttpServletRequest request, final HttpServletResponse response)
    throws ServletException, IOException, SchedulerException {
    SessionFactory sessionFactory = HibernateUtil.getSessionFactory();
    Session session = sessionFactory.openSession();
    try {
      // Obtain all reports currently queueing
      MngReport theMngRep = new MngReport();
      List<RunningReportEntry> theWaitingReports = theMngRep.searchWaitingReports(session);
      request.setAttribute(KEY_REPORTS_IN_QUEUE, theWaitingReports);

      // Obtain all report planification jobs stored
      List<JobExecution> tonightJobs = quartz.listAllScheduledJobsForTonight(session);
      request.setAttribute(KEY_REPORTS_IN_QUARTZ, tonightJobs);

      // Add data to the request
      RequestDispatcher dispatcher = getServletContext().getRequestDispatcher(FORMATTING_JSP_URL);
      dispatcher.forward(request, response);
    }
    finally {
      session.close();
    }
  }
}
