Struts框架內部的值調用機制的研究

 

Struts框架內部的值調用機制的研究

我們經常在使用struts框架,頻繁調用formaction等,但是我們可能對它內部的一些機制並不是很清楚。我們調用struts框架的流程一般爲:jsp把頁面上的值傳給form,再傳遞給action處理,然後把處理結果返回給jsp顯示。在這個過程中, jsp頁面所定義的值是如何傳遞的?form的生命週期又是怎麼樣的?我們並沒有深入研究,而一些問題也就由此產生。

下面針對我們在應用struts中,所遇到的這些問題,以及驗證後的結果現象,對struts內部的值調用機制進行詳細說明和解釋,希望有助於以後struts框架的使用。

1.出現的問題:

在項目中使用struts中,我們發現如下問題:struts框架下的值傳遞,form的值生命週期並不是我們原來想象的那麼簡單,具體現象如下:

有一個jsp頁面,如下圖所示:

 

 

 

頁面上有查詢和顯示兩部分操作功能,整個頁面的在struts框架下分爲幾個部分:一個jsp(如圖所示);一個form(與jsp中的元素相對應);爲了便於邏輯處理,設定兩個action(共用前面的form),一個action(命名爲action1),邏輯處理爲處理查詢操作,並把結果顯示於jsp頁面上,另一個action(命名爲action2),邏輯處理爲執行“取消疑點”操作,並調用到action1(由action1重新執行查詢邏輯後,把結果顯示於jsp頁面)。需要注意的是,這裏是action2調用action1,然後再由action1把結果返回到jsp頁面上,action2並不直接調用jsp頁面。

jsp頁面,爲實現“取消疑點”功能,目前採用兩種實現方法,

1)jsp頁面上,通過超連接,調用js函數來實現“取消”功能,形式如下:

 

<a href="javascript: goDetail('../action2.do?Param=11,22,33’);">取消疑點</a>

 

Jsp頁面上的goDetail()函數實現爲:

 

<script language="javascript">

<!--

function goDetail (str)

{

if(confirm("是否確定要取消這條記錄?"))

{

url = str;

form = document.form;

form.action=url;

form.submit();

}

2) jsp頁面上,通過超連接,不調用js函數直接實現“取消”功能,形式如下:

<a href="../action2.do?&Param=11,22,33">取消疑點</a>

在以上兩種實現方式下,看起來實現“取消”功能是一樣的:通過action2執行“取消”操作,然後通過action1把處理以後的結果顯示在jsp上。對於實現“取消”功能,以上兩種實現方法都可以實現,但是我們還要實現的附加功能之一是:jsp頁面上的查詢條件,例如:證照類型(zzlx)等,通過action2 action1的處理之後,值依然能保存,並在jsp頁面顯示出來。

測試的結果表明:方法一通過action2action1處理後,在jsp頁面上查詢條件是可以保存的,而方法二通過action2action1處理後,在jsp頁面上查詢條件並不能保存;同時我們發現,在方法一的測試中,如果在acton2中,用form.setZzlx(”10”)(在jsp頁面上,“10”代表“證照類型“爲“身份證”)來改變jsp頁面的屬性――“證照類型”原來的值(例如:原來的值爲“20”,代表“軍官證”,這個值是jsp頁面傳入的),並期待這個改變的值能在jsp頁面上顯示出來,其結果是失敗的。結果顯示的,證照類型在經過action2改變,通過action1jsp顯示時,其顯示值仍然爲“20”,並不是我們想象中的“10”

如果我們把第二種方法增加連接參數,改爲:

<a href="../action2.do?& zzlx =20&Param=11,22,33">取消疑點</a>

增加超連接的參數“zzlx =20”,查詢條件的值是可以通過action2action1處理後,值得到保存,並在jsp頁面上顯示出來。

2.問題的分析:

根據以上的現象,我們對struts-config.xml中的action權限範圍發生了興趣,經過查找,其權限範圍struts-config.xml中表現如下:

<action-mappings>

<action name="form" type="gov.chinatax.grsds.bims.web.compare.action1" scope="request" path="/action1">

<forward name="failure" path="error"/>

<forward name="success" path="/compare/agent_difference_biggish.jsp" />

</action>

<action name="form" type="gov.chinatax.grsds.bims.web.compare.action2" scope="request" path="/action2">

<forward name="failure" path="error"/>

<forward name="success" path="/compare/agent_difference_biggish.jsp" />

</action>

</action-mappings>

這表明action2action1的範圍爲“request(scope="request"得到)。由此,我們分析如下:

1)當jsp頁面調用*.do(例如:上面jsp頁面調用的是:action2.do),把屬性傳給action2這個類(具體位置爲:type="gov.chinatax.grsds.bims.web.compare.action2"),jsp把頁面上的屬性值(例如:證照類型的值)傳遞給request暫時保存(爲什麼是request?從struts-config.xmlscope="request"獲得);

2)當程序執行到action2時,生成一個 formrequest把從jsp中獲取的屬性值放入form中,這樣action2就可以通過form .get×××()來調用jsp頁面的屬性值了。當action2處理完成,轉入另一個action――action1時,action2所對應的form也將消失,新的action――action1開始生成一個新的formrequest 再把從jsp中獲取的值放入這個新生成的form中。我們用form.setZzlx(”10”)來試圖影響action1所對應的form是不能奏效的。因爲每個action都要生成一個新的formaction2生成的form只存在於action2的週期範圍內,action2結束,form中的值隨同form一起消失了,同時,在兩個action之間調用時,form set×××()並不能把值由form傳給request。因此在調用action1時,action2的值並不能傳入action1對應的form,所以也就不能由action1傳給jsp,在頁面上也不能顯示出來;

3)當action1調用jsp時,form中的值通過request傳給jsp頁面,這時候,用form.setZzlx(”10”)來改變條件的值,是可以在頁面上顯示的;

至於爲什麼jsp上的第一種方法是可以把屬性值傳過去的,而第二中方法爲什麼必須要增加超連接的參數“zzlx =20”,才能把這個條件參數傳過去。原因也不理解,看方法一與方法二有什麼差別?細心的各位已經發現區別了吧?對了,就是這個:第一個是用form.submit()提交,調用action的,而第二個是直接用超連接調用的。如果用submit()提交,jsp頁面上的所有值,都會放入request中,傳入action所對應的form中的;而直接用超連接調用,並不經過submit(),這樣,jsp頁面上的值並沒有任何渠道傳入request,除非,增加超連接的參數“zzlx =20”,讓request有渠道獲得zzlx參數的值。

權限範圍是不是真的從struts-config.xmlscope="××× "中獲得,你可能有所懷疑,不要怕,可以看看struts-config.xml中“登錄頁面”的action的設置?是不是scope="session"?這就表明,它的生命週期爲整個session的週期,所以登錄頁面設置的參數值將會在連接的整個生命週期內存在。

上面說action不能通過form.set×××()傳值給request,如果我們堅持通過actionrequest傳值怎麼辦?在action中調用request.setAttribute( )函數來實現吧。

3.結論

根據以上分析,我們可以得出使用struts框架的幾點結論:

1jsp調用actionaction調用jsp都是通過在struts-config.xml中設定的對應action的權限範圍進行的,例如上面我們設定爲request,則放入request中進行;

2Form在兩個action直接轉換時,form是要重新生成的,兩個action中對應的form值並不能直接傳遞;

3)試圖在action中通過設定form中屬性的值,進而來影響jsp傳入的屬性值,如果這個action還需要再調用一個action,而不是之際調用jsp,那麼這中方法將是徒勞的,因爲如果action不與jsp相互調用,通過orm set×××()方法時不能把值傳遞給action的權限範圍(例如:request)的;

4jsp頁面的屬性值,通過submit()提交來調用action和直接用超連接來調用action,其結果是不同的。利用submit()是可以把jsp頁面的屬性值傳給action的,而超連接則不能。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章