Soruyu cevaplamadan önce, arka planın düzgün olduğunu düşünüyorum.
Sorunun Özü
Yıllarca geliştiricilerle röportaj yaptıktan ve işe aldıktan sonra iki şey öğrendim:
Geliştiricilerin büyük çoğunluğu veritabanı tasarımı konusunda çok az deneyime sahiptir.
Veritabanlarını anlamayanlar ile ORM'lerden nefret edenler arasında gevşek bir ilişki olduğunu fark ettim .
(Not: ve evet, ORM'lerden nefret eden veritabanlarını çok iyi anlayanlar olduğunu biliyorum)
İnsanlar içinde üretici adını gömmek niye yabancı anahtarlar, neden önemli olduğunu anlamıyorum ne zaman item
masaya, ya da neden customer.address1
, customer.address2
ve customer.address3
alanlar yazma veritabanı hataları onlar için daha kolay hale getirmek için bir ORM ekleyerek, iyi bir fikir değildir hiçbir şey yardım etmeyecek.
Bunun yerine, uygun şekilde tasarlanmış bir veritabanı ve bir OLTP kullanım durumu ile ORM'ler altındır. Çoğu homurdanma çalışması gider ve DBIx :: Class :: Schema :: Loader gibi araçlarla , iyi bir veritabanı şemasından dakikalar içinde Perl kodunu çalıştırabilirim. Pareto Kuralından bahsederim ve problemlerimin% 80'inin işin% 20'si ile çözüldüğünü söylerdim, ancak gerçekte, faydaları bundan daha da fazla buluyorum.
Çözümü Kötüye Kullanma
Bazı insanların ORM'lerden nefret etmesinin bir başka nedeni de soyutlamanın sızmasına izin vermesidir. MVC web uygulamalarının ortak durumunu ele alalım. İşte yaygın olarak gördüğümüz bir şey (sözde kod):
GET '/countries/offices/$company' => sub {
my ( $app, $company_slug ) = @_;
my $company = $app->model('Company')->find({ slug => $company_slug })
or $app->redirect('/');
my $countries = $app->model('Countries')->search(
{
'company.company_id' => $company->company_id,
},
{
join => [ offices => 'company' ],
order_by => 'me.name',
},
);
$app->stash({
company => $company,
countries => $country,
});
}
İnsanlar bunun gibi kontrolör rotaları yazıyor ve iyi, temiz kod olduğunu düşünüyorlar. Denetleyicilerinde sabit kodlama SQL'de dehşete düşeceklerdi, ancak farklı bir SQL sözdizimini ortaya koymaktan çok daha fazlasını yapmamışlardı. ORM kodlarının bir modele aktarılması gerekir ve daha sonra bunu yapabilirler:
GET '/countries/offices/$company' => sub {
my ( $app, $company_slug ) = @_;
my $result = $app->model('Company')->countries($company_slug)
or $app->redirect('/');
$app->stash({ result => $result });
}
Şimdi ne olduğunu biliyor musun? Modelinizi düzgün bir şekilde kapsüllediniz, ORM'yi açığa çıkarmadınız ve daha sonra, bu verileri veritabanı yerine bir önbellekten alabileceğinizi fark ettiğinizde, denetleyici kodunuzu değiştirmeniz gerekmez (ve daha kolay bunun için testler yazmak ve mantığı yeniden kullanmak).
Gerçekte, insanların ORM kodlarını tüm denetleyicilerine (ve görünümlerine) sızdırmaları ve ölçeklenebilirlik sorunlarına çarptıklarında, mimarilerinden ziyade ORM'yi suçlamaya başlamasıdır. ORM kötü bir rap alır (Bunu birçok müşteri için tekrar tekrar görüyorum). Bunun yerine, ORM sınırlarını gerçekten vurduğunuzda, kodun bağlandığınız ORM ile çok sıkı bir şekilde eşleştirilmesine izin vermek yerine sorununuz için uygun çözümleri seçebilmeniz için bu soyutlamayı gizleyin.
Raporlama ve Diğer Sınırlamalar
Rob Kinyon'un yukarıda açıkladığı gibi, raporlama ORM'lerde zayıflık eğilimindedir. Bu, birden çok tabloya yayılan karmaşık SQL veya SQL'in bazen ORM'lerle iyi çalışmadığı daha büyük bir sorunun alt kümesidir. Örneğin, ORM bazen istemediğim bir birleştirme türünü zorlar ve bunu nasıl düzeltebileceğimi söyleyemem. Ya da belki MySQL'de bir indeks ipucu kullanmak istiyorum , ama bu kolay değil . Ya da bazen SQL o kadar karmaşıktır ki, sağlanan soyutlama yerine SQL yazmak daha iyi olur.
Bu DBIx :: Class :: Report yazmaya başlamamın bir parçasıdır . Şimdiye kadar iyi çalışıyor ve insanların burada yaşadıkları sorunların çoğunu çözüyor (salt okunur bir arayüzle iyi oldukları sürece). Ve bir koltuk değneği gibi görünse de, gerçekte, soyutlamadan sızmadığınız sürece (önceki bölümde açıklandığı gibi), çalışmayı DBIx::Class
daha da kolaylaştırır.
Peki DBIx :: Class'ı Ne Zaman Seçerim?
Benim için, çoğu zaman bir veritabanına bir arayüze ihtiyaç duyduğumu seçerdim . Yıllardır kullanıyorum. Bununla birlikte, bir OLAP sistemi için seçemeyebilirim ve yeni programcılar kesinlikle onunla mücadele edecek. Ayrıca, sık sık meta-programlamaya ihtiyacım olduğunu görüyorum ve DBIx::Class
araçları sağlarken , çok kötü belgeleniyorlar.
DBIx::Class
Doğru kullanmanın anahtarı çoğu ORM için olanla aynıdır:
Soyutlamayı sızdırmayın.
Lanet olasý testlerini yaz.
Gerektiğinde SQL'e nasıl bırakılacağını bilin.
Bir veritabanını nasıl normalleştireceğinizi öğrenin.
DBIx::Class
, bir kez öğrendikten sonra, ağır kaldırma işlemlerinizin çoğunu sizin için halledecek ve uygulamaları hızlı bir şekilde yazmayı bir esinti haline getirecektir.