Search code examples
javajspconfigurationstruts2struts2-convention-plugin

Struts 2 annotation issues in action


I have used Struts2 Annotation

My web.xml is:

<welcome-file-list>
    <welcome-file>index.jsp</welcome-file>
</welcome-file-list>

<filter>
    <filter-name>struts2</filter-name>
    <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>struts2</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

My JSP is:

      <s:form action="test" method="post">
            <s:textfield name="id" label="Id"></s:textfield>        
            <s:submit value="Submit"></s:submit>
     </s:form>

My class is:

      @Namespace("/")
      public class Test extends ActionSupport {

  private static final long serialVersionUID = 1L;

      @Action(value = "test", results = { @Result(name = "success", location =     "success.jsp") })
      public String input() {

         System.out.println("input call");
         return SUCCESS;
     }

 }

I got error:

HTTP Status 404 - There is no Action mapped for namespace / and action name test.

Folder structure:

my folder structure is


Solution

  • Do the following.

    Place your Test action in a package called "com.mydomain.action", the first part can be what ever you want but it must end in ".action" struts2-conventions will pick up your action. If there are additional packages such as: "com.mydomain.action.here" then the packages following "action" will be interpreted as a struts2 namespace.

    Please rename "success.jsp" to "test.jsp" and move it to: "/WEB-INF/content/test.jsp", /WEB-INF/content is where actions in the default namespace will have their view resolved. In the case of the /here package, views would need to be placed under /WEB-INF/content/here

    Lets rewrite your Test action to keep with conventions defaults:

    public class Test extends ActionSupport {
       private static final long serialVersionUID = 1L;
       public String execute() {
             System.out.println("input call");
             return SUCCESS;
       }
     }
    

    Something else to note. You could have called your view test-success.jsp instead of just test. This is because conventions will look first for a view with the String returned from the action appended to the Action name which in this case is test.

    Also while Classes are camel case: MyMagicTest a veiw for such an action class would be my-magic-test.jsp

    Now where annotations fit in:

    Now that you know you can do a lot without xml OR annotations... conventions makes use of annotations to OVERRIDE the defaults when needed. You do this to take shortcuts, and so annotations signal an exceptional case. Don't use them to define what conventions readily provides out of the box.

    For more information on conventions please see: https://cwiki.apache.org/WW/convention-plugin.html which I would strongly recommend you review fully so you'll know many of the possible features.