or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

caching-locking.mdcriteria-api.mdentity-manager.mdentity-mapping.mdindex.mdlifecycle-callbacks.mdmetamodel.mdqueries.mdspi.md

entity-mapping.mddocs/

0

# Entity Mapping and Relationships

1

2

Complete reference for entity annotations, relationship mappings, inheritance strategies, and mapping customizations in Jakarta Persistence.

3

4

## Imports

5

6

```java { .api }

7

import jakarta.persistence.*;

8

```

9

10

## Capabilities

11

12

### Entity Definition

13

14

Define entities that map Java classes to database tables.

15

16

```java { .api }

17

/**

18

* Specifies that the class is an entity

19

* @since 1.0

20

*/

21

@Target(TYPE)

22

@Retention(RUNTIME)

23

public @interface Entity {

24

/**

25

* (Optional) The entity name. Defaults to the unqualified name of the entity class.

26

* This name is used to refer to the entity in queries.

27

*/

28

String name() default "";

29

}

30

31

/**

32

* Specifies the primary table for the annotated entity

33

* @since 1.0

34

*/

35

@Target(TYPE)

36

@Retention(RUNTIME)

37

public @interface Table {

38

/** (Optional) The name of the table */

39

String name() default "";

40

41

/** (Optional) The catalog of the table */

42

String catalog() default "";

43

44

/** (Optional) The schema of the table */

45

String schema() default "";

46

47

/** (Optional) Unique constraints to be placed on the table */

48

UniqueConstraint[] uniqueConstraints() default {};

49

50

/** (Optional) Indexes for the table */

51

Index[] indexes() default {};

52

}

53

54

/**

55

* Designates a class whose mapping information is applied to entities that inherit from it

56

* @since 1.0

57

*/

58

@Target(TYPE)

59

@Retention(RUNTIME)

60

public @interface MappedSuperclass {

61

}

62

63

/**

64

* Specifies that a class whose instances are stored as an intrinsic part of an owning entity

65

* @since 1.0

66

*/

67

@Target(TYPE)

68

@Retention(RUNTIME)

69

public @interface Embeddable {

70

}

71

72

/**

73

* Specifies that the property or field is not persistent

74

* @since 1.0

75

*/

76

@Target({METHOD, FIELD})

77

@Retention(RUNTIME)

78

public @interface Transient {

79

}

80

```

81

82

**Usage Example:**

83

84

```java

85

@Entity

86

@Table(name = "customers", schema = "sales")

87

public class Customer {

88

@Id

89

private Long id;

90

private String name;

91

}

92

93

@MappedSuperclass

94

public abstract class BaseEntity {

95

@Id

96

@GeneratedValue(strategy = GenerationType.IDENTITY)

97

private Long id;

98

99

@Version

100

private Integer version;

101

}

102

103

@Embeddable

104

public class Address {

105

private String street;

106

private String city;

107

private String zipCode;

108

}

109

```

110

111

### Primary Keys

112

113

Define primary key fields and generation strategies.

114

115

```java { .api }

116

/**

117

* Specifies the primary key of an entity

118

* @since 1.0

119

*/

120

@Target({METHOD, FIELD})

121

@Retention(RUNTIME)

122

public @interface Id {

123

}

124

125

/**

126

* Provides for the specification of generation strategies for primary keys

127

* @since 1.0

128

*/

129

@Target({METHOD, FIELD})

130

@Retention(RUNTIME)

131

public @interface GeneratedValue {

132

/** (Optional) The primary key generation strategy */

133

GenerationType strategy() default GenerationType.AUTO;

134

135

/** (Optional) The name of the primary key generator */

136

String generator() default "";

137

}

138

139

/**

140

* Specifies a composite primary key class

141

* @since 1.0

142

*/

143

@Target(TYPE)

144

@Retention(RUNTIME)

145

public @interface IdClass {

146

/** The primary key class */

147

Class value();

148

}

149

150

/**

151

* Applied to a persistent field or property to denote a composite primary key

152

* @since 1.0

153

*/

154

@Target({METHOD, FIELD})

155

@Retention(RUNTIME)

156

public @interface EmbeddedId {

157

}

158

159

/**

160

* Defines a primary key generator that may be referenced by name

161

* @since 1.0

162

*/

163

@Target({TYPE, METHOD, FIELD})

164

@Retention(RUNTIME)

165

public @interface SequenceGenerator {

166

/** (Required) A unique generator name */

167

String name();

168

169

/** (Optional) The name of the database sequence object */

170

String sequenceName() default "";

171

172

/** (Optional) The catalog of the sequence generator */

173

String catalog() default "";

174

175

/** (Optional) The schema of the sequence generator */

176

String schema() default "";

177

178

/** (Optional) The value from which the sequence object is to start */

179

int initialValue() default 1;

180

181

/** (Optional) The amount to increment by when allocating sequence numbers */

182

int allocationSize() default 50;

183

}

184

185

/**

186

* Used to group SequenceGenerator annotations

187

* @since 2.2

188

*/

189

@Target({TYPE})

190

@Retention(RUNTIME)

191

public @interface SequenceGenerators {

192

/** Array of sequence generators */

193

SequenceGenerator[] value();

194

}

195

196

/**

197

* Defines a primary key generator using a database table

198

* @since 1.0

199

*/

200

@Target({TYPE, METHOD, FIELD})

201

@Retention(RUNTIME)

202

public @interface TableGenerator {

203

/** (Required) A unique generator name */

204

String name();

205

206

/** (Optional) Name of table that stores the generated id values */

207

String table() default "";

208

209

/** (Optional) The catalog of the table */

210

String catalog() default "";

211

212

/** (Optional) The schema of the table */

213

String schema() default "";

214

215

/** (Optional) Name of the primary key column in the table */

216

String pkColumnName() default "";

217

218

/** (Optional) Name of the column that stores the generated id value */

219

String valueColumnName() default "";

220

221

/** (Optional) The primary key value in the generator table */

222

String pkColumnValue() default "";

223

224

/** (Optional) The initial value to be used */

225

int initialValue() default 0;

226

227

/** (Optional) The amount to increment by */

228

int allocationSize() default 50;

229

230

/** (Optional) Unique constraints on the table */

231

UniqueConstraint[] uniqueConstraints() default {};

232

233

/** (Optional) Indexes for the table */

234

Index[] indexes() default {};

235

}

236

237

/**

238

* Used to group TableGenerator annotations

239

* @since 2.2

240

*/

241

@Target({TYPE})

242

@Retention(RUNTIME)

243

public @interface TableGenerators {

244

/** Array of table generators */

245

TableGenerator[] value();

246

}

247

```

248

249

**Usage Example:**

250

251

```java

252

// Simple primary key

253

@Entity

254

public class Product {

255

@Id

256

@GeneratedValue(strategy = GenerationType.IDENTITY)

257

private Long id;

258

}

259

260

// Sequence generator

261

@Entity

262

public class Order {

263

@Id

264

@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "order_seq")

265

@SequenceGenerator(name = "order_seq", sequenceName = "order_sequence", allocationSize = 10)

266

private Long id;

267

}

268

269

// Composite key with @IdClass

270

@Entity

271

@IdClass(OrderItemId.class)

272

public class OrderItem {

273

@Id

274

private Long orderId;

275

276

@Id

277

private Long productId;

278

279

private Integer quantity;

280

}

281

282

// Composite key with @EmbeddedId

283

@Entity

284

public class OrderItem {

285

@EmbeddedId

286

private OrderItemId id;

287

288

private Integer quantity;

289

}

290

291

@Embeddable

292

public class OrderItemId implements Serializable {

293

private Long orderId;

294

private Long productId;

295

}

296

```

297

298

### Column Mapping

299

300

Map entity fields to database columns with detailed configuration.

301

302

```java { .api }

303

/**

304

* Specifies the mapped column for a persistent property or field

305

* @since 1.0

306

*/

307

@Target({METHOD, FIELD})

308

@Retention(RUNTIME)

309

public @interface Column {

310

/** (Optional) The name of the column */

311

String name() default "";

312

313

/** (Optional) Whether the column is a unique key */

314

boolean unique() default false;

315

316

/** (Optional) Whether the database column is nullable */

317

boolean nullable() default true;

318

319

/** (Optional) Whether the column is included in SQL INSERT statements */

320

boolean insertable() default true;

321

322

/** (Optional) Whether the column is included in SQL UPDATE statements */

323

boolean updatable() default true;

324

325

/** (Optional) The SQL fragment to use when generating the DDL */

326

String columnDefinition() default "";

327

328

/** (Optional) The name of the table containing the column */

329

String table() default "";

330

331

/** (Optional) The column length (for String values) */

332

int length() default 255;

333

334

/** (Optional) The precision for a decimal column */

335

int precision() default 0;

336

337

/** (Optional) The scale for a decimal column */

338

int scale() default 0;

339

}

340

341

/**

342

* The simplest type of mapping to a database column

343

* @since 1.0

344

*/

345

@Target({METHOD, FIELD})

346

@Retention(RUNTIME)

347

public @interface Basic {

348

/** (Optional) Whether the value should be lazily fetched */

349

FetchType fetch() default FetchType.EAGER;

350

351

/** (Optional) Whether the value may be null */

352

boolean optional() default true;

353

}

354

355

/**

356

* Specifies that a persistent property or field should be persisted as a large object

357

* @since 1.0

358

*/

359

@Target({METHOD, FIELD})

360

@Retention(RUNTIME)

361

public @interface Lob {

362

}

363

364

/**

365

* Specifies that a persistent property or field should be persisted as an enumerated type

366

* @since 1.0

367

*/

368

@Target({METHOD, FIELD})

369

@Retention(RUNTIME)

370

public @interface Enumerated {

371

/** (Optional) The type used in mapping */

372

EnumType value() default EnumType.ORDINAL;

373

}

374

375

/**

376

* Must be specified for persistent fields or properties of type Date and Calendar

377

* @since 1.0

378

*/

379

@Target({METHOD, FIELD})

380

@Retention(RUNTIME)

381

public @interface Temporal {

382

/** (Required) The type used in mapping */

383

TemporalType value();

384

}

385

386

/**

387

* Specifies the version field or property for optimistic locking

388

* @since 1.0

389

*/

390

@Target({METHOD, FIELD})

391

@Retention(RUNTIME)

392

public @interface Version {

393

}

394

```

395

396

**Usage Example:**

397

398

```java

399

@Entity

400

public class Article {

401

@Id

402

@GeneratedValue

403

private Long id;

404

405

@Column(name = "title", nullable = false, length = 200)

406

private String title;

407

408

@Lob

409

@Column(name = "content")

410

private String content;

411

412

@Enumerated(EnumType.STRING)

413

@Column(length = 20)

414

private ArticleStatus status;

415

416

@Temporal(TemporalType.TIMESTAMP)

417

@Column(name = "created_at")

418

private Date createdAt;

419

420

@Column(precision = 10, scale = 2)

421

private BigDecimal price;

422

423

@Version

424

private Integer version;

425

}

426

```

427

428

### Embedded Objects

429

430

Embed objects as part of an entity.

431

432

```java { .api }

433

/**

434

* Specifies a persistent field or property whose value is an embeddable instance

435

* @since 1.0

436

*/

437

@Target({METHOD, FIELD})

438

@Retention(RUNTIME)

439

public @interface Embedded {

440

}

441

442

/**

443

* Used to override the mapping of a Basic property or field

444

* @since 1.0

445

*/

446

@Target({TYPE, METHOD, FIELD})

447

@Retention(RUNTIME)

448

public @interface AttributeOverride {

449

/** (Required) The name of the property whose mapping is being overridden */

450

String name();

451

452

/** (Required) The column that is being mapped to the persistent attribute */

453

Column column();

454

}

455

456

/**

457

* Used to override mappings of multiple properties or fields

458

* @since 1.0

459

*/

460

@Target({TYPE, METHOD, FIELD})

461

@Retention(RUNTIME)

462

public @interface AttributeOverrides {

463

/** Array of attribute overrides */

464

AttributeOverride[] value();

465

}

466

467

/**

468

* Used to override a mapping for an entity relationship

469

* @since 1.0

470

*/

471

@Target({TYPE, METHOD, FIELD})

472

@Retention(RUNTIME)

473

public @interface AssociationOverride {

474

/** (Required) The name of the relationship property whose mapping is being overridden */

475

String name();

476

477

/** (Optional) The join columns that are used for the association */

478

JoinColumn[] joinColumns() default {};

479

480

/** (Optional) The foreign key constraint specification */

481

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

482

483

/** (Optional) The join table that maps the relationship */

484

JoinTable joinTable() default @JoinTable;

485

}

486

487

/**

488

* Used to override mappings of multiple relationship properties or fields

489

* @since 1.0

490

*/

491

@Target({TYPE, METHOD, FIELD})

492

@Retention(RUNTIME)

493

public @interface AssociationOverrides {

494

/** Array of association overrides */

495

AssociationOverride[] value();

496

}

497

```

498

499

**Usage Example:**

500

501

```java

502

@Embeddable

503

public class Address {

504

private String street;

505

private String city;

506

private String zipCode;

507

}

508

509

@Entity

510

public class Person {

511

@Id

512

private Long id;

513

514

@Embedded

515

private Address homeAddress;

516

517

@Embedded

518

@AttributeOverrides({

519

@AttributeOverride(name = "street", column = @Column(name = "work_street")),

520

@AttributeOverride(name = "city", column = @Column(name = "work_city")),

521

@AttributeOverride(name = "zipCode", column = @Column(name = "work_zip"))

522

})

523

private Address workAddress;

524

}

525

```

526

527

### Relationships

528

529

Define relationships between entities.

530

531

```java { .api }

532

/**

533

* Specifies a single-valued association to another entity with one-to-one multiplicity

534

* @since 1.0

535

*/

536

@Target({METHOD, FIELD})

537

@Retention(RUNTIME)

538

public @interface OneToOne {

539

/** (Optional) The entity class that is the target of the association */

540

Class targetEntity() default void.class;

541

542

/** (Optional) The operations that must be cascaded to the target */

543

CascadeType[] cascade() default {};

544

545

/** (Optional) Whether the association should be lazily loaded or eagerly fetched */

546

FetchType fetch() default FetchType.EAGER;

547

548

/** (Optional) Whether the association is optional */

549

boolean optional() default true;

550

551

/** (Optional) The field that owns the relationship (bidirectional) */

552

String mappedBy() default "";

553

554

/** (Optional) Whether to apply the remove operation to orphaned entities */

555

boolean orphanRemoval() default false;

556

}

557

558

/**

559

* Specifies a many-valued association with one-to-many multiplicity

560

* @since 1.0

561

*/

562

@Target({METHOD, FIELD})

563

@Retention(RUNTIME)

564

public @interface OneToMany {

565

/** (Optional) The entity class that is the target of the association */

566

Class targetEntity() default void.class;

567

568

/** (Optional) The operations that must be cascaded to the target */

569

CascadeType[] cascade() default {};

570

571

/** (Optional) Whether the association should be lazily loaded or eagerly fetched */

572

FetchType fetch() default FetchType.LAZY;

573

574

/** (Optional) The field that owns the relationship */

575

String mappedBy() default "";

576

577

/** (Optional) Whether to apply the remove operation to orphaned entities */

578

boolean orphanRemoval() default false;

579

}

580

581

/**

582

* Specifies a single-valued association to another entity with many-to-one multiplicity

583

* @since 1.0

584

*/

585

@Target({METHOD, FIELD})

586

@Retention(RUNTIME)

587

public @interface ManyToOne {

588

/** (Optional) The entity class that is the target of the association */

589

Class targetEntity() default void.class;

590

591

/** (Optional) The operations that must be cascaded to the target */

592

CascadeType[] cascade() default {};

593

594

/** (Optional) Whether the association should be lazily loaded or eagerly fetched */

595

FetchType fetch() default FetchType.EAGER;

596

597

/** (Optional) Whether the association is optional */

598

boolean optional() default true;

599

}

600

601

/**

602

* Specifies a many-valued association with many-to-many multiplicity

603

* @since 1.0

604

*/

605

@Target({METHOD, FIELD})

606

@Retention(RUNTIME)

607

public @interface ManyToMany {

608

/** (Optional) The entity class that is the target of the association */

609

Class targetEntity() default void.class;

610

611

/** (Optional) The operations that must be cascaded to the target */

612

CascadeType[] cascade() default {};

613

614

/** (Optional) Whether the association should be lazily loaded or eagerly fetched */

615

FetchType fetch() default FetchType.LAZY;

616

617

/** (Optional) The field that owns the relationship */

618

String mappedBy() default "";

619

}

620

621

/**

622

* Specifies a column for joining an entity association

623

* @since 1.0

624

*/

625

@Target({METHOD, FIELD})

626

@Retention(RUNTIME)

627

public @interface JoinColumn {

628

/** (Optional) The name of the foreign key column */

629

String name() default "";

630

631

/** (Optional) The name of the column referenced by this foreign key column */

632

String referencedColumnName() default "";

633

634

/** (Optional) Whether the foreign key column is unique */

635

boolean unique() default false;

636

637

/** (Optional) Whether the foreign key column is nullable */

638

boolean nullable() default true;

639

640

/** (Optional) Whether the column is included in SQL INSERT statements */

641

boolean insertable() default true;

642

643

/** (Optional) Whether the column is included in SQL UPDATE statements */

644

boolean updatable() default true;

645

646

/** (Optional) The SQL fragment to use for the column definition */

647

String columnDefinition() default "";

648

649

/** (Optional) The name of the table containing the foreign key column */

650

String table() default "";

651

652

/** (Optional) The foreign key constraint specification */

653

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

654

}

655

656

/**

657

* Specifies the mapping for composite foreign keys

658

* @since 1.0

659

*/

660

@Target({METHOD, FIELD})

661

@Retention(RUNTIME)

662

public @interface JoinColumns {

663

/** Array of join columns */

664

JoinColumn[] value();

665

666

/** (Optional) The foreign key constraint specification */

667

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

668

}

669

670

/**

671

* Specifies the mapping of associations

672

* @since 1.0

673

*/

674

@Target({METHOD, FIELD})

675

@Retention(RUNTIME)

676

public @interface JoinTable {

677

/** (Optional) The name of the join table */

678

String name() default "";

679

680

/** (Optional) The catalog of the join table */

681

String catalog() default "";

682

683

/** (Optional) The schema of the join table */

684

String schema() default "";

685

686

/** (Optional) The foreign key columns of the join table */

687

JoinColumn[] joinColumns() default {};

688

689

/** (Optional) The foreign key columns of the join table (inverse side) */

690

JoinColumn[] inverseJoinColumns() default {};

691

692

/** (Optional) The foreign key constraint for join columns */

693

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

694

695

/** (Optional) The foreign key constraint for inverse join columns */

696

ForeignKey inverseForeignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

697

698

/** (Optional) Unique constraints on the join table */

699

UniqueConstraint[] uniqueConstraints() default {};

700

701

/** (Optional) Indexes for the join table */

702

Index[] indexes() default {};

703

}

704

705

/**

706

* Designates a ManyToOne or OneToOne relationship attribute for an EmbeddedId primary key

707

* @since 2.0

708

*/

709

@Target({METHOD, FIELD})

710

@Retention(RUNTIME)

711

public @interface MapsId {

712

/** (Optional) The name of the attribute within the composite key */

713

String value() default "";

714

}

715

```

716

717

**Usage Example:**

718

719

```java

720

// One-to-One

721

@Entity

722

public class User {

723

@Id

724

private Long id;

725

726

@OneToOne(cascade = CascadeType.ALL, orphanRemoval = true)

727

@JoinColumn(name = "profile_id")

728

private UserProfile profile;

729

}

730

731

// One-to-Many / Many-to-One (bidirectional)

732

@Entity

733

public class Department {

734

@Id

735

private Long id;

736

737

@OneToMany(mappedBy = "department", cascade = CascadeType.ALL)

738

private List<Employee> employees = new ArrayList<>();

739

}

740

741

@Entity

742

public class Employee {

743

@Id

744

private Long id;

745

746

@ManyToOne(fetch = FetchType.LAZY)

747

@JoinColumn(name = "department_id", nullable = false)

748

private Department department;

749

}

750

751

// Many-to-Many

752

@Entity

753

public class Student {

754

@Id

755

private Long id;

756

757

@ManyToMany

758

@JoinTable(

759

name = "student_course",

760

joinColumns = @JoinColumn(name = "student_id"),

761

inverseJoinColumns = @JoinColumn(name = "course_id")

762

)

763

private Set<Course> courses = new HashSet<>();

764

}

765

766

@Entity

767

public class Course {

768

@Id

769

private Long id;

770

771

@ManyToMany(mappedBy = "courses")

772

private Set<Student> students = new HashSet<>();

773

}

774

```

775

776

### Collection Mappings

777

778

Map collections of basic types and embeddables.

779

780

```java { .api }

781

/**

782

* Specifies a collection of instances of a basic type or embeddable class

783

* @since 2.0

784

*/

785

@Target({METHOD, FIELD})

786

@Retention(RUNTIME)

787

public @interface ElementCollection {

788

/** (Optional) The basic or embeddable class that is the element type of the collection */

789

Class targetClass() default void.class;

790

791

/** (Optional) Whether the association should be lazily loaded or eagerly fetched */

792

FetchType fetch() default FetchType.LAZY;

793

}

794

795

/**

796

* Specifies the table that is used for the mapping of collections

797

* @since 2.0

798

*/

799

@Target({METHOD, FIELD})

800

@Retention(RUNTIME)

801

public @interface CollectionTable {

802

/** (Optional) The name of the collection table */

803

String name() default "";

804

805

/** (Optional) The catalog of the table */

806

String catalog() default "";

807

808

/** (Optional) The schema of the table */

809

String schema() default "";

810

811

/** (Optional) The foreign key columns of the collection table */

812

JoinColumn[] joinColumns() default {};

813

814

/** (Optional) The foreign key constraint specification */

815

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

816

817

/** (Optional) Unique constraints on the table */

818

UniqueConstraint[] uniqueConstraints() default {};

819

820

/** (Optional) Indexes for the table */

821

Index[] indexes() default {};

822

}

823

824

/**

825

* Specifies the ordering of collection elements

826

* @since 1.0

827

*/

828

@Target({METHOD, FIELD})

829

@Retention(RUNTIME)

830

public @interface OrderBy {

831

/** (Optional) The ordering clause */

832

String value() default "";

833

}

834

835

/**

836

* Specifies a column that is used to maintain the persistent order of a list

837

* @since 2.0

838

*/

839

@Target({METHOD, FIELD})

840

@Retention(RUNTIME)

841

public @interface OrderColumn {

842

/** (Optional) The name of the ordering column */

843

String name() default "";

844

845

/** (Optional) Whether the column is nullable */

846

boolean nullable() default true;

847

848

/** (Optional) Whether the column is included in SQL INSERT statements */

849

boolean insertable() default true;

850

851

/** (Optional) Whether the column is included in SQL UPDATE statements */

852

boolean updatable() default true;

853

854

/** (Optional) The SQL fragment for column definition */

855

String columnDefinition() default "";

856

}

857

```

858

859

**Usage Example:**

860

861

```java

862

@Entity

863

public class Person {

864

@Id

865

private Long id;

866

867

@ElementCollection

868

@CollectionTable(name = "phone_numbers", joinColumns = @JoinColumn(name = "person_id"))

869

@Column(name = "phone_number")

870

private Set<String> phoneNumbers = new HashSet<>();

871

872

@ElementCollection

873

@CollectionTable(name = "addresses")

874

@OrderColumn(name = "address_index")

875

private List<Address> addresses = new ArrayList<>();

876

}

877

```

878

879

### Map Collections

880

881

Map collections with custom keys.

882

883

```java { .api }

884

/**

885

* Specifies the map key for associations of type Map

886

* @since 1.0

887

*/

888

@Target({METHOD, FIELD})

889

@Retention(RUNTIME)

890

public @interface MapKey {

891

/** (Optional) The name of the persistent field or property of the map key */

892

String name() default "";

893

}

894

895

/**

896

* Specifies the type of the map key

897

* @since 2.0

898

*/

899

@Target({METHOD, FIELD})

900

@Retention(RUNTIME)

901

public @interface MapKeyClass {

902

/** The type of the map key */

903

Class value();

904

}

905

906

/**

907

* Specifies the mapped column for the map key

908

* @since 2.0

909

*/

910

@Target({METHOD, FIELD})

911

@Retention(RUNTIME)

912

public @interface MapKeyColumn {

913

/** (Optional) The name of the map key column */

914

String name() default "";

915

916

/** (Optional) Whether the column is unique */

917

boolean unique() default false;

918

919

/** (Optional) Whether the column is nullable */

920

boolean nullable() default false;

921

922

/** (Optional) Whether the column is insertable */

923

boolean insertable() default true;

924

925

/** (Optional) Whether the column is updatable */

926

boolean updatable() default true;

927

928

/** (Optional) The SQL fragment for column definition */

929

String columnDefinition() default "";

930

931

/** (Optional) The name of the table containing the column */

932

String table() default "";

933

934

/** (Optional) The column length */

935

int length() default 255;

936

937

/** (Optional) The precision for numeric columns */

938

int precision() default 0;

939

940

/** (Optional) The scale for numeric columns */

941

int scale() default 0;

942

}

943

944

/**

945

* Specifies the enum type for a map key

946

* @since 2.0

947

*/

948

@Target({METHOD, FIELD})

949

@Retention(RUNTIME)

950

public @interface MapKeyEnumerated {

951

/** (Optional) The type used in mapping the map key enum */

952

EnumType value() default EnumType.ORDINAL;

953

}

954

955

/**

956

* Specifies the temporal type for a map key

957

* @since 2.0

958

*/

959

@Target({METHOD, FIELD})

960

@Retention(RUNTIME)

961

public @interface MapKeyTemporal {

962

/** (Required) The temporal type for the map key */

963

TemporalType value();

964

}

965

966

/**

967

* Specifies a mapping to an entity that is a map key

968

* @since 2.0

969

*/

970

@Target({METHOD, FIELD})

971

@Retention(RUNTIME)

972

public @interface MapKeyJoinColumn {

973

/** (Optional) The name of the foreign key column for the map key */

974

String name() default "";

975

976

/** (Optional) The name of the column referenced by this foreign key column */

977

String referencedColumnName() default "";

978

979

/** (Optional) Whether the column is unique */

980

boolean unique() default false;

981

982

/** (Optional) Whether the column is nullable */

983

boolean nullable() default false;

984

985

/** (Optional) Whether the column is insertable */

986

boolean insertable() default true;

987

988

/** (Optional) Whether the column is updatable */

989

boolean updatable() default true;

990

991

/** (Optional) The SQL fragment for column definition */

992

String columnDefinition() default "";

993

994

/** (Optional) The name of the table containing the column */

995

String table() default "";

996

997

/** (Optional) The foreign key constraint specification */

998

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

999

}

1000

1001

/**

1002

* Specifies the mapping for composite map key join columns

1003

* @since 2.0

1004

*/

1005

@Target({METHOD, FIELD})

1006

@Retention(RUNTIME)

1007

public @interface MapKeyJoinColumns {

1008

/** Array of map key join columns */

1009

MapKeyJoinColumn[] value();

1010

1011

/** (Optional) The foreign key constraint specification */

1012

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

1013

}

1014

```

1015

1016

**Usage Example:**

1017

1018

```java

1019

@Entity

1020

public class Company {

1021

@Id

1022

private Long id;

1023

1024

@OneToMany

1025

@MapKey(name = "employeeId")

1026

private Map<String, Employee> employeesByNumber = new HashMap<>();

1027

1028

@ElementCollection

1029

@MapKeyColumn(name = "department_name")

1030

@Column(name = "budget")

1031

private Map<String, BigDecimal> departmentBudgets = new HashMap<>();

1032

}

1033

```

1034

1035

### Inheritance Mapping

1036

1037

Map entity inheritance hierarchies to database tables.

1038

1039

```java { .api }

1040

/**

1041

* Specifies the inheritance strategy for an entity class hierarchy

1042

* @since 1.0

1043

*/

1044

@Target(TYPE)

1045

@Retention(RUNTIME)

1046

public @interface Inheritance {

1047

/** (Optional) The strategy to use */

1048

InheritanceType strategy() default InheritanceType.SINGLE_TABLE;

1049

}

1050

1051

/**

1052

* Specifies the discriminator column for SINGLE_TABLE and JOINED inheritance

1053

* @since 1.0

1054

*/

1055

@Target(TYPE)

1056

@Retention(RUNTIME)

1057

public @interface DiscriminatorColumn {

1058

/** (Optional) The name of the discriminator column */

1059

String name() default "DTYPE";

1060

1061

/** (Optional) The type of object used to represent the discriminator column */

1062

DiscriminatorType discriminatorType() default DiscriminatorType.STRING;

1063

1064

/** (Optional) The SQL fragment for column definition */

1065

String columnDefinition() default "";

1066

1067

/** (Optional) The column length for STRING discriminator types */

1068

int length() default 31;

1069

}

1070

1071

/**

1072

* Specifies the value of the discriminator column for entities of the given type

1073

* @since 1.0

1074

*/

1075

@Target(TYPE)

1076

@Retention(RUNTIME)

1077

public @interface DiscriminatorValue {

1078

/** (Required) The discriminator value */

1079

String value();

1080

}

1081

1082

/**

1083

* Specifies a primary key column used as a foreign key to join to another table

1084

* @since 1.0

1085

*/

1086

@Target({METHOD, FIELD, TYPE})

1087

@Retention(RUNTIME)

1088

public @interface PrimaryKeyJoinColumn {

1089

/** (Optional) The name of the primary key column */

1090

String name() default "";

1091

1092

/** (Optional) The name of the primary key column of the referenced table */

1093

String referencedColumnName() default "";

1094

1095

/** (Optional) The SQL fragment for column definition */

1096

String columnDefinition() default "";

1097

1098

/** (Optional) The foreign key constraint specification */

1099

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

1100

}

1101

1102

/**

1103

* Groups PrimaryKeyJoinColumn annotations for composite foreign keys

1104

* @since 1.0

1105

*/

1106

@Target({TYPE})

1107

@Retention(RUNTIME)

1108

public @interface PrimaryKeyJoinColumns {

1109

/** Array of primary key join columns */

1110

PrimaryKeyJoinColumn[] value();

1111

1112

/** (Optional) The foreign key constraint specification */

1113

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

1114

}

1115

```

1116

1117

**Usage Example:**

1118

1119

```java

1120

// Single table inheritance

1121

@Entity

1122

@Inheritance(strategy = InheritanceType.SINGLE_TABLE)

1123

@DiscriminatorColumn(name = "vehicle_type", discriminatorType = DiscriminatorType.STRING)

1124

public abstract class Vehicle {

1125

@Id

1126

private Long id;

1127

private String manufacturer;

1128

}

1129

1130

@Entity

1131

@DiscriminatorValue("CAR")

1132

public class Car extends Vehicle {

1133

private Integer numberOfDoors;

1134

}

1135

1136

@Entity

1137

@DiscriminatorValue("TRUCK")

1138

public class Truck extends Vehicle {

1139

private BigDecimal payloadCapacity;

1140

}

1141

1142

// Joined table inheritance

1143

@Entity

1144

@Inheritance(strategy = InheritanceType.JOINED)

1145

public abstract class Account {

1146

@Id

1147

private Long id;

1148

private String accountNumber;

1149

}

1150

1151

@Entity

1152

@PrimaryKeyJoinColumn(name = "account_id")

1153

public class SavingsAccount extends Account {

1154

private BigDecimal interestRate;

1155

}

1156

1157

@Entity

1158

@PrimaryKeyJoinColumn(name = "account_id")

1159

public class CheckingAccount extends Account {

1160

private BigDecimal overdraftLimit;

1161

}

1162

```

1163

1164

### Secondary Tables

1165

1166

Map a single entity to multiple tables.

1167

1168

```java { .api }

1169

/**

1170

* Specifies a secondary table for the annotated entity class

1171

* @since 1.0

1172

*/

1173

@Target(TYPE)

1174

@Retention(RUNTIME)

1175

public @interface SecondaryTable {

1176

/** (Required) The name of the secondary table */

1177

String name();

1178

1179

/** (Optional) The catalog of the table */

1180

String catalog() default "";

1181

1182

/** (Optional) The schema of the table */

1183

String schema() default "";

1184

1185

/** (Optional) The columns that are used to join with the primary table */

1186

PrimaryKeyJoinColumn[] pkJoinColumns() default {};

1187

1188

/** (Optional) The foreign key constraint specification */

1189

ForeignKey foreignKey() default @ForeignKey(ConstraintMode.PROVIDER_DEFAULT);

1190

1191

/** (Optional) Unique constraints on the table */

1192

UniqueConstraint[] uniqueConstraints() default {};

1193

1194

/** (Optional) Indexes for the table */

1195

Index[] indexes() default {};

1196

}

1197

1198

/**

1199

* Specifies multiple secondary tables for an entity

1200

* @since 1.0

1201

*/

1202

@Target(TYPE)

1203

@Retention(RUNTIME)

1204

public @interface SecondaryTables {

1205

/** Array of secondary tables */

1206

SecondaryTable[] value();

1207

}

1208

```

1209

1210

**Usage Example:**

1211

1212

```java

1213

@Entity

1214

@Table(name = "employee")

1215

@SecondaryTable(name = "employee_details",

1216

pkJoinColumns = @PrimaryKeyJoinColumn(name = "employee_id"))

1217

public class Employee {

1218

@Id

1219

private Long id;

1220

1221

@Column(name = "name")

1222

private String name;

1223

1224

@Column(table = "employee_details")

1225

private String biography;

1226

1227

@Column(table = "employee_details")

1228

private byte[] photo;

1229

}

1230

```

1231

1232

### Constraints and Indexes

1233

1234

Define database constraints and indexes.

1235

1236

```java { .api }

1237

/**

1238

* Specifies that a unique constraint is to be included in the generated DDL

1239

* @since 1.0

1240

*/

1241

@Target({})

1242

@Retention(RUNTIME)

1243

public @interface UniqueConstraint {

1244

/** (Optional) Constraint name */

1245

String name() default "";

1246

1247

/** (Required) An array of column names that make up the constraint */

1248

String[] columnNames();

1249

}

1250

1251

/**

1252

* Used in schema generation to specify creation of an index

1253

* @since 2.1

1254

*/

1255

@Target({})

1256

@Retention(RUNTIME)

1257

public @interface Index {

1258

/** (Optional) The name of the index */

1259

String name() default "";

1260

1261

/** (Required) The list of columns for the index */

1262

String columnList();

1263

1264

/** (Optional) Whether the index is unique */

1265

boolean unique() default false;

1266

}

1267

1268

/**

1269

* Used to specify the handling of foreign key constraints

1270

* @since 2.1

1271

*/

1272

@Target({})

1273

@Retention(RUNTIME)

1274

public @interface ForeignKey {

1275

/** (Optional) The name of the foreign key constraint */

1276

String name() default "";

1277

1278

/** (Optional) The constraint mode */

1279

ConstraintMode value() default ConstraintMode.PROVIDER_DEFAULT;

1280

1281

/** (Optional) The foreign key constraint definition */

1282

String foreignKeyDefinition() default "";

1283

}

1284

```

1285

1286

### Access Type

1287

1288

Specify field or property access for entities.

1289

1290

```java { .api }

1291

/**

1292

* Used to specify an access type for an entity class, mapped superclass, or embeddable class

1293

* @since 2.0

1294

*/

1295

@Target({TYPE, METHOD, FIELD})

1296

@Retention(RUNTIME)

1297

public @interface Access {

1298

/** (Required) The access type */

1299

AccessType value();

1300

}

1301

```

1302

1303

**Usage Example:**

1304

1305

```java

1306

@Entity

1307

@Access(AccessType.FIELD)

1308

public class Product {

1309

@Id

1310

private Long id;

1311

1312

private String name;

1313

1314

@Access(AccessType.PROPERTY)

1315

@Column(name = "price")

1316

public BigDecimal getPrice() {

1317

return price.setScale(2, RoundingMode.HALF_UP);

1318

}

1319

1320

public void setPrice(BigDecimal price) {

1321

this.price = price;

1322

}

1323

1324

private BigDecimal price;

1325

}

1326

```

1327

1328

### Attribute Converters

1329

1330

Convert entity attribute values to database column values.

1331

1332

```java { .api }

1333

/**

1334

* Specifies the conversion of a Basic field or property

1335

* @since 2.1

1336

*/

1337

@Target({METHOD, FIELD, TYPE})

1338

@Retention(RUNTIME)

1339

@Repeatable(Converts.class)

1340

public @interface Convert {

1341

/** (Optional) The converter class */

1342

Class converter() default void.class;

1343

1344

/** (Optional) The name of the attribute to which the converter is applied */

1345

String attributeName() default "";

1346

1347

/** (Optional) Whether to disable conversion */

1348

boolean disableConversion() default false;

1349

}

1350

1351

/**

1352

* Used to group Convert annotations

1353

* @since 2.1

1354

*/

1355

@Target({METHOD, FIELD, TYPE})

1356

@Retention(RUNTIME)

1357

public @interface Converts {

1358

/** Array of converts */

1359

Convert[] value();

1360

}

1361

1362

/**

1363

* Specifies that the annotated class is a converter

1364

* @since 2.1

1365

*/

1366

@Target(TYPE)

1367

@Retention(RUNTIME)

1368

public @interface Converter {

1369

/** (Optional) Whether the converter should be auto-applied */

1370

boolean autoApply() default false;

1371

}

1372

1373

/**

1374

* Interface for entity attribute value conversion

1375

* @since 2.1

1376

*/

1377

public interface AttributeConverter<X, Y> {

1378

/**

1379

* Converts the entity attribute value to database column value

1380

* @param attribute the entity attribute value

1381

* @return the database column value

1382

*/

1383

Y convertToDatabaseColumn(X attribute);

1384

1385

/**

1386

* Converts the database column value to entity attribute value

1387

* @param dbData the database column value

1388

* @return the entity attribute value

1389

*/

1390

X convertToEntityAttribute(Y dbData);

1391

}

1392

```

1393

1394

**Usage Example:**

1395

1396

```java

1397

@Converter(autoApply = true)

1398

public class BooleanToYNConverter implements AttributeConverter<Boolean, String> {

1399

@Override

1400

public String convertToDatabaseColumn(Boolean attribute) {

1401

return attribute != null && attribute ? "Y" : "N";

1402

}

1403

1404

@Override

1405

public Boolean convertToEntityAttribute(String dbData) {

1406

return "Y".equals(dbData);

1407

}

1408

}

1409

1410

@Entity

1411

public class Customer {

1412

@Id

1413

private Long id;

1414

1415

@Convert(converter = BooleanToYNConverter.class)

1416

private Boolean active;

1417

}

1418

```

1419

1420

### Entity Graphs

1421

1422

Define named entity graphs for optimizing fetch strategies and controlling which associations should be loaded.

1423

1424

```java { .api }

1425

/**

1426

* Used to specify the path and boundaries for a find operation or query

1427

* @since 2.1

1428

*/

1429

@Repeatable(NamedEntityGraphs.class)

1430

@Target(TYPE)

1431

@Retention(RUNTIME)

1432

public @interface NamedEntityGraph {

1433

/**

1434

* (Optional) The name of the entity graph. Defaults to the entity name of the root entity

1435

*/

1436

String name() default "";

1437

1438

/**

1439

* A list of attributes of the entity that are included in this graph

1440

*/

1441

NamedAttributeNode[] attributeNodes() default {};

1442

1443

/**

1444

* Include all of the attributes of the annotated entity class as attribute nodes

1445

*/

1446

boolean includeAllAttributes() default false;

1447

1448

/**

1449

* A list of subgraphs that are included in the entity graph

1450

*/

1451

NamedSubgraph[] subgraphs() default {};

1452

1453

/**

1454

* A list of subgraphs that will add additional attributes for subclasses

1455

*/

1456

NamedSubgraph[] subclassSubgraphs() default {};

1457

}

1458

1459

/**

1460

* Used to group NamedEntityGraph annotations

1461

* @since 2.1

1462

*/

1463

@Target(TYPE)

1464

@Retention(RUNTIME)

1465

public @interface NamedEntityGraphs {

1466

/** Array of NamedEntityGraph annotations */

1467

NamedEntityGraph[] value();

1468

}

1469

1470

/**

1471

* A member element of a NamedEntityGraph

1472

* @since 2.1

1473

*/

1474

@Target({})

1475

@Retention(RUNTIME)

1476

public @interface NamedAttributeNode {

1477

/**

1478

* The name of the attribute that must be included in the graph

1479

*/

1480

String value();

1481

1482

/**

1483

* If the attribute references a managed type, refer to that NamedSubgraph definition

1484

*/

1485

String subgraph() default "";

1486

1487

/**

1488

* If the attribute references a Map, specify a subgraph for the Entity key type

1489

*/

1490

String keySubgraph() default "";

1491

}

1492

1493

/**

1494

* A member element of a NamedEntityGraph, referenced from NamedAttributeNode

1495

* @since 2.1

1496

*/

1497

@Target({})

1498

@Retention(RUNTIME)

1499

public @interface NamedSubgraph {

1500

/**

1501

* The name of the subgraph as referenced from a NamedAttributeNode element

1502

*/

1503

String name();

1504

1505

/**

1506

* The type represented by this subgraph

1507

*/

1508

Class type() default void.class;

1509

1510

/**

1511

* The list of attributes of the class that must be included

1512

*/

1513

NamedAttributeNode[] attributeNodes();

1514

}

1515

```

1516

1517

**Usage Example:**

1518

1519

```java

1520

@Entity

1521

@NamedEntityGraph(

1522

name = "Order.detail",

1523

attributeNodes = {

1524

@NamedAttributeNode("customer"),

1525

@NamedAttributeNode(value = "items", subgraph = "items.detail")

1526

},

1527

subgraphs = {

1528

@NamedSubgraph(

1529

name = "items.detail",

1530

attributeNodes = {

1531

@NamedAttributeNode("product"),

1532

@NamedAttributeNode("quantity")

1533

}

1534

)

1535

}

1536

)

1537

public class Order {

1538

@Id

1539

private Long id;

1540

1541

@ManyToOne

1542

private Customer customer;

1543

1544

@OneToMany

1545

private List<OrderItem> items;

1546

}

1547

1548

// Use the entity graph

1549

EntityGraph<?> graph = em.getEntityGraph("Order.detail");

1550

Map<String, Object> props = new HashMap<>();

1551

props.put("jakarta.persistence.fetchgraph", graph);

1552

Order order = em.find(Order.class, orderId, props);

1553

```

1554

1555

### Container and CDI Injection

1556

1557

Annotations for dependency injection of persistence contexts and entity manager factories in Jakarta EE containers.

1558

1559

```java { .api }

1560

/**

1561

* Expresses a dependency on a container-managed EntityManager

1562

* @since 1.0

1563

*/

1564

@Repeatable(PersistenceContexts.class)

1565

@Target({TYPE, METHOD, FIELD})

1566

@Retention(RUNTIME)

1567

public @interface PersistenceContext {

1568

/**

1569

* (Optional) The name by which the entity manager is to be accessed

1570

*/

1571

String name() default "";

1572

1573

/**

1574

* (Optional) The name of the persistence unit as defined in persistence.xml

1575

*/

1576

String unitName() default "";

1577

1578

/**

1579

* (Optional) Specifies whether a transaction-scoped or extended persistence context is used

1580

*/

1581

PersistenceContextType type() default PersistenceContextType.TRANSACTION;

1582

1583

/**

1584

* (Optional) Specifies whether the persistence context is automatically synchronized

1585

* @since 2.1

1586

*/

1587

SynchronizationType synchronization() default SynchronizationType.SYNCHRONIZED;

1588

1589

/**

1590

* (Optional) Properties for the container or persistence provider

1591

*/

1592

PersistenceProperty[] properties() default {};

1593

}

1594

1595

/**

1596

* Declares one or more PersistenceContext annotations

1597

* @since 1.0

1598

*/

1599

@Target(TYPE)

1600

@Retention(RUNTIME)

1601

public @interface PersistenceContexts {

1602

/** One or more PersistenceContext annotations */

1603

PersistenceContext[] value();

1604

}

1605

1606

/**

1607

* Expresses a dependency on an EntityManagerFactory

1608

* @since 1.0

1609

*/

1610

@Repeatable(PersistenceUnits.class)

1611

@Target({TYPE, METHOD, FIELD})

1612

@Retention(RUNTIME)

1613

public @interface PersistenceUnit {

1614

/**

1615

* (Optional) The name by which the entity manager factory is to be accessed

1616

*/

1617

String name() default "";

1618

1619

/**

1620

* (Optional) The name of the persistence unit as defined in persistence.xml

1621

*/

1622

String unitName() default "";

1623

}

1624

1625

/**

1626

* Declares one or more PersistenceUnit annotations

1627

* @since 1.0

1628

*/

1629

@Target(TYPE)

1630

@Retention(RUNTIME)

1631

public @interface PersistenceUnits {

1632

/** One or more PersistenceUnit annotations */

1633

PersistenceUnit[] value();

1634

}

1635

1636

/**

1637

* Describes a single container or persistence provider property

1638

* @since 1.0

1639

*/

1640

@Target({})

1641

@Retention(RUNTIME)

1642

public @interface PersistenceProperty {

1643

/** The name of the property */

1644

String name();

1645

1646

/** The value of the property */

1647

String value();

1648

}

1649

```

1650

1651

**Usage Example:**

1652

1653

```java

1654

@Stateless

1655

public class OrderService {

1656

// Inject EntityManager

1657

@PersistenceContext(unitName = "orderDB")

1658

private EntityManager em;

1659

1660

// Inject EntityManagerFactory

1661

@PersistenceUnit(unitName = "orderDB")

1662

private EntityManagerFactory emf;

1663

1664

// With properties

1665

@PersistenceContext(

1666

unitName = "orderDB",

1667

type = PersistenceContextType.EXTENDED,

1668

properties = {

1669

@PersistenceProperty(name = "jakarta.persistence.cache.storeMode", value = "REFRESH")

1670

}

1671

)

1672

private EntityManager extendedEm;

1673

1674

public void processOrder(Long orderId) {

1675

Order order = em.find(Order.class, orderId);

1676

// Process order

1677

}

1678

}

1679

```

1680