我正在通過XML與SprinBoot/JPA進行集成。我必須讀取一個XML文件並將數據保存到我的數據庫中。 步驟:Hibernate拋出StackOverflow異常(Spring Boot)
- 我必須驗證,如果這個XML不是經常性的,如果它是,我必須更新這個寄存器。
每個XML都帶有一個項目列表,我必須驗證每個孩子是否已經存在,是否必須更新,如果沒有,我必須創建一個新的。
我必須驗證某些孩子是否經常性,如果不是,我必須刪除此項。
我必須驗證材料,顏色和產品是否存在,否則我必須爲每種情況創建一個新的。
一般來說,一切工作正常。但我有一些情況下,當我得到一個StackOverflow異常。
這不是因爲它是遞歸的,因爲90%的文件被正確保存並正確更新。
我試圖分開保存孩子,沒有成功。
它總是與拋出異常的文件相同。
這不是內存,因爲我有成功案例,該文件比失敗的文件大。
我可以多次保存成功文件,並且不會發生錯誤,但是如果我嘗試保存一個有問題的錯誤併發生異常。
這是我的課負責管理加載XML和持續
@Override
public void createProductionSet(ClientOrder clientOrder) throws Exception {
try{
List<Long> recurrent = new ArrayList<>();
ProductionOrder order = orderService.findByCodeAndClientCode(clientOrder.getOp(), clientOrder.getClientCode());
boolean newProdOrder = order == null,
hasChildrenInfo = hasChildrenInfo(clientOrder);
if(newProdOrder)
order = new ProductionOrder(clientOrder.getOp(), clientOrder.getClientCode(), clientOrder.getObservation());
order.setItems(new ArrayList<>());
if(hasChildrenInfo)
manageCollectionChildrenValues(clientOrder, order, newProdOrder, recurrent);
else
manageCollection(clientOrder, order, newProdOrder,recurrent,
loadColor(clientOrder.getColorReference(), clientOrder.getColor()),
loadMaterial(clientOrder.getMaterialReference(), clientOrder.getMaterial()),
loadProduct(clientOrder.getProductReference(), clientOrder.getProduct(), clientOrder.getUnitOfMeasurement()));
if(!newProdOrder)
prodOrderItemService.deleteNotIn(recurrent, order.getId());
orderService.save(order);
} catch(StackOverflowError t) {
throw new Exception("Erro de StackOverflowError : "+clientOrder.toString());
}catch (Exception e){
log.warn("ERRO >> "+e.getMessage());
}
}
private void manageCollection(ClientOrder clientOrder, ProductionOrder order, boolean newProdOrder, List<Long> recurrent,
MaterialColor materialColor, Material material, Product product) {
for(ItemOrder item : clientOrder.getItems()) {
item.setColorObj(materialColor);
item.setMaterialObj(material);
item.setProductObj(product);
manageItem(item, order, newProdOrder, recurrent);
}
}
private void manageCollectionChildrenValues(ClientOrder clientOrder, ProductionOrder order, boolean newProdOrder, List<Long> recurrent) {
for(ItemOrder item : clientOrder.getItems()) {
item.setColorObj(loadColor(item.getColorReference(), item.getColor()));
item.setMaterialObj(loadMaterial(item.getMaterialReference(), item.getMaterial()));
item.setProductObj(loadProduct(item.getProductReference(), item.getProduct(), clientOrder.getUnitOfMeasurement()));
manageItem(item, order, newProdOrder, recurrent);
}
}
private void manageItem(ItemOrder item, ProductionOrder order, boolean newProdOrder, List<Long> recurrent) {
ProdOrderItem aux = null;
if(!newProdOrder)
aux = prodOrderItemService.findOneByProductionOrderAndSize(order.getId(), item.getSize());
if(aux != null) {
aux.update(item);
recurrent.add(aux.getId());
}else {
aux = new ProdOrderItem(item, order);
order.getItems().add(aux);
}
}
private boolean hasChildrenInfo(ClientOrder clientOrder) {
return clientOrder.getColorReference() == null
&& clientOrder.getProductReference() == null
&& clientOrder.getMaterialReference() == null;
}
private Product loadProduct(String reference, String description, String unitOfMeasurement) {
if(reference != null && !reference.isEmpty()) {
Product product = productService.findProductByReference(reference);
if (product != null)
return product;
return productService.save(new Product(description, reference, unitOfMeasurement));
}
return productService.loadFirstOrDefault();
}
private MaterialColor loadColor(String reference, String description) {
if(reference != null && !reference.isEmpty()) {
MaterialColor materialColor = colorService.findByReference(reference);
if (materialColor != null)
return materialColor;
return colorService.save(new MaterialColor(reference, description));
}
return colorService.loadFirstOrDefault();
}
private Material loadMaterial(String reference, String description) {
if(reference != null && !reference.isEmpty()) {
Material material = materialService.findByReference(reference);
if (material != null)
return material;
return materialService.save(new Material(description, reference, null));
}
return materialService.loadFirstOrDefault();
}
}
這是我的模型:
@Entity(name = "production_order")
public class ProductionOrder {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private long id;
@Temporal(TemporalType.TIMESTAMP)
private Date created;
@Temporal(TemporalType.TIMESTAMP)
private Date updated;
@Type(type = "org.hibernate.type.NumericBooleanType")
private boolean deleted;
@Column(nullable = false, length = 30)
private String code;
@Column(length = 30)
private String clientCode;
@Column(length = 200)
private String observation;
@OneToMany(fetch = FetchType.EAGER, mappedBy ="productionOrder", orphanRemoval = true, cascade = {CascadeType.ALL})
@Cascade({org.hibernate.annotations.CascadeType.ALL})
private List<ProdOrderItem> items;
...
}
@Entity(name = "order_item")
public class ProdOrderItem {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Column(nullable = false, length = 10)
private String size;
@Column(nullable = false)
private float quantity;
@Column(nullable = false)
private float weight;
@Column(nullable = false)
private float tolerance;
@Temporal(TemporalType.TIMESTAMP)
private Date created;
@Temporal(TemporalType.TIMESTAMP)
private Date updated;
@Type(type = "org.hibernate.type.NumericBooleanType")
private boolean deleted;
@ManyToOne(optional = false)
@JoinColumn(name = "product_id")
private Product product;
@ManyToOne(optional = false)
@JoinColumn(name = "color_id")
private MaterialColor color;
@ManyToOne(optional = false)
private Material material;
@ManyToOne
@JoinColumn(name = "characteristic_id")
private Characteristic characteristic;
@ManyToOne(optional = false)
@JoinColumn(name="order_id")
private ProductionOrder productionOrder;
這是日誌:
java.lang.StackOverflowError
at org.apache.tomcat.jdbc.pool.ProxyConnection.invoke(ProxyConnection.java:131)
at org.apache.tomcat.jdbc.pool.JdbcInterceptor.invoke(JdbcInterceptor.java:108)
at org.apache.tomcat.jdbc.pool.DisposableConnectionFacade.invoke(DisposableConnectionFacade.java:81)
at com.sun.proxy.$Proxy106.prepareStatement(Unknown Source)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$5.doPrepare(StatementPreparerImpl.java:146)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$StatementPreparationTemplate.prepareStatement(StatementPreparerImpl.java:172)
at org.hibernate.engine.jdbc.internal.StatementPreparerImpl.prepareQueryStatement(StatementPreparerImpl.java:148)
at org.hibernate.loader.Loader.prepareQueryStatement(Loader.java:1929)
at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:1898)
at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:1876)
at org.hibernate.loader.Loader.doQuery(Loader.java:919)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:336)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:306)
at org.hibernate.loader.Loader.loadEntity(Loader.java:2204)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:60)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:50)
at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4019)
at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:508)
at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:478)
at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:219)
at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:278)
at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:121)
at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:89)
at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1129)
at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1022)
at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:639)
at org.hibernate.type.EntityType.resolve(EntityType.java:431)
at org.hibernate.type.ComponentType.resolve(ComponentType.java:687)
at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:848)
at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:714)
at org.hibernate.loader.Loader.processResultSet(Loader.java:972)
at org.hibernate.loader.Loader.doQuery(Loader.java:930)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:336)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:306)
at org.hibernate.loader.Loader.loadEntity(Loader.java:2204)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:60)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:50)
at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4019)
at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:508)
at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:478)
at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:219)
at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:278)
at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:121)
at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:89)
at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1129)
at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1022)
at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:639)
at org.hibernate.type.EntityType.resolve(EntityType.java:431)
at org.hibernate.type.ComponentType.resolve(ComponentType.java:687)
at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:848)
at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:714)
at org.hibernate.loader.Loader.processResultSet(Loader.java:972)
at org.hibernate.loader.Loader.doQuery(Loader.java:930)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:336)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:306)
at org.hibernate.loader.Loader.loadEntity(Loader.java:2204)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:60)
at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:50)
at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4019)
at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:508)
at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:478)
at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:219)
at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:278)
at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:121)
at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:89)
at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1129)
at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1022)
at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:639)
at org.hibernate.type.EntityType.resolve(EntityType.java:431)
at org.hibernate.type.ComponentType.resolve(ComponentType.java:687)
at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:848)
at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:714)
at org.hibernate.loader.Loader.processResultSet(Loader.java:972)
at org.hibernate.loader.Loader.doQuery(Loader.java:930)
at
完整的日誌here, together with 2 xml files
爲什麼你認爲你需要兩個'@OneToMany(級聯= ALL )'和'@Cascade(ALL)'? – crizzis
我的錯誤。我也必須消除渴望。 –