【问题标题】:Failed to convert property value of type 'java.lang.String' to required type 'java.util.List' for property 'transactions'无法将类型“java.lang.String”的属性值转换为属性“事务”所需的类型“java.util.List”
【发布时间】:2021-10-27 17:30:35
【问题描述】:

我正在使用 thymeleaf 并在将数据从 String 转换为 List 时遇到一些错误。在这里我附上了我的代码

我的实体类:

@Entity
@Table(name="customer")
public class Customer {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "id")
private int id;

@Column(name = "first_name")
@NotNull(message = "First Name cannot be empty")
@Size(min = 1, message = "First Name cannot be empty")
private String firstName;

@Column(name = "last_name")
@NotNull(message = "Last Name cannot be empty")
@Size(min = 1, message = "Last Name cannot be empty")
private String lastName;

@Column(name = "email")
@NotNull(message = "Email ID cannot be empty")
@Pattern(regexp = "^[a-zA-Z0-9.+_-]+@[a-zA-Z0-9.-]+$",
        message = "Enter valid mail id")
private String email;

@Column(name = "branch")
@NotNull(message = "Branch name cannot be empty")
private String branch;

@Column(name = "balance")
private double balance;

@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
@JoinColumn(name = "customer_id")
private List<Transaction> transactions;

public Customer(String firstName, String lastName, String email, String branch, double balance) {
    this.firstName = firstName;
    this.lastName = lastName;
    this.email = email;
    this.branch = branch;
    this.balance = balance;
}

public Customer() {
}

public int getId() {
    return id;
}

public void setId(int id) {
    this.id = id;
}

public String getFirstName() {
    return firstName;
}

public void setFirstName(String firstName) {
    this.firstName = firstName;
}

public String getLastName() {
    return lastName;
}

public void setLastName(String lastName) {
    this.lastName = lastName;
}

public String getEmail() {
    return email;
}

public void setEmail(String email) {
    this.email = email;
}

public String getBranch() {
    return branch;
}

public void setBranch(String branch) {
    this.branch = branch;
}

public double getBalance() {
    return balance;
}

public void setBalance(double balance) {
    this.balance = balance;
}

public List<Transaction> getTransactions() {
    return transactions;
}

public void setTransactions(List<Transaction> transactions) {
    this.transactions = transactions;
}

public void addTransaction(Transaction transaction){
    if(transaction == null) {
        transactions = new ArrayList<>();
    }
    transactions.add(transaction);
}

@Override
public String toString() {
    return "Customer{" +
            "id=" + id +
            ", firstName='" + firstName + '\'' +
            ", lastName='" + lastName + '\'' +
            ", email='" + email + '\'' +
            ", branch='" + branch + '\'' +
            ", balance=" + balance +
            '}';
  }


@Entity
@Table(name = "transactions")
public class Transaction {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "id")
private int id;

@Column(name = "transaction")
private double amount;

public Transaction() {
}

public Transaction(double amount) {
    this.amount = amount;
}

public int getId() {
    return id;
}

public void setId(int id) {
    this.id = id;
}

public double getAmount() {
    return amount;
}

public void setAmount(double amount) {
    this.amount = amount;
}

@Override
public String toString() {
    return "Transaction{" +
            "id=" + id +
            ", amount=" + amount +
            '}';
}

控制器:

@Controller
@RequestMapping("/customers")
public class CustomerController {
@Autowired
private CustomerRestService customerRestService;

public static String username;
public static Object password;

public CustomerController() {
}

@GetMapping("/list")
public String listCustomers(Model model, @CurrentSecurityContext(expression = "authentication")Authentication authentication) {
    username = authentication.getName();
    password = authentication.getCredentials();
    List<Customer> customers = customerRestService.getCustomerList();

    model.addAttribute("customers", customers);

    return "list-customers";
}

@GetMapping("/showFormToAddCustomer")
public String showFormToAddCustomer(Model model) {
    Customer customer = new Customer();
    model.addAttribute("customer", customer);
    return "customer-form";
}

@PostMapping("/saveCustomer")
public String saveCustomer(@ModelAttribute("customer") Customer customer) {
    System.out.println("\n" + customer);
    System.out.println(customer.getTransactions());
    customerRestService.saveCustomer(customer);
    return "redirect:/customers/list";
}

@GetMapping("/showFormToUpdateCustomer")
public String showformForUpdate(@RequestParam("customerId") int id,
                                Model model) {
    Customer customer = customerRestService.findCustomerById(id);
    System.out.println(customer);
    System.out.println(customer.getTransactions());
    
    model.addAttribute("customer", customer);
    
    return "customer-form";
}
}

服务:

@Service
public class CustomerRestServiceImple implements CustomerRestService{
private RestTemplate restTemplate;

private String restUrl;

@Autowired
public CustomerRestServiceImple(RestTemplate restTemplate,
                                @Value("${crm.rest.url}") String restUrl) {
    this.restTemplate = restTemplate;
    this.restUrl = restUrl;
}

private HttpHeaders httpHeaders() {
    String username = CustomerController.username;
    Object password = CustomerController.password;

    String plainCreds = username+":"+password.toString();
    byte[] plainCredsBytes = plainCreds.getBytes();
    byte[] base64CredsBytes = Base64.encodeBase64(plainCredsBytes);
    String base64Creds = new String(base64CredsBytes);

    HttpHeaders headers = new HttpHeaders();
    headers.add("Authorization", "Basic " + base64Creds);
    headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
    headers.setContentType(MediaType.APPLICATION_JSON);
    //HttpEntity<String> request = new HttpEntity<String>(headers);
    return headers;
}

@Override
public List<Customer> getCustomerList() {
    HttpEntity<String> request = new HttpEntity<>(httpHeaders());

    ResponseEntity<List<Customer>> responseEntity = restTemplate.exchange(restUrl, HttpMethod.GET, request,
            new ParameterizedTypeReference<List<Customer>>() {});

    List<Customer> customers = responseEntity.getBody();

    return customers;
}

@Override
public Customer findCustomerById(int id) {
    //Customer customer = restTemplate.getForObject(restUrl + "/" + id, Customer.class);
    HttpEntity<String> request = new HttpEntity<>(httpHeaders());
    ResponseEntity<Customer> responseEntity = restTemplate.exchange(restUrl + "/" + id, HttpMethod.GET, request, Customer.class);
    Customer customer = responseEntity.getBody();
    return customer;
}

@Override
public void saveCustomer(Customer customer) {
    System.out.println("\n" + customer);
    System.out.println(customer.getTransactions());

    HttpEntity<Customer> request = new HttpEntity<>(customer, httpHeaders());
    int customerId = customer.getId();

    if(customerId == 0){
        restTemplate.exchange(restUrl, HttpMethod.POST, request, Customer.class);
    } else {
        restTemplate.exchange(restUrl, HttpMethod.PUT, request, Customer.class);
        }
}
}

HTML 表单:

    <h3>Customer Directory</h3>
    <hr>

    <p class="h4 mb-4">Save Customer</p>

    <form action="#" th:action="@{/customers/saveCustomer}"
          th:object="${customer}" method="POST">

        <!-- Add hidden form field to handle the update -->
        <input type="hidden" th:field="*{id}" />

        <input type="text" th:field="*{firstName}"
            class="form-control mb-4 col-4" placeholder="First Name">

        <input type="text" th:field="*{lastName}"
               class="form-control mb-4 col-4" placeholder="Last Name">

        <input type="text" th:field="*{email}"
               class="form-control mb-4 col-4" placeholder="Email">

        <input type="text" th:field="*{branch}"
               class="form-control mb-4 col-4" placeholder="Branch">

        <input type="text" th:field="*{balance}"
               class="form-control mb-4 col-4" placeholder="Balance">

        <input type="text" th:field="*{transactions}"
               class="form-control mb-4 col-4" placeholder="Transactions">

        <!--input type="hidden" th:field="*{transactions}" /-->

        <button type="submit" class="btn btn-info col-2">Save</button>

    </form>

    <hr>
    <a th:href="@{/customers/list}">Back to Customers List</a>

</div>

错误:

字段“交易”的对象“客户”中的字段错误:拒绝值 [[Transaction{id=1, amount=1000.0}, Transaction{id=3, amount=100.0}]];代码 [typeMismatch.customer.transactions,typeMismatch.transactions,typeMismatch.java.util.List,typeMismatch];参数 [org.springframework.context.support.DefaultMessageSourceResolvable: 代码 [customer.transactions,transactions];论据 [];默认消息[事务]];默认消息 [无法将类型“java.lang.String”的属性值转换为属性“事务”所需的类型“java.util.List”;嵌套异常是 org.springframework.core.convert.ConversionFailedException:无法从类型 [java.lang.String] 转换为类型 [@javax.persistence.OneToMany @javax.persistence.JoinColumn com.kaneki.springboot.bankapplication.entity。交易] 价值 '[交易{id=1, 金额=1000.0}, 交易{id=3, 金额=100.0}]';嵌套异常是 java.lang.NumberFormatException: For input string: "[Transaction{id=1, amount=1000.0}, Transaction{id=3, amount=100.0}]"]

【问题讨论】:

    标签: java spring spring-boot hibernate transactions


    【解决方案1】:

    在这里,您从您的 HTML 中接收作为字符串的 Transaction 字段,因此在控制器中您必须处理该字符串并从中提取 id 和金额,然后将该 id 和金额设置到交易表中。试试这个,如果你已经在你的控制器中尝试或编写了它,请分享控制器的代码。

    【讨论】:

    • 我在这里添加了控制器代码。能否请您再重新审视一下这个问题
    猜你喜欢
    • 2020-05-24
    • 1970-01-01
    • 2021-06-13
    • 2017-05-06
    • 2015-03-29
    • 2013-10-26
    • 2021-06-26
    • 2019-07-11
    • 1970-01-01
    相关资源
    最近更新 更多