【问题标题】:How to validate dynamically generated fields server side如何验证动态生成的字段服务器端
【发布时间】:2012-05-16 08:29:47
【问题描述】:

我使用 Spring 3.1 开发了一个 Web 应用程序

在其中一个模块中,我需要保存一个具有许多 OperationParameter 对象的 Operation 对象。 因此,在视图中,我为用户提供了添加按钮来为特定操作创建 OperationParameters。

两个模型都有休眠映射,并且操作和操作参数之间存在一对多的关系。在操作模型中,我有操作参数列表,当用户将使用动态添加的操作参数创建新操作时,这些操作参数列表将插入数据库中。

当我不使用验证时,它可以正常工作。当我对 Operation 模型进行插入操作时,OperationParameters 列表也会插入到 OperationParameter 表中。

我的问题是如何对 OperationParameter 字段进行服务器端验证? 如果验证是通过错误完成的,那么我如何显示特定 OperationParameter 字段的错误?

Operation.java

    package com.abcprocure.servicerepo.model;
// Generated Feb 9, 2012 11:30:06 AM by Hibernate Tools 3.2.1.GA


import java.util.ArrayList;
import java.util.List;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Embedded;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.Table;

import org.apache.commons.collections.FactoryUtils;
import org.apache.commons.collections.list.LazyList;

@Entity
@Table(name="Operations"
    ,schema="dbo"

)
public class Operations  implements java.io.Serializable {


     private int operationId;
     @Embedded
     private Services services;
     private String operationName;
     private String isHqlsql;
     private String isMultipleTables;
     private String listOfTablesAffected;
     private String hqlQuery;
     private String typeOfOperation;
     private String operationDetail;
     private String inputVariables;
     private String outputparamdatatype;
     private String isCountQuery;
     private String isDynamicWhereQry;
     private String isPaginationRequired;
     private String biInputParameters;
    private List<OperationParameters> operationParameterses = LazyList
            .decorate(new ArrayList<OperationParameters>(),
                    FactoryUtils.instantiateFactory(OperationParameters.class));

    public Operations() {
    }


    public Operations(int operationId, Services services, String operationName) {
        this.operationId = operationId;
        this.services = services;
        this.operationName = operationName;
    }
    public Operations(int operationId, Services services, String operationName, String isHqlsql, String isMultipleTables, String listOfTablesAffected, String hqlQuery, String typeOfOperation, String operationDetail, String inputVariables, String outputparamdatatype, String isCountQuery, List operationParameterses) {
       this.operationId = operationId;
       this.services = services;
       this.operationName = operationName;
       this.isHqlsql = isHqlsql;
       this.isMultipleTables = isMultipleTables;
       this.listOfTablesAffected = listOfTablesAffected;
       this.hqlQuery = hqlQuery;
       this.typeOfOperation = typeOfOperation;
       this.operationDetail = operationDetail;
       this.inputVariables = inputVariables;
       this.outputparamdatatype = outputparamdatatype;
       this.isCountQuery = isCountQuery;
       this.operationParameterses = operationParameterses;
    }

    @Id 
    @GeneratedValue
    @Column(name="operationId", unique=true, nullable=false)
    public int getOperationId() {
        return this.operationId;
    }

    public void setOperationId(int operationId) {
        this.operationId = operationId;
    }

    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="serviceId", nullable=false)
    public Services getServices() {
        return this.services;
    }

    public void setServices(Services services) {
        this.services = services;
    }

    @Column(name="operationName", nullable=false, length=250)
    public String getOperationName() {
        return this.operationName;
    }

    public void setOperationName(String operationName) {
        this.operationName = operationName;
    }

    @Column(name="isHQLSQL", length=50)
    public String getIsHqlsql() {
        return this.isHqlsql;
    }

    public void setIsHqlsql(String isHqlsql) {
        this.isHqlsql = isHqlsql;
    }

    @Column(name="isMultipleTables", length=50)
    public String getIsMultipleTables() {
        return this.isMultipleTables;
    }

    public void setIsMultipleTables(String isMultipleTables) {
        this.isMultipleTables = isMultipleTables;
    }

    @Column(name="listOfTablesAffected", length=500)
    public String getListOfTablesAffected() {
        return this.listOfTablesAffected;
    }

    public void setListOfTablesAffected(String listOfTablesAffected) {
        this.listOfTablesAffected = listOfTablesAffected;
    }

    @Column(name="hqlQuery")
    public String getHqlQuery() {
        return this.hqlQuery;
    }

    public void setHqlQuery(String hqlQuery) {
        this.hqlQuery = hqlQuery;
    }

    @Column(name="typeOfOperation", length=50)
    public String getTypeOfOperation() {
        return this.typeOfOperation;
    }

    public void setTypeOfOperation(String typeOfOperation) {
        this.typeOfOperation = typeOfOperation;
    }

    @Column(name="operationDetail")
    public String getOperationDetail() {
        return this.operationDetail;
    }

    public void setOperationDetail(String operationDetail) {
        this.operationDetail = operationDetail;
    }

    @Column(name="inputVariables", length=5000)
    public String getInputVariables() {
        return this.inputVariables;
    }

    public void setInputVariables(String inputVariables) {
        this.inputVariables = inputVariables;
    }

    @Column(name="outputparamdatatype", length=50)
    public String getOutputparamdatatype() {
        return this.outputparamdatatype;
    }

    public void setOutputparamdatatype(String outputparamdatatype) {
        this.outputparamdatatype = outputparamdatatype;
    }

    @Column(name="isCountQuery", length=10)
    public String getIsCountQuery() {
        return this.isCountQuery;
    }

    public void setIsCountQuery(String isCountQuery) {
        this.isCountQuery = isCountQuery;
    }

    public String getIsDynamicWhereQry() {
        return isDynamicWhereQry;
    }


    public void setIsDynamicWhereQry(String isDynamicWhereQry) {
        this.isDynamicWhereQry = isDynamicWhereQry;
    }


    public String getIsPaginationRequired() {
        return isPaginationRequired;
    }


    public void setIsPaginationRequired(String isPaginationRequired) {
        this.isPaginationRequired = isPaginationRequired;
    }

    public String getBiInputParameters() {
        return biInputParameters;
    }


    public void setBiInputParameters(String biInputParameters) {
        this.biInputParameters = biInputParameters;
    }

    @OneToMany(cascade=CascadeType.ALL, fetch=FetchType.LAZY, mappedBy="operations")
    public List<OperationParameters> getOperationParameterses() {
        return this.operationParameterses;
    }

    public void setOperationParameterses(List<OperationParameters> operationParameterses) {
        this.operationParameterses = operationParameterses;
    }

}

OperationParameters.java

package com.abcprocure.servicerepo.model;

// Generated Feb 9, 2012 11:30:06 AM by Hibernate Tools 3.2.1.GA


import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

@Entity
@Table(name="OperationParameters"
    ,schema="dbo"

)
public class OperationParameters  implements java.io.Serializable {


     private int parameterId;
     private Operations operations;
     private String inputOutputParamName;
     private String inputOutputParamType;
     private String inputOutputParamDataType;

    public OperationParameters() {
    }

    public OperationParameters(int parameterId, Operations operations, String inputOutputParamName, String inputOutputParamType, String inputOutputParamDataType) {
       this.parameterId = parameterId;
       this.operations = operations;
       this.inputOutputParamName = inputOutputParamName;
       this.inputOutputParamType = inputOutputParamType;
       this.inputOutputParamDataType = inputOutputParamDataType;
    }

    @Id 
    @GeneratedValue
    @Column(name="parameterId", unique=true, nullable=false)
    public int getParameterId() {
        return this.parameterId;
    }

    public void setParameterId(int parameterId) {
        this.parameterId = parameterId;
    }
@ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name="operationId", nullable=false)
    public Operations getOperations() {
        return this.operations;
    }

    public void setOperations(Operations operations) {
        this.operations = operations;
    }

    @Column(name="inputOutputParamName", nullable=false, length=250)
    public String getInputOutputParamName() {
        return this.inputOutputParamName;
    }

    public void setInputOutputParamName(String inputOutputParamName) {
        this.inputOutputParamName = inputOutputParamName;
    }

    @Column(name="inputOutputParamType", nullable=false, length=250)
    public String getInputOutputParamType() {
        return this.inputOutputParamType;
    }

    public void setInputOutputParamType(String inputOutputParamType) {
        this.inputOutputParamType = inputOutputParamType;
    }

    @Column(name="inputOutputParamDataType", nullable=false, length=250)
    public String getInputOutputParamDataType() {
        return this.inputOutputParamDataType;
    }

    public void setInputOutputParamDataType(String inputOutputParamDataType) {
        this.inputOutputParamDataType = inputOutputParamDataType;
    }




}

提供发布请求以添加新操作的控制器方法。

/**
     * Method that will serve the post request to add the operation and operation parameters submitted by the user.
     * @param operations
     * @param map
     * @return {@link String} The view name that will redirect to the get request to display the previous page with newly entered operation in the list. 
     */
    @RequestMapping(value="/add", method=RequestMethod.POST)
    public String addOperations(@ModelAttribute Operations operations, ModelMap map) {
        operations.getOperationParameterses().removeAll(Collections.singleton(null));

        for(int i=0; i<operations.getOperationParameterses().size(); i++) {
            System.out.println("parameterName :: " + ((OperationParameters)operations.getOperationParameterses().get(i)).getInputOutputParamName());
            if(((OperationParameters)operations.getOperationParameterses().get(i)).getInputOutputParamName() == null || "".equalsIgnoreCase((((OperationParameters)operations.getOperationParameterses().get(i))).getInputOutputParamName())) {
                operations.getOperationParameterses().remove(i);
                System.out.println("empty parameter removed....");
            }
        }

        return "redirect:/operations/" + operations.getServices().getServiceId();
    }

在这方面任何好的建议或例子都会对我有很大的帮助。 :)

**

更新

**

我还想知道是否可以验证字段数组并在 jsp 文件中显示错误?

请帮帮我。

【问题讨论】:

    标签: spring spring-mvc spring-3 hibernate-validator


    【解决方案1】:

    您可以创建一个帮助程序类,根据其数据类型验证您的 OperationParameters。如果是字符串,请检查 null 或空字符串等。验证类,也可以有一些上下文验证,比如有效的电子邮件地址。

    有了这个,在保存操作对象之前,您将遍历操作参数的操作列表,检查数据类型和/或保存信息上下文的字段(例如电子邮件、工作日)并调用正确验证您的助手类。

    如果您确实发现了不一致,只需抛出一个自定义异常来描述它。处理它的代码部分可以将带有违规字段的 json 返回到您的页面,这反过来会向用户提供反馈(即,带有错误消息的字段下方的红色文本)。

    【讨论】:

    • 感谢您的回复。你非常接近我想要的,但不是确切的东西。根据您的回答,我需要在 ajax 的帮助下验证动态生成的字段。但我不想那样做。我想在用户将表单提交回控制器时对其进行验证(就像我们通常所做的那样)。但是,当您发布此答案时,我描述了确切的解决方案(多么共同的人!)。请检查我的答案。仍然为您的努力+1。 :)
    • 你为什么认为我在谈论 ajax?我的意思是,您将创建一个具有验证数据的方法的类(辅助类),然后在您的方法 addOperations for 循环中使用它。所有服务器端。如果您发现错误,您可以重定向到错误页面或返回一些描述错误的 json(ajax 方式)。
    • 那么好吧。我接受你的回答。你已经给出了和我类似的答案。无论如何感谢您的努力。 :)
    【解决方案2】:

    经过一周的头脑风暴,我自己找到了解决方案。 我真的很高兴我终于实现了这一目标。 :)

    为了验证动态生成的字段,您需要依赖服务器端的自定义验证。因为如果我们对动态生成的字段使用基于 Annotation 的验证,那么在验证之后它将不会进入控制器函数。

    因此,每当您进行自定义验证时,将从控制器函数中调用验证。在那里,您可以在列表中动态生成的字段上生成错误。

    如果验证不成功,那么您需要返回 jsp 页面并在表单上显示错误。您需要使用 显示动态生成的字段值及其错误。

    我希望这可以帮助其他想要同样工作的人。

    【讨论】:

    • 对不起.. 我现在没有那个代码。您可以按照上面解释的非常简单。您需要在控制器函数中手动验证 pojo 对象,而不是使用注释方法来验证您的 pojo 对象。如果验证失败,您可以设置错误并显示在 JSP 页面上。
    猜你喜欢
    • 2019-01-16
    • 2021-10-30
    • 1970-01-01
    • 2011-02-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-07
    相关资源
    最近更新 更多