/*
 * MyTasksAction.java
 *
 * Autor: Piotr Achinger <piotr.achinger at gmail.com>
 */
package dendrarium.portal.collisions;

import dendrarium.core.entities.TaskBusinessProcess;
import dendrarium.core.entities.User;
import dendrarium.portal.PaginatedList;
import dendrarium.trees.AnswerType;
import java.io.Serializable;
import java.util.Arrays;
import java.util.List;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.criterion.Restrictions.*;
import org.jboss.seam.ScopeType;
import org.jboss.seam.annotations.Factory;
import org.jboss.seam.annotations.In;
import org.jboss.seam.annotations.Logger;
import org.jboss.seam.annotations.Name;
import org.jboss.seam.annotations.Observer;
import org.jboss.seam.annotations.Scope;
import org.jboss.seam.annotations.datamodel.DataModel;
import org.jboss.seam.annotations.web.RequestParameter;
import org.jboss.seam.log.Log;

/**
 *
 * @author Piotr Achinger <piotr.achinger at gmail.com>
 */
@Name("collisionList")
@Scope(ScopeType.SESSION)
public class CollisionList implements Serializable {

    private static final int PAGE_SIZE = 10;

    @In
    Session session;

    @DataModel(value = "collisions")
    private List<TaskBusinessProcess> collisions;

    private PaginatedList<TaskBusinessProcess> collisionsPL;

    @DataModel(value = "solvedCollisions")
    private List<TaskBusinessProcess> solvedCollisions;

    private PaginatedList<TaskBusinessProcess> solvedCollisionsPL;

    @DataModel(value = "agreements")
    private List<TaskBusinessProcess> agreements;

    private PaginatedList<TaskBusinessProcess> agreementsPL;

    Integer tab;

    private List<User> userFilters;

    private String userFilter;

    private String textFilter = "";

    private List<AnswerType> answerTypeFilters;

    private AnswerType answerTypeFilter;

    @RequestParameter
    public Integer page_no;

    @RequestParameter
    public String list_id;

    @Logger
    Log log;

    public CollisionList() {
        answerTypeFilters = Arrays.asList(AnswerType.values());
        answerTypeFilter = null;
    }

    private String makeQueryText(String list_id) {
        String query = "";
        if ("collisions".equals(list_id)) {
            query = "from TaskBusinessProcess tbp where tbp.current = TRUE and "
                    + "((tbp.state = dendrarium.core.entities.TaskBusinessProcessState.COLLISION and "
                    + "tbp.user1Answer.confirmed = TRUE and tbp.user2Answer.confirmed = TRUE) "
                    + "or tbp.state = dendrarium.core.entities.TaskBusinessProcessState.INACCEPTANCE)";
        } else if ("solvedCollisions".equals(list_id)) {
            query = "from TaskBusinessProcess tbp where tbp.current = TRUE and "
                    + "tbp.state = dendrarium.core.entities.TaskBusinessProcessState.COLLISION_SOLVED";
        } else if ("agreements".equals(list_id)) {
            query = "from TaskBusinessProcess tbp where tbp.current = TRUE and "
                    + "tbp.state = dendrarium.core.entities.TaskBusinessProcessState.AUTOACCEPTED ";
        }

        //teraz filtry
        if (isActiveTab(list_id)) {
            if (userFilter != null) {
                query += " and (user1Answer.user.username = :user or user2Answer.user.username = :user)";
            }

            if (answerTypeFilter != null) {
                query += " and (user1Answer.type = :type or user2Answer.type = :type)";
            }

            if (!textFilter.equals("")) {
                query += " and task.sentence like :text";
            }
        }
        return query;
    }

    private boolean isActiveTab(String list_id) {
        return tab == null || ("collisions".equals(list_id) && tab == 0)
                || ("solvedCollisions".equals(list_id) && tab == 1)
                || ("agreements".equals(list_id) && tab == 2);
    }

    private void applyFilters(Query q) {
        if (userFilter != null) {
            String userFilterName = userFilter.substring(5, userFilter.length() - 1);
            q.setParameter("user", userFilterName);
        }
        if (answerTypeFilter != null) {
            q.setParameter("type", answerTypeFilter);
        }
        if (!textFilter.equals("")) {
            q.setParameter("text", "%" + textFilter + "%");
        }
    }

    private Long listCount(String list_id) {
        Query q = session.createQuery("select count(tbp) " + makeQueryText(list_id));
        if (isActiveTab(list_id)) {
            applyFilters(q);
        }
        return (Long) q.uniqueResult();
    }

    private Query makeQuery(String list_id) {
        Query q = session.createQuery(makeQueryText(list_id));
        if (isActiveTab(list_id)) {
            applyFilters(q);
        }
        return q;
    }

    //@Factory(value = "collisions")
    //@Observer("tbpchangestate")
    public void getCollisions() {
        Query allCollisions = makeQuery("collisions");
        Integer page = 0;

        if (collisionsPL != null) {
            page = collisionsPL.getPageNo();
        }
        collisionsPL = new PaginatedList<TaskBusinessProcess>(listCount("collisions"), allCollisions, PAGE_SIZE);
        getPage(page, "collisions");
        //return collisions;
    }

    //@Factory(value = "solvedCollisions")
    //@Observer("tbpchangestate")
    public void getSolvedCollisions() {
        Query allSolvedCollisions = makeQuery("solvedCollisions");
        Integer page = 0;

        if (solvedCollisionsPL != null) {
            page = solvedCollisionsPL.getPageNo();
        }
        solvedCollisionsPL = new PaginatedList<TaskBusinessProcess>(listCount("solvedCollisions"), allSolvedCollisions, PAGE_SIZE);
        getPage(page, "solvedCollisions");
        //return solvedCollisions;
    }
    /* humble co@author Tomasz Badowski*/

    //@Factory(value = "agreements")
    //@Observer("tbpchangestate")
    public void getAgreements() {
        Query allAgreements = makeQuery("agreements");
        Integer page = 0;

        if (agreementsPL != null) {
            page = agreementsPL.getPageNo();
        }
        agreementsPL = new PaginatedList<TaskBusinessProcess>(listCount("agreements"), allAgreements, PAGE_SIZE);
        getPage(page, "agreements");
        //return agreements;
    }

    private void getPage(int page, String list_id) {
        Query q = makeQuery(list_id);
        if ("collisions".equals(list_id)) {
            collisionsPL.getPage(q, page);
            collisions = collisionsPL.getCurrentPage();
        }
        if ("solvedCollisions".equals(list_id)) {
            solvedCollisionsPL.getPage(q, page);
            solvedCollisions = solvedCollisionsPL.getCurrentPage();
        }
        if ("agreements".equals(list_id)) {
            agreementsPL.getPage(q, page);
            agreements = agreementsPL.getCurrentPage();
        }
    }

    public void getPage() {
        getPage(page_no, list_id);
    }

    public PaginatedList<TaskBusinessProcess> getAgreementsPL() {
        return agreementsPL;
    }

    public PaginatedList<TaskBusinessProcess> getCollisionsPL() {
        return collisionsPL;
    }

    public PaginatedList<TaskBusinessProcess> getSolvedCollisionsPL() {
        return solvedCollisionsPL;
    }

    public void setTab(int nr) {
        if (!textFilter.equals("") || userFilter != null || answerTypeFilter != null) {
            collisionsPL = null;
            solvedCollisionsPL = null;
            agreementsPL = null;
        }
        textFilter = "";
        userFilter = null;
        answerTypeFilter = null;
        tab = nr;
    }

    // hak
    public Boolean lists() {
        getCollisions();
        getSolvedCollisions();
        getAgreements();
        return false;
    }

    public int getTab() {
        if (collisionsPL == null) {
            lists();
        }
        if (tab == null) {
            if (!collisionsPL.isEmpty()) {
                tab = 0;
            } else if (!solvedCollisionsPL.isEmpty()) {
                tab = 1;
            } else if (!agreementsPL.isEmpty()) {
                tab = 2;
            } else {
                tab = 0;
            }
        }
        return tab;
    }

    public String getTextFilter() {
        return textFilter;
    }

    public void setTextFilter(String textFilter) {
        this.textFilter = textFilter;
    }

    public String getUserFilter() {
        return userFilter;
    }

    public void setUserFilter(String userFilter) {
        this.userFilter = userFilter;
    }

    public List<User> getUserFilters() {
        if (userFilters == null) {
            userFilters = session.getNamedQuery("getDendrologs").list();
        }
        return userFilters;
    }

    public void setUserFilters(List<User> userFilters) {
        this.userFilters = userFilters;
    }

    public AnswerType getAnswerTypeFilter() {
        return answerTypeFilter;
    }

    public void setAnswerTypeFilter(AnswerType answerTypeFilter) {
        this.answerTypeFilter = answerTypeFilter;
    }

    public List<AnswerType> getAnswerTypeFilters() {
        return answerTypeFilters;
    }

    public void setAnswerTypeFilters(List<AnswerType> answerTypeFilters) {
        this.answerTypeFilters = answerTypeFilters;
    }

    public void getSearchAnswers() {
        collisionsPL = null;
        solvedCollisionsPL = null;
        agreementsPL = null;
    }
}
