Jak pracujφ databßze na Webu
Zp°φstupn∞nφ databßze p°es webovΘ rozhranφ

Ji°φ Kosek ml.

V minulΘm dφle jsme si ukßzali, jak p°istupovat k databßzi pomocφ nativnφho ovladaΦe v PHP. Rovn∞₧ jsme nakousli zp∙sob p°ipojenφ databßze p°es rozhranφ ODBC v ASP. Dnes dokonΦφme prßci s ODBC v ASP a pak si ukß₧eme, jak vyu₧φvat rozhranφ ODBC v PHP. P°edtφm se jeÜt∞ seznßmφme s n∞kter²mi d∙vody, kterΘ hovo°φ pro pou₧φvßnφ ODBC p°i p°φstupu k databßzφm.

V ASP se ji₧ umφme p°ipojit k databßzi a provΘst v nφ dotaz. V²sledek dotazu je nynφ p°φstupn² pomocφ objektu vysledek. P°i prßci s databßzemi p°es ODBC nem∙₧eme p°istupovat nßhodn∞ k libovolnΘmu zßznamu v²sledku, ale musφme je prochßzet postupn∞. K pohybu na dalÜφ zßznam v²sledku slou₧φ metoda MoveNext. Pomocφ metody EOF m∙₧eme zjistit, zda v²sledek obsahuje jeÜt∞ n∞jakΘ nezpracovanΘ zßznamy. K jednotliv²m polo₧kßm aktußlnφho zßznamu se dostaneme pomocφ volßnφ vysledek.fields("jmΘno_polo₧ky"). Skript pro vypsßnφ obsahu tabulky vypadß v ASP nßsledovn∞:

<HTML>
<HEAD>
<TITLE>V²pis vÜech zam∞stnanc∙</TITLE>
</HEAD>
<BODY>
<H1>V²pis vÜech zam∞stnanc∙</H1>
<TABLE BORDER=1 CELLPADDING=2>
<TR><TH>Osobnφ Φφslo</TH>
    <TH>JmΘno</TH>
    <TH>RodnΘ Φφslo</TH>
    <TH>Adresa</TH>
    <TH>Plat</TH>
</TR>    
<%
Set spojeni = Server.CreateObject("ADODB.Connection")
spojeni.Open "DSN=test"
Set vysledek = Server.CreateObject("ADODB.Recordset")
vysledek.Open "SELECT * FROM Zamestnanci", spojeni
Do Until vysledek.EOF   
  Response.Write "<TR>" & vbNewLine 
  Response.Write "<TD ALIGN=CENTER>" 
  Response.Write vysledek.fields("OsobniCislo")
  Response.Write "</TD>" & vbNewLine 
  Response.Write "<TD>" & vysledek.fields("Jmeno")
  Response.Write "</TD>" & vbNewLine 
  Response.Write "<TD>" & vysledek.fields("RC")
  Response.Write "</TD>" & vbNewLine 
  Response.Write "<TD>" & vysledek.fields("Adresa")
  Response.Write "</TD>" & vbNewLine 
  Response.Write "<TD ALIGN=RIGHT>" 
  Response.Write vysledek.fields("Plat")
  Response.Write "</TD>" & vbNewLine 
  Response.Write "</TR>" & vbNewLine
  vysledek.MoveNext
Loop
%>
</TABLE>
</BODY>
</HTML>

Velkou v²hodou ODBC je, ₧e stejn²m zp∙sobem m∙₧eme p°istupovat k libovolnΘ databßzi. Pokud se tedy z n∞jakΘho d∙vodu zm∞nφ SQL-server, na kterΘm b∞₧φ naÜe aplikace, nemusφme m∞nit v PHP-skriptech ₧ßdn² k≤d. StaΦφ upravit mapovßnφ datov²ch zdroj∙ na databßze v konfiguraΦnφm programu ODBC.

PoΦßteΦnφ nev²hodou, kterß mluvila proti pou₧itφ ODBC, byl ni₧Üφ v²kon oproti nativnφm ovladaΦ∙m. StarΘ ODBC ovladaΦe slou₧ily pouze jako mezistupe≥ mezi aplikacφ a nativnφm protokolem databßze. Nov∞jÜφ ODBC ovladaΦ jsou vÜak optimalizovßny a k databßzovΘmu serveru p°istupujφ p°φmo -- jejich v²kon je srovnateln² s pou₧itφm nativnφch ovladaΦ∙.

Poslednφ otßzka, kterß se nabφzφ, se t²kß vyu₧itelnosti ODBC na jin²ch platformßch ne₧ jsou Windows. ODBC bylo p∙vodn∞ vyvinuto pro platformu Windows, ale dnes jeho implementace existuje i pro vÜechny v²znamn∞jÜφ verze operaΦnφho systΘmu Unix.

Podφvejme se nynφ, jak se rozhranφ ODBC pou₧φvß v systΘmu PHP. Nßzvy vÜechny funkcφ pro prßci s ODBC a₧ neuv∞°iteln∞ zaΦφnajφ pφsmeny ODBC. Nejprve se musφme p°ipojit k datovΘmu zdroji pomocφ funkce ODBC_Connect(). Ta mß t°i parametry -- jmΘno datovΘho zdroje, jmΘno a heslo u₧ivatele, pod kter²m se ke zdroji p°ipojujeme. Funkce vracφ identifikßtor spojenφ. Pokud se ke zdroji nelze p°ipojit, vracφ funkce hodnotu false.

Vrßcenφ tΘto hodnoty bychom m∞li v₧dy oÜet°it, proto₧e se m∙₧e stßt, ₧e se nepoda°φ k databßzovΘmu serveru p°ipojit. V naÜich skriptech bychom m∞li v₧dy testovat a oÜet°it vÜechny mo₧nΘ chybovΘ stavy -- jen tak se poznß dob°e napsanß aplikace.

K provßd∞nφ SQL-dotaz∙ slou₧φ funkce ODBC_Exec(). Jejφmi parametry jsou identifikßtor spojenφ a SQL-dotaz. Funkce vracφ v²sledek dotazu. Pokud p°i provßd∞nφ SQL-dotazu doÜlo k chyb∞, vracφ funkce false -- dalÜφ mφsto v naÜem skriptu, kde bychom m∞li testovat chyby.

K zφskßnφ jednΘ °ßdky v²sledku slou₧φ funkce ODBC_Fetch_Row(vysledek). Funkce vracφ true, pokud se poda°ilo zφskat dalÜφ zßznam. Pro p°φstup k polo₧kßm aktußlnφho zßznamu slou₧φ funkce ODBC_Result(vysledek, polo₧ka).

V²sledn² skript je o n∞co delÜφ ne₧ p°edchozφ, proto₧e jsme do n∞j p°idali nezbytnΘ oÜet°enφ chyb -- znovu opakuji, ₧e by nem∞lo chyb∞t v ₧ßdnΘm skriptu.

<HTML>
<HEAD>
<TITLE>V²pis vÜech zam∞stnanc∙</TITLE>
</HEAD>
<BODY>
<H1>V²pis vÜech zam∞stnanc∙</H1>
<TABLE BORDER=1 CELLPADDING=2>
<TR><TH>Osobnφ Φφslo</TH>
    <TH>JmΘno</TH>
    <TH>RodnΘ Φφslo</TH>
    <TH>Adresa</TH>
    <TH>Plat</TH>
</TR>    
<?
@$spojeni = ODBC_Connect("test", "", "");
if (!$spojeni):
  echo "<TR><TH COLSPAN=5>Nepoda°ilo se p°ipojit
  		k databßzi!</TH></TR>";
else:
  @$vysledek = ODBC_Exec($spojeni, 
                  "SELECT * FROM Zamestnanci");
  if (!$vysledek):                
    echo "<TR><TH COLSPAN=5>Chyba p°i provßd∞nφ
    	  SQL-dotazu!</TH></TR>";
  else:
    while(ODBC_Fetch_Row($vysledek)):
      echo "<TR>\n";
      echo "<TD ALIGN=CENTER>". 
           ODBC_Result($vysledek, "OsobniCislo").
           "</TD>\n";
      echo "<TD>".ODBC_Result($vysledek, "Jmeno").
           "</TD>\n";
      echo "<TD>".ODBC_Result($vysledek, "RC").
            "</TD>\n";
      echo "<TD>".ODBC_Result($vysledek, "Adresa").
           "</TD>\n";
      echo "<TD ALIGN=RIGHT>".
           ODBC_Result($vysledek, "Plat").
           "</TD>\n";        
      echo "</TR>\n";
    endwhile;
  endif;  
  ODBC_Close($spojeni);
endif;
?>
</TABLE>
</BODY>
</HTML>
Zajφmavostφ je pou₧itφ zavinßΦe (@) p°ed p°φkazy, kterΘ nemusφ b²t v₧dy provedeny ·sp∞Ün∞. ZavinßΦ potlaΦφ vypsßnφ chybovΘho hlßÜenφ PHP, kterΘ m∙₧e b∞₧nΘho u₧ivatele zd∞sit. LepÜφ je chybu oÜet°it po svΘm a u₧ivatele informovat n∞jak²m srozumiteln²m zp∙sobem. Na obrßzku 1 si m∙₧ete prohlΘdnout, jak strßnka dopadne, kdy₧ dojde k chyb∞ a nepou₧ijeme zavinßΦ.

Obr. 1: Standardnφ chybovΘ hlßÜky by se nikdy nem∞ly dostat k b∞₧nΘmu u₧ivateli
Standardnφ chybovΘ hlßÜky by se nikdy nem∞ly dostat k b∞₧nΘmu u₧ivateli

Do skriptu lze vlo₧it libovoln² SQL-p°φkaz a tak m∙₧eme pomocφ skript∙ provßd∞t s tabulkami v databßzi libovolnΘ operace. Nynφ si ukß₧eme, jak m∙₧eme p°es webovΘ rozhranφ jednoduÜe p°idßvat novΘ zßznamy do tabulky Zamestnanci. Nejprve vytvo°φme formulß°, kter² bude slou₧it k zadßnφ ·daj∙ o novΘm zam∞stnanci u₧ivatelem. Ulo₧φme jej nap°. do souboru 15-02.php3:

<HTML>
<HEAD>
<TITLE>P°idßnφ novΘho zßznamu do tabulky Zamestnanci</TITLE>
</HEAD>
<BODY>
<H1>P°idßnφ novΘho zßznamu do tabulky Zamestnanci</H1>
<STRONG>Zadejte ·daje o novΘm zam∞stnanci:</STRONG>
<FORM ACTION=15-03.php3>
<TABLE>
<TR><TD>Osobnφ Φφslo:<TD><INPUT NAME=OsobniCislo>
<TR><TD>JmΘno:<TD><INPUT NAME=Jmeno>
<TR><TD>RodnΘ Φφslo:<TD><INPUT NAME=RC>
<TR><TD>Adresa:<TD><INPUT NAME=Adresa>
<TR><TD>Plat:<TD><INPUT NAME=Plat>
<TR><TH COLSPAN=2><INPUT TYPE=Submit VALUE="P°idßnφ zam∞stnance">
</TABLE>
</FORM>
</BODY>
</HTML>
K obsluze formulß°e slou₧φ skript 15-03.php3, kter² obstarß samotnΘ vlo₧enφ ·daj∙ z formulß°e do tabulky:
<HTML>
<HEAD>
<TITLE>P°idßnφ novΘho zßznamu do tabulky Zamestnanci</TITLE>
</HEAD>
<BODY>
<?
@$spojeni = ODBC_Connect("test", "", "");
if (!$spojeni):
  echo "<H1>Nepoda°ilo se p°ipojit 
            k databßzi!</H1>";
else:
  @$vysledek = ODBC_Exec($spojeni,
    	        "INSERT INTO Zamestnanci VALUES(
       	          $OsobniCislo, '$Jmeno', '$RC',
       	          '$Adresa', $Plat)");
  if (!$vysledek):
    echo "<H1>Nov² zßznam se 
              nepoda°ilo p°idat!</H1>";
  else: ?>
    <H1>Nov² zßznam byl ·sp∞Ün∞ p°idßn</H1>
    <FORM ACTION=15-01.php3>
    <INPUT TYPE=Submit 
           VALUE="Prohlφ₧enφ seznamu zam∞stnanc∙">
    </FORM>
    <FORM ACTION=15-01.php3>
    <INPUT TYPE=Submit 
           VALUE="P°idßnφ novΘho zam∞stnance">
    </FORM>
<?
  endif;
  ODBC_Close($spojeni);
endif;
?>
</BODY>
</HTML>
Do strßnky jsme navφc pomocφ formulß°∙ vlo₧ili dv∞ tlaΦφtka, kterß slou₧φ k vyvolßnφ skriptu pro v²pis obsahu naÜφ tabulky resp. pro p°idßnφ dalÜφho zam∞stnance.

Obr. 2: Formulß° pro p°idßnφ novΘho zßznamu
Formulß° pro p°idßnφ novΘho zßznamu

Obr. 3: V²stup skriptu pro p°idßnφ zßznamu
V²stup skriptu pro p°idßnφ zßznamu
© Ji°φ Kosek 1999