JavaSE02_Day04(下)-自定義空請求異常、XML解析(定義、格式、作用、解析方案及案例演示)
一、WebServer專案
1.1 版本七:自定義異常來解決空請求問題
Http協議允許客戶端傳送一個空請求,也就是客戶端與服務端斷開連線的時候,實際上並沒有傳送任何的內容,但是我們所書寫的程式碼是要對請求進行解析,那麼這就會導致解析產生異常,不能正確的拆分出三部分內容。當我們解析請求的時候,如果發現發過來的是一個空請求,我們將異常最終拋給ClientHandler類,並且ClientHandler在接收這個異常後就不做任何的處理,直接斷開連線。
步驟1:在http包下自定義一個異常類EmptyRequestException(空請求異常)
package cn.tedu.http;
/**
* 自定義異常類
* 用於解決瀏覽器傳送空請求問題
* @author cjn
*
*/
public class EmptyRequestException extends Exception{
/**
* Java的序列化機制是通過在執行時判斷類的serialVersionUID來驗證版本一致性的。
* 原因:在進行反序列化時,JVM會把傳來的位元組流中的serialVersionUID與本地實體
* 類中的serialVersionUID進行比較,如果相同則認為是一致的,便可以進行反序列化,
* 否則就會報序列化版本不一致的異常
*/
private static final long serialVersionUID = 1L;
/*
* source -> generate constructors from superClass
* 生成EmptyRequestException類的構造器,
* 並且把過載的構造器一併都生成,
* 在構造器的內部呼叫超類中的構造器方法
*/
public EmptyRequestException() {
super();
}
public EmptyRequestException(String message, Throwable cause, boolean enableSuppression,
boolean writableStackTrace) {
super(message, cause, enableSuppression, writableStackTrace);
}
public EmptyRequestException(String message, Throwable cause) {
super(message, cause);
}
public EmptyRequestException(String message) {
super(message);
}
public EmptyRequestException(Throwable cause) {
super(cause);
}
}
步驟2:在HttpRequest類中進行請求行解析時,如果發現是一個空請求,那麼咱們直接丟擲自定義異常,並將其拋給構造方法,再經構造方法拋給ClientHandler類。
步驟3:在ClientHandler類中的run方法中新增一個空請求的異常捕獲,以達到當例項化HttpRequest出現空請求後,跳過其他所有處理操作的目的。
執行結果出現相關資訊:
二、XML解析
2.1 XML定義
可擴充套件標記性語言eXtensible Markup Language
2.2 XML檔案格式
2.3 作用
使用XML可以進行對資料的儲存,也可以進行傳輸資料。
2.4 特殊字元
2.5 CDATA段
格式:< ! [CDATA [內容] ] >
作用:避免特殊字元讀取錯誤,可直接將內容方法CDATA[ ]中。
<![CDATA[ 伏爾泰說過一<句著名的話,不>經巨大的困難,不會有偉大<>的事業。這啟發了我. 小白老師的發"生,到底"需要如何做到,不小白''老師的發生,又&會如何產生。]]>
2.6 XML解析
獲取XML檔案中的內容
2.7 XML解析的方案
-
DOM:速度較慢,可以修改元素的內容;
-
SAX
2.8 DOM4J的依賴匯入
下載jar包或複製程式碼:
-
推薦【官方倉庫】:https://mvnrepository.com/
-
不推薦【阿里倉庫,查詢麻煩】:https://maven.aliyun.com/mvn/view
<!-- dom4j 1.6.1 -->
<dependency>
<groupId>dom4j</groupId>
<artifactId>dom4j</artifactId>
<version>1.6.1</version>
</dependency>
在pom.xml檔案中新增dom4j元件依賴:
注意:要加一對標籤<dependencies></dependencies>,新增後工具自動載入相關jar包
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>cn.tedu</groupId>
<artifactId>webserver01</artifactId>
<version>0.0.1-SNAPSHOT</version>
<dependencies>
<!-- https://mvnrepository.com/artifact/dom4j/dom4j -->
<dependency>
<groupId>dom4j</groupId>
<artifactId>dom4j</artifactId>
<version>1.6.1</version>
</dependency>
</dependencies>
</project>
2.9 XML檔案解析案例
新建emp.xml檔案:
2.10 相關API
-
獲取根節點: Element getRootElement();
-
獲取當前標籤的所有子元素
-
List elements();
-
List elements(String name);//獲取指定標籤的子元素
-
-
獲取標籤名稱 :String getName();
-
-
獲取標籤中的文字內容
-
String getText();
-
String elementText();//一般用這個
-
2.11 案例演示
package cn.tedu;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
/**
* 使用DOM4J進行解析emp.xml檔案
* 需要將emp.xml檔案從磁碟中讀取到記憶體中,然後通過
* DOM4J所提供的相關API解析獲取的員工資訊,封裝到
* Emp員工物件中。最後再將每一個Emp員工物件新增到
* List集合中。
* @author cjn
*
*/
public class ParseXML {
public static void main(String[] args) {
/*
* 具體解析步驟:
* 1.需要建立SAXReader物件
* 2.使用SAXReader物件進行讀取emp.xml檔案,讀取完以後會返回一個Document文件物件
* 3.通過Document物件獲取XML檔案的根標籤<list></list>
* 4.通過根標籤進行獲取裡面的子標籤對應的元素內容
*/
try {
//1.建立SAXReader物件
SAXReader reader = new SAXReader();
//2.使用SAXReader物件進行讀取emp.xml檔案,讀取完以後會返回一個Document文件物件
//File file = new File("./emp.xml");//./寫不寫效果都是一樣的,都是相對於當前專案而言
File file = new File("emp.xml");
Document document = reader.read(file);
//或 Document document = reader.read(new File("emp.xml"));
//3.通過Document物件獲取XML檔案的根標籤<list></list>
//獲取根節點list節點元素
Element root = document.getRootElement();
//4.通過根標籤進行獲取裡面的子標籤對應的元素內容
//獲取根節點中名稱為emp節點元素
List<Element> emps = root.elements("emp");
//5.準備集合物件,用於儲存Emp員工物件
List<Emp> empList = new ArrayList<Emp>();
//遍歷emps集合中的所有emp節點元素
for (Element e : emps) {
//獲取emp節點元素中的子節點
//獲取姓名 按照方式一獲取元素對應的文字內容,先獲取指定元素,再通過該元素獲取文字內容
Element nameEle = e.element("name");//<name>小瀋陽</name>
String empName = nameEle.getText();//小瀋陽
//獲取年齡 按照方式二獲取指定元素的文字內容
int empAge = Integer.parseInt(e.elementText("age"));
//獲取性別
String empGender = e.elementText("gender");
//獲取工資
double empSal = Double.parseDouble(e.elementText("sal"));
//獲取根標籤的屬性id
String empId = e.attributeValue("id");
System.out.println(empId);
//建立Emp員工物件,封裝員工資訊
Emp empObj = new