129 JSP

2020-08-13 21:06:29

一、引言

1.1現有問題

  • 在之前學習Servlet時,伺服器端通過Servlet響應用戶端頁面,有什麼不足之處?
    • 開發方式麻煩:繼承父類別、覆蓋方法、設定Web.xml或註解
    • 程式碼修改麻煩:重新編譯、部署、重新啓動服務
    • 顯示方式麻煩:獲取流、使用println(" "); 逐行列印
    • 協同開發麻煩:UI負責美化頁面,程式設計師負責編寫程式碼。UI不懂Java, 程式設計師又不能將所有前端頁面的內容通過流輸出

二、JSP (Java Server Pages)

2.1概念

  • 簡化的Servlet設計,在HTML標籤中巢狀Java程式碼,用以高效開發Web應用的動態網頁

2.2作用

  • 替換顯示頁面部分的Servlet (使用*.jsp檔案替換XxxJSP.java)

三、JSP開發【重點】

3.1建立JSP

  • 在web目錄下新建*.jsp檔案(與WEB-INF平級)

3.1.1 JSP編寫Java程式碼

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
	<tit1e>This 1s my first page</title>
</head>
<body>
	 NOW: <%= new java.util.Date() %>
</body>
</html>
  • 使用<%=%> 標籤編寫Java程式碼在頁面中列印當前系統時間

3.1.2 存取JSP

  • 在瀏覽器輸入 http://ip:port/專案路徑/資源名稱

3.2 JSP與Servlet

  • 關係

    • JSP檔案在容器中會轉換成Servlet執行。
    • JSP是對Servlet的一種高階封裝。本質還是Servlet。
  • 區別

    • 與Servlet相比:JSP可以很方便的編寫或者修改HTML網頁而不用去面對大量的println語句。
  • JSP 與 Servlet 區別

在这里插入图片描述

3.3 JSP實現原理

  • Tomcat會將xxx.jsp轉換成Java程式碼,進而編譯成.class檔案執行,最終將執行結果通過response響應給用戶端。

  • JSP實現原理

在这里插入图片描述

3.3.1 JSP.java原始檔存放目錄

  • 使用IDEA開發工具,Tomcat編譯後的JSP檔案 (Xxx jsp.class 和Xxx jsp.java) 的存放地點:
    • C:\Users\Administrator.IntelliJIdea2019.3\system\tomcat\Tomcat_7_0_90_javaweb_jsp

四、JSP與HTML整合開發

4.1指令碼

  • 指令碼可以編寫Java語句、變數、方法或表達式。

4.1.1普通指令碼(程式碼指令碼)

  • 語法:<% Java程式碼 %>
<html>
<head><title>Hello World</title></head> 
<body>
Hello World!<br/>
<%
     int a =10; //這是一個區域性變數
    //jsp中,使用小指令碼嵌入java程式碼! 
    out.println(a);//列印內容在用戶端頁面
    System.out.println(a);//列印內容在控制檯
%>
</body>
</html>
  • 經驗:普通指令碼可以使用所有Java語法,除了定義函數。
  • 注意:指令碼與指令碼之間不可巢狀,指令碼與HTML標籤不可巢狀

4.1.2宣告指令碼

  • 語法:<%! 定義變數、函數 %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>指令碼的使用</title>
</head>
<body>

    <%!
        int b = 20;//這是一個全域性變數
        public void paly(){
            System.out.println("paly...............");//在控制檯輸出
        }
        public int num(){
            return 100;
        }
    %>
    <%
        out.println(b);
        paly(); //呼叫 宣告指令碼中的無返回值方法
        int num = num();////呼叫 宣告指令碼中的有返回值方法
        out.println(num);
    %>
    <%=num()%>
</body>
</html>

  • 注意:宣告指令碼宣告的變數是全域性變數。(宣告指令碼 只能定義變數與函數,不能做存取的操作)

  • 宣告指令碼的內容必須在普通指令碼<%%>中呼叫。

  • 如果宣告指令碼中的函數具有返回值,可以使用輸出指令碼呼叫<%= %>

4.1.3輸出指令碼

  • 語法:<%= Java表達式 %> (就是 out.println(Java表達式);)
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
	<tit1e>This 1s my first page</title>
</head>
<body>
	 NOW: <%= new java.util.Date() %>
</body>
</html>
  • 經驗:輸出指令碼可以輸出帶有返回值的函數
  • 注意:輸出指令碼中不能加;(英文分號)

4.2 JSP註釋

  • JSP註釋主要有兩個作用:爲指令碼程式碼作註釋 以及 HTML內容註釋。

4.2.1語法規則

語法 描述
<%-- 註釋 --%> JSP註釋,註釋內容不會被髮送至瀏覽器甚至不會被編譯
< !-- 註釋 --> HTML註釋,通過瀏覽器檢視網頁原始碼時可以看見註釋內容
<%@ page language:"java" contentType="text/htnil; charset=UTF-8
pageEncoding="UTF-8"%>
<html>
<head>
    <title>指令碼的使用</title>
</head>
<body>
<%-- JSP註釋在網頁中不會被顯示--%>
<!-- HTML註釋在網頁原始碼中會顯示-->
<p>
     NOW: <%= new java.util.Date() %>
</p>

</body>
</html>

4.3 JSP指令

  • JSP指令用來設定與整個JSP頁面相關的屬性。
指令 描述
<%@ page …%> 定義頁面的依賴屬性,比如指令碼語言、error頁面、快取需求等等
<%@ include…%〉 包含其他檔案
<%@ taglib… %> 引入標籤庫的定義,可以是自定義標籤

4.3.1 page 指令

  • 語法:<%@ page attributel=「value1」 attribute2=「value2」 %>

  • Page指令爲容器提供當前頁面的使用說明。一個JSP頁面可以包含多個page指令。

屬性 描述
contentType 指定當前JSP頁面的MIME型別和字元編碼格式
error Page 指定當JSP頁面發生異常時需要轉向的錯誤處理頁面
isErrorPage 指定當前頁面是否可以作爲另一個JSP頁面的錯誤處理頁面
import 匯入要使用的Java類
language 定義JSP頁面所用的指令碼語言,預設是Java
session 指定JSP頁面是否使用session。預設爲true立即建立,false爲使用時建立
pageEncoding 指定JSP頁面的解碼格式

4.3.2 include 指令

  • 語法:<%@ include file =「被包含的JSP路徑」 %>

  • 通過indude指令來包含其他檔案。

  • 被包含的檔案可以是JSP檔案、HTML檔案或文字檔案。包含的檔案就好像是當前JSP檔案的一部分,會被同時編譯執行(靜態包含)。

<%@ include file="header.jsp"%> 
...
...
<%@ include file="footer.jsp" %>
  • 注意:可能會有重名的衝突問題,不建議使用。

4.3.3 taglib 指令

  • 語法:<%@ taglib uri=「外部標籤庫路徑」 prefix=" 字首"%>

  • 引入JSP的標準標籤庫

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>

4.4動作標籤

  • 語法:<jsp:action_name attribute=「value」 />

  • 動作標籤指的是JSP頁面在執行期間的命令

4.4.1include

  • 語法:<jsp:include page=「相對 URL 地址」/>

• < jsp:indude>動作元素會將外部檔案輸出結果包含在JSP中(動態包含)。

屬性 描述
page 包含在頁面中的相對URL地址。
  < jsp :include page="index.jsp"/>     
  • 注意:前面已經介紹過include指令,它是將外部檔案的輸出程式碼複製到了當前JSP檔案中。而這裏的jsphdiide動作不同,是將外部文 件的輸出結果引入到了當前JSP檔案中。

4.4.2 useBean

  • 語法:<jsp:useBean id=「name」 class=「package.className」 />

  • jsp:useBean動作用來載入一個將在JSP頁面中使用的JavaBean。

<jsp:useBean id="user" class="com.wlw.entity.User"/>
  • 在類載入後,我們可以通過jsp:setProperty和jsp:getProperty動作來修改和獲取bean的屬性。

4.4.3 setProperty

  • 可以在jsp:useBean元素之後使用jsp:setProperty進行屬性的賦值
屬性 描述
name name屬性是必需的。它表示要設定屬性的是哪個Bean。
property property屬性是必需的。它表示要設定哪個屬性。
value value屬性是可選的。該屬性用來指定Bean屬性的值。
<jsp:useBean id="user"  class="com.wlw.entity.User" />     
<jsp:setProperty name="user" property="name" value="gavin" />

4.4.4 getProperty

  • jsp:getProperty動作提取指定Bean屬性的值,轉換成字串,然後輸出。
屬性 描述
name 要檢索的Bean屬性名稱。Bean必須已定義。
property 表示要提取Bean屬性的值
<jsp:useBean id="user" class="com.wlw.entity.User" /> 
<jsp:setProperty name="user" property="name" value="gavin" />                         <jsp:getProperty name="user" property= "name1" />

4.4.5 forward

  • 語法:<jsp:forward page="相對 URL 地址」 />

  • jsp:forward動作把請求轉到另外的頁面。

屬性 描述
page page屬性包含的是一個相對URL。
  <jsp:forward page="index.jsp" />     

4.4.6 param

  • 語法:<jsp:param name=" " value=""/〉

  • 在轉發動作內部使用,做參數傳遞

<jsp :forward page="index. jsp">
    <!-- http請求參數傳遞-->
    <jsp:param name="sex" value= "nan" />
</jsp:forward>

4.5內建物件

  • 由JSP自動建立的物件,可以直接使用
物件名 型別 說明
request javax.servlet.http.HttpServletRequest
response javax.servlet.http.HttpServletResponse
session javax.servlet.http.HttpSession 由 session=「true」開關
application javax.servlet.ServletContext
config javax.servlet.ServletConfig
exception java.Iang.Throwable 甶 isErrorPage=「false」開關
out javax.servlet.jsp.JspWriter javax.servlet.jsp.JspWriter
pageContext javax.servlet.jsp. PageContext
page java.lang.Object 當前物件 this 當前servlet實f列

4.5.1四大域物件

  • JSP有四大作用域物件,儲存數據和獲取數據的方式一樣,不同的是取值的範圍有差別
    • pageContext (javax.servlet.jsp.PageContext)當前JSP頁面範圍
    • request (javax.servlet.http.HttpServletRequest)—次請求有效
    • session (javax.servlet.http.HttpSession)—次對談有效(關閉瀏覽器失效)
    • application (javax.servlet.ServletContext)整個Web應用有效(伺服器重新啓動或關閉失效)

4.5.2 pageContext 物件

  • pageContext物件是javax.servlet.jsp.PageContext類的範例,擁有作用域,用來代表整個JSP頁面。
    • 當前頁面的作用域物件,一旦跳轉則失效
    • 通過 setAttribute(「name」,value);儲存值
    • 通過 getAttribute("namen);獲取值
    • 用於獲取其他8個內建物件或者操作其他物件的作用域
<%
pageContext.setAttribute( name , value) ;//當前頁面作用域有效
%>

4.5.3 pageContext獲取其他內建物件

<%
pageContext .getRequest();//返回request內物件 
pageContext .getResponse();//返回response內S物件 
pageContext .getServletConfig();//返回config內建物件 
pageContext .getException();//返回exception內建物件 
pageContext .getPage();//返回page內建物件 (this)
pageContext .getOut();//返回out內建物件

pageContext .getServletContext();//返回 application 內建物件 
pageContext .getSession();//返回session內建物件
%>

4.5.4 pageContext操作其他內建物件的作用域

  • pageContext物件可以操作其他作用域儲存和獲取。
 <%
        pageContext.setAttribute("page","123");//當前JSP有效
        pageContext.setAttribute("req","aaa",PageContext.REQUEST_SCOPE);//request作用域 
        pageContext.setAttribute("sess","bbb",PageContext.SESSION_SCOPE);//session作用域
        pageContext.setAttribute("app","ccc",PageContext.APPLICATION_SCOPE); //application作用域

//        String req = (String)request.getAttribute("req");
//        String sess = (String)session.getAttribute("sess");
//        String app = (String) application.getAttribute("app");
		String page= (String)pageContext .getAttribute("page"); //當前頁面作用域
        String req = (String) pageContext.getAttribute("req",PageContext.REQUEST_SCOPE);//request作用域
        String sess = (String) pageContext.getAttribute("sess",PageContext.SESSION_SCOPE);//session作用域
        String app = (String) pageContext.getAttribute("app",PageContext.APPLICATION_SCOPE);//application作用域

        //pageContext、request、session、application
        String result = (String)pageContext.findAttribute("app");
    %>
    <h1>request:<%=req%></h1>
    <h1>session:<%=sess%></h1>
    <h1>application:<%=app%></h1>
    <h1>find:<%=result%></h1>

4.6整合

  • 將EmpProject專案所有顯示頁面JSP的Servlet替換爲JSP頁面,使用指令碼進行顯示
  • 就是(128 Servlet_11 _綜合案例 )
<%@ page import="java.util.List" %>
<%@ page import="com.wlw.emp.entity.Emp" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>顯示所有員工</title>
</head>
<body>
    <table border="1">
        <tr>
            <td>編號</td>
            <td>姓名</td>
            <td>工資</td>
            <td>年齡</td>
            <td colspan="2">操作</td>
        </tr>
    <%
        List<Emp> emps = (List<Emp>)request.getAttribute("emps");
        for (Emp emp:emps){
    %>
        <tr>
            <td><%=emp.getId()%></td>
            <td><%=emp.getName()%></td>
            <td><%=emp.getSalary()%></td>
            <td><%=emp.getAge()%></td>
            <td><a href="<%= request.getContextPath()+"/manager/safe/removeEmpController?id="+emp.getId()%>">刪除</a></td>
            <td><a href="<%= request.getContextPath()+"/manager/safe/showEmpController?id="+emp.getId()%>">修改</a></td>
        </tr>
    <%
        }
    %>
    </table>
</body>
</html>

<%@ page import="com.wlw.emp.entity.Emp" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>修改員工資訊頁面</title>
</head>
<body>
    <%
        Emp emp = (Emp) request.getAttribute("emp");
    %>

    <!--<form action="/empproject/manager/safe/updateEmpController" method="post"> -->
    <form action="<%=request.getContextPath()+"/manager/safe/updateEmpController" %>" method="post">
        編號:<input type="text" name="id" value="<%=emp.getId()%>" readonly><br/>
        姓名:<input type="text" name="name" value="<%=emp.getName()%>"><br/>
        工資:<input type="text" name="salary" value="<%=emp.getSalary()%>"><br/>
        年齡:<input type="text" name="age" value="<%=emp.getAge()%>"><br/>
        <input type="submit" value="修改">
    </form>
</body>
</html>