Native SQL Queries

Java Technologies - জেপিএ  (JPA)
204
204

JPA (Java Persistence API) একটি শক্তিশালী API যা Java অ্যাপ্লিকেশনগুলির জন্য অবজেক্ট-অরিয়েন্টেড ডেটাবেস ইন্টারঅ্যাকশন সরবরাহ করে। সাধারণত, JPA তে JPQL (Java Persistence Query Language) ব্যবহার করে ডেটা অ্যাক্সেস করা হয়, তবে কিছু পরিস্থিতিতে, বিশেষ করে যখন ডেটাবেস নির্দিষ্ট কুয়েরি বা অপ্টিমাইজড কুয়েরি প্রয়োজন হয়, তখন Native SQL Queries ব্যবহার করা হয়ে থাকে।

Native SQL Queries হল সেই SQL কুয়েরি যা ডেটাবেস নির্দিষ্ট এবং JPA এর স্বাভাবিক JPQL কুয়েরির বাইরে থাকে। এটি ডেটাবেসের আসল SQL ভাষায় লেখা হয় এবং EntityManager এর মাধ্যমে চালানো হয়।


Native SQL Queries এর সুবিধা এবং ব্যবহার

  1. ডেটাবেস নির্দিষ্ট কুয়েরি: কিছু বিশেষ SQL ফিচার যেমন JOINs, GROUP BY, HAVING, Window Functions ইত্যাদি JPQL তে সম্ভব নয়, তখন Native SQL কুয়েরি ব্যবহৃত হয়।
  2. পারফরম্যান্স অপটিমাইজেশন: Native SQL কুয়েরি ডেটাবেসের পারফরম্যান্স সঠিকভাবে টিউন করতে সাহায্য করতে পারে, কারণ এটি ডেটাবেসের বিশেষ ক্ষমতা বা ফিচার ব্যবহার করতে সক্ষম।
  3. বিকল্প কুয়েরি লেখার ক্ষমতা: কিছু কেসে JPQL নির্দিষ্ট ফিচার বা ফাংশন সাপোর্ট করে না, তখন Native SQL Query লেখার মাধ্যমে আপনি ডেটাবেসের পূর্ণ ক্ষমতা ব্যবহার করতে পারেন।

Native SQL Query ব্যবহার করার পদ্ধতি

EntityManager ব্যবহার করে Native SQL Query চালানো হয়। Native SQL Query চালানোর জন্য createNativeQuery() মেথড ব্যবহার করা হয়।

1. Native SQL Query ব্যবহার করা

উদাহরণ: Native SQL Query with Entity Mapping

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> findEmployeesWithSalaryGreaterThan(double salary) {
        // Native SQL Query to fetch employees with salary greater than a specified value
        String sql = "SELECT * FROM Employee WHERE salary > :salary";

        Query query = entityManager.createNativeQuery(sql, Employee.class);
        query.setParameter("salary", salary);

        return query.getResultList();
    }
}

এখানে, একটি Native SQL Query ব্যবহার করা হয়েছে যা Employee টেবিল থেকে সকল কর্মচারী নির্বাচন করবে, যাদের salary একটি নির্দিষ্ট মানের বেশি।

  • createNativeQuery: Native SQL Query তৈরি করতে ব্যবহৃত হয়।
  • Employee.class: এখানে আমরা এই SQL Query এর জন্য Employee Entity ক্লাসের মডেল ব্যবহার করেছি।
  • setParameter(): salary প্যারামিটারটি সেট করা হয়েছে।

উদাহরণ: Native SQL Query without Entity Mapping

যদি আপনি Native SQL Query ব্যবহার করে কিছু নির্দিষ্ট ডেটা ফেরত পেতে চান, কিন্তু Entity ক্লাসে সেই ডেটা ম্যাপ করতে চান না, তাহলে createNativeQuery() এর মাধ্যমে আপনি সোজাসুজি Object Array বা Object[] রিটার্ন করতে পারেন।

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> findEmployeeNamesAndSalaries() {
        // Native SQL Query to fetch employee names and salaries
        String sql = "SELECT name, salary FROM Employee";

        Query query = entityManager.createNativeQuery(sql);
        
        return query.getResultList();
    }
}

এখানে, Object[] রিটার্ন হচ্ছে যেখানে প্রতিটি Array এর মধ্যে name এবং salary ফিল্ড থাকবে। এই ক্ষেত্রে Entity ক্লাসের Mapping প্রয়োজন নেই।

2. Native SQL Query with Aggregation Functions

Native SQL Query তে আপনি Aggregation Functions যেমন COUNT, SUM, AVG, MAX, MIN ইত্যাদি ব্যবহার করতে পারেন। যেমন:

public long getEmployeeCountByDepartment(String department) {
    String sql = "SELECT COUNT(*) FROM Employee WHERE department = :department";

    Query query = entityManager.createNativeQuery(sql);
    query.setParameter("department", department);

    return ((Number) query.getSingleResult()).longValue();
}

এখানে, আমরা COUNT ফাংশন ব্যবহার করে একটি নির্দিষ্ট department এর Employee সংখ্যা গণনা করছি।

3. Named Native SQL Queries

JPA তে Named Native Queries আপনি @Query অ্যানোটেশন ব্যবহার করে Entity ক্লাসের মধ্যে ডিফাইন করতে পারেন, যাতে কোডে আরো পরিষ্কার এবং রক্ষণাবেক্ষণযোগ্য থাকে।

Named Native Query Example:

@Entity
@NamedNativeQuery(name = "Employee.findByDepartment",
                  query = "SELECT * FROM Employee WHERE department = :department",
                  resultClass = Employee.class)
public class Employee {
    // Entity class definition
}

এখন, আপনি NamedNativeQuery ব্যবহার করে নিচের মতো ডেটা পেতে পারেন:

Query query = entityManager.createNamedQuery("Employee.findByDepartment");
query.setParameter("department", "HR");

List<Employee> employees = query.getResultList();

4. Pagination in Native Queries

Native SQL Query তে পেজিনেশন (paginated queries) ব্যবহারের জন্য setFirstResult() এবং setMaxResults() ব্যবহার করা যায়।

String sql = "SELECT * FROM Employee WHERE department = :department";
Query query = entityManager.createNativeQuery(sql, Employee.class);
query.setParameter("department", "IT");
query.setFirstResult(0); // Start from the first result
query.setMaxResults(10); // Limit the number of results

List<Employee> employees = query.getResultList();

এখানে, আমরা পেজিনেশন করে IT ডিপার্টমেন্টের প্রথম 10 কর্মচারী নির্বাচিত করেছি।


Native SQL Query এর সুবিধা

  1. ডেটাবেস নির্দিষ্ট কুয়েরি সমর্থন: যখন আপনাকে ডেটাবেস নির্দিষ্ট কুয়েরি বা অপ্টিমাইজড কুয়েরি চালাতে হয়, তখন Native SQL কুয়েরি অত্যন্ত কার্যকরী।
  2. পারফরম্যান্স অপটিমাইজেশন: কিছু SQL ফিচার যেমন complex joins বা window functions, যেগুলি JPQL এ সহজে সমাধান করা সম্ভব নয়, Native SQL Query এর মাধ্যমে সরাসরি ডেটাবেসে ব্যবহৃত হয়।
  3. JPA এর বাইরে SQL ব্যবহার: JPQL এর সীমাবদ্ধতাগুলি এড়িয়ে Native SQL ব্যবহার করে সরাসরি ডেটাবেসের জন্য কাস্টম SQL কুয়েরি লিখতে পারবেন।

Native SQL Query এর সীমাবদ্ধতা

  1. ডেটাবেস নির্ভরশীলতা: Native SQL Query ডেটাবেস নির্দিষ্ট, অর্থাৎ এটি এক ডেটাবেসে কাজ করতে পারে, কিন্তু অন্য ডেটাবেসে কাজ নাও করতে পারে।
  2. JPA Features এর অভাব: JPQL ব্যবহার করলে Entity ও তার সম্পর্কের উপর কাজ করা সহজ, কিন্তু Native SQL Query তে এসব সুবিধা পাওয়া যায় না।
  3. পরবর্তী রক্ষণাবেক্ষণ সমস্যা: Native SQL ব্যবহার করলে ডেটাবেস কোডের রক্ষণাবেক্ষণ কঠিন হতে পারে, বিশেষত যখন আপনি ডেটাবেস পরিবর্তন করবেন।

সারাংশ


Native SQL Queries JPA তে একটি শক্তিশালী উপায় যা আপনাকে ডেটাবেস নির্দিষ্ট কুয়েরি লেখার সুযোগ দেয়। এটি যখন JPQL সীমাবদ্ধ থাকে বা ডেটাবেসের নির্দিষ্ট ফিচার প্রয়োজন হয়, তখন কার্যকরী হয়। Native SQL তে complex SQL কুয়েরি, joins, aggregation ফাংশন, এবং পেজিনেশন ব্যবহার করা যায় যা ডেটাবেসের পারফরম্যান্স অপটিমাইজেশন করতে সাহায্য করে।

Content added By

JPA তে Native Queries চালানোর প্রক্রিয়া

66
66

JPA (Java Persistence API) তে Native Queries চালানোর প্রক্রিয়া একটি শক্তিশালী উপায় যা আপনাকে ডেটাবেস নির্দিষ্ট SQL কুয়েরি চালানোর সুযোগ দেয়, বিশেষ করে যখন JPQL (Java Persistence Query Language) সীমাবদ্ধ হয়ে যায় অথবা আপনি ডেটাবেসের নিজস্ব ফিচার ব্যবহার করতে চান। Native SQL কুয়েরি EntityManager ব্যবহার করে চালানো হয় এবং এটি ডেটাবেসের আসল SQL সিনট্যাক্স ব্যবহার করে।

Native Queries চালানোর জন্য EntityManager ব্যবহার করা

JPA তে Native SQL Query চালানোর জন্য EntityManager এর createNativeQuery() মেথড ব্যবহার করা হয়। EntityManager কুয়েরি চালানোর জন্য একটি API প্রদান করে যা Native SQL কুয়েরি লেখার এবং ফলাফল পাওয়ার জন্য ব্যবহৃত হয়।

Native Query চালানোর ধাপসমূহ:

  1. Native SQL Query লেখার জন্য createNativeQuery() মেথড ব্যবহার করুন
  2. Query object তৈরি করুন এবং সেই Query তে parameter পাস করুন (যদি প্রয়োজন হয়)।
  3. Query execute করুন এবং ফলাফল সংগ্রহ করুন।

Native SQL Query চালানোর প্রক্রিয়া:

1. Native SQL Query with Entity Mapping

এই প্রক্রিয়ায়, আমরা Native SQL Query চালানোর জন্য Entity Class ব্যবহার করব, যাতে SQL Query এর ফলাফল সরাসরি Entity তে ম্যাপ করা যায়।

উদাহরণ:

ধরা যাক, আপনার কাছে Employee Entity ক্লাস রয়েছে এবং আপনি salary এর উপর ভিত্তি করে কর্মচারীদের তালিকা দেখতে চান। আপনার Native SQL Query হবে:

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> findEmployeesWithSalaryGreaterThan(double salary) {
        // Native SQL Query to fetch employees with salary greater than a specified value
        String sql = "SELECT * FROM Employee WHERE salary > :salary";

        Query query = entityManager.createNativeQuery(sql, Employee.class);
        query.setParameter("salary", salary);

        return query.getResultList();
    }
}

এখানে:

  • createNativeQuery() মেথডের মাধ্যমে Native SQL Query তৈরি করা হয়েছে।
  • Employee.class নির্দেশ করছে যে, SQL Query এর ফলাফল Employee Entity তে ম্যাপ হবে।
  • setParameter("salary", salary) প্যারামিটারটি সেট করে কাজ করা হয়েছে।

2. Native SQL Query without Entity Mapping

যখন আপনি Native SQL Query চালাতে চান কিন্তু Entity ক্লাসে সেই ডেটা ম্যাপ করতে চান না, তখন createNativeQuery() মেথডটি সরাসরি Object[] অথবা Object ব্যবহার করে ফলাফল ফেরত দিতে পারে।

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> findEmployeeNamesAndSalaries() {
        // Native SQL Query to fetch employee names and salaries
        String sql = "SELECT name, salary FROM Employee";

        Query query = entityManager.createNativeQuery(sql);
        
        return query.getResultList();
    }
}

এখানে:

  • Object[] আউটপুট টাইপে name এবং salary কলামসমূহের মান ফেরত আসবে।
  • ফলস্বরূপ, query.getResultList() কল করলে এটি একটি List<Object[]> ফেরত দেবে যেখানে প্রতিটি উপাদান একটি Array হবে।

3. Native SQL Query with Aggregation Functions

Native SQL Query তে aggregation functions (যেমন COUNT, SUM, AVG, MAX, MIN) ব্যবহার করা যায়। এখানে, আমরা Employee টেবিল থেকে salary এর উপর ভিত্তি করে গড় (average) গণনা করব।

public double getAverageSalary() {
    String sql = "SELECT AVG(salary) FROM Employee";

    Query query = entityManager.createNativeQuery(sql);

    return (Double) query.getSingleResult();
}

এখানে:

  • AVG(salary) দ্বারা কর্মচারীদের salary এর গড় বের করা হচ্ছে।
  • getSingleResult() মেথড ব্যবহার করে একটি একক মান (গড় salary) ফেরত পেয়েছি।

4. Native SQL Query with Named Parameters

যখন আপনার Native SQL Query তে প্যারামিটার থাকে, তখন named parameters ব্যবহার করা যেতে পারে:

public List<Employee> findEmployeesByDepartment(String department) {
    String sql = "SELECT * FROM Employee WHERE department = :department";

    Query query = entityManager.createNativeQuery(sql, Employee.class);
    query.setParameter("department", department);

    return query.getResultList();
}

এখানে:

  • :department প্যারামিটারটি SQL Query তে named parameter হিসেবে ব্যবহৃত হচ্ছে।
  • setParameter() মেথড ব্যবহার করে আমরা প্যারামিটারটি পাস করেছি।

5. Native SQL Query with Pagination

Native SQL Query তে পেজিনেশন (Paginated Results) ব্যবহার করার জন্য setFirstResult() এবং setMaxResults() ব্যবহার করা হয়।

public List<Employee> getPaginatedEmployees(int pageNumber, int pageSize) {
    String sql = "SELECT * FROM Employee";

    Query query = entityManager.createNativeQuery(sql, Employee.class);
    query.setFirstResult((pageNumber - 1) * pageSize);
    query.setMaxResults(pageSize);

    return query.getResultList();
}

এখানে:

  • setFirstResult(): এটি প্রথম ফলাফলটি নির্ধারণ করে।
  • setMaxResults(): এটি প্রতি পৃষ্ঠায় প্রদর্শিত সর্বোচ্চ ফলাফল সংখ্যা নির্ধারণ করে।

Native SQL Queries এর সুবিধা:

  1. ডেটাবেস নির্দিষ্ট কুয়েরি সাপোর্ট: যখন ডেটাবেস নির্দিষ্ট কুয়েরি বা অপ্টিমাইজড কুয়েরি চালাতে হয়, Native SQL খুবই কার্যকর।
  2. পারফরম্যান্স অপ্টিমাইজেশন: JPQL এর চেয়ে Native SQL কুয়েরি ডেটাবেসের নিজস্ব ক্ষমতা ব্যবহার করতে সাহায্য করতে পারে, যেমন indexing, optimizing joins, ইত্যাদি।
  3. ফিচার অ্যাক্সেস: কিছু ফিচার যেমন Window Functions, Full Text Search ইত্যাদি JPQL তে নেই, কিন্তু Native SQL তে ব্যবহার করা সম্ভব।

Native SQL Queries এর সীমাবদ্ধতা:

  1. ডেটাবেস নির্ভরশীলতা: Native SQL কুয়েরি ডেটাবেস নির্দিষ্ট হয়, অর্থাৎ এটি এক ডেটাবেসে কাজ করতে পারে, কিন্তু অন্য ডেটাবেসে কাজ নাও করতে পারে।
  2. JPQL সুবিধার অভাব: Native SQL কুয়েরি JPA এর শক্তিশালী Entity Relationships এবং automatic mapping সুবিধাগুলি সরবরাহ করে না।
  3. ডিবাগিং এবং রক্ষণাবেক্ষণ: Native SQL কুয়েরি কোডের রক্ষণাবেক্ষণ এবং ডিবাগিং সহজ নয়, বিশেষত যখন ডেটাবেসের মধ্যে পরিবর্তন আনা হয়।

সারাংশ


Native SQL Queries JPA তে ডেটাবেস নির্দিষ্ট কুয়েরি চালানোর একটি কার্যকরী উপায়। এটি EntityManager ব্যবহার করে createNativeQuery() মেথডের মাধ্যমে তৈরি করা হয় এবং এটি ডেটাবেসের আসল SQL সিনট্যাক্স ব্যবহার করে। Native SQL Queries JPQL এর তুলনায় অধিক কার্যকরী হতে পারে যখন complex joins, aggregation functions, window functions, বা database-specific features দরকার হয়। তবে, এর কিছু সীমাবদ্ধতা রয়েছে, যেমন এটি ডেটাবেস নির্ভরশীল, এবং জেপিএ এর automatic object mapping সুবিধাগুলি সরবরাহ করে না।

Content added By

@Query এবং EntityManager.createNativeQuery() এর ব্যবহার

61
61

JPA (Java Persistence API)-তে ডেটা অ্যাক্সেস করতে প্রধানত JPQL (Java Persistence Query Language) এবং Native SQL Queries ব্যবহার করা হয়। @Query এবং EntityManager.createNativeQuery() দুটি গুরুত্বপূর্ণ টুল যা ডেটাবেসের সাথে ইন্টারঅ্যাক্ট করতে ব্যবহৃত হয়।

  • @Query: এটি Spring Data JPA এ ব্যবহৃত হয়, যেখানে আপনি JPQL বা SQL কুয়েরি লিখে ডেটাবেস অ্যাক্সেস করতে পারেন।
  • EntityManager.createNativeQuery(): এটি JPA এর একটি মেথড যা Native SQL Queries চালানোর জন্য ব্যবহৃত হয়, যেখানে সরাসরি ডেটাবেসের আসল SQL ব্যবহার করা হয়।

এখানে আমরা @Query এবং EntityManager.createNativeQuery() এর ব্যবহার এবং পার্থক্য নিয়ে বিস্তারিত আলোচনা করব।


@Query এর ব্যবহার


@Query অ্যানোটেশন Spring Data JPA তে ব্যবহৃত হয় এবং এটি ডেটাবেসে JPQL বা Native SQL কুয়েরি চালানোর জন্য ব্যবহার করা হয়। যখন আপনি Spring Data JPA Repository ব্যবহার করেন, তখন @Query অ্যানোটেশনটি আপনার কাস্টম কুয়েরি সংজ্ঞায়িত করতে সাহায্য করে।

@Query উদাহরণ (JPQL)

import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.CrudRepository;
import java.util.List;

public interface EmployeeRepository extends CrudRepository<Employee, Long> {

    // JPQL query example using @Query annotation
    @Query("SELECT e FROM Employee e WHERE e.department = :department")
    List<Employee> findEmployeesByDepartment(String department);
}

এখানে:

  • @Query ব্যবহার করা হয়েছে Employee Entity এর department ফিল্ডে ভিত্তি করে কর্মচারীদের তালিকা ফেরত দেওয়ার জন্য।
  • এটি JPQL কুয়েরি, যেখানে Employee একটি Entity ক্লাস এবং department একটি ফিল্ড।

@Query উদাহরণ (Native SQL)

@Query অ্যানোটেশনটি Native SQL কুয়েরি ব্যবহারের জন্যও ব্যবহৃত হতে পারে, যেমন:

import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.CrudRepository;
import java.util.List;

public interface EmployeeRepository extends CrudRepository<Employee, Long> {

    // Native SQL query example using @Query annotation
    @Query(value = "SELECT * FROM Employee WHERE department = :department", nativeQuery = true)
    List<Employee> findEmployeesByDepartmentNative(String department);
}

এখানে:

  • nativeQuery = true ব্যবহৃত হয়েছে যাতে Spring Data JPA জানে যে এটি একটি Native SQL কুয়েরি।
  • SELECT * FROM Employee এক্সাক্ট SQL কুয়েরি যা Employee টেবিল থেকে ডেটা ফেরত দেবে।

EntityManager.createNativeQuery() এর ব্যবহার


EntityManager.createNativeQuery() JPA এর একটি মেথড যা Native SQL Queries চালানোর জন্য ব্যবহৃত হয়। এই মেথডটি আপনি যখন সরাসরি SQL কুয়েরি লিখতে চান বা ডেটাবেসের নির্দিষ্ট ফিচার ব্যবহার করতে চান তখন ব্যবহার করতে পারেন।

EntityManager.createNativeQuery() উদাহরণ

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> findEmployeesByDepartment(String department) {
        // Native SQL query to fetch employees by department
        String sql = "SELECT * FROM Employee WHERE department = :dept";

        // Create Native Query
        Query query = entityManager.createNativeQuery(sql, Employee.class);
        query.setParameter("dept", department);

        // Execute the query and return results
        return query.getResultList();
    }
}

এখানে:

  • createNativeQuery() ব্যবহার করা হয়েছে Native SQL কুয়েরি তৈরি করতে।
  • Employee.class ব্যবহার করা হয়েছে ফলাফল হিসেবে Employee Entity ফিরিয়ে দেওয়ার জন্য।
  • setParameter() ব্যবহার করে :dept প্যারামিটারটি সেট করা হয়েছে।

EntityManager.createNativeQuery() এর সাথে Object Mapping

কিছু ক্ষেত্রে, আপনি Native SQL কুয়েরি থেকে Object রিটার্ন করতে পারেন। এর জন্য, আপনি resultClass বা Object[] ব্যবহার করতে পারেন।

public List<Object[]> findEmployeeNamesAndSalaries() {
    String sql = "SELECT name, salary FROM Employee";
    
    // Create Native Query
    Query query = entityManager.createNativeQuery(sql);

    // Execute the query and return results
    return query.getResultList();
}

এখানে, SQL কুয়েরি name এবং salary ফিল্ডের মান দিচ্ছে, এবং ফলাফলটি Object[] হিসেবে ফেরত দিচ্ছে।


@Query এবং EntityManager.createNativeQuery() এর পার্থক্য

বৈশিষ্ট্য@Query (Spring Data JPA)EntityManager.createNativeQuery()
ব্যবহারSpring Data JPA এর Repository তে কাস্টম কুয়েরি লেখার জন্য ব্যবহৃত হয়JPA এর EntityManager এর মাধ্যমে Native SQL কুয়েরি চালানোর জন্য
JPQL বা Native SQLJPQL বা Native SQL, উভয়ই সমর্থিতমূলত Native SQL কুয়েরি ব্যবহৃত হয়
ডেটা মডেল ম্যাপিংJPQL কুয়েরি Entity ক্লাসে রূপান্তরিত হয়Native SQL কুয়েরি Entity বা ResultSet-এ রূপান্তরিত হয়
সহজ ইন্টিগ্রেশনSpring Data JPA Repository এবং @Query খুব সহজে ইন্টিগ্রেট করা যায়EntityManager এবং Native SQL Query এর সাথে কোড লেখা কিছুটা জটিল
ফ্লেক্সিবিলিটি@Query ডেটাবেস ইন্টারঅ্যাকশন কাস্টমাইজেশন সহজ করেNative SQL Queries ডেটাবেস নির্দিষ্ট কাস্টমাইজেশন বেশি সক্ষম

সারাংশ


@Query এবং EntityManager.createNativeQuery() দুইটি গুরুত্বপূর্ণ উপায় যা JPA তে Native SQL Queries চালানোর জন্য ব্যবহৃত হয়।

  • @Query অ্যানোটেশন Spring Data JPA ব্যবহারকারীদের জন্য সহজে JPQL বা Native SQL কুয়েরি চালানোর সুযোগ দেয়।
  • EntityManager.createNativeQuery() Java EE তে JPA ব্যবহার করে Native SQL কুয়েরি চালানোর জন্য সরাসরি ব্যবহৃত হয়, এবং এতে আপনি Entity বা Object[] রিটার্ন করতে পারেন।

যতটুকু সম্ভব JPQL ব্যবহার করার চেষ্টা করুন, তবে যখন Native SQL বা ডেটাবেস নির্দিষ্ট কুয়েরি প্রয়োজন হয়, তখন createNativeQuery() ব্যবহারের মাধ্যমে ডেটাবেসের শক্তিশালী ফিচার ব্যবহার করতে পারেন।

Content added By

Native Queries এর মাধ্যমে Complex Database Operations

62
62

JPA (Java Persistence API) আপনাকে JPQL (Java Persistence Query Language) ব্যবহার করে Entity গুলির সাথে ইন্টারঅ্যাক্ট করার সুবিধা প্রদান করে। তবে, কিছু জটিল ডেটাবেস অপারেশন বা ডেটাবেস নির্দিষ্ট ফিচার (যেমন complex joins, subqueries, aggregate functions) ব্যবহার করার জন্য Native SQL Queries অত্যন্ত কার্যকরী হতে পারে। Native SQL Queries সরাসরি ডেটাবেসে SQL কুয়েরি পাঠানোর মাধ্যমে complex database operations সম্পাদন করতে সহায়তা করে।

Native Queries দিয়ে Complex Database Operations

JPA তে Native SQL Query ব্যবহার করার মাধ্যমে আপনি ডেটাবেসের কিছু জটিল অপারেশন খুব সহজেই করতে পারেন, যেমন:

  1. Complex Joins (JOIN Operations)
  2. Aggregate Functions (COUNT, SUM, AVG, etc.)
  3. Subqueries
  4. Group By and Having
  5. Pagination

এগুলো JPA তে Native SQL Query ব্যবহার করে কীভাবে করা যায়, তা নিচে বিস্তারিতভাবে দেখানো হবে।


1. Complex Joins

Joins সাধারণত বিভিন্ন টেবিলের মধ্যে সম্পর্ক স্থাপন করতে ব্যবহৃত হয়। জটিল INNER JOIN, LEFT JOIN বা RIGHT JOIN ব্যবহারের মাধ্যমে আপনি একাধিক টেবিল থেকে ডেটা সংগ্রহ করতে পারেন।

উদাহরণ: Complex Join using Native Query

ধরা যাক, আমাদের দুটি টেবিল Employee এবং Department রয়েছে এবং আমরা Employee এবং Department টেবিলের মধ্যে INNER JOIN করতে চাই।

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> findEmployeeDepartmentDetails() {
        // Native SQL Query with JOIN operation
        String sql = "SELECT e.name, e.salary, d.name FROM Employee e " +
                     "INNER JOIN Department d ON e.department_id = d.id";
        
        Query query = entityManager.createNativeQuery(sql);
        
        return query.getResultList();  // Execute the query and return the result
    }
}

এখানে:

  • INNER JOIN ব্যবহার করে Employee এবং Department টেবিলের মধ্যে সম্পর্ক স্থাপন করা হয়েছে।
  • Object[] রিটার্ন টাইপ ব্যবহার করে একটি এক্সটার্নাল কাস্টম রেজাল্ট ফরম্যাটে ডেটা ফেরত পাওয়া যাবে (এখানে Employee এবং Department এর নাম ও বেতন ফিরে আসবে)।

2. Aggregate Functions (COUNT, SUM, AVG, MAX, MIN)

Aggregate Functions ডেটার উপর সমষ্টিগত অপারেশন সম্পাদন করতে ব্যবহৃত হয়, যেমন রেকর্ডের সংখ্যা, সর্বোচ্চ/সর্বনিম্ন মান, গড় মান, ইত্যাদি।

উদাহরণ: Aggregate Function using Native Query

ধরা যাক, আমরা Employee টেবিলের মধ্যে গড় বেতন বের করতে চাই।

import javax.persistence.EntityManager;
import javax.persistence.Query;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public double getAverageSalary() {
        // Native SQL Query to calculate average salary
        String sql = "SELECT AVG(salary) FROM Employee";
        
        Query query = entityManager.createNativeQuery(sql);
        
        return (Double) query.getSingleResult();  // Return the average salary
    }
}

এখানে:

  • AVG(salary) aggregate function ব্যবহার করে Employee টেবিলের গড় বেতন বের করা হয়েছে।

3. Subqueries

Subqueries একাধিক কুয়েরির মধ্যে একটি কুয়েরি হতে পারে, যা আরেকটি কুয়েরির ফলাফল ব্যবহার করে। Subqueries জটিল ডেটাবেস অপারেশন করার জন্য ব্যবহার করা হয়, যেখানে একটি কুয়েরির রেজাল্ট অন্য কুয়েরির শর্ত হিসেবে ব্যবহৃত হয়।

উদাহরণ: Using Subquery in Native Query

ধরা যাক, আমরা সেই Employee গুলি খুঁজতে চাই যাদের বেতন গড় বেতনের চেয়ে বেশি।

import javax.persistence.EntityManager;
import javax.persistence.Query;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> findEmployeesWithSalaryGreaterThanAverage() {
        // Native SQL Query with Subquery
        String sql = "SELECT * FROM Employee e WHERE e.salary > " +
                     "(SELECT AVG(salary) FROM Employee)";
        
        Query query = entityManager.createNativeQuery(sql, Employee.class);
        
        return query.getResultList();  // Execute the query and return the result
    }
}

এখানে:

  • Subquery ব্যবহার করা হয়েছে যা গড় বেতন বের করবে এবং তার পরে মূল কুয়েরি সেই বেতনের চেয়ে বেশি বেতন থাকা Employee গুলি ফেরত দেবে।

4. Group By and Having

GROUP BY এবং HAVING SQL ফিচার দুটি সাধারণত ডেটাকে গ্রুপ করা এবং একটি শর্তের ভিত্তিতে ডেটা ফিল্টার করার জন্য ব্যবহৃত হয়।

উদাহরণ: Using GROUP BY and HAVING in Native Query

ধরা যাক, আমরা Department অনুযায়ী Employee এর গড় বেতন বের করতে চাই, এবং শুধুমাত্র যেখানে গড় বেতন ৫০,০০০ এর বেশি।

import javax.persistence.EntityManager;
import javax.persistence.Query;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> getAverageSalaryByDepartment() {
        // Native SQL Query with GROUP BY and HAVING
        String sql = "SELECT d.name, AVG(e.salary) FROM Employee e " +
                     "INNER JOIN Department d ON e.department_id = d.id " +
                     "GROUP BY d.name HAVING AVG(e.salary) > 50000";
        
        Query query = entityManager.createNativeQuery(sql);
        
        return query.getResultList();  // Execute the query and return the result
    }
}

এখানে:

  • GROUP BY ব্যবহৃত হয়েছে Department অনুযায়ী গ্রুপিং করার জন্য।
Content added By

Practical উদাহরণ: Native Queries এর মাধ্যমে Data Extraction

60
60

JPA (Java Persistence API) তে Native SQL Queries ব্যবহার করে ডেটা এক্সট্র্যাকশন (Data Extraction) করতে হয়, যখন আপনি JPQL বা Criteria API এর মাধ্যমে যে সমস্ত কুয়েরি বা অপারেশন করতে পারেন না, সেই ক্ষেত্রে Native SQL Queries কার্যকরী হয়ে ওঠে। এটি ডেটাবেস নির্দিষ্ট কুয়েরি বা অপটিমাইজড SQL ফিচারের জন্য ব্যবহৃত হয়।

নিম্নলিখিত উদাহরণগুলোতে আমরা দেখব কীভাবে Native SQL Queries ব্যবহার করে ডেটা এক্সট্র্যাকশন করা যায়।


প্রথম উদাহরণ: Native Query দিয়ে Employee List Extraction

ধরা যাক, আমাদের একটি Employee Entity আছে এবং আমরা Employee টেবিল থেকে সমস্ত কর্মচারীকে বের করতে চাই, কিন্তু এই কুয়েরি Native SQL তে হবে।

Step 1: Employee Entity

import javax.persistence.Entity;
import javax.persistence.Id;

@Entity
public class Employee {

    @Id
    private Long id;
    private String name;
    private double salary;
    private String department;

    // Getter and Setter Methods
    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;
    }

    public double getSalary() {
        return salary;
    }

    public void setSalary(double salary) {
        this.salary = salary;
    }

    public String getDepartment() {
        return department;
    }

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

Step 2: Native SQL Query for Employee List

এখন, আমরা Native SQL Query ব্যবহার করে Employee টেবিল থেকে সমস্ত কর্মচারীর নাম এবং বেতন বের করতে চাই।

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> getAllEmployees() {
        // Native SQL Query to fetch all employees
        String sql = "SELECT * FROM Employee";

        Query query = entityManager.createNativeQuery(sql, Employee.class);
        
        // Fetching results as List of Employee objects
        return query.getResultList();  // Execute the query and return the result
    }
}

ব্যাখ্যা:

  • createNativeQuery: এটি Native SQL Query তৈরি করতে ব্যবহৃত হয় এবং ডেটাবেসের আসল SQL ব্যবহার করতে সহায়তা করে।
  • Employee.class: এটি Entity ক্লাস, যার মাধ্যমে Employee টেবিলের ডেটা Java Object হিসেবে ম্যাপ হয়।
  • getResultList(): এটি Native Query এর রেজাল্টের লিস্ট ফেরত দেয়।

দ্বিতীয় উদাহরণ: Native SQL Query দিয়ে Aggregate Data Extraction

ধরা যাক, আমরা Employee টেবিল থেকে department অনুযায়ী গড় বেতন বের করতে চাই, এবং HAVING ক্লজ ব্যবহার করে শুধুমাত্র সেই বিভাগের কর্মচারী গুলি দেখতে চাই যাদের গড় বেতন ৫০,০০০ টাকার বেশি।

Step 1: Aggregate Query with Group By and Having

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;
import java.util.Object;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> getAverageSalaryByDepartment() {
        // Native SQL Query with GROUP BY and HAVING
        String sql = "SELECT department, AVG(salary) FROM Employee " +
                     "GROUP BY department HAVING AVG(salary) > 50000";

        Query query = entityManager.createNativeQuery(sql);

        // Fetching aggregated data
        return query.getResultList();  // Execute the query and return the result
    }
}

ব্যাখ্যা:

  • AVG(salary): গড় বেতন বের করার জন্য AVG aggregate function ব্যবহার করা হয়েছে।
  • GROUP BY: ডেটা department অনুযায়ী গ্রুপ করা হয়েছে।
  • HAVING: গড় বেতন ৫০,০০০ টাকার বেশি এমন বিভাগগুলিই ফিল্টার করা হয়েছে।

এই কুয়েরি ব্যবহারের মাধ্যমে, আপনি department এবং গড় বেতন জানিয়ে বিভিন্ন বিভাগে কর্মচারীদের গড় বেতন বের করতে পারবেন।


তৃতীয় উদাহরণ: Native SQL Query দিয়ে Employee Pagination

আমরা যদি Employee টেবিলের ডেটা পেজিনেশন করতে চাই, তবে Native SQL Query এর মাধ্যমে তা করা সম্ভব। এখানে আমরা প্রথম ৫টি কর্মচারী দেখতে চাই, যারা HR বিভাগে কর্মরত।

Step 1: Native Query with Pagination

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Employee> getEmployeesByDepartmentWithPagination(String department) {
        // Native SQL Query with Pagination
        String sql = "SELECT * FROM Employee WHERE department = :department";

        Query query = entityManager.createNativeQuery(sql, Employee.class);
        query.setParameter("department", department);
        query.setFirstResult(0);  // Start from the first result
        query.setMaxResults(5);   // Limit the results to 5

        return query.getResultList();  // Fetch the paginated results
    }
}

ব্যাখ্যা:

  • setFirstResult(0): এটি প্রথম ৫টি রেকর্ড থেকে শুরু করবে (যেহেতু আমরা ৫টি রেকর্ডের জন্য সিলেক্ট করেছি)।
  • setMaxResults(5): এটি ৫টি রেকর্ডে সীমাবদ্ধ করবে, অর্থাৎ, পেজিনেশন এর মাধ্যমে ৫টি কর্মচারী রিটার্ন করবে।

এখানে, HR ডিপার্টমেন্টের প্রথম ৫টি কর্মচারী ফেরত আসবে।


চতুর্থ উদাহরণ: Native SQL Query with JOINs

আমরা যদি Employee এবং Department টেবিলের মধ্যে JOIN করতে চাই, তবে Native SQL Query এর মাধ্যমে তা করা যাবে।

Step 1: Native SQL Query with JOIN

import javax.persistence.EntityManager;
import javax.persistence.Query;
import java.util.List;

public class EmployeeService {

    private EntityManager entityManager;

    public EmployeeService(EntityManager entityManager) {
        this.entityManager = entityManager;
    }

    public List<Object[]> getEmployeeDepartmentDetails() {
        // Native SQL Query with JOIN operation
        String sql = "SELECT e.name, e.salary, d.name FROM Employee e " +
                     "INNER JOIN Department d ON e.department_id = d.id";

        Query query = entityManager.createNativeQuery(sql);

        // Fetching employee name, salary, and department name
        return query.getResultList();  // Execute the query and return the result
    }
}

ব্যাখ্যা:

  • INNER JOIN: Employee এবং Department টেবিলের মধ্যে INNER JOIN ব্যবহার করা হয়েছে।
  • Object[]: রিটার্ন টাইপ Object[] কারণ একাধিক কলাম (যেমন, Employee এর নাম, বেতন এবং Department এর নাম) একত্রে রিটার্ন করা হচ্ছে।

এটি Employee টেবিল এবং Department টেবিলের সংযুক্ত ডেটা (employee name, salary, department name) রিটার্ন করবে।


সারাংশ


Native SQL Queries JPA তে ডেটাবেস নির্দিষ্ট কুয়েরি এবং জটিল অপারেশন করার জন্য শক্তিশালী উপায়। আপনি joins, aggregation functions, subqueries, এবং pagination এর মতো কমপ্লেক্স ডেটাবেস অপারেশন Native SQL Query ব্যবহার করে সহজেই করতে পারেন। এগুলির মাধ্যমে আপনি ডেটাবেসের বিশেষ ক্ষমতাগুলো ব্যবহার করে ডেটা এক্সট্র্যাকশন করতে পারেন। EntityManager এর মাধ্যমে createNativeQuery() মেথড ব্যবহার করে Native Queries চালানো হয় এবং আপনি সহজেই Entity, Object[] অথবা DTO তে রেজাল্ট ম্যাপ করতে পারেন।

Content added By
টপ রেটেড অ্যাপ

স্যাট অ্যাকাডেমী অ্যাপ

আমাদের অল-ইন-ওয়ান মোবাইল অ্যাপের মাধ্যমে সীমাহীন শেখার সুযোগ উপভোগ করুন।

ভিডিও
লাইভ ক্লাস
এক্সাম
ডাউনলোড করুন
Promotion