package faqapp.struts.actions;

import java.rmi.RemoteException;
import javax.servlet.http.HttpServletRequest;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionErrors;
import org.apache.struts.action.ActionError;
import org.apache.struts.action.Action;

import faqapp.AppSessionFacade;
import faqapp.TopicTO;
import faqapp.AreaTO;
import faqapp.struts.forms.TopicForm;

/**
 * Implementation of TopicAction. This FAQApp specific action implementation implements
 * the business logic execution methods defined and invoked by FAQAbstractAction,
 * which are validate, create, update, saveCreate, saveUpdate, and query.
 */
public final class TopicAction extends FAQAbstractAction {
    public ActionErrors validate(ActionForm form, HttpServletRequest request,
                                 AppSessionFacade asf) throws RemoteException {
        /* Validate from data and return validation errors if necessary */
        TopicForm tf = (TopicForm)form;
        readAllAreas(tf, request, asf);
        ActionErrors errors = new ActionErrors();
        if ((tf.getTopicDesc() == null) || (tf.getTopicDesc().length() < 1))
            errors.add("topicDesc", new ActionError("errors.topicDesc.required"));
        return errors;
    }

    public String create(ActionForm form, HttpServletRequest request,
                         AppSessionFacade asf) throws RemoteException {
        /**
         * Read all Areas and store them in TopicForm for
         * further usage in view (Topic.jsp).
         */
        TopicForm tf = (TopicForm)form;
        return readAllAreas(tf, request, asf);
    }

    public String update(ActionForm form, HttpServletRequest request,
                         AppSessionFacade asf) throws RemoteException {
        /**
         * Read Topic based on TopicForm.id, the associated areaID and all Areas and
         * store all the data in TopicForm for further usage in view (Topic.jsp).
         */
        TopicForm tf = (TopicForm)form;
        TopicTO topic = asf.findTopicByPK(tf.getId());
        tf.setTopicDesc(topic.getTopicDesc());
        tf.setAreaID(topic.getAreaID());
        return readAllAreas(tf, request, asf);
    }

    public String saveCreate(ActionForm form, HttpServletRequest request,
                             AppSessionFacade asf) throws RemoteException{
        /**
         * Invoke createTopic(...) method on AppSessionFacade
         * with corresponding data from TopicForm
         */
        TopicForm tf = (TopicForm)form;
        tf.setId(asf.createTopic(tf.getTopicDesc(), tf.getAreaID()));
        return SUCCESS;
    }

    public String saveUpdate(ActionForm form, HttpServletRequest request,
                             AppSessionFacade asf) throws RemoteException{
        /**
         * Invoke updateTopic(...) method on AppSessionFacade
         * with corresponding data from TopicForm
         */
        TopicForm tf = (TopicForm)form;
        asf.updateTopic(tf.getId(), tf.getTopicDesc(), tf.getAreaID());
        return SUCCESS;
    }

    public String query(ActionForm form, HttpServletRequest request,
                        AppSessionFacade asf) throws RemoteException {
        /**
         * Read all Topics and associated Areas and store them
         * in HTTP request for further usage in view (TopicQuery.jsp).
         */
        TopicTO[] topics = asf.findTopicAll();
        request.setAttribute("topics", topics);
        AreaTO[] areas = new AreaTO[topics.length];
        for (int i=0; i<topics.length; i++) {
            areas[i] = asf.findAreaByPK(topics[i].getAreaID());
        }
        request.setAttribute("areas", areas);
        return SUCCESS;
    }

    private String readAllAreas(TopicForm form, HttpServletRequest request,
                                AppSessionFacade asf) throws RemoteException {
        /**
         * Read all Areas and store them in TopicForm for further usage in
         * view (Topic.jsp & TopicQuery.jsp).
         * Forward to "warning" page in case no areas exist.
         */
        AreaTO[] areas = asf.findAreaAll();
        if ((areas == null || areas.length < 1)) {
            ActionErrors errors = new ActionErrors();
            errors.add("warning", new ActionError("warning.noAreasExist"));
            request.setAttribute(Action.ERROR_KEY, errors);
            return WARNING;
        }
        form.setAreas(areas);
        return SUCCESS;
    }
}

