use of org.atmosphere.cpr.AtmosphereResourceEvent in project atmosphere by Atmosphere.
the class BlockingIOCometSupport method suspend.
/**
* Suspend the connection by blocking the current {@link Thread}
*
* @param action The {@link Action}
* @param req the {@link AtmosphereRequest}
* @param res the {@link AtmosphereResponse}
*/
protected void suspend(Action action, AtmosphereRequest req, AtmosphereResponse res) throws IOException, ServletException {
final CountDownLatch latch = new CountDownLatch(1);
req.setAttribute(LATCH, latch);
boolean ok = true;
AtmosphereResource resource = req.resource();
if (resource != null) {
try {
resource.addEventListener(new OnResume() {
@Override
public void onResume(AtmosphereResourceEvent event) {
latch.countDown();
}
});
if (action.timeout() != -1) {
ok = latch.await(action.timeout(), TimeUnit.MILLISECONDS);
} else {
latch.await();
}
} catch (InterruptedException ex) {
logger.trace("", ex);
} finally {
if (!ok) {
timedout(req, res);
} else {
((AtmosphereResourceImpl) resource).cancel();
}
}
}
}
use of org.atmosphere.cpr.AtmosphereResourceEvent in project atmosphere by Atmosphere.
the class AtmosphereServiceProcessor method handle.
@Override
public void handle(AtmosphereFramework framework, Class<Object> annotatedClass) {
try {
AtmosphereService a = annotatedClass.getAnnotation(AtmosphereService.class);
framework.setBroadcasterCacheClassName(a.broadcasterCache().getName());
atmosphereConfig(a.atmosphereConfig(), framework);
framework.setDefaultBroadcasterClassName(a.broadcaster().getName());
filters(a.broadcastFilters(), framework);
LinkedList<AtmosphereInterceptor> l = new LinkedList<>();
AtmosphereInterceptor aa = listeners(a.listeners(), framework);
if (aa != null) {
l.add(aa);
}
if (!a.servlet().isEmpty()) {
final ReflectorServletProcessor r = framework.newClassInstance(ReflectorServletProcessor.class, ReflectorServletProcessor.class);
r.setServletClassName(a.servlet());
String mapping = a.path();
AnnotationUtil.interceptorsForHandler(framework, Arrays.asList(a.interceptors()), l);
if (!a.dispatch()) {
AtmosphereHandler proxy = new AtmosphereServletProcessor() {
private String method = "GET";
@Override
public void onRequest(AtmosphereResource resource) throws IOException {
if (!resource.getRequest().getMethod().equalsIgnoreCase(method)) {
r.onRequest(resource);
}
}
@Override
public void onStateChange(AtmosphereResourceEvent event) throws IOException {
r.onStateChange(event);
}
@Override
public void destroy() {
r.destroy();
}
@Override
public void init(AtmosphereConfig config) throws ServletException {
String s = config.getInitParameter(ATMOSPHERERESOURCE_INTERCEPTOR_METHOD);
if (s != null) {
method = s;
}
r.init(config);
}
};
framework.addAtmosphereHandler(mapping, proxy, l);
} else {
framework.addAtmosphereHandler(mapping, r, l);
}
} else {
interceptors(a.interceptors(), framework);
}
} catch (Throwable e) {
logger.warn("", e);
}
}
use of org.atmosphere.cpr.AtmosphereResourceEvent in project atmosphere by Atmosphere.
the class AtmosphereResourceStateRecovery method inspect.
@Override
public Action inspect(final AtmosphereResource r) {
if (!Utils.pollableTransport(r.transport()) && !Utils.webSocketMessage(r)) {
final BroadcasterTracker tracker = track(r).tick();
List<Object> cachedMessages = retrieveCache(r, tracker, false);
if (!cachedMessages.isEmpty()) {
logger.trace("cached messages");
writeCache(r, cachedMessages);
return Action.CANCELLED;
} else {
r.addEventListener(new OnAlwaysSuspend() {
public void onSuspend(AtmosphereResourceEvent event) {
r.removeEventListener(this);
logger.trace("onSuspend first");
final AtomicBoolean doNotSuspend = new AtomicBoolean(false);
/**
* If a message gets broadcasted during the execution of the code below, we don't need to
* suspend the connection. This code is needed to prevent the connection being suspended
* with messages already written.
*/
r.addEventListener(new OnBroadcast() {
@Override
public void onBroadcast(AtmosphereResourceEvent event) {
r.removeEventListener(this);
doNotSuspend.set(true);
logger.trace("onBroadcast");
}
});
for (String broadcasterID : tracker.ids()) {
Broadcaster b = factory.lookup(broadcasterID, false);
logger.trace("About to associate resource {} with Broadcaster {}", r.uuid(), broadcasterID);
if (b != null && !b.getID().equalsIgnoreCase(r.getBroadcaster().getID())) {
logger.trace("Associate AtmosphereResource {} with Broadcaster {}", r.uuid(), broadcasterID);
b.addAtmosphereResource(r);
} else if (b == null) {
logger.trace("Broadcaster {} is no longer available for {}", broadcasterID, r);
} else {
logger.trace("AtmosphereResource {} already associated with {}", r.uuid(), broadcasterID);
}
}
/**
* Check the cache to see if messages has been added directly by using
* {@link BroadcasterCache#addToCache(String, org.atmosphere.cpr.AtmosphereResource, org.atmosphere.cache.BroadcastMessage)}
* after {@link Broadcaster#addAtmosphereResource(org.atmosphere.cpr.AtmosphereResource)} has been
* invoked.
*/
final List<Object> cachedMessages = retrieveCache(r, tracker, true);
if (logger.isTraceEnabled()) {
logger.trace("message size {}", cachedMessages.size());
}
if (!cachedMessages.isEmpty()) {
logger.trace("About to write to the cache {}", r.uuid());
writeCache(r, cachedMessages);
doNotSuspend.set(true);
}
// Force doNotSuspend.
if (doNotSuspend.get()) {
AtmosphereResourceImpl.class.cast(r).action().type(Action.TYPE.CONTINUE);
}
if (logger.isTraceEnabled()) {
logger.trace("doNotSuspend {}", doNotSuspend.get());
}
}
});
}
}
return Action.CONTINUE;
}
use of org.atmosphere.cpr.AtmosphereResourceEvent in project cxf by apache.
the class DefaultProtocolInterceptor method inspect.
@Override
public Action inspect(final AtmosphereResource r) {
LOG.log(Level.FINE, "inspect");
if (AtmosphereResource.TRANSPORT.WEBSOCKET != r.transport() && AtmosphereResource.TRANSPORT.SSE != r.transport() && AtmosphereResource.TRANSPORT.POLLING != r.transport()) {
LOG.fine("Skipping ignorable request");
return Action.CONTINUE;
}
if (AtmosphereResource.TRANSPORT.POLLING == r.transport()) {
final String saruuid = (String) r.getRequest().getAttribute(ApplicationConfig.SUSPENDED_ATMOSPHERE_RESOURCE_UUID);
final AtmosphereResponse suspendedResponse = suspendedResponses.get(saruuid);
LOG.fine("Attaching a proxy writer to suspended response");
r.getResponse().asyncIOWriter(new AtmosphereInterceptorWriter() {
@Override
public AsyncIOWriter write(AtmosphereResponse r, String data) throws IOException {
suspendedResponse.write(data);
suspendedResponse.flushBuffer();
return this;
}
@Override
public AsyncIOWriter write(AtmosphereResponse r, byte[] data) throws IOException {
suspendedResponse.write(data);
suspendedResponse.flushBuffer();
return this;
}
@Override
public AsyncIOWriter write(AtmosphereResponse r, byte[] data, int offset, int length) throws IOException {
suspendedResponse.write(data, offset, length);
suspendedResponse.flushBuffer();
return this;
}
@Override
public void close(AtmosphereResponse response) throws IOException {
}
});
// REVISIT we need to keep this response's asyncwriter alive so that data can be written to the
// suspended response, but investigate if there is a better alternative.
r.getResponse().destroyable(false);
return Action.CONTINUE;
}
r.addEventListener(new AtmosphereResourceEventListenerAdapter() {
@Override
public void onSuspend(AtmosphereResourceEvent event) {
final String srid = (String) event.getResource().getRequest().getAttribute(ApplicationConfig.SUSPENDED_ATMOSPHERE_RESOURCE_UUID);
LOG.log(Level.FINE, "Registrering suspended resource: {}", srid);
suspendedResponses.put(srid, event.getResource().getResponse());
AsyncIOWriter writer = event.getResource().getResponse().getAsyncIOWriter();
if (writer instanceof AtmosphereInterceptorWriter) {
((AtmosphereInterceptorWriter) writer).interceptor(interceptor);
}
}
@Override
public void onDisconnect(AtmosphereResourceEvent event) {
super.onDisconnect(event);
final String srid = (String) event.getResource().getRequest().getAttribute(ApplicationConfig.SUSPENDED_ATMOSPHERE_RESOURCE_UUID);
LOG.log(Level.FINE, "Unregistrering suspended resource: {}", srid);
suspendedResponses.remove(srid);
}
});
AtmosphereRequest request = r.getRequest();
if (request.getAttribute(REQUEST_DISPATCHED) == null) {
AtmosphereResponse response = null;
AtmosphereFramework framework = r.getAtmosphereConfig().framework();
try {
byte[] data = WebSocketUtils.readBody(request.getInputStream());
if (data.length == 0) {
if (AtmosphereResource.TRANSPORT.WEBSOCKET == r.transport() || AtmosphereResource.TRANSPORT.SSE == r.transport()) {
r.suspend();
return Action.SUSPEND;
}
return Action.CANCELLED;
}
if (LOG.isLoggable(Level.FINE)) {
LOG.log(Level.FINE, "inspecting data {0}", new String(data));
}
try {
AtmosphereRequest ar = createAtmosphereRequest(request, data);
response = new WrappedAtmosphereResponse(r.getResponse(), ar);
ar.localAttributes().put(REQUEST_DISPATCHED, "true");
String refid = ar.getHeader(WebSocketConstants.DEFAULT_REQUEST_ID_KEY);
if (refid != null) {
ar.localAttributes().put(WebSocketConstants.DEFAULT_REQUEST_ID_KEY, refid);
}
// This is a new request, we must clean the Websocket AtmosphereResource.
request.removeAttribute(FrameworkConfig.INJECTED_ATMOSPHERE_RESOURCE);
response.request(ar);
attachWriter(r);
Action action = framework.doCometSupport(ar, response);
if (action.type() == Action.TYPE.SUSPEND) {
ar.destroyable(false);
response.destroyable(false);
}
} catch (Exception e) {
LOG.log(Level.WARNING, "Error during request dispatching", e);
if (response == null) {
response = new WrappedAtmosphereResponse(r.getResponse(), request);
}
if (e instanceof InvalidPathException) {
response.setIntHeader(WebSocketUtils.SC_KEY, 400);
} else {
response.setIntHeader(WebSocketUtils.SC_KEY, 500);
}
OutputStream out = response.getOutputStream();
out.write(createResponse(response, null, true));
out.close();
}
return Action.CANCELLED;
} catch (IOException e) {
LOG.log(Level.WARNING, "Error during protocol processing", e);
}
} else {
request.destroyable(false);
}
return Action.CONTINUE;
}
use of org.atmosphere.cpr.AtmosphereResourceEvent in project flow by vaadin.
the class PushHandlerTest method mockConnectionLost.
private void mockConnectionLost(VaadinSession session, boolean setSession) {
AtomicBoolean sessionIsSet = new AtomicBoolean();
MockVaadinServletService service = new MockVaadinServletService() {
@Override
public com.vaadin.flow.server.VaadinSession findVaadinSession(VaadinRequest request) throws SessionExpiredException {
VaadinSession.setCurrent(session);
sessionIsSet.set(true);
Assert.assertNotNull(VaadinSession.getCurrent());
return session;
}
@Override
public UI findUI(VaadinRequest request) {
return null;
}
};
if (setSession) {
VaadinSession.setCurrent(session);
}
PushHandler handler = new PushHandler(service);
AtmosphereResource resource = Mockito.mock(AtmosphereResource.class);
AtmosphereRequest request = Mockito.mock(AtmosphereRequest.class);
Mockito.when(resource.getRequest()).thenReturn(request);
AtmosphereResourceEvent event = Mockito.mock(AtmosphereResourceEvent.class);
Mockito.when(event.getResource()).thenReturn(resource);
handler.connectionLost(event);
Assert.assertTrue(sessionIsSet.get());
}
Aggregations