mirror of
https://github.com/tiennm99/java-design-patterns.git
synced 2026-08-18 00:23:32 +00:00
docs: update metadata mapping
This commit is contained in:
+34
-11
@@ -1,14 +1,17 @@
|
|||||||
---
|
---
|
||||||
title: Metadata Mapping
|
title: Metadata Mapping
|
||||||
category: Architectural
|
category: Data access
|
||||||
language: en
|
language: en
|
||||||
tag:
|
tag:
|
||||||
- Data access
|
- Decoupling
|
||||||
|
- Enterprise patterns
|
||||||
|
- Object mapping
|
||||||
|
- Persistence
|
||||||
---
|
---
|
||||||
|
|
||||||
## Intent
|
## Intent
|
||||||
|
|
||||||
Holds details of object-relational mapping in the metadata.
|
Metadata Mapping is designed to manage the mapping between database records and objects in a way that keeps the database schema and object model decoupled and manageable.
|
||||||
|
|
||||||
## Explanation
|
## Explanation
|
||||||
|
|
||||||
@@ -151,7 +154,7 @@ public class UserService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// other CRUDs ->
|
// other CRUDs ->
|
||||||
...
|
// ...
|
||||||
|
|
||||||
public void close() {
|
public void close() {
|
||||||
HibernateUtil.shutdown();
|
HibernateUtil.shutdown();
|
||||||
@@ -161,19 +164,39 @@ public class UserService {
|
|||||||
|
|
||||||
## Class diagram
|
## Class diagram
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
## Applicability
|
## Applicability
|
||||||
|
|
||||||
Use the Metadata Mapping when:
|
Use this pattern when you need to bridge the gap between an object-oriented domain model and a relational database, without hard-coding database queries into the domain logic.
|
||||||
|
|
||||||
- you want reduce the amount of work needed to handle database mapping.
|
## Known Uses
|
||||||
|
|
||||||
## Known uses
|
* Object-Relational Mapping (ORM) frameworks like Hibernate, JPA, EclipseLink and MyBatis.
|
||||||
|
* Mapping database rows to domain objects in enterprise applications.
|
||||||
|
|
||||||
[Hibernate](https://hibernate.org/), [EclipseLink](https://www.eclipse.org/eclipselink/), [MyBatis](https://blog.mybatis.org/)......
|
## Consequences
|
||||||
|
|
||||||
|
Benefits:
|
||||||
|
|
||||||
|
* Decouples object model and database schema, allowing independent evolution.
|
||||||
|
* Reduces boilerplate code associated with data access.
|
||||||
|
* Centralizes mapping logic, making changes more manageable.
|
||||||
|
|
||||||
|
Trade-offs:
|
||||||
|
|
||||||
|
* Adds complexity due to an additional layer of abstraction.
|
||||||
|
* Can impact performance if not properly optimized.
|
||||||
|
|
||||||
|
## Related Patterns
|
||||||
|
|
||||||
|
* [Data Mapper](https://java-design-patterns.com/patterns/data-mapper/): Metadata Mapping is often used within the broader Data Mapper pattern to facilitate the mapping process.
|
||||||
|
* Active Record: Differently from Active Record, Metadata Mapping separates the data access logic from the domain entities.
|
||||||
|
* [Repository](https://java-design-patterns.com/patterns/repository/): Works well with the Repository pattern by abstracting data access further, allowing more complex domain logic to be cleanly separated from data mapping.
|
||||||
|
|
||||||
## Credits
|
## Credits
|
||||||
|
|
||||||
- [J2EE Design Patterns](https://www.amazon.com/gp/product/0596004273/ref=as_li_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596004273&linkCode=as2&tag=javadesignpat-20&linkId=48d37c67fb3d845b802fa9b619ad8f31)
|
* [J2EE Design Patterns](https://amzn.to/4dpzgmx)
|
||||||
|
* [Java Persistence with Hibernate](https://amzn.to/44tP1ox)
|
||||||
|
* [Patterns of Enterprise Application Architecture](https://amzn.to/3WfKBPR)
|
||||||
|
* [Pro JPA 2: Mastering the Java Persistence API](https://amzn.to/4b7UoMC)
|
||||||
|
|||||||
@@ -56,9 +56,8 @@ public class App {
|
|||||||
* Program entry point.
|
* Program entry point.
|
||||||
*
|
*
|
||||||
* @param args command line args.
|
* @param args command line args.
|
||||||
* @throws Exception if any error occurs.
|
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) throws Exception {
|
public static void main(String[] args) {
|
||||||
// get service
|
// get service
|
||||||
var userService = new UserService();
|
var userService = new UserService();
|
||||||
// use create service to add users
|
// use create service to add users
|
||||||
|
|||||||
@@ -49,8 +49,8 @@ public class UserService {
|
|||||||
try (var session = factory.openSession()) {
|
try (var session = factory.openSession()) {
|
||||||
var tx = session.beginTransaction();
|
var tx = session.beginTransaction();
|
||||||
List<User> userIter = session.createQuery("FROM User").list();
|
List<User> userIter = session.createQuery("FROM User").list();
|
||||||
for (var iterator = userIter.iterator(); iterator.hasNext();) {
|
for (User user : userIter) {
|
||||||
users.add(iterator.next());
|
users.add(user);
|
||||||
}
|
}
|
||||||
tx.commit();
|
tx.commit();
|
||||||
} catch (HibernateException e) {
|
} catch (HibernateException e) {
|
||||||
|
|||||||
@@ -24,6 +24,7 @@
|
|||||||
*/
|
*/
|
||||||
package com.iluwatar.metamapping.utils;
|
package com.iluwatar.metamapping.utils;
|
||||||
|
|
||||||
|
import lombok.Getter;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.hibernate.SessionFactory;
|
import org.hibernate.SessionFactory;
|
||||||
import org.hibernate.cfg.Configuration;
|
import org.hibernate.cfg.Configuration;
|
||||||
@@ -34,6 +35,7 @@ import org.hibernate.cfg.Configuration;
|
|||||||
@Slf4j
|
@Slf4j
|
||||||
public class HibernateUtil {
|
public class HibernateUtil {
|
||||||
|
|
||||||
|
@Getter
|
||||||
private static final SessionFactory sessionFactory = buildSessionFactory();
|
private static final SessionFactory sessionFactory = buildSessionFactory();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -50,14 +52,6 @@ public class HibernateUtil {
|
|||||||
return new Configuration().configure().buildSessionFactory();
|
return new Configuration().configure().buildSessionFactory();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Get session factory.
|
|
||||||
* @return session factory
|
|
||||||
*/
|
|
||||||
public static SessionFactory getSessionFactory() {
|
|
||||||
return sessionFactory;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Close session factory.
|
* Close session factory.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -33,7 +33,6 @@ import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
|
|||||||
class AppTest {
|
class AppTest {
|
||||||
/**
|
/**
|
||||||
* Issue: Add at least one assertion to this test case.
|
* Issue: Add at least one assertion to this test case.
|
||||||
*
|
|
||||||
* Solution: Inserted assertion to check whether the execution of the main method in {@link App#main(String[])}
|
* Solution: Inserted assertion to check whether the execution of the main method in {@link App#main(String[])}
|
||||||
* throws an exception.
|
* throws an exception.
|
||||||
*/
|
*/
|
||||||
|
|||||||
Reference in New Issue
Block a user