PHP教程.數據庫連接(1) - 中國WEB開發者網絡 (http://www.webasp.net) -- 技術教程 (http://www.webasp.net/article/) --- PHP教程.數據庫連接(1) (http://www.webasp.net/article/16/15040.htm) |
| -- 作者:未知 -- 發佈日期: 2004-11-23 |
| 中場一:數據庫連接
前兩章中集中介紹了PHP語言,現在停下來開始創建一個應用程序。在本章中將創建一個連接MySQL數據庫的應用程序。 在學習過前面兩章之後,你肯定已經學會了怎樣處理PHP內部數據,以及怎樣編寫語句和函數。下一步從邏輯上講,應該到了學習如何用SQL(結構化查詢語句)處理PHP的外部數據的時候了。但是,在開始學習這部分內容前,讓我們暫時中斷基本原理的學習,放鬆一下。 讓我帶你一道探究PHP應用程序的開發歷程。從字面意義上講,每一個應用程序都應該是獨特的,但是每一個應用程序也都能在此前的工作基礎上,即一系列通用功能的基礎上構建。我建議將這兩項技術混合在一起。盲目地使用前人已編寫好的功能,會剝奪在程序中加入新特色,還會阻止為提高函數的效率而去修改舊函數。從另一方面講,使用已有函數意味著能更快的開發出應用程序。所以必須在這兩個極端中把握好自己,才能成為一個優秀的程序設計員。 注意:如果現在還對HTML不熟悉,那麼現在就是開始學習的時間了。本書中假定你已經熟悉HTML了。如果還不熟悉HTML表格和表單的話,很快就會被搞糊塗的。 5.1 開端 每當開始一個新項目時,我喜歡從一個新的空目錄開始。在這裡,讓我們把這個目錄稱為phpbook/ch05。當然,這個目錄必須在Web服務器的根目錄下。如果你是按照第一章的指令安裝PHP的話,那麼,Web服務器的根目錄就應該為/usr/local/apache/htdocs。接著,我們將創建一個名為menu.php3的文件,其中包含有一個後台管理任務菜單,如清單5.1所示。 清單5.1 menu.php3 <?php require('common.inc'); ?> <?php affy_header('Administrative Menu') ?> <h1>Administrative Menu</h1> <ol> <li><a href="connect.php3">Creat Database Connection</a></li> </ol> <?php affy_footer() ?> 在文件common.inc中包含對函數affy_header和affy_footer的定義。這些函數在本章中稍後還會出現。 5.2 創建連接 當點擊Create Database Connect(創建數據庫連接)聯接時,將會執行connect.php3文件,該文件將嘗試連接在第二章學習中安裝的MySQL數據庫服務器。 清單5.2 顯示了connect.php3文件使用用戶名codebits和密碼codebits嘗試進行數據庫連接,因為在安裝MySQL時還沒有創建該用戶名,所以連接肯定失敗。然而失敗 -- 最起碼在本例中 -- 卻是一件好事,因為我們可以看看應該如何處理這個問題。圖5.1給出了連接失敗後將會顯示的錯誤信息和表單。 清單5.2 connect.php3 Page 107 -108 清單 5.2 Page 108 Figure 5.1 圖5.1 連接失敗時的錯誤信息顯示 當數據庫連接失敗時,程序會給出一個錯誤信息提示和一個表單,用戶可以在裡面輸入root用戶的密碼。就像在本章稍後講的那樣,有了root的密碼,就可以創建名為codebits的用戶。現在先跳過有關$arr_request數組的部分。 當函數mysql_connect被調用且連接失敗時,該函數通常會顯示如下信息: Warnint: MySQL connection Failed: Access denied for user: 'codebits@localhost' (Using password: YES) 絕大多數應用程序需要精確的控制顯示的內容,尤其是高度圖形化的應用程序。在函數mysql_connect前加上(@)符號將會抑制錯誤信息的顯示。 注意表單語句的action屬性指定點擊submit按鈕時,將會執行connect.php3文件。這是一個遞歸程序的例子,也就是說允許PHP文件調用它自己。 應用遞歸編程技術,可以將有關同一個主題的所有代碼編製在同一個文件中。至於什麼時候應該將函數組合成一個文件,或將程序分解成幾個文件,這得憑經驗。我的首要原則是:當實現一個特定功能所編的程序代碼超過100行以上時,就要創建一個獨立的文件。 5.3 獲取HTML表單信息 即使輸入一個密碼並點擊連接數據庫,連接仍然會失敗,原因是connect.php3還沒有使用表單中的輸入值去建立數據庫連接。 PHP引擎將每一個表單域放到一個叫做$HTTP_POST_VARS的數組中。在上述給出的例子中,數組有兩個元素:username和password。在此程序中可以通過$HTTP_POST_VARS['username']和$HTTP_POST_VARS['password']訪問表單信息。 使用$HTTP_POST_VARS['password']獲得表單中的信息看起來比較簡單。但是仍有一些隱藏的問題。首先,要檢查表單域的名字(本例中的password)是大寫、小寫、還是大小寫都有。 第二件問題包含的內容與本例關係不大。除了表單方法以外,還可以使用URL來運行PHP腳本,例如: http://.../connect.php3?username=root&password=password 可以看到,用戶名和密碼通過URL進行傳遞,問號「?」標誌著域信息的開始,「&」則是域的定界符。幸運的是,PHP引擎也自動分析URL行,並將結果存入$HTTP_GET_VARS數組中。 問題(如果你認為它是的話)在於,程序可以從不止一個地方獲得信息 -- 數組$HTTP_GET_VARS和數組 $HTTP_POST_VARS。 對待這些(或其它一些的)問題,我的解決辦法是創建一個名為$arr_request的數組,它從兩個$HTTP數組中獲得初始化的信息。在common.inc中可以使用如下編碼行對數組$arr_repuest進行數值初始化。 // declare the request array which holds both // url-based (get) and form-based (post) parameters. $arr_request = array(); // move the url and form parameters into the // request array. Form parameters supercede url // parameters. Additionally, all keys are vonverted // to lower-case. If (count($HTTP_GET-VARS)) { While (list($key, $value) = each ($HTTP_GET_VARS)) { $arr_request[strtolower($key)] = $value; } } if (count($HTTP_POST_VARS)) { while (list($key, $value) = each ($HTTP_POST_VARS)) { $arr_request[strtolower($key)] = $value; } } 如果在所有的PHP腳本中都包含有common.inc文件的話,那麼不用擔心腳本是怎麼運行的。所有傳過去的信息都以小寫形式保存在數組$arr_request中,這就意味著,可以使用$arr_request['username']得到用戶名信息。 PHP提供了數組$HTTP_GET_VARS和數組$HTTP_POST_VARS的替代方式,HTML表單和基於URL的信息都可以直接做為PHP變量進行訪問。例如,在PHP 腳本中,一個定義為<input type = "input" name="last_name">的域信息可以直接在PHP程序中用$last_name訪問,同樣的基於URL的信息,比方說,http://www.site.com?last_name=join,能由$last_name獲得。不過,我還是比較喜歡使用數組$arr_request,因為對於要循環使用傳遞給程序的所有信息來講,這是非常有用的。如果該信息是一個標量,那麼它就不適合被循環使用。例如:將所有參數名改為大寫,以保證不致於因為使用換檔鍵而破壞程序;或者在錯誤檢測時,會需要顯示所有的輸入參數。 注意:本節只對CGI(通用網關接口)協議作很簡單的介紹,更詳細的內容請參閱本書附錄A,「因特網資源」中所列內容。 5.4 使用HTML表單信息 既然可以很容易地從PHP腳本程序中存取表單信息,現在是利用這些信息連接數據庫的時間了。第一步是檢查連接數據庫的代碼: $id_link = @mysql_connect('localhost', 'affy', 'affy'); 在這行代碼中,用戶名和密碼都是字符串數值。為了能利用表單中的信息,這行代碼需要加以變動,用變量代替數值: $id_link = @mysql_connect( 'localhost', $username, $password); 既然用到了變量,那麼必須對變量進行初始化。以下代碼將執行這種初始化: if ( count($arr_request) ) { $username = $arr_request['username']; $password = $arr_request['password']; } else { $username = 'phpuser'; $password = 'phpuser'; } 當表單信息可用時,函數count的結果將大於1,使得if語句執行真條件的子句,此子句依次從$arr_request數組中取出用戶名和密碼信息。 當沒有表單信息存在時,用戶名和密碼仍可以用字符串數值進行初始化。 第三種可能性是一個表單有這兩個域但沒有表單信息。如果調用connect.php3的表單沒有username和password域,會發生什麼情況呢?如果這樣,以上代碼將失敗。通過直接檢查表單字段,而不是只依賴於$arr_request數組的元素數目可以讓這段代碼的更強壯(即,能處理這種環境下的失敗)。例如: $username = $arr_request['username']; $password = $arr_request['password']; if (empty($username)) $username = 'phpuser'; if (empty($password)) $password = 'phpuser'; 因為PHP對沒有初始化的數組元素將返回空字符串,以上代碼的適應性將更強。使用標量比使用數組可以使代碼更容易理解,並且在某些方面更有效率。如果這兩個變量有一個為空時,這意味著表單沒有提供任何值,將使用缺省值。 清單5.3顯示了有以上更改的connect.php3文件,可以在上下文看到這兩個變化的描述。 清單5.3 connect.php3修訂版 Page 112 - 113 清單 5.3 當正確的root密碼如圖5.2所示被輸入到表單時,將會成功地建立數據庫連接。 Page 113, Figure 5.2 圖5.2 證實成功地建立了數據庫連接 5.5 common.inc文件 清單5.4顯示了本章需要的common.inc文件的版本。 清單5.4 common.inc--多個應用程序使用的一套例程。 <?php function affy_footer() { echo '</body></html>'; } function affy_header($title) { echo '<html><head><title>'; echo "$title"; echo '</title></head><body>'; } function affy_message($msg) { echo '<table>'; echo '<tr><td>'; echo "$msg"; echo '</td></tr>'; echo '</table>'; } ?> 5.6 總結 本章介紹了如何使用PHP連接數據庫,第一步創建了一個Web菜單頁,用它可以運行連接數據庫的腳本,然後創建了可以連接數據庫的connect.php3文件。 當connect.php3文件使用affy用戶名企圖連接數據庫時失敗了,從而導致顯示出了需要root用戶密碼的表單。 表單中的信息通過common.inc文件被放在$arr_request數組中。並修改了connect.php3文件,使其使用變量$arr_request中的用戶名和密碼來連接數據庫。 |
| webasp.net |