2015-06-11 2 views
0

Я следил за учебником по электронной коммерции NetBeans AffableBean, но вместо этого использовал IntelliJ в качестве моей IDE. Я доработал все до того момента, когда мне нужно добавить клиентов в базу данных, а также CustomerOrder, относящихся к заказу, который они размещают. Раздел учебника видна здесь:Ограничение внешнего ключа JPA на EntityManager flush

https://netbeans.org/kb/docs/javaee/ecommerce/transaction.html#placeOrder

Когда я размещаю заказ, я получаю следующее сообщение об ошибке:

com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Cannot add or update a child row: a foreign key constraint fails (`larrys`.`customer_order`, CONSTRAINT `fk_customer_order_customer` FOREIGN KEY (`customer_id`) REFERENCES `customer` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION) 

При промывке EntityManager здесь:

private void addOrderedItems(CustomerOrder order, ShoppingCart cart) { 

    em.flush(); //Here 

    List<ShoppingCartItem> items = cart.getItems(); 

    for (ShoppingCartItem scItem : items) { 

     int productId = scItem.getProduct().getId(); 

     OrderedProductPK orderedProductPK = new OrderedProductPK(); 
     orderedProductPK.setCustomerOrderId(order.getId()); 
     orderedProductPK.setProductId(productId); 

     OrderedProduct orderedItem = new OrderedProduct(orderedProductPK); 

     orderedItem.setQuantity(scItem.getQuantity()); 

     em.persist(orderedItem); 
    } 
} 

Мой полный код OrderManager отображается здесь:

http://pastebin.com/jRintrTS

Пожалуйста, поправьте меня, в противном случае, но от того, что я могу понять об ошибке, я пытаюсь вставить строку в customer_order таблицы, но не может сделать это в качестве внешнего ключа ссылки на customer_id не существует в customer таблице , Однако я создал клиента и сохранил его перед заказом, поэтому я не понимаю, почему он не передает данные в базу данных, прежде чем пытаться создать CustomerOrder.

Это схема SQL обеспечивается NetBeans для проекта электронной коммерции:

https://netbeans.org/projects/samples/sources/samples-source-code/content/samples/javaee/AffableBean/setup/schemaCreation.sql

И мой файл persistence.xml, идентичен тому, представленной в учебнике:

<?xml version="1.0" encoding="UTF-8"?> 
<persistence xmlns="http://java.sun.com/xml/ns/persistence" version="2.0"> 

    <persistence-unit name="LarrysPU" transaction-type="JTA"> 
     <jta-data-source>jdbc/larrys</jta-data-source> 
     <properties/> 
    </persistence-unit> 
</persistence> 

Единственное отличие моего проекта и проекта NetBeans заключается в том, что в моей таблице customer я изменил cityRegion на town, добавлено и county, и мой проект использует другое имя для AffableBean.

У кого-нибудь есть идеи относительно того, где я могу ошибаться?

EDIT - GlassFish Войти при обнаружении ошибки:

[2015-06-11T21:18:57.799+0100] [glassfish 4.1] [FINE] [] [org.eclipse.persistence.session.file:/OBFUSCATED/Larrys/out/artifacts/Larrys/WEB-INF/classes/_LarrysPU.sql] [tid: _ThreadID=26 _ThreadName=http-listener-1(2)] [timeMillis: 1434053937799] [levelValue: 500] [[ 
    INSERT INTO larrys.customer (id, address, cc_number, county, email, name, phone, postcode, town) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?) 
    bind => [9 parameters bound]]] 

[2015-06-11T21:18:57.800+0100] [glassfish 4.1] [FINEST] [] [org.eclipse.persistence.session.file:/OBFUSCATED/Larrys/out/artifacts/Larrys/WEB-INF/classes/_LarrysPU.query] [tid: _ThreadID=26 _ThreadName=http-listener-1(2)] [timeMillis: 1434053937800] [levelValue: 300] [[ 
    Execute query InsertObjectQuery([email protected])]] 

[2015-06-11T21:18:57.801+0100] [glassfish 4.1] [FINE] [] [org.eclipse.persistence.session.file:/OBFUSCATED/Larrys/out/artifacts/Larrys/WEB-INF/classes/_LarrysPU.sql] [tid: _ThreadID=26 _ThreadName=http-listener-1(2)] [timeMillis: 1434053937801] [levelValue: 500] [[ 
    INSERT INTO larrys.customer_order (id, amount, confirmation_number, date_created, customer_id) VALUES (?, ?, ?, ?, ?) 
    bind => [5 parameters bound]]] 

[2015-06-11T21:18:57.802+0100] [glassfish 4.1] [FINE] [] [org.eclipse.persistence.session.file:/OBFUSCATED/Larrys/out/artifacts/Larrys/WEB-INF/classes/_LarrysPU.sql] [tid: _ThreadID=26 _ThreadName=http-listener-1(2)] [timeMillis: 1434053937802] [levelValue: 500] [[ 
    SELECT 1]] 

[2015-06-11T21:18:57.802+0100] [glassfish 4.1] [WARNING] [] [org.eclipse.persistence.session.file:/OBFUSCATED/Larrys/out/artifacts/Larrys/WEB-INF/classes/_LarrysPU] [tid: _ThreadID=26 _ThreadName=http-listener-1(2)] [timeMillis: 1434053937802] [levelValue: 900] [[ 

Local Exception Stack: 
Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.5.2.v20140319-9ad6abd): org.eclipse.persistence.exceptions.DatabaseException 
Internal Exception: com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Cannot add or update a child row: a foreign key constraint fails (`larrys`.`customer_order`, CONSTRAINT `fk_customer_order_customer` FOREIGN KEY (`customer_id`) REFERENCES `customer` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION) 
Error Code: 1452 

ответ

1

Оказалось, что проблема, с которой я столкнулся, была вызвана тем фактом, что мои идентификаторы доступа не имели @GeneratedValue(strategy = GenerationType.IDENTITY), поэтому я добавил это для каждого объекта.

Что касается фиксации ошибки Unknown column 'SOMETHING' in 'field list', которую я получил, оказалось, что я получил это только для класса OrderedProduct. Вместо использования @Annotations в полях я решил использовать их в своих методах доступа, что может позволить настроить в будущем; но я забыл об этом:

@EmbeddedId 
protected OrderedProductPK orderedProductPK; 

где @EmbeddedId аннотаций должны были присутствовать на аксессору для OrderedProductPK.

0

Я предполагаю, что есть CUSTOMERID собственности на OrderedProduct и вам нужно вызвать orderedItem.setCustomerId() или orderedItem.setCustomer() с действительным идентификатор клиента или действительный объект клиента в зависимости от того, как вы создали классы сущностей. Кажется, что это единственные две строки, которые задают значения для объекта orderedItem.

// order id 
orderedProductPK.setCustomerOrderId(order.getId()); 
// product id 
orderedProductPK.setProductId(productId); 
// object created with order and product associations 
OrderedProduct orderedItem = new OrderedProduct(orderedProductPK); 
// quantity set 
orderedItem.setQuantity(scItem.getQuantity()); 
// customer is not associated 

Заказчик должен быть связан с orderItem.

EDIT: Глядя на учебник, похоже, что клиент связан с объектом заказа. Что вы получаете для order.getCustomer()? Если это null, это ваша проблема.

+0

Прежде чем я вызову метод addOrderedItems, я также вызываю 'addCustomer' и' addOrder'. Полный код для OrderManager отображается здесь - http://pastebin.com/jRintrTS - ошибка возникает в 'em.flush();', прежде чем она достигнет строки orderedItem. – driima

+0

'order.getCustomer()' не возвращает null, он возвращает объект Customer, назначенный для заказа. – driima

+0

Я думаю, что это не так, извините. Вы можете сделать order.getCustomer(). GetId()? Сохраняется ли клиент в рамках одной и той же транзакции? Если да, что произойдет, если вы сначала попытаетесь сохранить клиента? Если нет, можете ли вы напрямую запросить базу данных, чтобы убедиться, что запись клиента существует? Это может быть полезно: http://stackoverflow.com/questions/10769865/how-to-populate-foreign-key-values-in-a-hibernate-spring-jpa-configuration-whe – John

Смежные вопросы