private void processEvent(AsyncEvent event) throws IOException { Entity prior = recorder.getTraceEntity(); try { Entity entity = (Entity) event.getSuppliedRequest().getAttribute(ENTITY_ATTRIBUTE_KEY); recorder.setTraceEntity(entity); if (null != event.getThrowable()) { entity.addException(event.getThrowable()); } filter.postFilter(event.getSuppliedRequest(), event.getSuppliedResponse()); } finally { recorder.setTraceEntity(prior); } }
private void onAsyncStart(AsyncContext newAsyncContext) { final boolean setupRequired = SecurityActions.currentServletRequestContext() == null; ThreadSetupAction.Handle handle = null; if (setupRequired) { handle = servletRequestContext.getDeployment().getThreadSetupAction().setup(exchange); } try { //now run request listeners setupRequestContext(setupRequired); try { for (final BoundAsyncListener listener : asyncListeners) { //make sure we use the new async context AsyncEvent event = new AsyncEvent(newAsyncContext, listener.servletRequest, listener.servletResponse); try { listener.asyncListener.onStartAsync(event); } catch (IOException e) { UndertowServletLogger.REQUEST_LOGGER.ioExceptionDispatchingAsyncEvent(e); } } } finally { tearDownRequestContext(setupRequired); } } finally { if (setupRequired) { handle.tearDown(); } } }
@Override public void onComplete(AsyncEvent arg0) throws IOException { // 返回信息 OutputStream os = ac.getResponse().getOutputStream(); InputStream is = response.getEntity().getContent(); // 调用微信平台的Callback HttpClientCallbackResult result = new HttpClientCallbackResult(is, os); result.setRetCode(getStatusCode()); try { callback.completed(result); } catch (RuntimeException e) { // ignore } finally { os.flush(); os.close(); is.close(); } }
@Override public void onError(AsyncEvent arg0) throws IOException { // 也要返回合理的错误信息 try { OutputStream os = ac.getResponse().getOutputStream(); HttpClientCallbackResult result = new HttpClientCallbackResult(null, os); HttpAsyncException exp = new HttpAsyncException(HttpAsyncException.ExceptionEvent.REQASYNC_ERROR, arg0.getThrowable()); result.setRetCode(getStatusCode()); result.setException(exp); callback.failed(result); } catch (RuntimeException e) { // ignore } }
@Override public void onTimeout(AsyncEvent arg0) throws IOException { // 超时,也要返回合理的错误信息 try { OutputStream os = ac.getResponse().getOutputStream(); HttpClientCallbackResult result = new HttpClientCallbackResult(null, os); HttpAsyncException exp = new HttpAsyncException(HttpAsyncException.ExceptionEvent.REQASYNC_TIMEOUT, arg0.getThrowable()); result.setRetCode(getStatusCode()); result.setException(exp); callback.failed(result); } catch (RuntimeException e) { // ignore } }
private void handleTimeoutOrError(AsyncEvent event, String message) { PrintWriter writer = null; try { future.cancel(true); HttpServletResponse response = (HttpServletResponse) event.getAsyncContext().getResponse(); //HttpServletRequest request = (HttpServletRequest) event.getAsyncContext().getRequest(); //request.getRequestDispatcher("/app/error.htm").forward(request, response); writer = response.getWriter(); writer.print(message); writer.flush(); } catch (Exception ex) { // FIXME: logger.error(ex); } finally { event.getAsyncContext().complete(); if (writer != null) { writer.close(); } } }
public void setStarted(Context context, ServletRequest request, ServletResponse response, boolean originalRequestResponse) { synchronized (asyncContextLock) { this.request.getCoyoteRequest().action(ActionCode.ASYNC_START, this); this.context = context; this.servletRequest = request; this.servletResponse = response; this.hasOriginalRequestAndResponse = originalRequestResponse; this.event = new AsyncEvent(this, request, response); List<AsyncListenerWrapper> listenersCopy = new ArrayList<AsyncListenerWrapper>(); listenersCopy.addAll(listeners); listeners.clear(); for (AsyncListenerWrapper listener : listenersCopy) { try { listener.fireOnStartAsync(event); } catch (Throwable t) { ExceptionUtils.handleThrowable(t); log.warn("onStartAsync() failed for listener of type [" + listener.getClass().getName() + "]", t); } } } }
@Test public void startDeferredResultProcessingTimeoutAndResumeThroughCallback() throws Exception { final DeferredResult<Integer> deferredResult = new DeferredResult<Integer>(); deferredResult.onTimeout(new Runnable() { @Override public void run() { deferredResult.setResult(23); } }); this.asyncManager.startDeferredResultProcessing(deferredResult); AsyncEvent event = null; this.asyncWebRequest.onTimeout(event); assertTrue(this.asyncManager.hasConcurrentResult()); assertEquals(23, this.asyncManager.getConcurrentResult()); assertEquals("/test", ((MockAsyncContext) this.servletRequest.getAsyncContext()).getDispatchedPath()); }
@Test public void startDeferredResultProcessingTimeoutAndResumeThroughInterceptor() throws Exception { DeferredResult<Integer> deferredResult = new DeferredResult<Integer>(); DeferredResultProcessingInterceptor interceptor = new DeferredResultProcessingInterceptorAdapter() { @Override public <T> boolean handleTimeout(NativeWebRequest request, DeferredResult<T> result) throws Exception { result.setErrorResult(23); return true; } }; this.asyncManager.registerDeferredResultInterceptor("interceptor", interceptor); this.asyncManager.startDeferredResultProcessing(deferredResult); AsyncEvent event = null; this.asyncWebRequest.onTimeout(event); assertTrue(this.asyncManager.hasConcurrentResult()); assertEquals(23, this.asyncManager.getConcurrentResult()); assertEquals("/test", ((MockAsyncContext) this.servletRequest.getAsyncContext()).getDispatchedPath()); }
@Test public void startDeferredResultProcessingAfterTimeoutException() throws Exception { DeferredResult<Integer> deferredResult = new DeferredResult<Integer>(); final Exception exception = new Exception(); DeferredResultProcessingInterceptor interceptor = new DeferredResultProcessingInterceptorAdapter() { @Override public <T> boolean handleTimeout(NativeWebRequest request, DeferredResult<T> result) throws Exception { throw exception; } }; this.asyncManager.registerDeferredResultInterceptor("interceptor", interceptor); this.asyncManager.startDeferredResultProcessing(deferredResult); AsyncEvent event = null; this.asyncWebRequest.onTimeout(event); assertTrue(this.asyncManager.hasConcurrentResult()); assertEquals(exception, this.asyncManager.getConcurrentResult()); assertEquals("/test", ((MockAsyncContext) this.servletRequest.getAsyncContext()).getDispatchedPath()); }
/** * Async operation timeout (AsyncListener interface) * * @param event Async event */ @Override public void onTimeout(AsyncEvent event) { AsyncContext context = event.getAsyncContext(); lock.lock(); try { pendingWaits.remove(context); JSONObject response = new JSONObject(); response.put("events", new JSONArray()); response.put("requestProcessingTime", System.currentTimeMillis()-timestamp); try (Writer writer = context.getResponse().getWriter()) { response.writeJSONString(writer); } catch (IOException exc) { Logger.logDebugMessage(String.format("Unable to return API response to %s: %s", address, exc.toString())); } context.complete(); timestamp = System.currentTimeMillis(); } finally { lock.unlock(); } }
public void setStarted(Context context, ServletRequest request, ServletResponse response, boolean originalRequestResponse) { this.request.getCoyoteRequest().action( ActionCode.ASYNC_START, this); this.context = context; this.servletRequest = request; this.servletResponse = response; this.hasOriginalRequestAndResponse = originalRequestResponse; this.event = new AsyncEvent(this, request, response); List<AsyncListenerWrapper> listenersCopy = new ArrayList<AsyncListenerWrapper>(); listenersCopy.addAll(listeners); for (AsyncListenerWrapper listener : listenersCopy) { try { listener.fireOnStartAsync(event); } catch (Throwable t) { ExceptionUtils.handleThrowable(t); log.warn("onStartAsync() failed for listener of type [" + listener.getClass().getName() + "]", t); } } listeners.clear(); }
public void setStarted(Context context, ServletRequest request, ServletResponse response, boolean originalRequestResponse) { this.request.getCoyoteRequest().action( ActionCode.ASYNC_START, this); this.context = context; this.servletRequest = request; this.servletResponse = response; this.hasOriginalRequestAndResponse = originalRequestResponse; this.event = new AsyncEvent(this, request, response); List<AsyncListenerWrapper> listenersCopy = new ArrayList<AsyncListenerWrapper>(); listenersCopy.addAll(listeners); for (AsyncListenerWrapper listener : listenersCopy) { try { listener.fireOnStartAsync(event); } catch (IOException ioe) { log.warn("onStartAsync() failed for listener of type [" + listener.getClass().getName() + "]", ioe); } } listeners.clear(); }
public void setErrorState(Throwable t) { if (t!=null) request.setAttribute(RequestDispatcher.ERROR_EXCEPTION, t); request.getCoyoteRequest().action(ActionCode.ASYNC_ERROR, null); AsyncEvent errorEvent = new AsyncEvent(event.getAsyncContext(), event.getSuppliedRequest(), event.getSuppliedResponse(), t); List<AsyncListenerWrapper> listenersCopy = new ArrayList<AsyncListenerWrapper>(); listenersCopy.addAll(listeners); for (AsyncListenerWrapper listener : listenersCopy) { try { listener.fireOnError(errorEvent); } catch (IOException ioe) { log.warn("onStartAsync() failed for listener of type [" + listener.getClass().getName() + "]", ioe); } } }
public OpenEJBAsyncContext(final HttpServletRequest request, final ServletResponse response, final String contextPath) { if (es == null) { synchronized (OpenEJBAsyncContext.class) { // we don't care since impl is not really thread safe, just here for testing if (es == null) { init(); } } } this.request = request; this.contextPath = contextPath; if (contextPath != null) { for (final AppContext app : SystemInstance.get().getComponent(ContainerSystem.class).getAppContexts()) { for (final WebContext web : app.getWebContexts()) { if (web.getContextRoot().replace("/", "").equals(contextPath.replace("/", ""))) { this.context = web; break; } } } } this.response = response; this.socket = Socket.class.cast(request.getAttribute("openejb_socket")); this.event = new AsyncEvent(this, request, response); INITIALIZED.add(this); }
@Override public void onTimeout(AsyncEvent event) throws IOException { // in this time, maybe: // 1.invocation in executor's queue // 2.already executing in executor // 3.already send response // to avoid concurrent, must lock request ServletRequest request = event.getSuppliedRequest(); HttpServletRequestEx requestEx = (HttpServletRequestEx) request.getAttribute(RestConst.REST_REQUEST); synchronized (requestEx) { ServletResponse response = event.getAsyncContext().getResponse(); if (!response.isCommitted()) { LOGGER.error("Rest request timeout, method {}, path {}.", requestEx.getMethod(), requestEx.getRequestURI()); // invocation in executor's queue response.setContentType(MediaType.APPLICATION_JSON); // we don't know if developers declared one statusCode in contract // so we use cse inner statusCode here ((HttpServletResponse) response).setStatus(ExceptionFactory.PRODUCER_INNER_STATUS_CODE); PrintWriter out = response.getWriter(); out.write(TIMEOUT_MESSAGE); response.flushBuffer(); } request.removeAttribute(RestConst.REST_REQUEST); } }
@Before public void setup() { event = new AsyncEvent(context, requestEx, response); requestEx.setAttribute(RestConst.REST_REQUEST, requestEx); new MockUp<HttpServletResponse>(response) { @Mock void setContentType(String type) { contentType = type; } @Mock void setStatus(int sc) { statusCode = sc; } @Mock boolean isCommitted() { return committed; } @Mock PrintWriter getWriter() throws IOException { return printWriter; } @Mock void flushBuffer() throws IOException { flushed = true; } }; }
@Override public void onError(AsyncEvent asyncEvent) throws IOException { synchronized (User.this) { asyncContext.getResponse().setContentType("text/plain; charset=UTF-8"); try (Writer writer = asyncContext.getResponse().getWriter()) { JSON.emptyJSON.writeJSONString(writer); } asyncContext.complete(); asyncContext = null; } }
@Override public void onTimeout(AsyncEvent asyncEvent) throws IOException { synchronized (User.this) { asyncContext.getResponse().setContentType("text/plain; charset=UTF-8"); try (Writer writer = asyncContext.getResponse().getWriter()) { JSON.emptyJSON.writeJSONString(writer); } asyncContext.complete(); asyncContext = null; } }
private AsyncEvent customizeEvent(AsyncEvent event) { if (servletRequest != null && servletResponse != null) { return new AsyncEvent(event.getAsyncContext(), servletRequest, servletResponse, event.getThrowable()); } else { return event; } }
public void setStarted(Context context, ServletRequest request, ServletResponse response, boolean originalRequestResponse) { synchronized (asyncContextLock) { this.request.getCoyoteRequest().action( ActionCode.ASYNC_START, this); this.context = context; this.servletRequest = request; this.servletResponse = response; this.hasOriginalRequestAndResponse = originalRequestResponse; this.event = new AsyncEvent(this, request, response); List<AsyncListenerWrapper> listenersCopy = new ArrayList<AsyncListenerWrapper>(); listenersCopy.addAll(listeners); listeners.clear(); for (AsyncListenerWrapper listener : listenersCopy) { try { listener.fireOnStartAsync(event); } catch (Throwable t) { ExceptionUtils.handleThrowable(t); log.warn("onStartAsync() failed for listener of type [" + listener.getClass().getName() + "]", t); } } } }
@Override public void onTimeout(AsyncEvent event) throws IOException { TestAsyncContextImpl.track("onTimeout-"); if (completeOnTimeout){ event.getAsyncContext().complete(); } if (dispatchUrl != null) { event.getAsyncContext().dispatch(dispatchUrl); } }
@Override public void onError(AsyncEvent event) throws IOException { TestAsyncContextImpl.track("onError-"); if (completeOnError) { event.getAsyncContext().complete(); } }
@Override public void complete() { for (AsyncListener listener : this.listeners) { try { listener.onComplete(new AsyncEvent(this, this.request, this.response)); } catch (IOException e) { throw new IllegalStateException("AsyncListener failure", e); } } }
@Override public void complete() { try { servletResponse.flushBuffer(); } catch (IOException e1) { e1.printStackTrace(); } for (AsyncListener asyncListener : getAsyncListeners()) { try { asyncListener.onComplete(new AsyncEvent(this)); } catch (IOException e) { e.printStackTrace(); } } }
@Override public void onComplete(AsyncEvent event) throws IOException { if (done) { return; } activeRequestsCounter.dec(); updateStatusMetric(startTime, request.getMethod(), response.getStatus()); }
@Test public void testAWSXRayServletAsyncListenerEmitsSegmentWhenProcessingEvent() throws IOException, ServletException { AWSXRayServletFilter servletFilter = new AWSXRayServletFilter("test"); AsyncContext asyncContext = Mockito.mock(AsyncContext.class); HttpServletRequest request = Mockito.mock(HttpServletRequest.class); Mockito.when(request.getRequestURL()).thenReturn(new StringBuffer("test_url")); Mockito.when(request.getMethod()).thenReturn("TEST_METHOD"); Mockito.when(request.isAsyncStarted()).thenReturn(true); Mockito.when(request.getAsyncContext()).thenReturn(asyncContext); HttpServletResponse response = Mockito.mock(HttpServletResponse.class); FilterChain chain = Mockito.mock(FilterChain.class); AsyncEvent event = Mockito.mock(AsyncEvent.class); Mockito.when(event.getSuppliedRequest()).thenReturn(request); Mockito.when(event.getSuppliedResponse()).thenReturn(response); servletFilter.doFilter(request, response, chain); Entity currentEntity = AWSXRay.getTraceEntity(); Mockito.when(request.getAttribute("com.amazonaws.xray.entities.Entity")).thenReturn(currentEntity); AWSXRayServletAsyncListener listener = (AWSXRayServletAsyncListener) Whitebox.getInternalState(servletFilter, "listener"); listener.onComplete(event); Mockito.verify(AWSXRay.getGlobalRecorder().getEmitter(), Mockito.times(1)).sendSegment(Mockito.any()); }
@Override public void onComplete(AsyncEvent event) throws IOException { for (Runnable handler : this.completionHandlers) { handler.run(); } this.asyncContext = null; this.asyncCompleted.set(true); }
private void onAsyncTimeout() { for (final BoundAsyncListener listener : asyncListeners) { AsyncEvent event = new AsyncEvent(this, listener.servletRequest, listener.servletResponse); try { listener.asyncListener.onTimeout(event); } catch (IOException e) { UndertowServletLogger.REQUEST_LOGGER.ioExceptionDispatchingAsyncEvent(e); } } }
private void onAsyncError(Throwable t) { final boolean setupRequired = SecurityActions.currentServletRequestContext() == null; ThreadSetupAction.Handle handle = null; if (setupRequired) { handle = servletRequestContext.getDeployment().getThreadSetupAction().setup(exchange); } try { //now run request listeners setupRequestContext(setupRequired); try { for (final BoundAsyncListener listener : asyncListeners) { AsyncEvent event = new AsyncEvent(this, listener.servletRequest, listener.servletResponse, t); try { listener.asyncListener.onError(event); } catch (IOException e) { UndertowServletLogger.REQUEST_LOGGER.ioExceptionDispatchingAsyncEvent(e); } } } finally { tearDownRequestContext(setupRequired); } } finally { if (setupRequired) { handle.tearDown(); } } }
@Override public void onComplete(AsyncEvent event) throws IOException { final AsyncContextState state = (AsyncContextState) event.getAsyncContext(); final HttpServletRequest request = (HttpServletRequest) state.getRequest(); final HttpServletResponse response = (HttpServletResponse) state.getResponse(); updateResponses(request, response, startTime); }