Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/11.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

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
选择带有对象的标记-Thymeleaf和Spring MVC_Spring_Spring Mvc_Thymeleaf - Fatal编程技术网

选择带有对象的标记-Thymeleaf和Spring MVC

选择带有对象的标记-Thymeleaf和Spring MVC,spring,spring-mvc,thymeleaf,Spring,Spring Mvc,Thymeleaf,我试图更改此示例的代码,因此我更改了类类型的枚举类型: Type.java public class Type { private Integer id; private String type; ...getters and setters } SeedStarterMngController.java @ModelAttribute("allTypes") public List<Type> populateTypes() {

我试图更改此示例的代码,因此我更改了类类型的枚举类型:

Type.java

public class Type { 

    private Integer id; 
    private String type; 
   ...getters and setters 
}
SeedStarterMngController.java

@ModelAttribute("allTypes") 
    public List<Type> populateTypes() { 
        Type type1 = new Type(); 
        type1.setId(1); 
        type1.setType("OUTDOOR"); 

        Type type2 = new Type(); 
        type2.setId(2); 
        type2.setType("INDOOR"); 

        List<Type> tipos = new ArrayList<Type>(); 
        tipos.add(type1); 
        tipos.add(type2); 
        return tipos; 
    } 
@modeldattribute(“所有类型”)
公共列表populateTypes(){
类型1=新类型();
类型1.setId(1);
类型1.设置类型(“室外”);
类型2=新类型();
类型2.setId(2);
类型2.设置类型(“室内”);
List tipos=new ArrayList();
附加提示(类型1);
附加提示(类型2);
返回tipos;
} 
seedstartermng.html

<select th:field="*{type}">
    <option th:each="type : ${allTypes}" th:value="${type}" th:text="${type.type}">Wireframe</option>
</select>

线框
所以,我不能添加种子发酵剂

我的输出html是

<select id="type" name="type">
    <option value="thymeleafexamples.stsm.business.entities.Type@2c08cec0">OUTDOOR</option>
    <option value="thymeleafexamples.stsm.business.entities.Type@26cf024">INDOOR</option>
</select>

户外的
室内的
错误是

无法将java.lang.String类型的属性值转换为必需的 属性类型的类型为examples.stsm.business.entities.type; 嵌套异常为java.lang.IllegalStateException:无法转换 将[java.lang.String]类型的值转换为所需类型 [Examples.stsm.business.entities.Type]属性类型:否 找到匹配的编辑器或转换策略


如何正确映射到类型?我希望你能帮助我。多谢各位

该错误消息基本上是说Spring不知道如何转换字符串
thymeleafexamples.stsm.business.entities。Type@2c08cec0
导入类型的实例。这是代码中的一个bug,因为这样做没有任何意义

您不应该使用对象的
toString()
值作为表单下拉标识符。您需要有一个(更好的)代码策略来识别用户选择的类型

常用的方法是使用
id
属性:

<option th:each="type : ${allTypes}" th:value="${type.id}" th:text="${type.type}">Wireframe</option>
线框
提交表单后,您需要根据控制器上的id名称注销类型实例

我知道这个问题很老,但下面的答案可能会对某些人有所帮助,因为我无法轻松找到它

为了解决这个问题,Thymeleaf使用格式化程序在对象和字符串之间进行转换

  • 在显示阶段(GET),格式化程序服务将对象转换为 绳子
  • 在提交阶段(POST),格式化程序服务将转换字符串 回到

    反对

首先为要在标记中使用的类实现格式化程序服务:

@Service
public class TypeFormatter implements Formatter<Type> {

    @Autowired
    TypeService typeService;//Service -> DB

    @Override
    public String print(Type object, Locale locale) {
        return (object != null ? object.getId().toString() : "");
    }

    @Override
    public Type parse(String text, Locale locale) throws ParseException {
        Integer id = Integer.valueOf(text);
        return this.typeService.get(id);//return Type object form DB
    }
}
现在我们的解决方案可以在html文件中实现了,但是如何告诉Thymeleaf应用转换呢? 答案是使用th:field=“*{type}”属性和双括号语法th:value=“${type}”

<select th:field="*{type}">
    <option th:value="NULL" th:text="---Select Type---"></option>
    <option th:each="type : ${allTypes}" th:value="${{type}}" th:text="${type.type}">Wireframe</option>
</select>

线框
  • th:field=“*{type}”默认情况下正在应用已注册的格式化程序服务。它会将类型转换为字符串(这里的字符串是类型Id)
  • th:value=“${{type}}”也在将类型转换为字符串
  • 在submit中,Spring将使用格式化程序服务将Id转换回来 反对

最后要说的是,有时我们想在下拉列表中添加一个标题,如“----选择类型------”,以防止默认选择,并向用户解释。在这种情况下,必须设置th:value=“NULL”,除非出现转换错误。

在th:value中添加ID,这将向浏览器公开该值。我尽量不显示任何身份证。这就是为什么我在控制器中使用“@SessionAttributes”和“@InitBinder”。然后做任何你需要的事情,这样你就可以将某种字符串标识符传递到下拉列表中,并在发布表单时将其取回。字符串
emplieafexamples.stsm.business.entities。Type@2c08cec0
将永远不会成为java对象。时期考虑java枚举、序列化、使用另一个非敏感标识符等。希望遵循您的指令,但我无法找到Type Service类。你能告诉我它在哪个罐子里吗?谢谢。解决了,这只是一个刀类,需要自己实现。
<select th:field="*{type}">
    <option th:value="NULL" th:text="---Select Type---"></option>
    <option th:each="type : ${allTypes}" th:value="${{type}}" th:text="${type.type}">Wireframe</option>
</select>