Tutoriel du gestionnaire d'entités : schéma d'entité de commande

Création de quatre classes entité à l'aide de relations uniques et bidirectionnelles, de listes ordonnées et de relations de clés externes. Les API Entity sont utilisées pour conserver et rechercher les entités. Construite sur les entités Order et Customer des sections précédentes du tutoriel, cette étape ajoute deux entités supplémentaires : Item et OrderLine.

Pourquoi et quand exécuter cette tâche

Figure 1. Schéma d'entité de commande. Une entité Order (de commande) a une référence à un client et à zéro ou plus lignes de commande (OrderLines). Chaque entité OrderLine a une référence à un seul article et inclut la quantité commandée.
Schéma d'entité de commande (Order)

Procédure

  1. Créez l'entité client, similaire aux exemples précédents.
    Customer.java
    @Entity
    public class Customer
    {
        @Id String id;
        String firstName;
        String surname;
        String address;
        String phoneNumber;
    }
  2. Créez l'entité Item, qui contient les informations sur un produit inclus dans le stock du magasin, telles que la description, la quantité et le prix du produit.
    Item.java
    @Entity
    public class Item
    {
        @Id String id;
        String description;
        long quantityOnHand;
        double price;
    }
  3. Créez l'entité OrderLine. Chaque entité Order possède zéro ou plus entités OrderLines, qui identifient la quantité de chaque article de la commande. La clé pour OrderLine est une clé composée qui comprend l'entité Order possédée par l'entité OrderLine et un nombre entier qui affecte un numéro à la ligne de commande. Ajoutez le modificateur de conservation de cascade à chaque relation de vos entités.
    OrderLine.java
    @Entity
    public class OrderLine
    {
        @Id @ManyToOne(cascade=CascadeType.PERSIST) Order order;
        @Id int lineNumber;
        @OneToOne(cascade=CascadeType.PERSIST) Item item;
        int quantity;
        double price;
    }
  4. Créez l'objet Order final, doté d'une référence au client de la commande et à une collection d'objets OrderLine.
    Order.java
    @Entity
    public class Order {
        @Id String orderNumber;
        java.util.Date date;
        @ManyToOne(cascade=CascadeType.PERSIST) Customer customer;
        @OneToMany(cascade=CascadeType.ALL, mappedBy="order") 
    			@OrderBy("lineNumber") List<OrderLine> lines; 
    } 

    La cascade ALL est utilisée comme modificateur des lignes. Ce modificateur signale EntityManager pour cascader les opérations PERSIST et REMOVE. Par exemple, si l'entité Order est conservée ou supprimée, toutes les entités OrderLine sont également conservées ou supprimées.

    Si une entité OrderLine est supprimée de la liste des lignes dans l'objet Order, la référence est rompue. Toutefois, l'entité OrderLine n'est pas supprimée du cache. Vous devez utiliser l'API de suppression d'EntityManager pour supprimer les entités du cache. L'opération REMOVE n'est pas utilisée sur l'entité Customer ou Item de la ligne de commande. Ainsi, l'entité Customer est conservée même si la commande ou l'article est supprimé(e) lors de la suppression de la ligne de commande.

    Le modificateur mappedBy indique une relation inverse avec l'entité cible. Le modificateur identifie l'attribut de l'entité cible qui référence l'entité source, ainsi que le côté propriétaire de la relation un à un ou plusieurs à plusieurs. En règle générale, vous pouvez omettre le modificateur. Toutefois, une erreur s'affiche indiquant qu'il doit être spécifié si WebSphere eXtreme Scale ne parvient pas à le détecter automatiquement. Une entité OrderLine qui contient deux des attributs Order dans une relation plusieurs à un provoque généralement cette erreur.

    L'annotation @OrderBy spécifie l'ordre dans lequel les entités OrderLine doivent apparaître dans la liste des lignes. Si l'annotation n'est pas spécifiée, les lignes s'affichent dans un ordre arbitraire. Bien que les lignes soient ajoutées à l'entité Order par la soumission d'une liste ArrayList, qui conserve l'ordre, EntityManager ne reconnaît pas nécessairement cet ordre. Lorsque vous émettez la méthode de recherche pour récupérer l'objet Order depuis le cache, l'objet List n'est pas un objet ArrayList.

  5. Créez l'application. L'exemple suivant illustre l'objet Order final, qui est doté d'une référence au client de la commande et à une collection d'objets OrderLine.
    1. Recherchez les articles à commander, qui deviennent ensuite des entités gérées.
    2. Créez l'entité OrderLine et liez-la à chaque article.
    3. Créez l'entité Order et associez-la à chaque ligne de commande et au client.
    4. Conservez la commande, qui conserve automatiquement chaque ligne de commande.
    5. Validez la transaction, qui détache chaque entité et synchronise l'état des entités avec le cache.
    6. Imprimez les informations de la commande. Les entités OrderLine sont automatiquement triées par l'ID OrderLine.
    Application.java
    
    static public void main(String [] args)
            throws Exception
        {
            ...
    
            // Ajoutez des articles à notre stock.
            em.getTransaction().begin();
            createItems(em);
            em.getTransaction().commit();
    
            // Créez un client ayant des articles dans son panier.
            em.getTransaction().begin();
            Customer cust = createCustomer();
            em.persist(cust);
    
            // Créez une commande et ajoutez une ligne de commande pour chaque article.
            // Chaque article d'une ligne est automatiquement conservé, 
    				// car l'option Cascade=ALL est définie.
            Order order = createOrderFromItems(em, cust, "ORDER_1", 
    					new String[]{"1", "2"}, new int[]{1,3});
            em.persist(order);
            em.getTransaction().commit();
    
            // Imprimez le récapitulatif de la commande.
            em.getTransaction().begin();
            order = (Order)em.find(Order.class, "ORDER_1");
            System.out.println(printOrderSummary(order));
            em.getTransaction().commit();
        }
    
        public static Customer createCustomer() {
            Customer cust = new Customer();
            cust.address = "Main Street";
            cust.firstName = "John";
            cust.surname = "Smith";
            cust.id = "C001";
            cust.phoneNumber = "5555551212";
            return cust;
        }
    
        public static void createItems(EntityManager em) {
            Item item1 = new Item();
            item1.id = "1";
            item1.price = 9.99;
            item1.description = "Widget 1";
            item1.quantityOnHand = 4000;
            em.persist(item1);
    
            Item item2 = new Item();
            item2.id = "2";
            item2.price = 15.99;
            item2.description = "Widget 2";
            item2.quantityOnHand = 225;
            em.persist(item2);
    
        }
    
        public static Order createOrderFromItems(EntityManager em, 
    			Customer cust, String orderId, String[] itemIds, int[] qty) {
    
            Item[] items = getItems(em, itemIds);
    
            Order order = new Order();
            order.customer = cust;
            order.date = new java.util.Date();
            order.orderNumber = orderId;
            order.lines = new ArrayList<OrderLine>(items.length);          
    			 for(int i=0;i<items.length;i++){
    						OrderLine line = new OrderLine();
                line.lineNumber = i+1;
                line.item = items[i];
                line.price = line.item.price;
                line.quantity = qty[i];
                line.order = order;
                order.lines.add(line);
            }
            return order;
        }
    
        public static Item[] getItems(EntityManager em, String[] itemIds) {
            Item[] items = new Item[itemIds.length];
            for(int i=0;i<items.length;i++){
    			 items[i] = (Item) em.find(Item.class, itemIds[i]);
            }
            return items;
        }
    L'étape suivante consiste à supprimer une entité. L'interface d'EntityManager est dotée d'une méthode de suppression qui désigne un objet comme étant supprimé. L'application doit supprimer l'entité de toutes les collections de relations avant d'appeler la méthode de suppression. Pour la dernière étape, modifiez les références et émettez la méthode de suppression, em.remove(object).