Jackson反序列化java.util.Date报错,React函数组件设置太平洋时间日期选择器
Hey there, let's tackle your two issues one by one—first the Jackson deserialization error, then getting your React date picker to default to Pacific Time.
The error you're seeing happens because Jackson tries to parse a JSON object (like {"year":2024,"month":4,...}) into a java.util.Date, but it doesn't know how to handle that by default. Here are two reliable fixes:
Option 1: Annotate fields with @JsonFormat
Add this annotation to your Date fields to explicitly tell Jackson what string format to expect (match the pattern to what your frontend sends):
import com.fasterxml.jackson.annotation.JsonFormat; @JsonProperty("startDate") @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm") private Date startDate; @JsonProperty("endDate") @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm") private Date endDate;
This works perfectly if your frontend sends dates in ISO 8601 format (like 2024-05-20T14:30), which aligns with what datetime-local inputs produce.
Option 2: Configure Jackson globally (for apps with multiple Date fields)
If you have Date fields across multiple classes, set up a global Jackson config instead of annotating each field:
import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.SerializationFeature; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; @Configuration public class JacksonConfig { @Bean public ObjectMapper objectMapper() { ObjectMapper mapper = new ObjectMapper(); // Register module to handle Java 8+ date types (works with java.util.Date too) mapper.registerModule(new JavaTimeModule()); // Disable timestamp serialization; use ISO 8601 strings instead mapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS); return mapper; } }
Important: Make sure your React frontend sends dates as ISO 8601 strings (not JavaScript Date objects). If you send a Date object directly in a JSON request, it will serialize as a complex object with nested fields, triggering the deserialization error.
Your current React code has a few issues: miswritten onChange handler, mutable Date object usage, and incorrect initial time conversion. Here's the fixed version:
import { useState } from 'react'; import TextField from '@mui/material/TextField'; // Assuming Material UI usage const YourComponent = ({ classes }) => { // Initialize state with Pacific Time in ISO format (datetime-local expects yyyy-MM-dd'T'HH:mm) const [startDate, setStartDate] = useState(() => { const now = new Date(); // Convert current time to Pacific Time (automatically handles DST) const pacificTime = new Date(now.toLocaleString("en-US", { timeZone: "America/Los_Angeles" })); // Format to ISO string and truncate to required length return pacificTime.toISOString().slice(0, 16); }); // Proper onChange handler to update state when user selects a date const handleDateChange = (e) => { setStartDate(e.target.value); }; return ( <TextField id="datetime-local-startTime" type="datetime-local" value={startDate} className={classes.textField} onChange={handleDateChange} InputLabelProps={{ shrink: true, }} /> ); }; export default YourComponent;
Key improvements:
- Initial state calculation: Uses a function in
useStateto compute Pacific Time once on component mount. UsingtimeZone: "America/Los_Angeles"automatically handles daylight saving time, so you don't need hardcoded-8hour adjustments. - No state mutation: Creates a new Date instance instead of modifying the original one, avoiding unexpected state bugs.
- Controlled input: Uses
valueinstead ofdefaultValueto ensure the input always reflects the current state (better than uncontrolled inputs for form handling). - Correct onChange handler: Passes a function that uses the event's target value (the ISO string from the input) to update state.
内容的提问来源于stack exchange,提问作者Learner

