Struts 2 JUnit Plugin v2.2.3:测试类扩展StrutsTestCase; 'request'为空

时间:2011-06-03 20:40:35

标签: plugins struts2 junit4

我正在尝试使用Struts2 JUnit插件(v2.2.3 w / Struts2 v2.2.3)并遇到了几个问题。

我尝试使用Struts2 JUnit Plugin Tutorial作为指南。我需要做的第一个更改(不在指南中)是用以下内容注释我的测试类:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations={"classpath*:applicationContext-test.xml"}) 

因为我在尝试运行单元测试时遇到错误:

SEVERE:   [56:51.239] ********** FATAL ERROR STARTING UP STRUTS-SPRING INTEGRATION **********
Looks like the Spring listener was not configured for your web app! 
Nothing will work until WebApplicationContextUtils returns a valid ApplicationContext.
You might need to add the following to web.xml: 
    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>
SEVERE:   [56:51.254] Dispatcher initialization failed

这与教程不同 - 有谁知道为什么我需要这样做?

我还必须添加以下Spring Jars(我的类路径中包含必要的Struts2 jar):

  • 弹簧豆-2.5.6.jar
  • 弹簧上下文2.5.6.jar
  • 弹簧芯2.5.6.jar
  • 弹簧 - 测试 - 2.5.6.jar
  • 弹簧的web-2.5.6.jar

我没有在我的struts应用程序中使用Spring,但我认为需要使用这些jar来模拟request中的模拟StrutsTestCase对象。

我的测试课程:

package com.actions;

import java.io.UnsupportedEncodingException;
import java.util.List;

import javax.servlet.ServletException;

import org.apache.log4j.Logger;
import org.apache.struts2.StrutsTestCase;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.beans.LabelValueBean;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations={"classpath*:applicationContext-test.xml"}) 
public class DocumentCategoryTest extends StrutsTestCase {

    private static Logger log = Logger.getLogger(DocumentCategoryTest .class);

    /**
     * Testing RetrieveDocumentTypesForDocumentCategory
     * Expecting the List<LabelValueBean> is not null
     * @throws ServletException 
     * @throws UnsupportedEncodingException 
     */
    @Test
    public void testRetrieveDocumentTypesForDocumentCategory() throws UnsupportedEncodingException, ServletException {

        final String docCategory = "Employment";

        //set parameters
        request.setParameter("documentCategoryDescription", docCategory);   

        //execute the action
        executeAction("/recipient/RetrieveDocumentTypesForDocumentCategory.action");  

        //retrieve the document types
        @SuppressWarnings("unchecked")
        List<LabelValueBean> testDocTypeList = (List<LabelValueBean>) findValueAfterExecute("documentTypes");

        //make sure the document type list is not null and has at least one document type
        assertNotNull(testDocTypeList);
        assertTrue("At least one document type should exist for category 'Employment'", testDocTypeList.size() > 0);

        //print types
        log.debug("Document types for category '" + docCategory + "'");
        log.debug(testDocTypeList);
    }
}          

当我执行操作时,我会在NullPointerException代码上获得request.setParameter

java.lang.NullPointerException
at com.actions.DocumentCategoryTest.testRetrieveDocumentTypesForDocumentCategory(DocumentCategoryTest.java:38)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.springframework.test.context.junit4.SpringTestMethod.invoke(SpringTestMethod.java:160)
at org.springframework.test.context.junit4.SpringMethodRoadie.runTestMethod(SpringMethodRoadie.java:233)
at org.springframework.test.context.junit4.SpringMethodRoadie$RunBeforesThenTestThenAfters.run(SpringMethodRoadie.java:333)
at org.springframework.test.context.junit4.SpringMethodRoadie.runWithRepetitions(SpringMethodRoadie.java:217)
at org.springframework.test.context.junit4.SpringMethodRoadie.runTest(SpringMethodRoadie.java:197)
at org.springframework.test.context.junit4.SpringMethodRoadie.run(SpringMethodRoadie.java:143)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.invokeTestMethod(SpringJUnit4ClassRunner.java:160)
at org.junit.internal.runners.JUnit4ClassRunner.runMethods(JUnit4ClassRunner.java:51)
at org.junit.internal.runners.JUnit4ClassRunner$1.run(JUnit4ClassRunner.java:44)
at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:27)
at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:37)
at org.junit.internal.runners.JUnit4ClassRunner.run(JUnit4ClassRunner.java:42)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:97)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:49)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

这是因为出于某种原因,requestStrutsTestCase为空。为什么是这样?我正如教程所指示的那样做!

我的操作类扩展了另一个扩展BaseAction并实现ActionSupport的类(SessionAware)。

package com.actions;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;

import org.apache.commons.lang.StringUtils;
import org.apache.log4j.Logger;

import com.actions.BaseAction;

/**
 * Retrieves the document types for the passed in document category
 */
public class DocumentIndexingData extends BaseAction {

    private static final long serialVersionUID = 1L;    
    private static Logger log = Logger.getLogger(DocumentIndexingData.class);

    /*=========================================================================
     * FIELDS
     *=========================================================================*/
    /**
     * The description to use to look up the document types for that category
     */
    private String documentCategoryDescription;
    /**
     * List of document types for a category
     */
    private List<LabelValueBean> documentTypes;

    /*=========================================================================
     * PUBLIC METHODS
     *=========================================================================*/
    /**
     * Retrieves & sets list of document types for document category with passed in ID
     * 
     * @return If there is an error, document type will be set to ERROR; SUCCESS is always returned by this method
     */
    public String retrieveDocumentTypesForDocumentCategory() {      

        List<LabelValueBean> docTypes = new ArrayList<LabelValueBean>();

        //retrieve document types for passed in category ID
        log.debug("looking up document types for category: " + getDocumentCategoryDescription());   

                ////////////////
        //retrieve the document types for the document category here...
                ////////////////

        this.setDocumentTypes(docTypes);

        log.debug("document types found: " + getDocumentTypes());

        return SUCCESS;
    }

    /*=========================================================================
     * GETTERS/SETTERS
     *=========================================================================*/
    /**
     * Retrieves the list of document types
     * 
     * @return  list of document types
     */
    public List<LabelValueBean> getDocumentTypes() {
        return documentTypes;
    }
    /**
     * Sets the list of document types
     * 
     * @param documentTypes
     */
    public void setDocumentTypes(List<LabelValueBean> documentTypes) {
        this.documentTypes = documentTypes;
    }
    /**
     * Retrieves the document category to retrieve document types for
     * 
     * @return  the document category
     */
    public String getDocumentCategoryDescription() {
        return documentCategoryDescription;
    }
    /**
     * Sets the document category to retrieve document types for 
     * 
     * @param documentCategoryDescription   the document category to retrieve document types for 
     */
    public void setDocumentCategoryDescription(String documentCategoryDescription) {
        this.documentCategoryDescription = documentCategoryDescription;
    }
}

struts.xml条目:

<!-- indexing attributes action -->
<action name="RetrieveDocumentTypesForDocumentCategory" class="com.actions.DocumentIndexingData" method="retrieveDocumentTypesForDocumentCategory">
    <result type="json">
        <param name="root">documentTypes</param>
    </result>
</action>

我非常仔细地遵循教程,为什么request为空?非常感谢你的帮助!

更新(我的解决方案!来自@Alex): 我现在只在我的类路径中包含以下Struts JAR:

  • struts2的-的junit-插件-2.2.3.jar
  • spring-beans-2.5.6.jar
  • spring-context-2.5.6.jar
  • spring-core-2.5.6.jar
  • spring-test-2.5.6.jar
  • spring-web-2.5.6.jar

样品测试:

    public class MyTest extends StrutsTestCase {  

        @Test
        public void testMyAction() throws Exception {  

            request.setParameter("aParameter", "aValue");

            //create action proxy
            ActionProxy proxy = getActionProxy("/test/MyAction");
            assertNotNull(proxy);       
            MyAction action = (MyAction) proxy.getAction();
            assertNotNull(action);

            //execute the action
            String result = proxy.execute();

            //make assertions, expecting success and no error messags   
            assertTrue("There should be no field errors: " + action.getFieldErrors(), action.getFieldErrors().size() == 0);
            assertTrue("There should be no action errors: " + action.getActionErrors(), action.getActionErrors().size() == 0);
            assertEquals("Result did not match expected value; ", Action.SUCCESS, result);
        } 
    } 

1 个答案:

答案 0 :(得分:3)

  

我没有在我的struts应用程序中使用Spring,但我认为这些jar需要使用模拟请求对象,例如StrutsTestCase。

鉴于您在上面看到的异常消息,您的应用程序认为它使用Spring。你的类路径上有Struts2-Spring-Plugin吗?如果您没有将Spring用于IoC,则不应将其包含在类路径中。

如果你不使用Spring,你应该可以按照你没有任何弹簧罐引用的指南来测试你的行为。尝试删除所有弹簧罐和struts2-spring-plugin jar。你当然也不需要:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations={"classpath*:applicationContext-test.xml"})
如果你不使用spring,请在你的测试类中

同时检查struts.xml是否包含以下行:

<constant name="struts.objectFactory" value="org.apache.struts2.spring.StrutsSpringObjectFactory"/>