Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/asp.net-mvc-3/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Hybris表单组件验证_Java_Hybris - Fatal编程技术网

Java Hybris表单组件验证

Java Hybris表单组件验证,java,hybris,Java,Hybris,我编写了自定义组件,这是一个简单的表单。提交表单后,我想验证表单,如果出现错误,我想显示它们。我试图在我的类MyFormComponentController扩展AbstractAcceleratorMSComponentController中创建一个具有请求后映射的方法,但它得到一个错误,表示不允许该方法。因此,我编写了一个控制器,并在表单组件中添加了操作 @Controller @RequestMapping(value = "/action") public class MyFormPag

我编写了自定义组件,这是一个简单的表单。提交表单后,我想验证表单,如果出现错误,我想显示它们。我试图在我的类
MyFormComponentController扩展AbstractAcceleratorMSComponentController
中创建一个具有请求后映射的方法,但它得到一个错误,表示不允许该方法。因此,我编写了一个控制器,并在表单组件中添加了操作

@Controller
@RequestMapping(value = "/action")
public class MyFormPageController extends AbstractPageController {

    @RequestMapping(method = RequestMethod.POST)
    public String doMyPageController(@Valid final MyForm myForm, final BindingResult bindingResult, final Model model)
            return ???; //..in case of error?
但是当我的表单中出现错误并且我不想返回到视图时,只显示组件。我试图将我从组件控制器中的
getView()
方法获得的值传递到那里,但没有任何帮助

编辑:我还尝试使用ajax调用进行表单提交,如:

$(document).on("submit",'#myForm', function(e){
            e.preventDefault();
            var postData = $("#myForm").serialize();
            var url= $(".js-my-action").data("url");
            $.ajax({
                url: url,
                data: JSON.stringify(postData),
                type: "POST",
                success: function (response){
                }
            });
        })
我想调用的方法是

@RequestMapping(value = "/action", method = RequestMethod.POST)
    public String doMyPageController(@RequestBody @Valid final MyForm catalogOrderForm, final Model model) throws IOException, JaloBusinessException, CMSItemNotFoundException {
在这里,我尝试使用表单名称将
@RequestBody
更改为
@modeldattribute
,但我只得到
拒绝访问(CSRFToken)
错误:

ERROR [hybrisHTTP24] [SikoAcceleratorAccessDeniedHandler] Access denied happend - org.springframework.security.web.csrf.InvalidCsrfTokenException: Invalid CSRF Token '66d045fd-c9ae-4210-ae97-f2a0e739bcbf"' was found on the request parameter 'CSRFToken' or header 'CSRFToken'.
我在ajax调用中传递的数据:

"firstName=Test&lastName=Test&street=Test&city=Test&postalCode=38801&email=test%40test.com&_inspiration=on&_kitchen=on&_door=on&_gdpr=on&CSRFToken=66d045fd-c9ae-4210-ae97-f2a0e739bcbf"
然后我尝试在ajax调用中传递数据,如下所示:

data: {myForm: postData}

但是它也不起作用。

您可以使用ResponseEntity作为返回类型

@RequestMapping(method = RequestMethod.POST)
    public ResponseEntity<string> doMyPageController...
        return new ResponseEntity<"Error message" , HttpStatus.BAD_REQUEST>
@RequestMapping(method=RequestMethod.POST)
公共响应域页面控制器。。。
返回新响应

您需要在jsp文件中处理此响应。Accelerator有一些用于处理这些响应的标签,您可以查看TemplateStoreFront。

因为您使用的是Spring,所以答案是:

在您的控制器类上放置
@Valid
注释

这将导致控制器返回一个400错误,以及一个JSON负载,为遇到的每一个错误指明确切的错误原因


请参见不同页面上的Spring 3类型转换和验证组件
由于您已经创建了用于呈现表单的组件,我希望您希望在多个页面上使用该组件。在这种情况下,您不能返回任何硬代码视图,因为表单可以从任何页面(视图)提交。我建议通过ajax调用处理表单提交

单个页面上的组件-如果您知道此组件将在单个页面上使用。然后,您可以简单地使用普通页面提交,并从控制器返回该页面视图。在这里,您不需要使用AJAX


建议:

您可以创建JspIncludeComponent的实例,并指向您的JSP/视图,而不是仅为表单创建自定义组件


编辑: 拒绝访问(CSRFToken)错误-Hybris Commerce提供默认启用的CSRF保护机制
CSRFHandlerInterceptor
验证CSRF令牌的每个POST请求。要绕过任何请求的CSRF检查,可以将URL模式添加到
csrfAllowedUrlPatterns
列表中

要解决您的问题,只需使用spring表单,它在隐藏字段中呈现CSRFToken。现在,您可以使用
form.serialize()
提交整个表单

JSP:

控制器:

@SuppressWarnings("boxing")
@ResponseBody
@RequestMapping(value = "/myForm", method = RequestMethod.POST)
public String saveMyForm(@Valid @ModelAttribute("myForm") final MyForm myForm, final Model model)
{
        return "succcess";
}

在CMS组件中使用表单是一个棘手的问题。解决方案可能取决于您的用例。以下是我迄今为止看到的一些解决方案:

仅在特定URL/页面上使用组件 考虑购物车页面。有很多种形式。它们只能在购物车页面(/cart)上使用。您还可以定义一个内容页,以便在失败/成功时查看。搜索页面就是一个例子。使用搜索组件时,输入搜索词时,始终会重定向到搜索页/搜索空白页

使用参考信息 登录组件使用更智能的方法。当您从特定页面(如产品页面)登录时,登录控制器会检查referer URL并重定向到您以前访问过的页面

URL格式中的参数 一些解决方案在表单中添加一个额外的字符串参数来存储当前URL。我还看到了使用SessionService在会话中存储参数的解决方案。但是,此解决方案有一个缺点,即在一个会话中只能使用一个表单

配置每个CMS组件的使用位置和重定向到成功/失败的位置 还可以定义在成功/失败后显示的特定内容页/URL。在这种情况下,您可以拥有该组件的多个实例,这些实例都会在成功/失败时重定向到特定页面

使用AJAX 另一个解决方案是使用AJAX提交表单,并用JavaScript处理失败/成功操作


可能还有其他更有效的实现。请和我分享你的想法

不,不是。我对验证本身没有问题,它工作得很好。我需要的是post方法中的正确返回值,以便使用插入的hybris组件返回整个页面。注意,我已经有了注释,我将在问题中对其进行编辑。由于您已经创建了用于呈现表单的组件,我希望您希望在多个页面上使用该组件。在这种情况下,您不能返回任何硬代码视图,因为表单可以从任何页面(视图)提交。我建议通过ajax调用处理表单提交。请告诉我们您的需求,以及您正试图实现的目标。可能有另一种解决方案。也许你是对的,我应该使用ajax调用来实现这一点。我想实现这一点-有一个插入组件的经典页面,这就是我的表单。提交表单后,我将进行验证,如果出现错误,我希望在该表单上显示完全相同的页面,但当它插入到JspIncludeComponent时,它如何与formComponentController连接以填充该表单?是否也应该是一个实例<代码>插入更新表单组件$contentCV[unique=true];uid[唯一
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@ taglib prefix="spring" uri="http://www.springframework.org/tags" %>

    <form:form id="myForm" action="${myFormActionURL}" method="POST" modelAttribute="myForm">
        <input type="text" placeholder="<spring:theme code="myform.firstName"/>" name="fname" required>
         ...
    </form:form>
var form = $("#myForm");
    $.ajax({
        url: url,
        data: form.serialize(),
        type: 'POST',
        success: function (data) {

        },
        error: function (data) {

        }
    });
@SuppressWarnings("boxing")
@ResponseBody
@RequestMapping(value = "/myForm", method = RequestMethod.POST)
public String saveMyForm(@Valid @ModelAttribute("myForm") final MyForm myForm, final Model model)
{
        return "succcess";
}