Spring MVC формы - модель с привязкой к объекту

1

Я создал форму, которая имеет 2 поля (название и цена продукта) и выпадающий список объектов категории (категории товаров). Я не знаю, как сделать эту работу, когда у меня есть объекты категории, которые будут установлены в объекте Product.

Продукт:

public class Product {
    private String name;
    private Category category;
    private int price;

    public Product() {
    }

    public Product(String name, Category category, int price) {
        this.name = name;
        this.category = category;
        this.price = price;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Category getCategory() {
        return category;
    }

    public void setCategory(Category category) {
        this.category = category;
    }

    public int getPrice() {
        return price;
    }

    public void setPrice(int price) {
        this.price = price;
    }

}

Контроллер продукта:

    @ModelAttribute("categoryList")
    public List<Category> categoryList() {
          return categoryService.getCategories();
    }

    @RequestMapping("/products/add")
    public ModelAndView addProductForm() {
        ModelAndView mv = new ModelAndView("addProduct");

        mv.addObject("product", new Product());
        return mv;
    }
    @RequestMapping(value = "/products/add/process", method = RequestMethod.POST)
    public ModelAndView addProduct(@ModelAttribute("product") Product product) {
        ModelAndView mv = new ModelAndView("products");
        System.out.println("added " + product.getName() + " " + product.getPrice());
        return mv;
    }

Форма:

<form class="form-horizontal" action="#"
        th:action="@{/products/add/process}" th:object="${product}"
        method="post">
        <fieldset>

            <!-- Form Name -->
            <legend>Add product</legend>

            <!-- Text input-->
            <div class="form-group">
                <label class="col-md-4 control-label" for="textinput">Product
                    name</label>
                <div class="col-md-4">
                    <input id="textinput" name="textinput" placeholder="Product name"
                        class="form-control input-md" required="" type="text"
                        th:field="*{name}"></input>
                </div>
            </div>

            <!-- Select Basic -->
            <div class="form-group">
                <label class="col-md-4 control-label" for="selectbasic">Category</label>
                <div class="col-md-4">
                    <select th:field="*{category}">
                        <option th:each="cat : ${categoryList}" th:value="${cat.getId()}"
                            th:text="${cat.getName()}"></option>
                    </select>
                </div>
            </div>

            <!-- Text input-->
            <div class="form-group">
                <label class="col-md-4 control-label" for="textinput">Price</label>
                <div class="col-md-4">
                    <input id="textinput" name="textinput" placeholder=""
                        class="form-control input-md" required="" type="text"
                        th:field="*{price}"></input>
                </div>
            </div>

            <!-- Button -->
            <div class="form-group">
                <label class="col-md-4 control-label" for="singlebutton"></label>
                <div class="col-md-4">
                    <button id="singlebutton" name="singlebutton"
                        class="btn btn-success">Add product</button>
                </div>
            </div>
        </fieldset>
    </form>

Дополнительная информация от комментариев
Когда я его отправлю (см. Метод addProduct - это обработчик формы), я получаю: java.lang.IllegalStateException: Cannot convert value of type [java.lang.String] to required type [com.example.shop.Category] for property 'category': no matching editors or conversion strategy found]. Я просто не могу преобразовать String из раскрывающегося списка в объект

  • 0
    Поэтому я правильно понимаю вопрос: выпадающий список Категория пуст, потому что вы никогда не устанавливаете его. Как вы получаете значения заполняются и возвращаются в форму?
  • 0
    @Ascalonian Я показываю их в раскрывающемся списке, я передаю их в виде списка (я выбираю его с помощью categoryService), используя аннотацию ModelAttribute.
Показать ещё 4 комментария
Теги:
spring
spring-mvc
forms
spring-form

1 ответ

2
Лучший ответ

Проблема в том, что Spring не имеет встроенной возможности преобразования из String в Category. Он знает, что ему нужна Category для использования setCategory(Category category) Product, но не имеет способа преобразовать String она получает из вашей выложенной вниз, в одну. Таким образом, вам нужно быть дорогим и помогать Spring, рассказывая ему, как сделать преобразование и определить конвертер, см. Документацию Spring для получения дополнительной информации.

Самый простой вариант - использовать конвертер SPI:

package com.example.shop.converter;

final class StringToCategoryConverter implements Converter<String, Category> {
  public Category convert(String source) {
    Category category;

    // Put your conversion logic here

    return category;
  }
}

В вашем случае, я думаю, вы захотите использовать: CategoryService.getCategory(int id) или аналогичный метод.

Затем вам нужно настроить Spring, чтобы на самом деле использовать ваш конвертер, вот пример XML, как это сделать:

<mvc:annotation-driven conversion-service="conversionService" />

<bean id="conversionService"
      class="org.springframework.context.support.ConversionServiceFactoryBean">
    <property name="converters">
        <list>
            <bean class="com.example.shop.converter.StringToCategoryConverter" />
        </list>
    </property>
</bean>
  • 0
    Большое спасибо! Вы были правы - мне пришлось добавить конвертер :). Более того - если у вас включен «аннотации», вам также необходимо зарегистрировать конвертер следующим образом: <mvc: аннотации на основе конвертирования-службы = «ConversionService» />
  • 0
    Хороший вопрос, отредактированный ответ, чтобы включить его для тех, кто придет сюда позже.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню