Struts2- URL标记 - 隐藏查询字符串

时间:2013-02-19 03:53:11

标签: url struts2 tags

经过对stackoverflow的大量研究后,我发布了这个问题,因为我找不到解决问题的方法。

需求场景:根据每个客户ID作为参数,从客户列表中更新客户。

尝试解决方案:根据从jsp收到的客户ID,将其传递给Action as Struts2 url标记。

问题Faced - 在URL上可见的查询字符串     http://foo.com/Struts2Example/getCustomerAction?customerId=2

问题:

  1. 如果我们使用struts Url标记,我们是否可以隐藏查询字符串?
  2. 如果我们在使用Url标签时无法隐藏使用查询字符串?上述场景的替代方案是什么。
  3. 下面的struts.xml,jsp和action的代码 -

    <h2>All Customers Details</h2>
    
    <s:if test="customerList.size() > 0">
        <table border="1px" cellpadding="8px">
            <tr>
                <th>Customer Id</th>
                <th>First Name</th>
                <th>Last Name</th>
                <th>Age</th>
                <th>Created Date</th>
            </tr>
            <s:iterator value="customerList" status="userStatus">
                <tr>
                    <td><s:url var="editCustomer" action="getCustomerAction">
                            <s:param name="customerId" value="%{customerId}" />
                        </s:url>
    
                        <p>
                            <s:a href="%{editCustomer}">
                                <s:property value="customerId" />
                            </s:a>
                        </p></td>
    
                    <td><s:property value="firstname" /></td>
                    <td><s:property value="lastname" /></td>
                    <td><s:property value="age" /></td>
                    <td><s:date name="createdDate" format="dd/MM/yyyy" /></td>
                </tr>
            </s:iterator>
        </table>
    </s:if>
    <br />
    <br />
    

    struts.xml中 -

    <!-- Get Customer Details - To Pre-Populate the form to update a Customer -->
        <action name="getCustomerAction" method="getCustomerById"
            class="com.hcl.customer.action.CustomerAction">
            <result name="success">pages/customerForm.jsp </result>
        </action>
    

    客户行动类 -

    public class CustomerAction extends ActionSupport implements ModelDriven {
    
    Logger logger = Logger.getLogger(CustomerAction.class);
    
    Customer customer = new Customer();
    
    List<Customer> customerList = new ArrayList<Customer>();
    CustomerDAO customerDAO = new CustomerDAOImpl();
    
    public Customer getCustomer() {
        return customer;
    }
    
    //Set Customer onto Value Stack
    public void setCustomer(Customer customer) {
        this.customer = customer;
    }
    
    public List<Customer> getCustomerList() {
        return customerList;
    }
    
    //Set Customer List onto Value Stack
    public void setCustomerList(List<Customer> customerList) {
        this.customerList = customerList;
    }
    
    public String execute() throws Exception {
        return SUCCESS;
    }
    
    public Object getModel() {
        return customer;
    }
    
    
    
    // Edit customer details, it will retrieve the records based on customerId
    //SkipValidation is used to skip the validate()
    @SkipValidation
    public String getCustomerById() {
    
        logger.info("** Customer Id to edit ** " + customer.getCustomerId());
    
        customer = customerDAO.customerById(customer.getCustomerId());
    
        return SUCCESS;
    
    }
    

2 个答案:

答案 0 :(得分:1)

另一种方法是加密userID并将其发送回HTML页面。在客户端维护映射。提交请求时,请POST加密值。解密/加密逻辑将在服务器端。 这将增加系统的开销,但与安全性相比,这是一个足够好的性能权衡。 另请查看@ jcryption.org/info,它在麻省理工学院和GPL许可下。

更简单的解决方案是将其转换为“POST”操作,以便在HTTP Request Body中传递值。如果它通过HTTPS,它将被加密,但您仍然可以使用Google Developer Tools或IE9 Developer模式进行用户ID查找

答案 1 :(得分:1)

一些无序的考虑因素:

  • 使用不同的Actions(仅使用execute方法)或相同Action的不同方法来执行不同的“动作”;
  • 每个操作/方法的名称应与执行的操作相匹配,并且不言自明,例如,您应该使用editCustomer方法(或操作)编辑客户和getCustomer方法(或行动)获取客户;
  • GET HTTP方法应该用于读取数据,而POST HTTP方法应该用于发送数据;理想情况下,每个非阅读操作应该通过POST执行;使用GET发送数据是20年前出生的一个古老的坏习惯,从未死过:/使用POST的原因是隐藏的URL,更高的负载能力,发送二进制数据的能力等等......

也就是说,像http://foo.com/Struts2Example/getCustomerAction?customerId=2这样的网址应该是可见的(例如被标记为书签),理想情况下应该被美化(REST风格,如StackOverflow):类似于http://foo.com/Struts2Example/Customer/2/

http://foo.com/Struts2Example/editCustomerAction?customerId=2这样的网址无法使用,因为您没有传递任何其他参数;你知道要编辑的客户的ID,但不知道要改变的数据... 它会变成这样的东西: http://foo.com/Struts2Example/editCustomerAction?customerId=2&name=foo&lastname=bar&age=42,这会有效,但正如所说(以及问题中的问题)应该被隐藏,并通过POST处理。

如果您要在source页面的ID打印,则无需将其隐藏给用户;

您需要做的是确保用户无法更改您指定范围之外的ID; 如果您在页面中绘制了ID {1,2,3}的客户列表,则必须阻止用户尝试更改ID并尝试使用ID = 4更新客户...以实现此目的,只需存储填充页面前session中的ID列表,并根据列表检查页面返回的ID。如果它们不匹配,则阻止恶意操作。

希望有所帮助