• Liferay Struts Action Hook

    Posted on December 14, 2014 by Hamidul Islam in Liferay.

    Struts-Action-Hook-Top


    aimLiferay Struts Action Hook is another type of hook that can be used to override existing struts action and also we can add our own struts action. To follow this article you should know the basics of struts actions. Struts actions are defined as classes and they’re all connected in a struts-config.xml file.In liferay source code the path of this file is /portal-web/docroot/WEB-INF/struts-config.xml. Before starting this tutorial you can have look to this file.


    Override Existing Struts Action by Struts Action Hook

    Override-Existing-Struts-Action

    Whenever we login com.liferay.portlet.login.action.LoginAction is the action class generally we invoke. We are going to change it by Struts Action Hook. Follow the steps

    1. Create Liferay Plugin Project of type Hook.

    2. Modify liferay-hook.xml

    <?xml version="1.0"?>
    <!DOCTYPE hook PUBLIC "-//Liferay//DTD Hook 6.2.0//EN" "http://www.liferay.com/dtd/liferay-hook_6_2_0.dtd">
    
    <hook>
        <struts-action>
            <struts-action-path>/login/login</struts-action-path>
            <struts-action-impl>com.proliferay.demo.ExampleLoginAction</struts-action-impl>
        </struts-action>
    </hook>
    

     

    3. ExampleLoginAction.java

    package com.proliferay.demo;
    
    import javax.portlet.ActionRequest;
    import javax.portlet.ActionResponse;
    import javax.portlet.PortletConfig;
    import javax.portlet.RenderRequest;
    import javax.portlet.RenderResponse;
    
    import com.liferay.portal.kernel.struts.BaseStrutsPortletAction;
    import com.liferay.portal.kernel.struts.StrutsPortletAction;
    
    /**
     *
     * @author Hamidul Islam
     *
     */
    
    public class ExampleLoginAction extends BaseStrutsPortletAction{
    
        @Override
        public void processAction(StrutsPortletAction originalStrutsPortletAction,
                PortletConfig portletConfig, ActionRequest actionRequest,
                ActionResponse actionResponse) throws Exception {
            /**
             * This is the custom process action
             * Once you try to login this method will be invoked
             * We can write our own logic here
             * Invoke the original struts action at the end
             */
            
            System.out.println("#############ExampleLoginAction###############");
            
            originalStrutsPortletAction.processAction(
                    originalStrutsPortletAction, portletConfig, actionRequest,
                    actionResponse);
        }
    
        public String render(
                StrutsPortletAction originalStrutsPortletAction,
                PortletConfig portletConfig, RenderRequest renderRequest,
                RenderResponse renderResponse)
            throws Exception {
            
            /**
             * Our own render method
             * This method is for rendering the view
             * At the end call the original struts action
             */
           
            System.out.println("##########Rendering view############");
            return originalStrutsPortletAction.render(
                null, portletConfig, renderRequest, renderResponse);
    
        }
    }
    

    Note: Read the comments of the code

    4. Deploy the Hook. Try to login. Check whether this action class is invoking or not.

    Best Practice: While overriding existing struts action by Struts Action Hook override the method that takes the original Struts action as a parameter and execute that original Struts action.

    Add Struts Action by Struts Action Hook

    The way we overridden existing struts action we can also add new struts action. The process is same as above.In the above demonstration we have seen action associated with portlet. In this section we will demonstrate how to add struts action in portal level.

    1. Add below in liferay-hook.xml

     <struts-action>
            <struts-action-path>/portal/proliferay</struts-action-path>
            <struts-action-impl>com.proliferay.demo.AddedAction</struts-action-impl>
      </struts-action>
    

    Note: Portal level struts action are invoked by adding /c/...in the path. For example if we invoke http://localhost:8080/c/portal/proliferay in the browser address bar then method of AddedAction class will be invoked.

    2. AddedAction.java

    package com.proliferay.demo;
    
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    
    import com.liferay.portal.kernel.struts.BaseStrutsAction;
    
    /**
     *
     * @author Hamidul Islam
     *
     */
    public class AddedAction extends BaseStrutsAction {
        public String execute(HttpServletRequest request,
                HttpServletResponse response) throws Exception {
            
            return "/portal/proliferay.jsp";
        }
    
    }
    

    Note 1: AddedAction class extends BaseStrutsAction but not BaseStrutsPortletAction.  This is the way to add action class in portal level.

    Note 2: The action class return proliferay.jsp under portal. So there should be proliferay.jsp in the portal directory. We can add this jsp by JSP Hook. Download the source code and check it.

    Note 3: If you try access http://localhost:8080/c/portal/proliferay it will prompt for login. We can make this URL public by adding auth.public.paths=/portal/proliferay in portal.properties of the hook. Download the source code and check it.

    3. Deploy the Hook and access http://localhost:8080/c/portal/proliferay. It should display proliferay.jsp


    Remember!!!

    Note

    1. While overriding existing portlet action our custom class should extends BaseStrutsPortletAction

    2. While adding new struts action in portal level our custom class should extends BaseStrutsAction

     

     


     

    Download Source Code

     

5 Responses so far.

  1. sahasradeep says:

    Hi Hamidul,

    Could you please help me for the following situation.

    I have hook which overrides the login portlet.
    Now whenever i redirect to a custom JSP like /html/portlet/login/success.jsp.
    It redirects properly to the mentioned JSP page.It redirects to the link like localhost:8080/html/portlet/login/success.jsp

    But i want this JSP to be rendered within the Login Portlet like localhost:8080/LoginPortletPath/success.jsp.
    Which should be rendered inside the portlet.not the whole page.

    Could you please help.

    Regards
    Shasradeep Nadar

  2. Aditya says:

    Good job hamidul.
    In your diagram spelling of Struts is wrong
    Overriding Existing Strusts Action

  3. pffiat says:

    Hi

    Thanks for your articles, they are nice explained I like them a lot =) .

  4. Pierpaolo says:

    Nice article... thank you.
    P.S. I think you forget to annotate with @Override the render method of ExampleLoginAction.

  5. Nabil says:

    Hi,
    when I add an action class and reference it in liferay-hook.xml, I have an error cannot be cast to org.apache.struts.action.Action.

    Thanks
    Nabil

Leave a Reply

Your email address will not be published. Required fields are marked *

Are you human? * Time limit is exhausted. Please reload CAPTCHA.

Top
%d bloggers like this:

By continuing to use the site, you agree to the use of cookies. more information

The cookie settings on this website are set to "allow cookies" to give you the best browsing experience possible. If you continue to use this website without changing your cookie settings or you click "Accept" below then you are consenting to this.

Close