#java
#java
Вопрос:
У меня есть два класса Promotion и PromotionZona и имеют эту ошибку.
Вот мой запрос json, который я хочу сохранить в базе данных.
"promotionZona":{"localidad":{"latitud":0.0,"longitud":0.0},"provincia":{},"todoElPais":true,"promotion":0,"promoZonaId":0}
Вы можете увидеть продвижение, но я не могу сохранить его в своей базе данных, у меня такая ошибка:
2020-10-25 20:06:50.113 INFO 5550 --- [ main] o.s.s.quartz.SchedulerFactoryBean : Starting Quartz Scheduler now
2020-10-25 20:06:50.113 INFO 5550 --- [ main] org.quartz.core.QuartzScheduler : Scheduler quartzScheduler_$_NON_CLUSTERED started.
2020-10-25 20:06:50.133 INFO 5550 --- [ main] a.c.b.s.s.SuipBackofficeApplication : Started SuipBackofficeApplication in 31.486 seconds (JVM running for 57.573)
2020-10-25 20:06:50.323 INFO 5550 --- [ main] org.apache.jasper.servlet.TldScanner : At least one JAR was scanned for TLDs yet contained no TLDs. Enable debug logging for this logger for a complete list of JARs that were scanned but no TLDs were found in them. Skipping unneeded JARs during scanning can improve startup time and JSP compilation time.
2020-10-25 20:06:50.419 INFO 5550 --- [ main] org.apache.coyote.ajp.AjpNioProtocol : Starting ProtocolHandler ["ajp-nio-8109"]
2020-10-25 20:06:50.430 INFO 5550 --- [ main] org.apache.catalina.startup.Catalina : Server startup in [47,370] milliseconds
2020-10-25 20:07:21.325 INFO 5550 --- [nio-8180-exec-3] o.a.c.c.C.[.[.[/suip-backoffice] : Initializing Spring DispatcherServlet 'dispatcherServlet'
2020-10-25 20:07:21.327 INFO 5550 --- [nio-8180-exec-3] o.s.web.servlet.DispatcherServlet : Initializing Servlet 'dispatcherServlet'
2020-10-25 20:07:21.413 INFO 5550 --- [nio-8180-exec-3] o.s.web.servlet.DispatcherServlet : Completed initialization in 86 ms
2020-10-25 20:07:21.759 WARN 5550 --- [nio-8180-exec-3] .w.s.m.s.DefaultHandlerExceptionResolver : Resolved [org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Cannot construct instance of `us.com.model.Promocion` (although at least one Creator exists): no int/Int-argument constructor/factory method to deserialize from Number value (0); nested exception is com.fasterxml.jackson.databind.exc.MismatchedInputException: Cannot construct instance of `us.com.model.suipportalmodel.model.Promotion` (although at least one Creator exists): no int/Int-argument constructor/factory method to deserialize from Number value (0)
at [Source: (PushbackInputStream); line: 1, column: 2650] (through reference chain: ar.com.model.suipportalmodel.dto.PromotionDTO["promotionZona"]->java.lang.Object[][0]->.PromotionZona["promotion"])]
Моя зона продвижения объекта:
@Table(name="promotion_zona")
public class PromotionZona implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)//9
@Column(name = "id_promotion_zona", unique = true, nullable= false)
private Long idPromotionZona;
@Column(name="todo_el_pais")
private Boolean todoElPais;
@Column(name="fecha_desde_solicitada")
private Date fechaDesdeSolicitada;
@Column(name="fecha_hasta_solicitada")
private Date fechaHastaSolicitada;
@Column(name="fecha_desde_confirmada")
private Date fechaDesdeConfirmada;
@Column(name="fecha_hasta_confirmada")
private Date fechaHastaConfirmada;
@ManyToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
@JoinColumn(name="id_localidad",nullable=false)
private Localidad localidad;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "id_provincia", nullable = true)
private Provincia provincia;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name="id_promocion",nullable=false)
private Promotion promotion; ```
Комментарии:
1. Не уверен, связано ли это, но у вас есть
Promocion
в вашей сущности иpromotion
в вашем запросе.2. Это не имеет значения, я меняю сейчас, но та же ошибка
3. Ваш json на самом деле не является допустимым json. Вам нужно будет обернуть его в {}, чтобы сделать его действительным.
Ответ №1:
Ошибка возникает, когда spring mvc не удается десериализовать данные json для вашего класса Promotion
, точнее, это сбой "promotion":0 -> instance of class Promotion
, поскольку Promotion
это класс, он должен выглядеть примерно так:
public class Promotion {
private int field1;
//getters and setters
}
затем в ваших данных json это должно быть:
"promotion":{"filed1": 0}
Итак, есть несколько способов решить эту проблему:
- в настоящее время вы можете изменить свой запрос на:
"promotionZona":{"localidad":{"latitud":0.0,"longitud":0.0},"provincia":{},"todoElPais":true,"promotion":{"field1":0},"promoZonaId":0}
- добавьте конструктор int-argument в класс
Promotion
:
public class Promotion {
private int field1;
public Promotion(int field1) {
this.field1 = field1;
}
//getters and setters
}
- добавьте пользовательский
JsonDeserializer
:
public class PromotionJsonDeserializer extends JsonDeserializer<Promotion> {
@Override
public Promotion deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
if(jsonParser == null)return null;
Promotion promotion = new Promotion();
promotion.setField1(Integer.valueOf(jsonParser.getText()));
return promotion;
}
}
затем в PromotionZona аннотируйте поле promotion
с помощью PromotionJsonDeserializer
:
@Table(name="promotion_zona")
public class PromotionZona implements Serializable {
...
@JsonDeserialize(using = PromotionJsonDeserializer.class)
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name="id_promocion",nullable=false)
private Promotion promotion;