Comparing Strings in Struts2 <s:if> Tag

16,954

Solution 1

You are comparing a string in the s:if statements and it worked good in the test file when you used a string value for the variable. So, "'GUEST'" worked. Without quotes OGNL is trying to parse the value in double quotes and if it can't find a variable named GUEST in the value stack it returns null. Then you tried to print this value that is converted to empty string. You have also hardcoded the value of 'GUEST' in the JSP, it's not good.

Solution: business logic you shouldn't write in JSP. You should define the session variable in the action and access this session variable inside JSP instead of redefining a variable value based on some logical condition.

<head>
<!--
    <s:set var="accessType" value="GUEST" />
    removed session code for testing -->
</head>

<body>
    <nav>
        <s:if test="#session.currentAccessType.equals('GUEST')">
            <ul>
                <li><a href="index.jsp">Home</a></li>
                <li><a href="#">Login</a></li>
                <li><a href="http://www.iacademy.edu.ph" target="_blank">Main Site</a></li>
            </ul>
        </s:if>

        <s:else>
            <ul>
                <li><a href="index.jsp">Home</a></li>
                <li><a href="#">Control Panel</a></li>
                <li><a href="#">Logout</a></li>
                <li><a href="http://www.iacademy.edu.ph" target="_blank">Main Site</a></li>
            </ul>
        </s:else>
    </nav>

    <br />

    Access type is <s:property value="#session.currentAccessType" />.
</body>

Solution 2

I have found the culprit.

To set String value in Struts2 var, this line:

<s:set var="accessType" value="GUEST" />

Should be:

<s:set var="accessType" value="'GUEST'" />

Single quotes (' ') must surround the String literal when placed inside the value="" attribute.

The if-check was correct.

Share:
16,954
silver
Author by

silver

Updated on June 28, 2022

Comments

  • silver
    silver almost 2 years

    I have an index.jsp page wherein certain elements turn on/off depending on whether the user has logged in or not.

    <head>
        <s:set var="accessType" value="GUEST" />
        <s:if test="#session.containsKey('currentAccessType')">
            <s:set var="accessType" value="#session.currentAccessType" />
        </s:if>
    </head>
    
    <body>
        <nav>
            <s:if test="#accessType.equals('GUEST')">
                <ul>
                    <li><a href="index.jsp">Home</a></li>
                    <li><a href="#">Login</a></li>
                    <li><a href="http://www.mywebsite.com" target="_blank">Main Site</a></li>
                </ul>
            </s:if>
    
            <s:else>
                <ul>
                    <li><a href="index.jsp">Home</a></li>
                    <li><a href="#">Control Panel</a></li>
                    <li><a href="#">Logout</a></li>
                    <li><a href="http://www.mywebsite.com" target="_blank">Main Site</a></li>
                </ul>
            </s:else>
        </nav>
    </body>
    

    The accessType is set to GUEST. However, it's entering the else-block even if the user has not logged in yet.

    Did I commit an error in my String comparison?

    UPDATE:
    I removed the session part from the index.jsp just to see and it now looks like this:

    <head>
        <s:set var="accessType" value="GUEST" />
        <!-- removed session code for testing -->
    </head>
    
    <body>
        <nav>
            <s:if test="#accessType.equals('GUEST')">
                <ul>
                    <li><a href="index.jsp">Home</a></li>
                    <li><a href="#">Login</a></li>
                    <li><a href="http://www.mywebsite.com" target="_blank">Main Site</a></li>
                </ul>
            </s:if>
    
            <s:else>
                <ul>
                    <li><a href="index.jsp">Home</a></li>
                    <li><a href="#">Control Panel</a></li>
                    <li><a href="#">Logout</a></li>
                    <li><a href="http://www.mywebsite.com" target="_blank">Main Site</a></li>
                </ul>
            </s:else>
        </nav>
    
        <br />
    
        Access type is <s:property value="#accessType" />.
    </body>
    

    Problems:

    1. Condition enters <s:else> block.
    2. Access type is not printing (somehow not being set).
  • silver
    silver over 9 years
    I see, so GUEST value should come from backend. If the user is viewing the index.jsp for the first time, how would the application know he is guest? Do I need to use interceptor to set this value?
  • Roman C
    Roman C over 9 years
    Struts in MVC framework, first you call a controller then render a view, don't call JSPs directly. In the action (controller) you define a session variable.
  • silver
    silver over 9 years
    Hey, I've been thinking about "calling a controller". I have index.jsp in the <welcome-file-list> of my web.xml, so it goes to the JSP every time I run it in Eclipse. How do I call a controller?
  • Roman C
    Roman C over 9 years
    A controller doesn't have .jsp at the end. And welcome files should redirect to a controller.
  • silver
    silver over 9 years
    With the help of this thread, I have successfully called a TestAction Class (using a test.jsp with <s:action>) and render the index.jsp after. Thank you for the tip and for all your +reps yesterday, RomanC. (Edit: I updated to the "hacky" version, where you place an empty file with the same name as the action name.)
  • Roman C
    Roman C over 9 years
    I knew about it from this question, but your thread is older, I have added struts2 tag.