iBATIS - SQL Dinamis

SQL dinamis adalah fitur iBATIS yang sangat kuat. Terkadang Anda harus mengubah kriteria klausa WHERE berdasarkan status objek parameter Anda. Dalam situasi seperti itu, iBATIS menyediakan satu set tag SQL dinamis yang dapat digunakan dalam pernyataan yang dipetakan untuk meningkatkan kegunaan kembali dan fleksibilitas SQL.

Semua logika dimasukkan ke dalam file .XML menggunakan beberapa tag tambahan. Berikut adalah contoh di mana pernyataan SELECT akan bekerja dalam dua cara -

  • Jika Anda meneruskan ID, maka itu akan mengembalikan semua catatan yang sesuai dengan ID itu.
  • Jika tidak, itu akan mengembalikan semua catatan di mana ID karyawan diatur ke NULL.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE sqlMap PUBLIC "-//ibatis.apache.org//DTD SQL Map 2.0//EN" "http://ibatis.apache.org/dtd/sql-map-2.dtd">

<sqlMap namespace="Employee">

   <select id="findByID" resultClass="Employee">
      SELECT * FROM EMPLOYEE
		
      <dynamic prepend="WHERE ">
         <isNull property="id">
            id IS NULL
         </isNull>
			
         <isNotNull property="id">
            id = #id#
         </isNotNull>
      </dynamic>
		
   </select>
</sqlMap>

Anda dapat memeriksa kondisi menggunakan tag <isNotEmpty> sebagai berikut. Di sini kondisi hanya akan ditambahkan jika properti yang diteruskan tidak kosong.

..................
<select id="findByID" resultClass="Employee">
   SELECT * FROM EMPLOYEE
	
   <dynamic prepend="WHERE ">
      <isNotEmpty property="id">
         id = #id#
      </isNotEmpty>
   </dynamic>
	
</select>
..................

Jika Anda menginginkan kueri tempat kami dapat memilih id dan / atau nama depan Karyawan, pernyataan SELECT Anda adalah sebagai berikut -

..................
<select id="findByID" resultClass="Employee">
   SELECT * FROM EMPLOYEE
	
   <dynamic prepend="WHERE ">
      <isNotEmpty prepend="AND" property="id">
         id = #id#
      </isNotEmpty>
		
      <isNotEmpty prepend="OR" property="first_name">
         first_name = #first_name#
      </isNotEmpty>
   </dynamic>
</select>
..................

Contoh SQL Dinamis

Contoh berikut menunjukkan bagaimana Anda dapat menulis pernyataan SELECT dengan SQL dinamis. Pertimbangkan, kami memiliki tabel EMPLOYEE berikut di MySQL -

CREATE TABLE EMPLOYEE (
   id INT NOT NULL auto_increment,
   first_name VARCHAR(20) default NULL,
   last_name  VARCHAR(20) default NULL,
   salary     INT  default NULL,
   PRIMARY KEY (id)
);

Anggaplah tabel ini hanya memiliki satu record sebagai berikut -

mysql> select * from EMPLOYEE;
+----+------------+-----------+--------+
| id | first_name | last_name | salary |
+----+------------+-----------+--------+
|  1 | Zara       | Ali       |   5000 |
+----+------------+-----------+--------+
1 row in set (0.00 sec)

Kelas POJO Karyawan

Untuk melakukan operasi baca, mari kita memiliki kelas Karyawan di Employee.java sebagai berikut -

public class Employee {
   private int id;
   private String first_name; 
   private String last_name;   
   private int salary;  

   /* Define constructors for the Employee class. */
   public Employee() {}
  
   public Employee(String fname, String lname, int salary) {
      this.first_name = fname;
      this.last_name = lname;
      this.salary = salary;
   }

   /* Here are the method definitions */
   public int getId() {
      return id;
   }
	
   public String getFirstName() {
      return first_name;
   }
	
   public String getLastName() {
      return last_name;
   }
	
   public int getSalary() {
      return salary;
   }
	
} /* End of Employee */

File Employee.xml

Untuk mendefinisikan pernyataan pemetaan SQL menggunakan iBATIS, kami akan menambahkan tag <select> yang dimodifikasi berikut di Employee.xml dan di dalam definisi tag ini, kami akan mendefinisikan "id" yang akan digunakan di IbatisReadDy.java untuk mengeksekusi kueri Dynamic SQL SELECT pada database.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE sqlMap PUBLIC "-//ibatis.apache.org//DTD SQL Map 2.0//EN" "http://ibatis.apache.org/dtd/sql-map-2.dtd">

<sqlMap namespace="Employee">
   <select id="findByID" resultClass="Employee">
      SELECT * FROM EMPLOYEE
	
      <dynamic prepend="WHERE ">
         <isNotNull property="id">
            id = #id#
         </isNotNull>
      </dynamic>
		
   </select>
</sqlMap>

Pernyataan SELECT di atas akan bekerja dalam dua cara -

  • Jika Anda meneruskan ID, maka itu mengembalikan catatan yang sesuai dengan ID itu Jika tidak, itu mengembalikan semua catatan.

Berkas IbatisReadDy.java

File ini memiliki logika tingkat aplikasi untuk membaca catatan bersyarat dari tabel Karyawan -

import com.ibatis.common.resources.Resources;
import com.ibatis.sqlmap.client.SqlMapClient;
import com.ibatis.sqlmap.client.SqlMapClientBuilder;

import java.io.*;
import java.sql.SQLException;
import java.util.*;

public class IbatisReadDy{
   public static void main(String[] args) throws IOException,SQLException{
   
      Reader rd=Resources.getResourceAsReader("SqlMapConfig.xml");
      SqlMapClient smc=SqlMapClientBuilder.buildSqlMapClient(rd);

      /* This would read all records from the Employee table.*/
      System.out.println("Going to read records.....");
      Employee rec = new Employee();
      rec.setId(1);

      List <Employee> ems = (List<Employee>)  
         smc.queryForList("Employee.findByID", rec);
      Employee em = null;
		
      for (Employee e : ems) {
         System.out.print("  " + e.getId());
         System.out.print("  " + e.getFirstName());
         System.out.print("  " + e.getLastName());
         System.out.print("  " + e.getSalary());
         em = e; 
         System.out.println("");
      }    
      System.out.println("Records Read Successfully ");
   }
}

Kompilasi dan Jalankan

Berikut adalah langkah-langkah untuk mengkompilasi dan menjalankan perangkat lunak yang disebutkan di atas. Pastikan Anda telah mengatur PATH dan CLASSPATH dengan benar sebelum melanjutkan untuk kompilasi dan eksekusi.

  • Buat Employee.xml seperti yang ditunjukkan di atas.
  • Buat Employee.java seperti yang ditunjukkan di atas dan kompilasi.
  • Buat IbatisReadDy.java seperti yang ditunjukkan di atas dan kompilasi.
  • Jalankan biner IbatisReadDy untuk menjalankan program.

Anda akan mendapatkan hasil berikut, dan record akan dibaca dari tabel EMPLOYEE.

Going to read records.....
   1  Zara  Ali  5000
Record Reads Successfully

Coba contoh di atas dengan melewatkan nullsebagai smc.queryForList ("Employee.findByID", null) .

Ekspresi iBATIS OGNL

iBATIS menyediakan ekspresi berbasis OGNL yang kuat untuk menghilangkan sebagian besar elemen lainnya.

  • jika Pernyataan
  • pilih, kapan, sebaliknya Pernyataan
  • dimana Pernyataan
  • Pernyataan foreach

Pernyataan if

Hal yang paling umum dilakukan dalam SQL dinamis adalah menyertakan bagian klausa where. Misalnya -

<select id="findActiveBlogWithTitleLike" parameterType="Blog" resultType="Blog">
   SELECT * FROM BLOG
   WHERE state = 'ACTIVE.
	
   <if test="title != null">
      AND title like #{title}
   </if>
	
</select>

Pernyataan ini menyediakan jenis fungsionalitas pencarian teks opsional. Jika Anda tidak memasukkan judul, maka semua Blog aktif akan dikembalikan. Tetapi jika Anda mengirimkan judul, itu akan mencari judul dengan yang diberikanlike kondisi.

Anda dapat menyertakan beberapa if kondisi sebagai berikut -

<select id="findActiveBlogWithTitleLike" parameterType="Blog" resultType="Blog">
   SELECT * FROM BLOG
   WHERE state = 'ACTIVE.
	
   <if test="title != null">
      AND title like #{title}
   </if>
	
   <if test="author != null">
      AND author like #{author}
   </if>
	
</select>

Pilih, kapan, dan sebaliknya Pernyataan

iBATIS menawarkan a chooseelemen yang mirip dengan pernyataan switch Java. Ini membantu memilih hanya satu kasus di antara banyak opsi.

Contoh berikut akan mencari hanya menurut judul jika ada, lalu hanya menurut penulis jika ada. Jika tidak ada yang disediakan, itu hanya mengembalikan blog unggulan -

<select id="findActiveBlogWithTitleLike" parameterType="Blog" resultType="Blog">
   SELECT * FROM BLOG
   WHERE state = 'ACTIVE.
	
   <choose>
      <when test="title != null">
         AND title like #{title}
      </when>
		
      <when test="author != null and author.name != null">
         AND author like #{author}
      </when>
		
      <otherwise>
         AND featured = 1
      </otherwise>
   </choose>
	
</select>

Pernyataan dimana

Lihat contoh kami sebelumnya untuk melihat apa yang terjadi jika tidak ada ketentuan yang terpenuhi. Anda akan mendapatkan SQL yang terlihat seperti ini -

SELECT * FROM BLOG
WHERE

Ini akan gagal, tetapi iBATIS memiliki solusi sederhana dengan satu perubahan sederhana, semuanya berfungsi dengan baik -

<select id="findActiveBlogLike" parameterType="Blog" resultType="Blog">
   SELECT * FROM BLOG
	
   <where>
      <if test="state != null">
         state = #{state}
      </if>
		
      <if test="title != null">
         AND title like #{title}
      </if>
		
      <if test="author != null>
         AND author like #{author}
      </if>
   </where>
	
</select>

Itu whereelemen menyisipkan WHERE hanya ketika tag yang mengandung mengembalikan konten apa pun. Selain itu, jika konten tersebut dimulai dengan DAN atau ATAU, ia tahu untuk menghapusnya.

Pernyataan foreach

Elemen foreach memungkinkan Anda untuk menentukan koleksi dan mendeklarasikan variabel item dan indeks yang dapat digunakan di dalam tubuh elemen.

Ini juga memungkinkan Anda untuk menentukan string pembuka dan penutup, dan menambahkan pemisah untuk ditempatkan di antara iterasi. Anda bisa membangunIN kondisi sebagai berikut -

<select id="selectPostIn" resultType="domain.blog.Post">
   SELECT *
   FROM POST P
   WHERE ID in
	
   <foreach item="item" index="index" collection="list"
      open="(" separator="," close=")">
      #{item}
   </foreach>
	
</select>