Rumah  >  Artikel  >  pembangunan bahagian belakang  >  Cara Mengendalikan Pertanyaan S/DQL Tersuai Pada Enjin Pangkalan Data Berbeza dengan DoctrineExpression

Cara Mengendalikan Pertanyaan S/DQL Tersuai Pada Enjin Pangkalan Data Berbeza dengan DoctrineExpression

Mary-Kate Olsen
Mary-Kate Olsenasal
2024-10-28 08:45:02601semak imbas

How To Handle Custom S/DQL Queries On Different Database Engine with DoctrineExpression

Dalam perjalanan membina projek Symfony yang mantap, selalunya terdapat satu titik di mana kaedah Repositori Entiti yang mudah seperti findBy() tidak lagi mencukupi. Bagi saya, titik itu tiba, dan saya mencapai kuasa pertanyaan DQL tersuai untuk mengendalikan keperluan mendapatkan data yang lebih kompleks. Pada masa itu, saya menggunakan MySQL sebagai pangkalan data lalai saya. Semuanya berfungsi dengan sempurna sehingga saya menyimpan projek saya dan memutuskan untuk beralih kepada PostgreSQL untuk prestasi dan fleksibiliti ciri.

Tetapi, oh tidak! Pertanyaan DQL saya serta-merta mula membuang ralat ?‍?. Apa yang silap? Sintaks DQL tersuai saya telah direka dengan sempurna untuk ciri dan fungsi MySQL tetapi tidak serasi dengan PostgreSQL. Pilihannya kini antara dua laluan yang mencabar:

Pilihan 1: Kembali ke MySQL untuk memastikan keadaan selamat.

Tetapi bagaimana jika saya ingin berkongsi projek dengan pembangun yang lebih suka PostgreSQL?

Pilihan 2: Tulis semula DQL saya untuk menyokong PostgreSQL.

Tetapi, bagaimana jika saya perlu menukar kembali kepada MySQL nanti? Atau bagaimana jika saya menggunakan alat yang hanya menyokong MySQL?

Memilih antara ini bukanlah mudah—kedua-dua pilihan boleh mengunci saya ke dalam satu persekitaran pangkalan data, mengehadkan kefleksibelan dalam pilihan teknologi masa hadapan. Jadi, saya memutuskan untuk mengambil pendekatan yang berbeza dan mencipta penyelesaian untuk mengendalikan pertanyaan khusus pangkalan data secara dinamik dengan cara yang bersih dan boleh digunakan semula.


Memperkenalkan DoctrineExpression

DoctrineExpression ialah perpustakaan PHP yang direka untuk mendayakan pertanyaan DQL dan SQL agnostik silang platform, pangkalan data dan SQL dalam Symfony atau mana-mana projek yang menggunakan doktrin. Dengan DoctrineExpression, anda boleh menentukan sintaks tersuai untuk setiap platform pangkalan data (MySQL, PostgreSQL, SQLite, dll.), dan ia akan memilih ungkapan yang betul berdasarkan pemacu pangkalan data semasa. Ia berfungsi seperti ini:

  1. Tentukan Berbilang Ungkapan: Tulis sintaks yang berbeza untuk setiap pemacu pangkalan data, nyatakan pertanyaan unik yang sepadan dengan fungsi dan kebiasaan setiap platform.
  2. Pengesanan Pemacu Automatik: DoctrineExpression menyemak platform Doctrine yang sedang digunakan, kemudian secara automatik menggunakan sintaks yang betul untuk MySQL, PostgreSQL atau mana-mana pangkalan data lain yang disokong.
  3. Fleksibiliti Bukti Masa Depan: Dengan membenarkan anda menukar pangkalan data dengan mudah, DoctrineExpression membuktikan kod anda pada masa hadapan, memastikan anda boleh menyokong berbilang pangkalan data tanpa penulisan semula yang meluas.

Kini, dengan DoctrineExpression, saya mempunyai fleksibiliti untuk menggunakan MySQL atau PostgreSQL (atau bahkan SQLite), memastikan kod saya bersih dan boleh diselenggara. Saya boleh menukar platform berdasarkan keperluan projek, keutamaan pasukan atau pertimbangan prestasi tanpa perlu risau tentang pemfaktoran semula setiap pertanyaan tersuai.

Bagaimana DoctrineExpression Menyelesaikan Masalah

Mari kita lihat contoh mudah di mana kita perlu mendapatkan semula pengguna yang mendaftar dalam tempoh 24 jam yang lalu. Ini selalunya dikendalikan secara berbeza dalam MySQL dan PostgreSQL.


Tanpa DoctrineExpression

  1. MySQL: Menggunakan DATE_SUB(NOW(), INTERVAL 1 DAY) untuk mencari rekod dalam masa 24 jam yang lalu.
  2. PostgreSQL: Menggunakan NOW() - INTERVAL '1 hari' untuk pertanyaan yang sama.

Begini cara anda boleh menulis ini secara berasingan tanpa DoctrineExpression:

// MySQL Query
$mysqlQuery = $entityManager->createQuery(
    "SELECT u FROM App\Entity\User u WHERE u.registeredAt > DATE_SUB(NOW(), INTERVAL 1 DAY)"
);

Jika anda menggunakan PostgreSQL, anda akan menulis dalam format ini:

// PostgreSQL Query
$postgresQuery = $entityManager->createQuery(
    "SELECT u FROM App\Entity\User u WHERE u.registeredAt > NOW() - INTERVAL '1 day'"
);

Jika anda menukar pangkalan data, anda perlu mengubah suai kod ini, yang menyusahkan dan mudah ralat.


Dengan DoctrineExpression

Dengan DoctrineExpression, anda mentakrifkan kedua-dua sintaks dan biarkan pustaka mengendalikan selebihnya:

use Ucscode\DoctrineExpression\DoctrineExpression;
use Ucscode\DoctrineExpression\DriverEnum;

// Create an expression instance with an EntityManager argument
$expression = new DoctrineExpression($entityManager);

// Registration S/DQL for varying database
$expression
    ->defineQuery(DriverEnum::PDO_MYSQL, function($entityManager) {
        return $entityManager->createQuery(
            "SELECT u FROM App\Entity\User u WHERE u.registeredAt > DATE_SUB(NOW(), INTERVAL 1 DAY)"
        );
    })
    ->defineQuery(DriverEnum::PDO_PGSQL, function($entityManager) {
        return $entityManager->createQuery(
            "SELECT u FROM App\Entity\User u WHERE u.registeredAt > NOW() - INTERVAL '1 day'"
        );
    });

// Fet any of the defined query based on the active doctine driver being used
$query = $expression->getCompatibleResult();

Kini, DoctrineExpression menyemak platform pangkalan data yang sedang digunakan dan secara dinamik memasukkan sintaks yang betul untuk persekitaran semasa. Tidak penting lagi anda menggunakan MySQL atau PostgreSQL, ia akan memilih ungkapan yang betul, menjimatkan anda daripada perlu mengubah suai pertanyaan anda setiap kali anda menukar platform dan juga menghilangkan pelat dandang menggunakan if-else berulang kali

Kesimpulannya:

DoctrineExpression menjimatkan masa dan usaha dengan membenarkan anda menggunakan pangkalan data yang berbeza tanpa menulis semula pertanyaan anda. Ia amat berguna dalam projek kontena atau berbilang persekitaran di mana anda perlu menggunakan sintaks tersuai tetapi pilihan pangkalan data mungkin berubah bergantung pada keperluan penggunaan atau kebiasaan pasukan. Cubalah, dan beritahu saya cara ia berfungsi untuk anda!

Lihat DoctrineExpression di GitHub

Selamat mengekod!

Atas ialah kandungan terperinci Cara Mengendalikan Pertanyaan S/DQL Tersuai Pada Enjin Pangkalan Data Berbeza dengan DoctrineExpression. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn