package jp.sourceforge.glad.struts.action;

import static org.easymock.EasyMock.*;

import java.lang.reflect.Method;

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

import jp.sourceforge.glad.struts.annotation.StrutsAction;
import jp.sourceforge.glad.struts.annotation.StrutsException;
import jp.sourceforge.glad.struts.annotation.StrutsForm;
import jp.sourceforge.glad.struts.annotation.StrutsForward;
import jp.sourceforge.glad.struts.config.ModuleConfigBuilder;
import jp.sourceforge.glad.struts.config.impl.ModuleConfigBuilderImpl;
import junit.framework.TestCase;

import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.validator.ValidatorForm;

/**
 * {@link AbstractAction} の単体テスト。
 * 
 * @author GLAD!!
 */
public class AbstractActionTest extends TestCase {

    DispatchAction action;

    ModuleConfigBuilder builder;

    protected void setUp() throws Exception {
        action = new DispatchAction();
        builder = new ModuleConfigBuilderImpl();
    }

    protected void tearDown() throws Exception {
        action = null;
        builder = null;
    }

    public void testIndex() throws Exception {
        Method method = DispatchAction.class.getMethod("index");
        ActionMapping mapping = (ActionMapping)
                builder.createActionConfig(DispatchAction.class, method);
        ActionForm form = null;
        HttpServletRequest request = createMock(HttpServletRequest.class);
        HttpServletResponse response = createMock(HttpServletResponse.class);
        ActionForward forward =
                action.execute(mapping, form, request, response);
        assertEquals("success", forward.getName());
        assertEquals("index", action.invocation[0]);
    }

    @StrutsForm
    static class SimpleForm extends ValidatorForm {
    }

    static class DispatchAction extends AbstractAction {

        Object[] invocation;

        void invoked(Object... args) {
            invocation = args;
        }

        @StrutsAction(
            path = "/dispatch",
            forwards = @StrutsForward(path = "/dispatch/input.do"))
        public void index() {
            invoked("index");
        }

        @StrutsAction
        public void input() {
            invoked("input");
        }

        @StrutsAction(validate = true)
        public String confirm(SimpleForm form, HttpServletRequest request) {
            invoked("confirm", form, request);
            return SUCCESS;
        }

        @StrutsAction(
            forwards = {
                @StrutsForward(path = "/dispatch/complete.do", redirect = true),
                @StrutsForward(name = "error", path = "/dispatch/input.do")
            },
            exceptions = @StrutsException(
                type = RuntimeException.class, path = "/dispatch/input.do"))
        public String execute(HttpServletRequest request) {
            invoked("execute", request);
            return SUCCESS;
        }

        @StrutsAction
        public void complete(HttpServletRequest request) {
            invoked("complete", request);
        }

    }

}
