strust2框架來歷簡介:
WebWork是由OpenSymphony組織開發的,致力于組件化和代碼重用的J2EE Web框架。(同時也是一個成熟的基于Web的MVC框架)
MVC:Model View Controller, model是模型,view是視圖,controller是控制器,是一種框架模式.
隨著WebWork框架的發展,衍生出了strust2框架,因此strust2框架是WebWork的升級,而不是一個全新的框架,因此穩點性、性能等方面都有很好的保證,而且也同時吸收了struts1框架和WebWork倆者的優點.所以strust2框架也是一個基于Web的MVC框架
注意:strust2框架并不是struts1框架的延續或者升級,倆者有著很大的不同
web項目中的三層架構(和MVC是倆個完全不同的架構)
表示層
Struts2框架就是工作在這個地方
業務邏輯層
service層,處理業務邏輯,比如判斷用戶名是否存在、密碼是否正確、權限是否擁有、賬號是否被凍結、賬號是否異常、用戶積分是否到達操作要求等等,多為一些執行某一個操作條件的判斷
數據訪問層
dao層,專門處理和數據庫進行交換的事情,jdbc/hibernate就在這里使用
在項目中,這些不同的分層的表現形式,其實就是在我們自己建的不同的package中寫上各自分層中所使用的java類.比如在項目中我們建了三個package,三個package中java類的作用分別為表示層的代碼、業務邏輯層代碼、數據訪問層代碼.
注意:可以理解為,MVC架構是這里說描述的三層架構的一部分,即:三層架構中的表示層可以使用mvc架構的框架來實現,例如使用struts2框架.
使用struts2框架的好處(為什么要使用struts2框架)
減少編程人員代碼的編寫,使代碼更加簡潔明了,縮短開發時間,增加開發效率.
struts2框架引入到web項目中
首先使用Eclipse/MyEclipse中建一個web項目.
- 把struts2相關jar包引入到項目中
- 把struts2的配置文件直接放到src下面,名字要叫做struts.xml.(運行時配置文件會被框架自動讀取).
注意:如果struts.xml文件中不能自動提示出標簽,把相應的dtd文件配置上去. - 在web.xml文件中配置struts2框架的過濾器.
這個過濾器的作用:攔截struts2框架中的action.注意:如果不配置這個filter,struts2框架就不能夠工作.
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>*.action</url-pattern>
</filter-mapping>
struts2框架中的Action
struts2框架中有一種java類叫做Action,這種說法就像J2EE項目中有一種java類加Servlet.(人們的生活中有一種人的職業叫警察)struts2框架底層還是封裝了Servlet的相關內容而實現出來的.只不過struts2框架除了servlet的功能以外還擴展出了很多其他的功能,同時還大大簡化了以前在servlet中繁瑣的操作.
在struts2框架中有一種類就是用代替以前我們在web項目中所使用到的servlet,那么這種類,在struts2框架中被稱為Action.所以Action其實也是一種java類,比servlet功能更加強大的java類,同時還比servlet中的操作簡單.
為什么Action會有比servlet強大的功能以及簡潔的操作
因為我們在web.xml文件中配置了struts2框架中專門的過濾器,用作攔截訪問action的請求,攔截住之后,struts2框架就可以給Action添加很多豐富的功能了.
如何寫一個struts2框架中的Action
三種方式:
-
只需要類中有一個固定的方法:
public String execute(){ return "..." }
不需要實現或者繼承任何接口或者父類。
注意: execute方法一定要返回String類型的對象,每一個字符串都可以對應一個跳轉的頁面.(字符串是可以自己隨便定義的,字符串對應哪一個跳轉的頁面也是自己定義,在struts.xml文件中定義)
- 實現指定的一個接口:
com.opensymphony.xwork2.Action
這個接口中只有一個抽象方法public abstract String execute()throws Exception;
同時還有5個String類型的靜態屬性:ERROR SUCCESS INPUT NONE LOGIN
public static final String SUCCESS = "success";
public static final String NONE = "none";
public static final String ERROR = "error";
public static final String INPUT = "input";
public static final String LOGIN = "login";
- 繼承一個指定的父類:com.opensymphony.xwork2.ActionSupport
注意:這種是我們之后一直使用的方式。
像之前寫完servlet類一樣,寫完action類后需要在struts.xml文件中進行配置.
在struts.xml配置action的目的和作用:通知struts2框架我們寫的這個類是一個Action,將來struts2框架中要給這個類創建對象,調用方法以及這個Action加入更多豐富的功能。
例如:
<package name="test" extends="struts-default" namespace="/test">
<action name="MyTest">
<result>/index.jsp</result>
</action>
<action name="test1" class="com.briup.web.action.ActionTest1">
<result name="myFirstAction">/success.jsp</result>
<result name="myError">/error.jsp</result>
</action>
</package>
配置中<package>
標簽及其屬性的介紹:
<package name="test" extends="struts-default" namespace="/test">
<package>:一個struts.xml文件中可以配置多個<package>標簽,一個<package>標簽里面可以配置多個<action>標簽,一個<action>標簽里面可以配置多個<result>
-
name="test"
表示給當前package起一個名字為test
作用:- 唯一標識當前這個package。
- 方便package與package之間通過這個名字來實現繼承的關系.(像類和類之間的繼承一樣,要通過父類的名字來繼承)
extends="struts-default"
表示當前這個package繼承了另外一個名字叫做struts-default的package,這個package在struts2的核心jar包中的struts-default.xml文件中定義的,里面定義了很默認的配置.
注意:我們在struts2中定義的所有package,都會是直接或者間接的繼承了struts-default這個package.(像java中所有類都是直接或間接的繼承了Object類一樣)namespace="/test"
表示當前package的命名空間為/test,將來這個package里面的所有的action在被訪問的時候,路徑里面都要加上這個命名空間.
配置中<action>標簽屬性及其子標簽介紹:
name="test1"
表示當前配置這個action的名字為test1,這個名字是隨便起的,可以和action類的名字相同或者不同.同時將來瀏覽器中的地址欄里面就是要出現這個名字來訪問當前這個action類class=".."
表示當前配置的action對應的是哪一個java類,我們可以配置一個action,但是這個action可以沒有對應任何java類。就像上面配置的MyTest的例子.-
<result>
標簽表示將來這個action訪問完了之后有哪些跳轉.
<result name="myError">/error.jsp</result>
表示當前這個action如果返回的字符串是myError,就那么頁面就跳轉到/error.jsp中
注意:每一個action被訪問完之后都會有一個字符串類型的返回值,即使訪問一個每一個任何java類對應action的時候,這個action也會默認返回字符串:success <result name="success">/index.jsp</result> 等價于 <result>/index.jsp</result> <result>標簽中的name屬性默認值就是success
特殊的action配置:使用通配符來配置
使用前提:原本需要配送的多個action名字或者類的名字是有一定規律的.
例如:原來需要配置這樣三個action:
<action name="testCh1" class="com.briup.web.action.ActionTestCh1">
<result>/successCh1.jsp</result>
<result name="error">/errorCh1.jsp</result>
</action>
<action name="testCh2" class="com.briup.web.action.ActionTestCh2">
<result>/successCh2.jsp</result>
<result name="error">/errorCh2.jsp</result>
</action>
<action name="testCh3" class="com.briup.web.action.ActionTestCh3">
<result>/successCh3.jsp</result>
<result name="error">/errorCh3.jsp</result>
</action>
這時候,我們就可以使用通配符配置一個action來代替這個三個action:
<action name="test*" class="com.briup.web.action.ActionTest{1}">
<result>/success{1}.jsp</result>
<result name="error">/error{1}.jsp</result>
</action>
{1}代表的時候前面name屬性中所出現的第一個號如果有第二個號,可以用{2}來表示。
test就是將來在瀏覽器中輸入的這個action名字,如果輸入的時候test1,那么這個號就代表1,如果輸入的是testlogin,那么這個*號就是代表login.
注意:如果原本需要配置的多個action沒有非常明顯的規律,那么就不要用這種方式來配置了.
action的特點及其訪問
特點:
- servlet是線程不安全的,因為servlet是單例。
- struts2框架中的action是線程安全的,因為每次訪問都會創建一個新的Action對象.所有在action里面可以隨便的定義成員變量(只有成員變量才有線程安全的問題)
訪問:
默認情況下,訪問action的時候,使用namespace/actionName.action或者namespace/actionName就可以訪問的到.
例如:
<package name="test" extends="struts-default" namespace="/test">
<action name="test1" class="類A">
<result>/index.jsp</result>
</action>
</package>
http://ip地址:端口號/項目名字/test/test1.action
或者
http://ip地址:端口號/項目名字/test/test1
訪問成功頁面就會跳轉到index.jsp頁面了
但是由于不加任何后綴名也可以訪問到這個action,這樣容易和其他資源的訪問產生沖突,
比如servlet的訪問(本來是訪問項目的servlet的,但是Struts2框架卻當成了這是訪問action的請求來處理).
所以我們需要配置一下,把action訪問規定成,只能使用后綴名.action或者是.do 或者是其他形式來訪問.
//可以使用.action或者.do來訪問
<constant name="struts.action.extension" value="action,do"></constant>
//只能使用.action
<constant name="struts.action.extension" value="action"></constant>
訪問action的時候,action中方法的調用
默認情況下,訪問action的時候會調用action中的execute方法,這個方法執行完返回一個字符串,然后根據字符串進行跳轉.
-
可以在
<action>
標簽里面加上一個method屬性,來指明將來訪問這個action的時候會調用哪一個方法.
例如:<action name="test" class=".." method="login">
注意:倆個不同名字的action可以對應的是相同的一個java類.
<action name="test1" class="類A" method="login"> <action name="test2" class="類A" method="register">
這樣使用test1和test2倆個不同名字的action就是訪問到同一個類中的倆個不同的方法:login和regist方法.但是login方法和register方法必須和execute方法類似的,都是返回String的值.
-
地址欄中動態指定要調用的方法
例如:<package name="test" extends="struts-default" namespace="/test"> <action name="MyTest" class="類A"> <result>/index.jsp</result> </action> </package>
類A里面有倆個方法:register login
默認情況下地址欄中通過MyTest.action來訪問這個action會訪問到它的execute方法,同時我們還可以在地址欄中動態的指定要訪問的方法:
MyTest!login.action 這樣就能訪問到名字為MyTest的action對應類A中的login方法了.
測試:http://ip地址:端口號/項目名字/test/MyTest!login.action