Shiro 單元測(cè)試

2021-06-21 10:43 更新

單元測(cè)試主要是關(guān)于測(cè)試您的代碼,而僅是在有限范圍內(nèi)的代碼??紤]到 Shiro 時(shí),您 true 要關(guān)注的是您的代碼可以與 Shiro 的* API *一起正常工作-您并不需要測(cè)試 Shiro 的實(shí)現(xiàn)是否正常工作(這是 Shiro 開發(fā)團(tuán)隊(duì)必須確保的事情)在 Shiro 的代碼庫(kù)中)。

檢驗(yàn) Shiro 的實(shí)現(xiàn)是否可以與您的實(shí)現(xiàn)一起工作的測(cè)試實(shí)際上是集成測(cè)試(下面討論)。

Shiro單元測(cè)試實(shí)例

因?yàn)閱卧獪y(cè)試更適合測(cè)試您自己的邏輯(而不是您的邏輯可能調(diào)用的任何實(shí)現(xiàn)),所以“模擬”您邏輯所依賴的任何 API 是一個(gè)好主意。這在 Shiro 上非常有效-您可以模擬?Subject?接口,并使其反映您希望被測(cè)代碼對(duì)之做出反應(yīng)的任何條件。我們可以利用諸如EasyMock和Mockito之類的現(xiàn)代模擬框架為我們完成此任務(wù)。

但是如上所述,Shiro 測(cè)試中的關(guān)鍵是要記住在測(cè)試執(zhí)行期間必須將任何 Subject 實(shí)例(模擬或真實(shí))綁定到線程。因此,我們要做的就是綁定模擬主題,以確保事情按預(yù)期進(jìn)行。

(此示例使用 EasyMock,但 Mockito 的效果也一樣):

import org.apache.shiro.subject.Subject;
import org.junit.After;
import org.junit.Test;

import static org.easymock.EasyMock.*;

/**
 * Simple example test class showing how one may perform unit tests for 
 * code that requires Shiro APIs.
 */
public class ExampleShiroUnitTest extends AbstractShiroTest {

    @Test
    public void testSimple() {

        //1.  Create a mock authenticated Subject instance for the test to run:
        Subject subjectUnderTest = createNiceMock(Subject.class);
        expect(subjectUnderTest.isAuthenticated()).andReturn(true);

        //2. Bind the subject to the current thread:
        setSubject(subjectUnderTest);

        //perform test logic here.  Any call to
        //SecurityUtils.getSubject() directly (or nested in the
        //call stack) will work properly.
    }

    @After
    public void tearDownSubject() {
        //3. Unbind the subject from the current thread:
        clearSubject();
    }

}

如您所見,我們沒有設(shè)置 Shiro ?SecurityManager?實(shí)例或配置?Realm?或類似的東西。我們只是在創(chuàng)建一個(gè)模擬?Subject?實(shí)例,并通過?setSubject?方法調(diào)用將其綁定到線程。這樣可以確保測(cè)試代碼或我們正在測(cè)試的?SecurityUtils.getSubject()?代碼中的所有調(diào)用均能正常工作。

請(qǐng)注意,?setSubject?方法實(shí)現(xiàn)會(huì)將您的模擬 Subject 綁定到線程,并且將保留在那里,直到您使用其他?Subject?實(shí)例調(diào)用?setSubject?或通過?clearSubject()?調(diào)用從線程中明確清除它為止。

保持主題與線程綁定多長(zhǎng)時(shí)間(或?qū)⑵涮鎿Q為其他測(cè)試中的新實(shí)例)取決于您和您的測(cè)試要求。

tearDownSubject()

該示例中的?tearDownSubject()?方法使用 Junit 4 注解,以確保無論執(zhí)行哪種測(cè)試方法,在執(zhí)行線程后都會(huì)從線程中清除 Subject。這要求您設(shè)置一個(gè)新的?Subject?實(shí)例,并為每個(gè)執(zhí)行的測(cè)試(通過?setSubject?)進(jìn)行設(shè)置。

但是,這并非絕對(duì)必要。例如,您可以在每個(gè)測(cè)試的開始(例如,以?@Before?Comments 的方法)(通過setSujbect)綁定一個(gè)新的 ?Subject? 實(shí)例。但是,如果要執(zhí)行此操作,則最好使用?@After tearDownSubject()?方法保持事物對(duì)稱和“干凈”。

您可以在每種方法中手動(dòng)混合和匹配此設(shè)置/拆卸邏輯,或者使用@Before 和@AfterComments(如果您認(rèn)為合適)。但是,由于所有測(cè)試中的tearDownShiro()方法中都有?@AfterClass?注解,因此?AbstractShiroTest?超類將在所有測(cè)試后將其從線程中解除綁定。

以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)