4 回答
TA贡献1830条经验 获得超3个赞
问题发生是因为数据转换
com.mysql.cj.jdbc.ClientPreparedStatement:选择 flight0_.id 作为 id1_0_,flight0_.arrival_city 作为 arrival_2_0_,flight0_.date_of_departure 作为 date_of_3_0_,flight0_.departure_city 作为 departur4_0_,flight0_.estimated_departure_time 作为 estimate5_0_,flight0_.flight_number 作为 flight_n6_ 0_, flight0_.operating_airlines作为 operatin7_0_ 来自航班 flight0_,其中 flight0_.departure_city='AUS' and flight0_.arrival_city='NYC' and flight0_.date_of_departure='2018-02-04 18:30:00.0'
如您所见,日期未转换为正确的格式,因此我们推出了自己的转换器来解决此问题。
flightreservationapp/converters/LocalDateAttributeConverter.java
package com.dgs.flightreservationapp.converters;
import javax.persistence.AttributeConverter;
import javax.persistence.Converter;
import java.time.LocalDate;
@Converter(autoApply = true)
public class LocalDateAttributeConverter implements AttributeConverter<LocalDate, String> {
@Override
public String convertToDatabaseColumn(LocalDate locDate) {
return locDate == null ? null : locDate.toString();
}
@Override
public LocalDate convertToEntityAttribute(String sqlDate) {
return sqlDate == null ? null : LocalDate.parse(sqlDate);
}
}
添加此文件后,您将开始获得结果
您还有其他选择。为 JPA 方法添加注解
List<Flight> findByDepartureCityAndArrivalCityAndDateOfDeparture(String from, String to,
@DateTimeFormat(iso= DateTimeFormat.ISO.DATE)
LocalDate departureDate);
然后您需要确保将时区也设置为 UTC
public class FlightReservationAppApplication {
public static void main(String[] args) {
SpringApplication.run(FlightReservationAppApplication.class, args);
}
@PostConstruct
void init() {
TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
}
}
另一种选择是在你的程序中使用更高版本的 hibernatepom.xml
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-java8</artifactId>
<version>5.1.0.Final</version>
</dependency>
并设置时区
public class FlightReservationAppApplication {
public static void main(String[] args) {
SpringApplication.run(FlightReservationAppApplication.class, args);
}
@PostConstruct
void init() {
TimeZone.setDefault(TimeZone.getTimeZone("UTC"));
}
}
TA贡献1827条经验 获得超7个赞
我认为您需要在实体中注释日期字段@Temporal(TemporalType.DATE)
喜欢
@Entity
public class Flight extends AbstractEntity {
private String flightNumber;
private String operatingAirlines;
private String departureCity;
private String arrivalCity;
@Temporal(TemporalType.DATE)
private Date dateOfDeparture;
private Timestamp estimatedDepartureTime;
}
TA贡献1155条经验 获得超0个赞
在你的非工作存储库中,你有这个额外的配置application.properties
:
spring.datasource.url=jdbc:mysql://localhost:3306/reservation?useSSL=false&serverTimezone=UTC
该部分serverTimezone=UTC
导致您输入的日期和数据库中的日期不匹配=>错误的结果
所以现在,要么将两者设置为相同的时区,要么避免在 Java 中使用 Local*** 类
TA贡献1798条经验 获得超7个赞
MySqlDate类型不包含任何时间部分,因此Date您在实体上使用的类型Flight及其时间部分可能会破坏您的查询。尝试Date用LocalDateJava8 Date/Time API 替换,它也只包含没有任何时间信息的日期。
private LocalDate dateOfDeparture;
&
@Param("dateOfDeparture") LocalDate departureDate
最重要的是,您不需要@Query为这样一个简单的逻辑使用 a 。您可以使用方法名称作为查询,这是 Spring Data JPA 的一个很好的特性。
public interface FlightRepository extends JpaRepository<Flight, Long> {
List<Flight> findByDepartureCityAndArrivalCityAndDateOfDeparture(String from, String to, LocalDate departureDate);
}
并从您的控制器中调用它;
@PostMapping("/processFlights")
public String processFlights(..) {
List<Flight> flights = flightRepository.findByDepartureCityAndArrivalCityAndDateOfDeparture(from, to, departureDate);
modelMap.addAttribute("flights", flights);
return "displayFlights";
}
虽然它看起来很糟糕,因为名字变得太长了。您可以添加一个默认方法来包装它以隐藏丑陋的命名。
public interface FlightRepository extends JpaRepository<Flight, Long> {
List<Flight> findByDepartureCityAndArrivalCityAndDateOfDeparture(String from, String to, LocalDate departureDate);
// you can use this from your controller
default List<Flight> findFlights(String from, String to, LocalDate departureDate) {
return findByDepartureCityAndArrivalCityAndDateOfDeparture(from, to, departureDate);
}
}
这样做将隐藏由于在其中使用@Query注释和硬编码 JPQL 而导致的复杂性和可能的错误,除非对于更高级的情况绝对必要。
我在你的中添加了以下代码flightreservationapp;
@SpringBootApplication
public class FlightReservationAppApplication {
public static void main(String[] args) {
ConfigurableApplicationContext run = SpringApplication.run(FlightReservationAppApplication.class, args);
FlightRepository flightRepository = run.getBean(FlightRepository.class);
Flight flight = new Flight();
flight.setDepartureCity("AUS");
flight.setArrivalCity("NYC");
flight.setDateOfDeparture(LocalDate.of(2018, 1, 5));
flightRepository.save(flight);
List<Flight> list = flightRepository.findByDepartureCityAndArrivalCityAndDateOfDeparture("AUS", "NYC", LocalDate.of(2018, 1, 5));
System.out.println(list.size()); // prints out 1
}
}
存储库有效,我无法运行其他端点等,但查询/模式等没有问题。
添加回答
举报