➤AJAX實作(javascript)-站內搜尋
講解的這個範例算是頗實用的(棧長是參考W3C再進行改寫的),在前端頁搭配javascript的方式來撈取後端MySQL資料達成AJAX非同步處理的效果(網路上也有人是使用jquery的方式來達成)。
該效果應用面算是很廣,包含像是臉書的搜尋朋友、google的翻譯等等都是透過AJAX方式達成,亦即當我們在鍵盤上打字當手離開鍵盤時(onkeyup事件),前端會傳值給後端,而後端也會將取出的資料庫內容送回前端把資料秀出來。
下圖中,還未輸入文字時,會出現我的大頭照,之後我在左邊欄位內輸入"陳",就會立即透過AJAX呼叫後端的資料秀在右邊(這次就不用SHE當範例😆)。
在phpmyadmin當中請建立一個ktmysqlclass資料庫,編碼使用utf8_unicode_ci(基於相容性很多人都開始用utf8mb4_unicode_ci,不過這裡僅為作範例講解,就使用utf8_unicode_ci)。
建立一個名為score的資料表,設7個欄位,型態如下圖所示:
名字、資料等可以自己隨意取名來新增
建立好之後,就是重點了,我們需要兩個頁面,一個是前端頁取名為index.php,一個是後端頁取名為ajax.php。來達到非同步處理的效果。
這邊我有用到boostrap4第三方框架,所以是有自適應rwd的,格子我是採用左邊5(col-md-5 col-sm-12)、右邊7(col-md-7 col-sm-12)。
*boostrap4的格子系統(連結)
#前端頁index.php
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>AJAX-站內搜尋</title>
<style>
h1, h2, h3, h4{ font-family: '微軟正黑體';}
table {
border-collapse: collapse;
text-align: center;
margin: 20px 0 0 0px; /*外距:上右下左*/
box-shadow: 0px 15px 22px rgba(0, 0, 0, 0.2);
width: 100%;
}
th {
background-color: #f7c24a;
border : 2px solid black;
padding: 5px;
}
td {
color: #5b3202;
border : 3px solid black;
padding: 5px;
}
.section-1 {
padding-top: 50px;
}
.box1{
height: 400px;
width: 100%;
position: absolute; /*絕對位置*/
border: 4px solid #ab0303;
border-radius: 5px;
}
.panel1{
background-color: #fffebd;
padding-top: 120px;
}
.panel2{
padding-top: 30px;
}
</style>
<script>
function showSite(str)
{
if (str == "")
{
//收集輸入字段的值,其id為“txtHint”。
document.getElementById("txtHint").innerHTML="";
return;
}
if (window.XMLHttpRequest)
{
// IE7+, Firefox, Chrome, Opera, Safari 瀏覽器執行碼(建立物件)
xmlhttp = new XMLHttpRequest();
}
else
{
// IE6, IE5 瀏覽器執行碼(建立物件)
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
}
//'onreadystatechange'是XMLHttpRequest物件的屬性,只要'readyState'屬性發生更改,就會調用該屬性。 我們將其分配給下一個要宣告的函數。
xmlhttp.onreadystatechange=function()
{
//檢查'readyState'屬性的值是否為4,以及結果代碼200表明對請求的響應是成功的。。
if (xmlhttp.readyState==4 && xmlhttp.status==200)
{
//設置要在div中顯示的字符串的值,其id為'txtHint',作為XMLHttpRequest物件的'responseText'屬性。 'responseText'是對文本請求的響應。
document.getElementById("txtHint").innerHTML=xmlhttp.responseText;
}
}
//此方法傳遞了三個參數。 'GET'確定httprequest的類型。 'ajax.php'設置後端文件,並設置第三個參數'true'表示異步處理請求。
xmlhttp.open("GET", "ajax.php?name="+str, true);
xmlhttp.send();
}
</script>
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" >
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.8.1/css/all.css">
</head>
<body align="center">
<section class="section-1">
<div class="container alert text-center">
<div class="row box1">
<div class="col-md-5 col-sm-12 panel1">
<h4 style="color:black;">AJAX-站內搜尋</h4>
<input name="name" onkeyup="showSite(this.value)">
<p>請輸入您要查詢的名字</p>
</div>
<div class="col-md-7 col-sm-12 panel2">
<div class="text-center">
<div id="txtHint">
<img src="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiUUQkj6NwE1eHB_c4e15DF3-XVDJ8zSV_0MEVjfjm-q-Jp5FlQOWZ7Y7kxteky6NoC8yOyVXPqZ3sqXqCUSreexsK3RjioAaCFOooThTXW1JNy577JG6i4aHi5lE6sXtvdtUV-B3IwgWaA/s1600/%25E8%25B3%25BD%25E4%25BA%259E%25E4%25BA%25BA%25E5%2598%259F%25E5%2598%25B4.jpg">
<br>
<b>查詢結果會秀出在這邊呦~~棧友們</b>
</div>
</div>
</div>
</div>
</div>
</section>
<script src="https://code.jquery.com/jquery-3.4.0.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js"></script>
</body>
</html>
接著後端頁取名為ajax.php,這邊資料庫連線是採用mysqli建立資料庫物件,傳統的mysql則較不建議再用。或是更建議您採用PDO搭配stmt預備語法的方式,它在預防SQL injection會更完善(這邊有接觸過ASP.NET的棧友們是不是有聯想到了ADO.NET了,ASP.NET若是直接用datasource精靈連線是存有一定風險,但透過後置程式碼於C#使用ADO.NET較能有效預防SQL injection)。
資料庫連線的起手式 : 連線->撈資料->倒出資料->關閉資料庫
#後端頁ajax.php
<?php
$host = "localhost"; //本機端
$username = "root"; //mysql帳號
$passwd = "1234"; //mysql密碼
$database = "ktmysqlclass"; //mysql資料庫
//建立資料庫物件
$kt_conn = new mysqli($host, $username, $passwd, $database);
if ($kt_conn -> connect_error){
echo "連結mysql資料庫失敗";
}
else{
$kt_conn -> query("SET NAMES 'utf8'");
//echo "連結mysql資料庫成功,語系設為utf8";
}
//接收從前端傳來的內容,撈取資料後透過ajax丟回前端
if($_GET['name'] != "") {
@$n = $_GET['name'];
/*從score資料表,撈取所有欄位(用*米字號),當所傳來的值是字首、中、尾有符合(LIKE)資料name欄位的名字,
就會呼叫出來,並且透過id欄位來設定為升序(ASC是升序(小跑到大)、DESC是降序(大跑到小))*/
$sql = "SELECT * FROM score WHERE name LIKE '%$n%' ORDER BY id ASC";
$score_result = mysqli_query($kt_conn,$sql);
}
echo "<table border='1'>
<tr>
<th>編號</th>
<th>姓名</th>
<th>國文</th>
<th>英文</th>
<th>數學</th>
<th>電子信箱</th>
</tr>";
while($row = mysqli_fetch_array($score_result))
{
echo "<tr>";
echo "<td>" . $row['id'] . "</td>";
echo "<td>" . $row['name'] . "</td>";
echo "<td>" . $row['chinese'] . "</td>";
echo "<td>" . $row['english'] . "</td>";
echo "<td>" . $row['math'] . "</td>";
echo "<td>" . $row['email'] . "</td>";
echo "</tr>";
}
echo "</table>";
//關閉資料庫
mysqli_close($kt_conn);
?>
你好 我想請問
回覆刪除如果我全部語法複製貼上了
然後資料庫裡也有東西
但是輸入後還是沒有抓到資料
可能是哪裡出了問題
JD你好,資料抓不到建議你從兩方向著手檢查,
回覆刪除第1是javascript的部分>
檢查html中是否有抓到上方js語法的function(也就是onkeyup事件),
上方js語法的getElementById("txtHint"),是否下方有確實填上div id="txtHint"
注意js語法的xmlhttp.open("GET", "ajax.php?name="+str, true),其中ajax.php名字必須要對應你撈資料的檔案。
第2是mysql撈資料的部分(ajax.php)>
*帳號、密碼是否有誤
*連線是否正常,未必要用資料庫物件,也可用mysqli
*SQL語法是否有誤
--------------------------------
可以參考w3school這個網站有介紹>
https://www.w3school.com.cn/js/js_ajax_database.asp
PS.您也可以參考我寫的另一篇用jQuery方式去做ajax,都是達到相同效果
可以參考這篇是採用jQuery方式來呈現的。
回覆刪除AJAX實作(jQuery)-站內搜尋(二)
https://reurl.cc/oD2aMg
不好意思 我會一直遇到在
回覆刪除if($_GET['author_name'] != "") {
@$n = $_GET['author_name'];
這邊會一直說我的author不存在
Notice: Undefined index: author_name
可以問一下是為甚麼嗎
你的前端要讓ajax.php檔獲取資料,讓他根據這個資料去搜尋表,通常是id,前端網址後面要有php?id=123,可以搜尋如何獲取網址參數~
刪除