JPA Inheritance Mapping

Java Technologies - স্প্রিং বুট ওআরএম (Spring Boot ORM)
111
111

JPA Inheritance Mapping হলো একটি টেকনিক, যার মাধ্যমে জাভার ইনহেরিটেন্স (Inheritance) স্ট্রাকচারকে ডেটাবেস টেবিলের সঙ্গে ম্যাপ করা যায়। এটি ডেটা মডেলকে আরও কার্যকরভাবে ডিজাইন করার সুযোগ দেয়। JPA বিভিন্ন ইনহেরিটেন্স স্ট্রাটেজি সমর্থন করে, যা ডেটাবেসের কাঠামো অনুযায়ী নির্বাচন করা যায়।


JPA Inheritance Mapping-এর স্ট্রাটেজি

১. Single Table Strategy

সব ক্লাসের ডেটা একটি টেবিলে রাখা হয়। প্রতিটি ইনহেরিটেড ক্লাসের জন্য একটি আলাদা কলাম থাকে।

২. Table Per Class Strategy

প্রত্যেক সাবক্লাসের জন্য আলাদা টেবিল তৈরি হয়। অভিভাবক (Parent) ক্লাসের টেবিল থাকে না।

৩. Joined Strategy

অভিভাবক এবং প্রত্যেক সাবক্লাসের জন্য আলাদা টেবিল তৈরি হয়। Parent এবং Child টেবিলগুলো একটি সম্পর্কের (Join) মাধ্যমে যুক্ত থাকে।


JPA Inheritance Mapping অ্যানোটেশন

  1. @Inheritance: ইনহেরিটেন্স স্ট্রাটেজি নির্ধারণের জন্য ব্যবহৃত হয়।
  2. @DiscriminatorColumn: Single Table স্ট্রাটেজির ক্ষেত্রে টেবিলে সাবক্লাস চিহ্নিত করার জন্য একটি কলাম নির্ধারণ করে।
  3. @MappedSuperclass: কোনো ক্লাসকে Entity হিসেবে চিহ্নিত না করে শুধুমাত্র ইনহেরিটেন্সের জন্য Parent হিসেবে ব্যবহার করা হয়।

উদাহরণ: JPA Inheritance Mapping

নিচে একটি উদাহরণ দেওয়া হলো যেখানে একটি Person ক্লাস Parent এবং Employee এবং Customer ক্লাস Child।

Parent Entity: Person

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.JOINED) // স্ট্রাটেজি: Joined
public abstract class Person {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    private String name;

    // Getters and Setters
    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

Child Entity: Employee

import jakarta.persistence.Entity;

@Entity
public class Employee extends Person {

    private String department;

    // Getters and Setters
    public String getDepartment() {
        return department;
    }

    public void setDepartment(String department) {
        this.department = department;
    }
}

Child Entity: Customer

import jakarta.persistence.Entity;

@Entity
public class Customer extends Person {

    private String membershipLevel;

    // Getters and Setters
    public String getMembershipLevel() {
        return membershipLevel;
    }

    public void setMembershipLevel(String membershipLevel) {
        this.membershipLevel = membershipLevel;
    }
}

Database Table Mapping: Joined Strategy

Joined স্ট্রাটেজির ক্ষেত্রে ডেটাবেসে তিনটি টেবিল তৈরি হবে:

  1. Person টেবিল:

    CREATE TABLE Person (
        id BIGINT AUTO_INCREMENT PRIMARY KEY,
        name VARCHAR(255)
    );
    
  2. Employee টেবিল:

    CREATE TABLE Employee (
        id BIGINT PRIMARY KEY,
        department VARCHAR(255),
        FOREIGN KEY (id) REFERENCES Person(id)
    );
    
  3. Customer টেবিল:

    CREATE TABLE Customer (
        id BIGINT PRIMARY KEY,
        membershipLevel VARCHAR(255),
        FOREIGN KEY (id) REFERENCES Person(id)
    );
    

Repository উদাহরণ

JPA Repository ব্যবহার করে ডেটাবেস অপারেশন সম্পন্ন করা যায়:

import org.springframework.data.jpa.repository.JpaRepository;

public interface PersonRepository extends JpaRepository<Person, Long> {
    // Custom query methods
}

Controller উদাহরণ

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@RequestMapping("/persons")
public class PersonController {

    @Autowired
    private PersonRepository personRepository;

    @GetMapping
    public List<Person> getAllPersons() {
        return personRepository.findAll();
    }

    @PostMapping("/employee")
    public Person addEmployee(@RequestBody Employee employee) {
        return personRepository.save(employee);
    }

    @PostMapping("/customer")
    public Person addCustomer(@RequestBody Customer customer) {
        return personRepository.save(customer);
    }
}

সুবিধা ও সীমাবদ্ধতা

সুবিধা:

  • ডেটাবেস এবং অবজেক্ট মডেলের মধ্যে সহজ সম্পর্ক তৈরি।
  • কোডের পুনরায় ব্যবহারযোগ্যতা নিশ্চিত।
  • বিভিন্ন স্ট্রাটেজি প্রয়োগের মাধ্যমে পারফরম্যান্স টিউনিং।

সীমাবদ্ধতা:

  • কিছু ক্ষেত্রে স্ট্রাটেজি অনুযায়ী ডেটাবেসের পারফরম্যান্স কম হতে পারে।
  • Joined স্ট্রাটেজিতে কেরি জটিল হতে পারে।

সারাংশ

JPA Inheritance Mapping স্প্রিং বুটে ডেটা মডেলিংকে আরও কার্যকর করে। এর মাধ্যমে ডেটাবেসের কাঠামো এবং জাভার ইনহেরিটেড ক্লাসগুলোর মধ্যে মেলবন্ধন তৈরি করা যায়। বিভিন্ন স্ট্রাটেজি ব্যবহার করে আপনার প্রজেক্টের চাহিদা অনুযায়ী উপযুক্ত মডেল তৈরি করা সম্ভব।


Content added By

JPA এর মধ্যে Inheritance কি এবং এর প্রয়োজনীয়তা

81
81

Java Persistence API (JPA) অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিং মডেলের একটি গুরুত্বপূর্ণ বৈশিষ্ট্য হল Inheritance। এটি ডাটাবেসের টেবিল এবং জাভা ক্লাসের মধ্যে অবজেক্ট-ওরিয়েন্টেড উত্তরাধিকার (Inheritance) মডেল পরিচালনার জন্য ব্যবহৃত হয়। জাভার ইনহেরিটেন্স কনসেপ্টকে ডাটাবেসে রিফ্লেক্ট করতে JPA বিভিন্ন স্ট্র্যাটেজি প্রদান করে।


Inheritance কি?

Inheritance হল অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিংয়ের একটি মৌলিক বৈশিষ্ট্য, যা এক ক্লাসের বৈশিষ্ট্য (Attributes) এবং মেথড (Methods) আরেকটি ক্লাসে শেয়ার করার সুযোগ দেয়। JPA ইনহেরিটেন্সের মাধ্যমে, আমরা প্যারেন্ট ক্লাসের তথ্য একাধিক চাইল্ড ক্লাসের মধ্যে শেয়ার করতে পারি এবং সেগুলো ডাটাবেস টেবিলের মধ্যে সঠিকভাবে ম্যাপ করতে পারি।


JPA Inheritance এর প্রয়োজনীয়তা

  1. কোড পুনরায় ব্যবহারযোগ্য করা: প্যারেন্ট ক্লাসের সাধারণ বৈশিষ্ট্যগুলো চাইল্ড ক্লাসে ব্যবহার করা যায়।
  2. ডাটাবেস মডেলিং সহজতর করা: অবজেক্ট-ওরিয়েন্টেড ইনহেরিটেন্সের সমতুল্য একটি রিলেশনাল ডাটাবেস মডেল তৈরি করা।
  3. ডাটা সংগঠনের সুবিধা: অভিন্ন বৈশিষ্ট্যগুলো এক জায়গায় রাখা, যা ডাটার পুনরাবৃত্তি (Data Redundancy) কমায়।
  4. পরিচালনা সহজ করা: ইনহেরিটেড ক্লাসগুলোর মাধ্যমে ডাটাবেস অপারেশন পরিচালনা আরও কার্যকর হয়।

JPA Inheritance এর স্ট্র্যাটেজি

JPA-তে ইনহেরিটেন্স ব্যবস্থাপনার জন্য তিনটি স্ট্র্যাটেজি ব্যবহৃত হয়:

Single Table Strategy

একটি মাত্র টেবিলে সব প্যারেন্ট এবং চাইল্ড ক্লাসের তথ্য রাখা হয়। এটি দ্রুত এবং কার্যকর কিন্তু ডাটা রিডান্ডেন্সি বাড়তে পারে।

উদাহরণ:

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "type", discriminatorType = DiscriminatorType.STRING)
public class Employee {
    @Id
    private Long id;
    private String name;
}

@Entity
public class FullTimeEmployee extends Employee {
    private double salary;
}

@Entity
public class PartTimeEmployee extends Employee {
    private double hourlyRate;
}

টেবিল গঠন:

IDNAMETYPESALARYHOURLY_RATE
1AliceFullTimeEmployee50000NULL
2BobPartTimeEmployeeNULL20

Table Per Class Strategy

প্রতিটি ক্লাসের জন্য আলাদা টেবিল তৈরি হয়। এটি রিলেশনাল ডাটাবেসের জন্য আরও স্বচ্ছ, কিন্তু কার্যকারিতা কিছুটা কম হতে পারে।

উদাহরণ:

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Employee {
    @Id
    private Long id;
    private String name;
}

@Entity
public class FullTimeEmployee extends Employee {
    private double salary;
}

@Entity
public class PartTimeEmployee extends Employee {
    private double hourlyRate;
}

টেবিল গঠন:

  • Employee (প্যারেন্ট টেবিল):

    IDNAME
    1Alice
    2Bob
  • FullTimeEmployee (চাইল্ড টেবিল):

    IDSALARY
    150000
  • PartTimeEmployee (চাইল্ড টেবিল):

    IDHOURLY_RATE
    220

Joined Strategy

প্যারেন্ট ক্লাস এবং চাইল্ড ক্লাসের জন্য আলাদা টেবিল তৈরি হয় এবং তাদের মধ্যে যোগসূত্র থাকে। এটি নরমালাইজড ডাটাবেস মডেল তৈরি করে এবং ডাটা রিডান্ডেন্সি কমায়।

উদাহরণ:

@Entity
@Inheritance(strategy = InheritanceType.JOINED)
public class Employee {
    @Id
    private Long id;
    private String name;
}

@Entity
public class FullTimeEmployee extends Employee {
    private double salary;
}

@Entity
public class PartTimeEmployee extends Employee {
    private double hourlyRate;
}

টেবিল গঠন:

  • Employee (প্যারেন্ট টেবিল):

    IDNAME
    1Alice
    2Bob
  • FullTimeEmployee (চাইল্ড টেবিল):

    IDSALARY
    150000
  • PartTimeEmployee (চাইল্ড টেবিল):

    IDHOURLY_RATE
    220

কোন স্ট্র্যাটেজি কখন ব্যবহার করবেন?

  1. Single Table Strategy:
    • যখন পারফরম্যান্স গুরুত্বপূর্ণ।
    • সাধারণ ইনহেরিটেন্স কাঠামোর জন্য।
  2. Table Per Class Strategy:
    • ছোট টেবিল এবং সহজ স্ট্রাকচার দরকার হলে।
  3. Joined Strategy:
    • ডাটা রিডান্ডেন্সি কমানোর প্রয়োজন হলে এবং রিলেশনাল ডাটাবেসের সাথে মিলিয়ে কাজ করতে হলে।

সারাংশ

JPA Inheritance ডাটাবেস এবং জাভা অবজেক্টের মধ্যে ইনহেরিটেন্স মডেল তৈরি করতে গুরুত্বপূর্ণ ভূমিকা পালন করে। এটি ডাটাবেস মডেলিংকে আরও কার্যকর এবং অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামিংয়ের সাথে সামঞ্জস্যপূর্ণ করে। Inheritance এর বিভিন্ন স্ট্র্যাটেজি ব্যবহার করে আপনি আপনার অ্যাপ্লিকেশনের প্রয়োজন অনুযায়ী ডাটাবেস ডিজাইন করতে পারেন।

Content added By

Table-per-Class, Single Table, এবং Joined Table Inheritance Strategy

79
79

স্প্রিং বুট এবং JPA (Java Persistence API) বিভিন্ন ধরণের ইনহেরিটেন্স স্ট্র্যাটেজি প্রদান করে। ইনহেরিটেন্স স্ট্র্যাটেজি ডেটাবেসে অবজেক্ট-ওরিয়েন্টেড সম্পর্ককে টেবিল ফর্ম্যাটে মানচিত্র করতে সাহায্য করে। JPA তিনটি প্রধান ইনহেরিটেন্স স্ট্র্যাটেজি প্রদান করে:

  • Table-per-Class
  • Single Table
  • Joined Table

Table-per-Class Strategy

সংজ্ঞা

এই স্ট্র্যাটেজিতে প্রতিটি ক্লাসের জন্য একটি স্বতন্ত্র টেবিল তৈরি করা হয়। বেস ক্লাস এবং ডেরাইভড ক্লাসের ডেটা আলাদাভাবে সংরক্ষণ করা হয়।

বৈশিষ্ট্য

  • প্রতিটি ক্লাসের জন্য আলাদা টেবিল।
  • ডেটাবেসে সম্পর্কিত ডেটা রাখতে দ্রুত এবং সহজ।
  • ডুপ্লিকেট কলাম থাকতে পারে।

কনফিগারেশন

Inheritance Type: InheritanceType.TABLE_PER_CLASS

উদাহরণ

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
public class Car extends Vehicle {
    private int seatingCapacity;

    // Getters and Setters
}

@Entity
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

টেবিল গঠন

  • Car Table: id, name, seatingCapacity
  • Bike Table: id, name, hasCarrier

Single Table Strategy

সংজ্ঞা

এই স্ট্র্যাটেজিতে সমস্ত ক্লাসের ডেটা একটি টেবিলে রাখা হয়। টেবিলটি একটি discriminator column ব্যবহার করে ডেটা আলাদা করে।

বৈশিষ্ট্য

  • ডেটার জন্য শুধুমাত্র একটি টেবিল।
  • স্টোরেজ দক্ষ।
  • বড় টেবিলে অনেক নাল ভ্যালু থাকতে পারে।

কনফিগারেশন

Inheritance Type: InheritanceType.SINGLE_TABLE

উদাহরণ

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "vehicle_type", discriminatorType = DiscriminatorType.STRING)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
@DiscriminatorValue("CAR")
public class Car extends Vehicle {
    private int seatingCapacity;

    // Getters and Setters
}

@Entity
@DiscriminatorValue("BIKE")
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

টেবিল গঠন

  • Vehicle Table: id, name, vehicle_type, seatingCapacity, hasCarrier

Joined Table Strategy

সংজ্ঞা

এই স্ট্র্যাটেজিতে প্রতিটি ক্লাসের জন্য আলাদা টেবিল থাকে, তবে তাদের মধ্যে সম্পর্ক গঠন করার জন্য JOIN অপারেশন ব্যবহৃত হয়।

বৈশিষ্ট্য

  • সম্পর্কিত ডেটা সংরক্ষণের জন্য কার্যকর।
  • ডেটার রিডন্ডেন্সি (Redundancy) কম।
  • কোয়েরির সময় জয়েন অপারেশন করার প্রয়োজন হয়।

কনফিগারেশন

Inheritance Type: InheritanceType.JOINED

উদাহরণ

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.JOINED)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
public class Car extends Vehicle {
    private int seatingCapacity;

    // Getters and Setters
}

@Entity
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

টেবিল গঠন

  • Vehicle Table: id, name
  • Car Table: id, seatingCapacity
  • Bike Table: id, hasCarrier

পার্থক্য

বৈশিষ্ট্যTable-per-ClassSingle TableJoined Table
সংরক্ষণ কৌশলপ্রতিটি ক্লাসের জন্য আলাদা টেবিলএকক টেবিলে সমস্ত ডেটাসম্পর্কিত টেবিল ব্যবহার
ডেটার অখণ্ডতাকমকমবেশি
স্টোরেজ দক্ষতাকমবেশিমাঝারি
কোয়েরি জটিলতাকমসহজবেশি
নাল ভ্যালু সমস্যানাহ্যাঁনা

সারাংশ

Spring Boot এবং JPA-তে Table-per-Class, Single Table, এবং Joined Table ইনহেরিটেন্স স্ট্র্যাটেজি ব্যবহার করে ডেটাবেস সম্পর্ক গঠন এবং ডেটা সংরক্ষণ করা যায়। প্রতিটি স্ট্র্যাটেজির নিজস্ব সুবিধা এবং সীমাবদ্ধতা রয়েছে। আপনার প্রয়োজন অনুসারে স্ট্র্যাটেজি বেছে নেওয়া উচিত।

Content added By

উদাহরণ সহ JPA Inheritance Mapping

94
94

JPA Inheritance Mapping ব্যবহার করে আমরা ডাটাবেস টেবিলের মধ্যে Object-Oriented Programming এর Inheritance ধারণা প্রয়োগ করতে পারি। এটি বিশেষভাবে উপকারী যখন আমাদের কাছে Parent এবং Child ক্লাস থাকে এবং আমরা ডেটা টেবিলগুলোর মধ্যে সম্পর্ক তৈরি করতে চাই।

JPA বিভিন্ন স্ট্র্যাটেজি ব্যবহার করে Inheritance Mapping সম্পন্ন করে। এগুলো হলো:

  • SINGLE_TABLE (ডিফল্ট স্ট্র্যাটেজি)
  • TABLE_PER_CLASS
  • JOINED

১. SINGLE_TABLE স্ট্র্যাটেজি

SINGLE_TABLE স্ট্র্যাটেজিতে Parent এবং Child ক্লাসের সব ডেটা একটি একক টেবিলে সংরক্ষিত হয়।

উদাহরণ

Entity ক্লাস (Parent এবং Child):

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "type", discriminatorType = DiscriminatorType.STRING)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
@DiscriminatorValue("Car")
public class Car extends Vehicle {
    private int seatCount;

    // Getters and Setters
}

@Entity
@DiscriminatorValue("Bike")
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

জেনারেট হওয়া টেবিল:

idnametypeseatCounthasCarrier
1ToyotaCar5NULL
2YamahaBikeNULLtrue

২. TABLE_PER_CLASS স্ট্র্যাটেজি

TABLE_PER_CLASS স্ট্র্যাটেজিতে Parent ক্লাস এবং প্রতিটি Child ক্লাসের জন্য আলাদা আলাদা টেবিল তৈরি হয়।

উদাহরণ

Entity ক্লাস (Parent এবং Child):

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
public class Car extends Vehicle {
    private int seatCount;

    // Getters and Setters
}

@Entity
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

জেনারেট হওয়া টেবিল:

Car টেবিল:

idnameseatCount
1Toyota5

Bike টেবিল:

idnamehasCarrier
1Yamahatrue

৩. JOINED স্ট্র্যাটেজি

JOINED স্ট্র্যাটেজিতে Parent ক্লাস এবং Child ক্লাসের জন্য আলাদা টেবিল তৈরি হয়, এবং তাদের মধ্যে একটি JOIN সম্পর্ক থাকে।

উদাহরণ

Entity ক্লাস (Parent এবং Child):

import jakarta.persistence.*;

@Entity
@Inheritance(strategy = InheritanceType.JOINED)
public abstract class Vehicle {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;

    // Getters and Setters
}

@Entity
public class Car extends Vehicle {
    private int seatCount;

    // Getters and Setters
}

@Entity
public class Bike extends Vehicle {
    private boolean hasCarrier;

    // Getters and Setters
}

জেনারেট হওয়া টেবিল:

Vehicle টেবিল:

idname
1Toyota
2Yamaha

Car টেবিল:

idseatCount
15

Bike টেবিল:

idhasCarrier
2true

Service এবং Repository উদাহরণ

Repository:

import org.springframework.data.jpa.repository.JpaRepository;

public interface VehicleRepository extends JpaRepository<Vehicle, Long> {
}

Service:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

@Service
public class VehicleService {

    @Autowired
    private VehicleRepository vehicleRepository;

    public void saveVehicles() {
        Car car = new Car();
        car.setName("Toyota");
        car.setSeatCount(5);
        vehicleRepository.save(car);

        Bike bike = new Bike();
        bike.setName("Yamaha");
        bike.setHasCarrier(true);
        vehicleRepository.save(bike);
    }
}

Inheritance স্ট্র্যাটেজি বেছে নেওয়ার পরামর্শ

  • SINGLE_TABLE: পারফরম্যান্স ভালো এবং টেবিল কম প্রয়োজন। তবে অনেক ক্ষেত্রেই NULL ভ্যালু তৈরি হয়।
  • TABLE_PER_CLASS: আলাদা টেবিল প্রয়োজন এবং Parent ক্লাসের ডেটা Child টেবিলে মাইগ্রেট হয়।
  • JOINED: ডেটা নরমালাইজড এবং ডেটার রিপিটেশন নেই, তবে JOIN অপারেশনের কারণে স্লো হতে পারে।

সারাংশ

JPA Inheritance Mapping ব্যবহার করে Parent-Child সম্পর্কের ডেটা টেবিলের সঙ্গে মানিয়ে নেওয়া যায়। SINGLE_TABLE, TABLE_PER_CLASS, এবং JOINED স্ট্র্যাটেজির মধ্যে সঠিক একটি নির্বাচন অ্যাপ্লিকেশনের প্রয়োজন অনুযায়ী নির্ভর করে। প্রতিটি স্ট্র্যাটেজির নিজস্ব সুবিধা এবং সীমাবদ্ধতা রয়েছে।


Content added By
Promotion