這篇文章將為大家詳細講解有關Java Web項目的基礎知識,小編覺得挺實用的,因此分享給大家做個參考,希望大家閱讀完這篇文章后可以有所收獲。
一、Java Web 模塊結構
JSP文件和AXPX文件類似,路徑和URL一一對應,都會被動態編譯為單獨class。Java Web和ASP.NET的核心是分別是Servlet和IHttpHandler接口,因此無論是基礎的Page文件(JSP、ASPX)方式還是后來發展的MVC方式(Spring MVC、ASP.NET MVC)都是基于核心接口的基礎上再次封裝和擴展(DispatcherServlet、MvcHandler)。
除JSP文件外,其他全部文件部署在應用目錄的WEB-INF子目錄下,WEB-INF目錄可以認為是ASP.NET中將web.config文件、bin目錄和App_開頭的運行時目錄存放在了一個統一的根目錄中。
Java Web的配置文件web.xml也存放在WEB-INF目錄下,而ASP.NET的配置文件web.config一般直接存放在應用目錄下(ASP.NET其他目錄同樣可以有web.config文件)。ASP.NET將所有的引用和代碼生成的dll都部署在bin中,而Java Web的引用jar和生成的class分別存放在WEB-INF的子目錄lib和classes中(參考1)。
綜上,類似ASP.NET中的web.config、bin、App_Data等,Java Web中的WEB-INF、web.xml、lib和classes是我們必須了解和掌握的。
|--Assembly Root
|---WEB-INF/
|--web.xml
|--lib/
|--classes/1、WEB-INF目錄:Java Web文件的根目錄。
2、web.xml文件:配置文件(asp.net web.config)。
3、lib目錄:存放類庫文件(asp.net bin)。
4、classes目錄:存放class文件(asp.net bin)。
二、Maven Web項目的基本結構
鑒于目前Java IDE眾多并且都有一定的擁泵,Eclipse的Java Web項目不具有可移植性。Maven即解決了項目結構的規范問題又提供了強大引用處理等強大的功能,在項目布局等方面已經是目前事實上的標準。Maven項目的主要結構如下(參考2):
|--root
|--pom.xml
|--src/
|--main/
|--java/
|--resources/
|--webapp/
|--test/
|--java/
|--resources
|--target/Eclipse中新建一個Maven web app項目。文件結構如下:
|--MavenWP
|--pom.xml
|--.project
|--.classpath
|--.settings/
|--src/
|--target/
|--classes/
|--m2e-wtp/1、pom.xml:maven項目配置文件。
2、.project文件和.classpath文件以及.settings目錄和target/m2e-wtp目錄下的文件為Eclipse項目配置文件。
3、src和target:maven標準項目目錄。
Eclipse4.5.1中對應的項目資源管理視圖
|--MavenWP |--Deployment Desciptor/ |--Java Resources/ |--JavaScript Resources/ |--Deployed Resources/ |--src |--target |--pom.xml
1、認創建的項目會添加一個index.jsp并報錯:使用maven搜索并添加servlet依賴更新后就可以正常運行。
2、Java構建路徑問題警告:使用maven搜索并添加compiler插件并配置configuration節點更新就可以消除。
3、墻的問題配置maven鏡像,我采用的是http://maven.oschina.net/content/groups/public/。
4、默認創建的maven webapp缺少的src/main/java、src/test/java和src/test/resources等目錄需要自己手動添加。
5、修改.settings/org.eclipse.wst.common.project.facet.core.xml,更新<installed facet="jst.web" version="3.1"/>。
6、web.xml根節點開始部分修改如下:
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" version="3.1">
Maven的配置文件pom.xml:
<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/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>me.test</groupId>
<artifactId>MavenWP</artifactId>
<packaging>war</packaging>
<version>0.0.1-SNAPSHOT</version>
<name>MavenWP Maven Webapp</name>
<url>http://maven.apache.org</url>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
</dependency>
</dependencies>
<build>
<finalName>MavenWP</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.3</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>
</build>
</project>三、Java Web項目的基本結構[Eclipse Dynamic Web Project]
Eclipse Dynamic Web Project項目
(1)可以配置需要編譯的源碼目錄和輸出目錄,默認編譯src目錄下的源文件到build\classes目錄下。
(2)可以配置WEB-INF的根目錄,默認為WebContent。
(3)可以選擇是否生成默認web.xml文件。
我們創建一個命名為DynamicWP的默認生成web.xml的Dynamic Web Proejct項目。文件結構如下:
|--DynamicWP
|--.settings/
|--build/
|--classes/
|--src/
|--WebContent/
|--META-INF/
|--MANIFEST.MF
|--WEB-INF/
|--web.xml
|--lib/在Eclipse的項目資源管理器中DyanmicWP項目的視圖如下:
|--DynamicWP
|--Deployment Desciptor
|--JAX-WS Web Services
|--Java Resources
|--JavaScript Resources
|--build
|--WebContent
|--META-INF/
|--MANIFEST.MF
|--WEB-INF/
|--web.xml
|--lib/1、.settings為Eclipse項目文件夾,存放了Eslipse項目的各種配置。在Eclipse項目視圖中不可見。
2、src目錄存放源碼。在Eclipse的項目視圖中對應為Java Resources/src。
3、build存放編譯后的文件。
4、可以在類似的\workspace\.metadata\.plugins\org.eclipse.wst.server.core\tmp1\wtpwebapps\DynamicWP目錄中查看運行時的文件結構。
四、servlet基礎
正如ASP.NET的核心是IHttpHandler一樣,Java Web的核心是Servlet接口,位于javax.servlet命名空間中。Filter的概念可以參考ASP.NET的HttpModule,Servlet中的各種Listener可以參考ASP.NET HttpApplicaiton中類似的event。
無論是Java還是.NET的Web技術,都是基于HTTP協議的具體實現。Java Web和ASP.NET中的一些核心項對應如下:
Servlet和ASP.NET的簡化示意圖:

用于簡化web.xml配置的Servlet的注解(3.0開始支持,在ASP.NET中沒有對應項):
(1)WebServlet:作用在javax.servlet.http.HttpServlet的實現類上。
(2)WebFilter:作用在javax.servlet.Filter的實現類上。
(3)WebListener:作用在Listener的實現類上(javax.servlet.ServletContextListener、javax.servlet.ServletContextAttributeListener、javax.servlet.ServletRequestListener、javax.servlet.ServletRequestAttributeListener、javax.servlet.http.HttpSessionListener、javax.servlet.http.HttpSessionAttributeListener)。
(4)WebInitParam:結合WebServlet和WebFilter注解用來配置屬性。
(5)MultipartConfig:作用在javax.servlet.http.HttpServlet的實現類上。標注請求是mime/multipart類型。
用于Servlet容器初始化的ServletContainerInitializer(可實現無web.xml,3.0開始支持,可類比ASP.NET的Application_Start方法):
(1)Servlet容器啟動時查找ServletContainerInitializer的實例。
(2)ServletContainerInitializer實例使用HandlesTypes標注一個或多個類型,Servlet容器將在啟動時掃描classpath,獲取這些類型的實例。
(3)Servlet容器在啟動時調用ServletContainerInitializer實現類的onStartup方法,該方法可以獲取HandlesTypes標注的所有類型對象。
五、自定義Session
Session在存儲安全性要求較高的會話信息方面是必不可少的,Session當然絕對不是用來存儲用戶登錄狀態的,但類似驗證碼等敏感信息卻必須存儲在Session中。對于分布式Web應用自定義Session支持獨立的狀態服務器或集群是必須的。
ASP.NET通過SessionStateModule通過配置文件配置實際的Session提供程序,Session提供程序實現了SessionStateStoreProviderBase,因此在ASP.NET中實現自定義Session是通過繼承SessionStateStoreProviderBase實現,配置Session是通過Web.config。

同理,Java Servlet中使用自定義Session通過Filter可以實現。由于不同的servlet容器對Session的實現不同,所以通用性最好的方式是繼承HttpServletRequestWrapper重寫getSession方法返回自定義的Session對象。
(1)首先自定義繼承HttpSession的MySession(為了便于演示,僅包裝了容器的session并轉發調用)。
import java.util.Enumeration;
import javax.servlet.ServletContext;
import javax.servlet.http.HttpSession;
public class MySession implements HttpSession {
private HttpSession _containerSession;
public MySession(HttpSession session) {
this._containerSession = session;
}
@Override
public long getCreationTime() {
return this._containerSession.getCreationTime();
}
@Override
public String getId() {
return this._containerSession.getId();
}
@Override
public long getLastAccessedTime() {
return this._containerSession.getLastAccessedTime();
}
@Override
public ServletContext getServletContext() {
return this._containerSession.getServletContext();
}
@Override
public void setMaxInactiveInterval(int interval) {
this._containerSession.setMaxInactiveInterval(interval);
}
@Override
public int getMaxInactiveInterval() {
return this._containerSession.getMaxInactiveInterval();
}
@SuppressWarnings("deprecation")
@Override
public HttpSessionContext getSessionContext() {
return this._containerSession.getSessionContext();
}
@Override
public Object getAttribute(String name) {
return this._containerSession.getAttribute(name);
}
@SuppressWarnings("deprecation")
@Override
public Object getValue(String name) {
return this._containerSession.getValue(name);
}
@Override
public Enumeration<String> getAttributeNames() {
return this._containerSession.getAttributeNames();
}
@SuppressWarnings("deprecation")
@Override
public String[] getValueNames() {
return this._containerSession.getValueNames();
}
@Override
public void setAttribute(String name, Object value) {
this._containerSession.setAttribute(name, value);
}
@SuppressWarnings("deprecation")
@Override
public void putValue(String name, Object value) {
this._containerSession.putValue(name, value);
}
@Override
public void removeAttribute(String name) {
this._containerSession.removeAttribute(name);
}
@SuppressWarnings("deprecation")
@Override
public void removeValue(String name) {
this._containerSession.removeValue(name);
}
@Override
public void invalidate() {
this._containerSession.invalidate();
}
@Override
public boolean isNew() {
return this._containerSession.isNew();
}
}(2)自定義繼承HttpServletRequestWrapper的MyRequest
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
import javax.servlet.http.HttpSession;
public class MyRequest extends HttpServletRequestWrapper {
public MyRequest() {
super(null);
}
public MyRequest(HttpServletRequest request) {
super(request);
// TODO 自動生成的構造函數存根
}
@Override
public HttpSession getSession(boolean create) {
return new MySession(super.getSession(create));
}
@Override
public HttpSession getSession() {
return new MySession(super.getSession());
}
}(3)自定義Filter將Request包裝為MyRequest
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
@WebFilter("/*")
public class MyFilter implements Filter {
@Override
public void init(FilterConfig filterConfig) throws ServletException {
// TODO 自動生成的方法存根
}
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
throws IOException, ServletException {
chain.doFilter(new MyRequest((HttpServletRequest) request), response);
}
@Override
public void destroy() {
// TODO 自動生成的方法存根
}
}通過注解配置了Filter,也可以通過原始的web.xml方式配置。
小結:
你至少應該知道的:
(1)配置文件:ASP.NET的web.config和Java的web.xml
(2)Web核心:ASP.NET的IHttpHandler接口和Java的Servlet接口
(3)攔截器:ASP.NET的HttpModule和Java的Filter
(4)應用程序事件:ASP.NET的HttpApplication event和Java的各種Listener
(5)啟動器:ASP.NET的Application_Start和Java的ServletContainerInitializer
(6)引用管理:ASP.NET的Nuget和Java的Maven
感想:
ASP.NET的核心對象不像Java Servlet一樣,從一開始就基于接口,這是缺點。但Java Servlet的核心對象全靠容器實現,就連HttpSession同樣如此,這也是缺點。比如自定義個Session十分麻煩,沒有像ASP.NET一樣簡單配置即可。另外Servlet的一些抽象定義有點過頭了,不夠簡潔。
關于Java Web項目的基礎知識就分享到這里了,希望以上內容可以對大家有一定的幫助,可以學到更多知識。如果覺得文章不錯,可以把它分享出去讓更多的人看到。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。