23 Sep

PHP de try catch Kullanımı

<?php
// bunu belirttik, çünkü tarayıcıda türkçe karakter problemi yaşamak istemiyoruz
header ( 'Content-type:text/html; charset=UTF8' );
/**
 * örneklerimizde kullanacağımız iki tablo
 * bunları siz kendi sunucunuzda çalıştırıp
 * örnekleri uygulamak için kullanabilirsiniz
 */


$_veritabani = 'create database testdb';

$kullaniciTablosu = 'CREATE TABLE `testdb`.`user` (
`id` INTEGER  NOT NULL AUTO_INCREMENT,
`name` VARCHAR(25)  NOT NULL,
`password` VARCHAR(32)  NOT NULL,
PRIMARY KEY (`id`)
)
ENGINE = InnoDB;'
;

$gonderiTablosu = 'CREATE TABLE `testdb`.`user_posts` (
`id` INTEGER  NOT NULL AUTO_INCREMENT,
`user_id` INTEGER  NOT NULL,
`title` VARCHAR(255)  NOT NULL,
`content` TEXT  NOT NULL,
PRIMARY KEY (`id`)
)
ENGINE = InnoDB;'
;

$kullanici = 'kull';
$sifre = 'sifr';
$sorgu1 = 'delete from user where id=2';
$sorgu2 = 'delete from user_posts where user_id=2';
/**
 *
 *try catch , daha önce de kısaca değindiğim gibi bir hata yönetim mekanizmasıdır.
 *Uygulamnımızın kararlılığını arttırmak için hatayı yakalamak ve onu işlemek de önemlidir.
 *Tabi hatayı yakalamak ve işlemek sadece try catch ile olabilen birşey değil,
 * ama neden kullanmalı ona değinmeye çalışacağım.
 *
 * Normal kullanım
 */


$baglanti = mysql_connect ( 'localhost', $kullanici, $sifre );
if ($baglanti)
{
   if (! mysql_select_db ( 'testdb', $baglanti ))
      die ( 'Veritabanı seçemedi' );
} else
{
   die ( 'veritabanına bağlanamadı' );
}
/*
* Yeri gelmişken yazalım. mysql_unbuffered_query fonksiyonu, çalıştıracağınız sorgudan geriye
* veri döndürmeyecekseniz , işinize yarayabilecek bir fonksiyondur. Bu fonksiyon geriye
* bir sonuç kümesi döndürmez , onun yerine sorgunun sağlıklı çalışıp çalışmadığını
* belirten bir boolean değer döndürür.Böylece değer döndürmeyen sorgularınız daha hızlı çalışır.
*/

if (mysql_unbuffered_query ( $sorgu1, $baglanti ))
{
   if (mysql_unbuffered_query ( $sorgu2, $baglanti ))
   {
      echo 'Sorgular başarı ile çalıştırıldı';
   } else
   {
      echo 'sorgu 2 çalışmadı';
   }
} else
{
   echo 'sorgu 1 çalışmadı';
}

mysql_close ( $baglanti );

/**
 * Buraya kadar heşey normal gibi görünüyor. Normal olarak kabul de edebiliriz, kod karmaşasını saymaz isek.
 * Peki gelin bir de böyle deniyelim :
 */


try
{
   $veritabani = new PDO ( 'mysql:dbname=testdb;host=127.0.0.1', $kullanici, $sifre );
   $veritabani->setAttribute ( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION );
   $veritabani->beginTransaction ();
   try
   {
      if ($veritabani->exec ( $sorgu1 ) == 0)
         
         throw new Exception ( 'birinci sorgu çalışmadı' );
      echo 'sorgu 1 çalıştı <br />;';
      if ($veritabani->exec ( $sorgu2 ) == 0)
         
         throw new Exception ( 'ikinci sorgu çalışmadı' );
      echo 'sorgu 2 çalıştı';
      $veritabani->commit ();
   } catch ( Exception $istisna )
   {
      echo $istisna->getMessage ();
      $veritabani->rollBack ();
   }
} catch ( Exception $baglantiIstistisnasi )
{
   echo 'bağlantı sağlanamadı sebep : <br /><b>' . $baglantiIstistisnasi->getMessage () . '</b>';
}

/**
* Şimdi kod daha sade değil mi ? Gerçi bakıma ihtiyacı olsa da, bir önceki örneğimizden daha anlaşılır ve daha işlevsel.
* Şimdi gelelim işleyişe. Kod try bloğuna girer ve bir istisna (Exceptipon) fırlatıladılmadıkça o blok çalışmasına devam eder.
* Eğer başarılı olmuşsa kendisini takip eden catch bloğunu ( catch() {} ) es geçerek bir alt satıra geçer.
* Ama eğer try bloğu içerisinde bir Exception fırlatılır ise o zaman kod, Exception fırlatılan satırdan sonra (örneğin ilk sorgumuz
* çalışmadığında biz bir istisna fırlatıyoruz, böylece try bloku içerisindeki o satırdan sonraki kodlar çalıştırılmaz)
* catch bloğuna geçer.
*
* Bunu şöyle deneyebilirsiniz, bu örneği alıp kaydedin ve veritabanını oluşturun. Sonra da hiçbir kayıt girmeden örneği çalıştırın.
* Bu durumda size "birinci sorgu çalışmadı" diye bir mesaj verecek. Böylce yukarıda değindiğimiz gibi, try blokundaki kod exception
* fırlatılan satıra kadar çalışır , exception fırlatılırsa exception dan sonraki satır çalışmaz ve catch bloğuna geçer (böylece biz
* birinci sorgu çalıştı mesajını görmeyiz) ve bu blok çalışır.
*
* try catch işleminin sağlıklı yürüyebilmesi için, Exception fırlatan bir mekanizmanın olması gerekir. PHP 5. versiyonundan sonra
* nesne yönemli programlamaya  ağırlık verildiğinden, eski nesnelerin çoğu ile kullanmak mümkün değildir.
* Kimi yeni nesneler ve sizin kendi oluşturacağınız nesneler ile try catch mekanizmasını kullanabilirsiniz.
*
* Bu bölümde son olarak finally e değinmek istiyorum. Diğer dillerde (Java , C# gibi) try catch blokunun son halkası olan finally
* mevcuttur, bu blok ister try bloku çalışsın isterse catch bloku çalışsın buna bakılmaksızın en son ve her halukarda çalıştırılan
* bir bloktur. Ama bu işlev ne yazıkki php de mevcut değil henüz. Bu yüzden kısaca değinip geçiyorum.
*
* Bundan sonraki bölümde bu örneğimizden devam ederek, transaction e değinmeye çalışacağım. Sonrasında Exception nesnesini biraz açmaya
* çalışacağım. Eksik,hatalı veya karmaşık anlatılmış yerler konusunda yorum yazarak uyarır iseniz mutluluk duyarım.
*
* Güzel günler dileği ile.
*/

5 thoughts on “PHP de try catch Kullanımı

  1. makale için teşekkürler. rollback fonksiyonu tam olarak ne işe yarıyor onu anlayamadım. son işlemi geri filan mı alıyor?

  2. rollback işlemi mysql5 in desteklediği bir sistemdir, dediğiniz gibi yapılan değişiklikleri (O bağlantı esnasında yapılmış bütün sorgular) geri alır. Örneğin bir bağlantı açtınız, A tablosuna veri girdiniz, B tablosundan bir satır sildiniz, rollback yaptığınızda A tablosuna girdiğiniz satır silinir, B tablosundan sildiğiniz satır geri alınır.

  3. $istisna->getMessage() fonksiyonu ile hatayı ekrana bastırmayıp da bir log dosyasına da kayıt edebiliriz galiba değil mi?

Comments are closed.