[java] Java Jersey에서 요청 처리시 처리 시간 측정하는 방법은?
Jersey는 Java로 구현된 RESTful 웹 서비스 프레임워크입니다. 이 중에서도 요청의 처리 시간 측정은 매우 중요한 기능 중 하나입니다. 이를 통해 애플리케이션의 성능을 모니터링하거나 병목 현상을 발견할 수 있습니다.
Java Jersey에서 요청 처리 시간을 측정하는 방법은 다음과 같습니다:
- 필터를 사용하는 방법:
ContainerRequestFilter
와ContainerResponseFilter
인터페이스를 구현하는 필터 클래스를 생성합니다.ContainerRequestFilter
에서ContainerRequestContext
객체를 통해 요청 시작 시간을 기록합니다.ContainerResponseFilter
에서ContainerRequestContext
객체를 통해 요청 종료 시간을 기록하고, 두 시간을 빼서 처리 시간을 계산합니다.
import javax.ws.rs.container.ContainerRequestContext;
import javax.ws.rs.container.ContainerRequestFilter;
import javax.ws.rs.container.ContainerResponseContext;
import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.core.Response;
import java.io.IOException;
public class TimingFilter implements ContainerRequestFilter, ContainerResponseFilter {
private static final String START_TIME = "startTime";
@Override
public void filter(ContainerRequestContext requestContext) throws IOException {
requestContext.setProperty(START_TIME, System.currentTimeMillis());
}
@Override
public void filter(ContainerRequestContext requestContext, ContainerResponseContext responseContext) throws IOException {
long startTime = (long) requestContext.getProperty(START_TIME);
long endTime = System.currentTimeMillis();
long elapsedTime = endTime - startTime;
Response.ResponseBuilder builder = Response.fromResponse(responseContext.getResponse());
builder.header("X-Processing-Time", elapsedTime);
responseContext.setResponse(builder.build());
}
}
- Interceptor를 사용하는 방법:
ReaderInterceptor
와WriterInterceptor
인터페이스를 구현하는 인터셉터 클래스를 생성합니다.ReaderInterceptor
에서ReaderInterceptorContext
를 통해 요청 시작 시간을 기록합니다.WriterInterceptor
에서WriterInterceptorContext
를 통해 요청 종료 시간을 기록하고, 두 시간을 빼서 처리 시간을 계산합니다.
import javax.ws.rs.WebApplicationException;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.MultivaluedMap;
import javax.ws.rs.ext.ReaderInterceptor;
import javax.ws.rs.ext.ReaderInterceptorContext;
import javax.ws.rs.ext.WriterInterceptor;
import javax.ws.rs.ext.WriterInterceptorContext;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public class TimingInterceptor implements ReaderInterceptor, WriterInterceptor {
private static final String START_TIME = "startTime";
@Override
public Object aroundReadFrom(ReaderInterceptorContext context) throws IOException, WebApplicationException {
context.setProperty(START_TIME, System.currentTimeMillis());
return context.proceed();
}
@Override
public void aroundWriteTo(WriterInterceptorContext context) throws IOException, WebApplicationException {
long startTime = (long) context.getProperty(START_TIME);
long endTime = System.currentTimeMillis();
long elapsedTime = endTime - startTime;
MultivaluedMap<String, Object> headers = context.getHeaders();
headers.add("X-Processing-Time", elapsedTime);
context.proceed();
}
}
- 어노테이션을 사용하는 방법:
@NameBinding
어노테이션을 사용하여 자신만의 어노테이션을 생성합니다.- 해당 어노테이션을 필터나 인터셉터에 적용하여 처리 시간을 측정합니다.
import javax.ws.rs.GET;
import javax.ws.rs.NameBinding;
import javax.ws.rs.Path;
import javax.ws.rs.container.ContainerRequestFilter;
import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.container.DynamicFeature;
import javax.ws.rs.container.ResourceInfo;
import javax.ws.rs.core.FeatureContext;
import javax.ws.rs.core.Response;
import javax.ws.rs.ext.Provider;
@NameBinding
public @interface TimingMeasurement {
}
@Path("/example")
public class ExampleResource {
@GET
@TimingMeasurement
public Response exampleMethod() {
// 처리할 로직
return Response.ok().build();
}
}
@Provider
public class TimingFeature implements DynamicFeature {
@Override
public void configure(ResourceInfo resourceInfo, FeatureContext context) {
if (resourceInfo.getResourceMethod().isAnnotationPresent(TimingMeasurement.class)) {
context.register(TimingFilter.class);
}
}
}
이렇게 하는 것으로 Java Jersey에서 요청 처리 시간을 측정할 수 있습니다. 성능 모니터링 및 병목 현상 분석에 유용하게 사용할 수 있습니다.
참고 자료: