[英]How to start a Jersey Test Container (Grizzly) once for all tests in a test class?
我正在努力修復其中一個項目中的集成測試。 目前,所有集成測試類都擴展了JerseyTest類。 通過JerseyTest類,我意識到它使用Junit的Before和After注釋為每個測試方法啟動和停止容器。
為什么這有必要? 如果我們提起容器一次,運行測試並在結束時將其關閉,這還不夠嗎?
我們也使用Spring,上下文初始化需要時間。
在Junit4之前,我們通過使用布爾標志手動處理它來解決這個限制。
@Before
public void setup() {
if(!containerStarted) {
// start
containerStarted = true;
}
// else do nothing
}
您可以使用@BeforeClass和@AfterClass來覆蓋JerseyTest的@Before和@After生命周期。 這是代碼模板:
public abstract class MyJerseyTest {
private JerseyTest jerseyTest;
public MyJerseyTest(){
}
@BeforeClass
public void setUp() throws Exception {
initJerseyTest()
jerseyTest.setUp();
}
@AfterClass
public void tearDown() throws Exception {
jerseyTest.tearDown();
}
private void initJerseyTest() {
jerseyTest = new JerseyTest() {
@Override
protected Application configure() {
// do somthing like
enable(...);
set(...);
// create ResourceConfig instance
ResourceConfig rc = new ResourceConfig();
// do somthing like
rc.property(...);
rc.register(...);
return rc;
}
};
}
}
希望這是有幫助的。
我們有類似的情況,使用球衣加彈簧作為依賴注入框架(平針彈簧橋)。 使用JerseyTest
框架編寫集成測試很棘手,因為它在測試之前啟動容器並在測試之后停止容器。 這種方法可能有一個優點,但考慮到spring每次都會掃描和自動裝配bean這一事實,它非常耗時且棘手。
如何初始化一個灰熊容器並將其用於測試類中的所有測試?
為實現上述目標,我按照以下步驟操作:
在測試類中作為實例變量,聲明HttpServer
的實例如下
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { "classpath:applicationContext.xml" })
public class OrderResourceTest {
...
public static final String BASE_URI = "http://localhost:8989/";
private static HttpServer server = null;
...
...
}
請注意,我不使用JerseyTest
因為我想自己處理測試容器的啟動/停止。 現在,您需要使用@Before
和@AfterClass
來設置服務器實例。 在@Before
我們將設置server
實例,以便在web.xml
加載我們的自定義過濾器/偵聽器定義(例如以編程方式將web.xml加載到server
實例中)
@Before
public void setUp() throws Exception {
if (server == null) {
System.out.println("Initializing an instance of Grizzly Container");
final ResourceConfig rc = new ResourceConfig(A.class, B.class);
WebappContext ctx = new WebappContext() {};
ctx.addContextInitParameter("contextConfigLocation", "classpath:applicationContext.xml");
ctx.addListener("com.package.something.AServletContextListener");
server = GrizzlyHttpServerFactory.createHttpServer(URI.create(BASE_URI), rc);
ctx.deploy(server);
}
}
如果您注意到我正在使用@Before但if條件將使其作為@BeforeClass運行。 不要完全記住為什么我沒有使用@BeforeClass
,我的猜測可能是由於if塊中的一些配置。 無論如何,如果你好奇,試一試。
web.xml
上下文init參數,例如applicationContext
。 applicationContext
包含基於spring的配置。 ctx
。 ResourceConfig
實例,使用Grizzly實例初始化server
WebappContext
,它只是web.xml,現在使用它的deploy方法將服務器實例傳遞給它。 這將運行WebappContext
配置並將其部署到server
實例。 現在,你有一個測試運行Grizzly的實例,你的web.xml加上應用於實例的特定於spring的配置。
@AfterClass
看起來如下
@AfterClass
public static void tearDown() throws Exception {
System.out.println("tearDown called ...");
if (server != null && server.isStarted()) {
System.out.println("Shutting down the initialized Grizzly instance");
server.shutdownNow();
}
}
並使用REST保證框架進行示例測試
@Test
public void testGetAllOrderrs() {
List<Orders> orders= (List<Orders>)
when().
get("/orders").
then().
statusCode(200).
extract().
response().body().as(List.class);
assertThat(orders.size()).isGreaterThan(0);
}
上面的原因在沒有指定基本路徑的情況下工作是因為我將REST保證的基本路徑設置如下
RestAssured.baseURI = "http://localhost:8989/";
如果您不想使用REST保證那么
@Test
public void testGetAllOrders() {
Client client = ClientBuilder.newBuilder().newClient();
WebTarget target = client.target(BASE_URI);
Response response = target
.path("/orders")
.request(MediaType.APPLICATION_JSON)
.get();
assertThat(response.getStatus()).isEqualTo(200);
JSONArray result = new JSONArray(response.readEntity(String.class));
assertThat(result.length()).isGreaterThan(0);
}
澤西島進口
import org.glassfish.grizzly.http.server.HttpServer;
import org.glassfish.grizzly.servlet.WebappContext;
import org.glassfish.jersey.grizzly2.httpserver.GrizzlyHttpServerFactory;
import org.glassfish.jersey.server.ResourceConfig;
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.