Sobes.tech
Junior

What is a composite key?

sobes.tech AI

Answer from AI

A composite (or concatenated) key in a database is a primary key consisting of two or more columns of a table. The uniqueness of a record is determined by the combination of values of all columns included in the composite key.

In Java applications using JPA, a composite key is usually implemented in one of two ways:

  1. Using @Embeddable and @EmbeddedId:

    A separate class marked with the @Embeddable annotation is created, which encapsulates the fields that make up the composite key. In the entity, this class is embedded using the @EmbeddedId annotation. The class representing the composite key must implement Serializable and override the equals() and hashCode() methods.

    // Composite key class
    @Embeddable
    public class OrderItemId implements Serializable {
    
        private Long orderId;
        private Long productId;
    
        // Constructors, getters, setters
    
        @Override
        public boolean equals(Object o) {
            if (this == o) return true;
            if (o == null || getClass() != o.getClass()) return false;
            OrderItemId that = (OrderItemId) o;
            return Objects.equals(orderId, that.orderId) &&
                   Objects.equals(productId, that.productId);
        }
    
        @Override
        public int hashCode() {
            return Objects.hash(orderId, productId);
        }
    }
    
    // Entity with composite key
    @Entity
    public class OrderItem {
    
        @EmbeddedId
        private OrderItemId id;
    
        private int quantity;
    
        // Constructors, getters, setters
    }
    
  2. Using @IdClass:

    A separate class representing the composite key (also implementing Serializable and overriding equals() and hashCode()) is created, and the entity specifies the name of this class using the @IdClass annotation. The fields that are part of the composite key are declared directly in the entity and marked with the @Id annotation. The field names in the entity and the key class must match.

    // Composite key class
    public class OrderItemId implements Serializable {
    
        private Long orderId;
        private Long productId;
    
        // Constructors, getters, setters
    
        @Override
        public boolean equals(Object o) {
            if (this == o) return true;
            if (o == null || getClass() != o.getClass()) return false;
            OrderItemId that = (OrderItemId) o;
            return Objects.equals(orderId, that.orderId) &&
                   Objects.equals(productId, that.productId);
        }
    
        @Override
        public int hashCode() {
            return Objects.hash(orderId, productId);
        }
    }
    
    // Entity with composite key
    @Entity
    @IdClass(OrderItemId.class)
    public class OrderItem {
    
        @Id
        private Long orderId;
    
        @Id
        private Long productId;
    
        private int quantity;
    
        // Constructors, getters, setters
    }