下面列出了javax.servlet.http.HttpUpgradeHandler#io.undertow.servlet.api.InstanceHandle 实例代码,或者点击链接到github查看源代码,也可以在右侧发表评论。
public Object decodeText(final Class<?> targetType, final String message) throws DecodeException {
if (EncodingFactory.isPrimitiveOrBoxed(targetType)) {
return decodePrimitive(targetType, message);
}
List<InstanceHandle<? extends Decoder>> decoders = textDecoders.get(targetType);
if (decoders != null) {
for (InstanceHandle<? extends Decoder> decoderHandle : decoders) {
Decoder decoder = decoderHandle.getInstance();
if (decoder instanceof Decoder.Text) {
if (((Decoder.Text) decoder).willDecode(message)) {
return ((Decoder.Text) decoder).decode(message);
}
} else {
try {
return ((Decoder.TextStream) decoder).decode(new StringReader(message));
} catch (IOException e) {
throw new DecodeException(message, "Could not decode string", e);
}
}
}
}
throw new DecodeException(message, "Could not decode string");
}
public Object decodeBinary(final Class<?> targetType, final byte[] bytes) throws DecodeException {
List<InstanceHandle<? extends Decoder>> decoders = binaryDecoders.get(targetType);
if (decoders != null) {
for (InstanceHandle<? extends Decoder> decoderHandle : decoders) {
Decoder decoder = decoderHandle.getInstance();
if (decoder instanceof Decoder.Binary) {
if (((Decoder.Binary) decoder).willDecode(ByteBuffer.wrap(bytes))) {
return ((Decoder.Binary) decoder).decode(ByteBuffer.wrap(bytes));
}
} else {
try {
return ((Decoder.BinaryStream) decoder).decode(new ByteArrayInputStream(bytes));
} catch (IOException e) {
throw new DecodeException(ByteBuffer.wrap(bytes), "Could not decode binary", e);
}
}
}
}
throw new DecodeException(ByteBuffer.wrap(bytes), "Could not decode binary");
}
public Session connectToServer(Class<?> aClass, WebsocketConnectionBuilder connectionBuilder) throws DeploymentException, IOException {
if (closed) {
throw new ClosedChannelException();
}
ConfiguredClientEndpoint config = getClientEndpoint(aClass, true);
if (config == null) {
throw JsrWebSocketMessages.MESSAGES.notAValidClientEndpointType(aClass);
}
try {
AnnotatedEndpointFactory factory = config.getFactory();
InstanceHandle<?> instance = config.getInstanceFactory().createInstance();
return connectToServerInternal(factory.createInstance(instance), config, connectionBuilder);
} catch (InstantiationException e) {
throw new RuntimeException(e);
}
}
@Override
public InstanceHandle<Servlet> createInstance() throws InstantiationException {
return new InstanceHandle<Servlet>() {
@Override
public Servlet getInstance() {
return new DispatcherServlet(wac);
}
@Override
public void release() {
}
};
}
@Override
public InstanceHandle<Filter> createInstance() throws InstantiationException {
return new InstanceHandle<Filter>() {
@Override
public Filter getInstance() {
return filter;
}
@Override
public void release() {}
};
}
public InstanceHandle<? extends Servlet> getServlet() throws ServletException {
if(servletContext.getDeployment().getDeploymentState() != DeploymentManager.State.STARTED) {
throw UndertowServletMessages.MESSAGES.deploymentStopped(servletContext.getDeployment().getDeploymentInfo().getDeploymentName());
}
if (!started) {
synchronized (this) {
if (!started) {
instanceStrategy.start();
started = true;
}
}
}
return instanceStrategy.getServlet();
}
@Override
public InstanceHandle<? extends Servlet> getServlet() throws ServletException {
final InstanceHandle<? extends Servlet> instanceHandle;
final Servlet instance;
//TODO: pooling
try {
instanceHandle = factory.createInstance();
} catch (Exception e) {
throw UndertowServletMessages.MESSAGES.couldNotInstantiateComponent(servletInfo.getName(), e);
}
instance = instanceHandle.getInstance();
new LifecyleInterceptorInvocation(servletContext.getDeployment().getDeploymentInfo().getLifecycleInterceptors(), servletInfo, instance, new ServletConfigImpl(servletInfo, servletContext)).proceed();
return new InstanceHandle<Servlet>() {
@Override
public Servlet getInstance() {
return instance;
}
@Override
public void release() {
try {
instance.destroy();
} catch (Throwable t) {
UndertowServletLogger.REQUEST_LOGGER.failedToDestroy(instance, t);
}
instanceHandle.release();
}
};
}
public String encodeText(final Object o) throws EncodeException {
List<InstanceHandle<? extends Encoder>> encoders = textEncoders.get(o.getClass());
if(encoders == null) {
for(Map.Entry<Class<?>, List<InstanceHandle<? extends Encoder>>> entry : textEncoders.entrySet()) {
if(entry.getKey().isAssignableFrom(o.getClass())) {
encoders = entry.getValue();
break;
}
}
}
if (encoders != null) {
for (InstanceHandle<? extends Encoder> decoderHandle : encoders) {
Encoder decoder = decoderHandle.getInstance();
if (decoder instanceof Encoder.Text) {
return ((Encoder.Text) decoder).encode(o);
} else {
try {
StringWriter out = new StringWriter();
((Encoder.TextStream) decoder).encode(o, out);
return out.toString();
} catch (IOException e) {
throw new EncodeException(o, "Could not encode text", e);
}
}
}
}
if (EncodingFactory.isPrimitiveOrBoxed(o.getClass())) {
return o.toString();
}
throw new EncodeException(o, "Could not encode text");
}
public ByteBuffer encodeBinary(final Object o) throws EncodeException {
List<InstanceHandle<? extends Encoder>> encoders = binaryEncoders.get(o.getClass());
if(encoders == null) {
for(Map.Entry<Class<?>, List<InstanceHandle<? extends Encoder>>> entry : binaryEncoders.entrySet()) {
if(entry.getKey().isAssignableFrom(o.getClass())) {
encoders = entry.getValue();
break;
}
}
}
if (encoders != null) {
for (InstanceHandle<? extends Encoder> decoderHandle : encoders) {
Encoder decoder = decoderHandle.getInstance();
if (decoder instanceof Encoder.Binary) {
return ((Encoder.Binary) decoder).encode(o);
} else {
try {
ByteArrayOutputStream out = new ByteArrayOutputStream();
((Encoder.BinaryStream) decoder).encode(o, out);
return ByteBuffer.wrap(out.toByteArray());
} catch (IOException e) {
throw new EncodeException(o, "Could not encode binary", e);
}
}
}
}
throw new EncodeException(o, "Could not encode binary");
}
public UndertowSession(Channel channel, URI requestUri, Map<String, String> pathParameters,
Map<String, List<String>> requestParameterMap, EndpointSessionHandler handler, Principal user,
InstanceHandle<Endpoint> endpoint, EndpointConfig config, final String queryString,
final Encoding encoding, final SessionContainer openSessions, final String subProtocol,
final List<Extension> extensions, WebsocketConnectionBuilder clientConnectionBuilder,
Executor executor) {
channel.closeFuture().addListener(new GenericFutureListener<Future<? super Void>>() {
@Override
public void operationComplete(Future<? super Void> future) throws Exception {
closeInternal(new CloseReason(CloseReason.CloseCodes.GOING_AWAY, null));
}
});
this.clientConnectionBuilder = clientConnectionBuilder;
assert openSessions != null;
this.channel = channel;
this.queryString = queryString;
this.encoding = encoding;
this.openSessions = openSessions;
container = handler.getContainer();
this.user = user;
this.requestUri = requestUri;
this.requestParameterMap = Collections.unmodifiableMap(requestParameterMap);
this.pathParameters = Collections.unmodifiableMap(pathParameters);
this.config = config;
remote = new WebSocketSessionRemoteEndpoint(this, encoding);
this.endpoint = endpoint;
this.sessionId = new SecureRandomSessionIdGenerator().createSessionId();
this.attrs = Collections.synchronizedMap(new HashMap<>(config.getUserProperties()));
this.extensions = extensions;
this.subProtocol = subProtocol;
this.executor = executor;
setupWebSocketChannel(channel);
}
AnnotatedEndpoint(final InstanceHandle<?> instance, final BoundMethod webSocketOpen, final BoundMethod webSocketClose, final BoundMethod webSocketError, final BoundMethod textMessage, final BoundMethod binaryMessage, final BoundMethod pongMessage) {
this.instance = instance;
this.webSocketOpen = webSocketOpen;
this.webSocketClose = webSocketClose;
this.webSocketError = webSocketError;
this.textMessage = textMessage;
this.binaryMessage = binaryMessage;
this.pongMessage = pongMessage;
}
@Override
public <T> T getEndpointInstance(final Class<T> endpointClass) throws InstantiationException {
InstanceFactory<?> factory = currentInstanceFactory.get();
if(factory != null) {
InstanceHandle<?> instance = factory.createInstance();
currentInstanceHandle.set(instance);
return (T) instance.getInstance();
}
try {
return endpointClass.newInstance();
} catch (IllegalAccessException e) {
throw new RuntimeException(e);
}
}
@Override
public InstanceHandle<Servlet> createInstance() throws InstantiationException {
return new InstanceHandle<Servlet>() {
@Override
public Servlet getInstance() {
return new DispatcherServlet(wac);
}
@Override
public void release() {
}
};
}
@Override
public InstanceHandle<Filter> createInstance() throws InstantiationException {
return new InstanceHandle<Filter>() {
@Override
public Filter getInstance() {
return filter;
}
@Override
public void release() {}
};
}
@Override
public InstanceHandle<T> createInstance() throws InstantiationException {
BeanContainer.Instance<T> instance = factory.create();
return new InstanceHandle<T>() {
@Override
public T getInstance() {
return instance.get();
}
@Override
public void release() {
instance.close();
}
};
}
public InstanceHandle<? extends Servlet> getServlet() throws ServletException {
if(servletContext.getDeployment().getDeploymentState() != DeploymentManager.State.STARTED) {
throw UndertowServletMessages.MESSAGES.deploymentStopped(servletContext.getDeployment().getDeploymentInfo().getDeploymentName());
}
if (!started) {
synchronized (this) {
if (!started) {
instanceStrategy.start();
started = true;
}
}
}
return instanceStrategy.getServlet();
}
@Override
public InstanceHandle<? extends Servlet> getServlet() throws ServletException {
final InstanceHandle<? extends Servlet> instanceHandle;
final Servlet instance;
//TODO: pooling
try {
instanceHandle = factory.createInstance();
} catch (Exception e) {
throw UndertowServletMessages.MESSAGES.couldNotInstantiateComponent(servletInfo.getName(), e);
}
instance = instanceHandle.getInstance();
new LifecyleInterceptorInvocation(servletContext.getDeployment().getDeploymentInfo().getLifecycleInterceptors(), servletInfo, instance, new ServletConfigImpl(servletInfo, servletContext)).proceed();
return new InstanceHandle<Servlet>() {
@Override
public Servlet getInstance() {
return instance;
}
@Override
public void release() {
try {
instance.destroy();
} catch (Throwable t) {
UndertowServletLogger.REQUEST_LOGGER.failedToDestroy(instance, t);
}
instanceHandle.release();
}
};
}
@Override
public InstanceHandle<Endpoint> createInstance() throws InstantiationException {
return new InstanceHandle<Endpoint>() {
@Override
public Endpoint getInstance() {
return endpoint;
}
@Override
public void release() {
}
};
}
@Override
public InstanceHandle<Servlet> createInstance() throws InstantiationException {
return new InstanceHandle<Servlet>() {
@Override
public Servlet getInstance() {
return new DispatcherServlet(wac);
}
@Override
public void release() {
}
};
}
@Override
public InstanceHandle<Filter> createInstance() throws InstantiationException {
return new InstanceHandle<Filter>() {
@Override
public Filter getInstance() {
return filter;
}
@Override
public void release() {}
};
}
@Override
public InstanceHandle<T> createInstance() {
try {
return new HammockInstanceHandle<>(new Unmanaged<>(beanManager, clazz).newInstance());
}
catch (Exception e) {
try {
return new BasicInstanceFactory<T>(clazz.newInstance());
} catch (Exception ex) {
throw new RuntimeException("Unable to instantiate "+clazz, ex);
}
}
}
@Override
public void handleRequest(final HttpServerExchange exchange) throws IOException, ServletException {
if (managedServlet.isPermanentlyUnavailable()) {
UndertowServletLogger.REQUEST_LOGGER.debugf("Returning 404 for servlet %s due to permanent unavailability", managedServlet.getServletInfo().getName());
exchange.setStatusCode(StatusCodes.NOT_FOUND);
return;
}
if (managedServlet.isTemporarilyUnavailable()) {
UndertowServletLogger.REQUEST_LOGGER.debugf("Returning 503 for servlet %s due to temporary unavailability", managedServlet.getServletInfo().getName());
exchange.setStatusCode(StatusCodes.SERVICE_UNAVAILABLE);
return;
}
final ServletRequestContext servletRequestContext = exchange.getAttachment(ServletRequestContext.ATTACHMENT_KEY);
if(!managedServlet.getServletInfo().isAsyncSupported()) {
servletRequestContext.setAsyncSupported(false);
}
ServletRequest request = servletRequestContext.getServletRequest();
ServletResponse response = servletRequestContext.getServletResponse();
InstanceHandle<? extends Servlet> servlet = null;
try {
servlet = managedServlet.getServlet();
servlet.getInstance().service(request, response);
//according to the spec we have to call AsyncContext.complete() at this point
//straight after the service method
//not super sure about this, surely it would make more sense to do this when the request has returned to the container, however the spec is quite clear wording wise
//todo: should we actually enable this? Apparently other containers do not do it
//if(!request.isAsyncStarted()) {
// AsyncContextImpl existingAsyncContext = servletRequestContext.getOriginalRequest().getAsyncContextInternal();
// if (existingAsyncContext != null) {
// existingAsyncContext.complete();
// }
//}
} catch (UnavailableException e) {
managedServlet.handleUnavailableException(e);
if (e.isPermanent()) {
exchange.setStatusCode(StatusCodes.NOT_FOUND);
} else {
exchange.setStatusCode(StatusCodes.SERVICE_UNAVAILABLE);
}
} finally {
if(servlet != null) {
servlet.release();
}
}
}
@Override
public InstanceHandle<T> createInstance() throws InstantiationException {
return new ImmediateInstanceHandle<>(instance);
}
public InstanceHandle<? extends Servlet> getServlet() {
return instanceHandle;
}
public Encoding(final Map<Class<?>, List<InstanceHandle<? extends Encoder>>> binaryEncoders, final Map<Class<?>, List<InstanceHandle<? extends Decoder>>> binaryDecoders, final Map<Class<?>, List<InstanceHandle<? extends Encoder>>> textEncoders, final Map<Class<?>, List<InstanceHandle<? extends Decoder>>> textDecoders) {
this.binaryEncoders = binaryEncoders;
this.binaryDecoders = binaryDecoders;
this.textEncoders = textEncoders;
this.textDecoders = textDecoders;
}
public AnnotatedEndpoint createInstance(InstanceHandle<?> endpointInstance) {
if(!endpointClass.isInstance(endpointInstance.getInstance())) {
throw JsrWebSocketMessages.MESSAGES.endpointNotOfCorrectType(endpointInstance, endpointClass);
}
return new AnnotatedEndpoint(endpointInstance, OnOpen, OnClose, OnError, textMessage, binaryMessage, pongMessage);
}
static InstanceHandle<?> clearCurrentInstanceFactory() {
currentInstanceFactory.remove();
InstanceHandle<?> handle = currentInstanceHandle.get();
currentInstanceHandle.remove();
return handle;
}
@Override
public void handleRequest(final HttpServerExchange exchange) throws IOException, ServletException {
if (managedServlet.isPermanentlyUnavailable()) {
UndertowServletLogger.REQUEST_LOGGER.debugf("Returning 404 for servlet %s due to permanent unavailability", managedServlet.getServletInfo().getName());
exchange.setStatusCode(StatusCodes.NOT_FOUND);
return;
}
if (managedServlet.isTemporarilyUnavailable()) {
UndertowServletLogger.REQUEST_LOGGER.debugf("Returning 503 for servlet %s due to temporary unavailability", managedServlet.getServletInfo().getName());
exchange.setStatusCode(StatusCodes.SERVICE_UNAVAILABLE);
return;
}
final ServletRequestContext servletRequestContext = exchange.getAttachment(ServletRequestContext.ATTACHMENT_KEY);
if(!managedServlet.getServletInfo().isAsyncSupported()) {
servletRequestContext.setAsyncSupported(false);
}
ServletRequest request = servletRequestContext.getServletRequest();
ServletResponse response = servletRequestContext.getServletResponse();
InstanceHandle<? extends Servlet> servlet = null;
try {
servlet = managedServlet.getServlet();
servlet.getInstance().service(request, response);
//according to the spec we have to call AsyncContext.complete() at this point
//straight after the service method
//not super sure about this, surely it would make more sense to do this when the request has returned to the container, however the spec is quite clear wording wise
//todo: should we actually enable this? Apparently other containers do not do it
//if(!request.isAsyncStarted()) {
// AsyncContextImpl existingAsyncContext = servletRequestContext.getOriginalRequest().getAsyncContextInternal();
// if (existingAsyncContext != null) {
// existingAsyncContext.complete();
// }
//}
} catch (UnavailableException e) {
managedServlet.handleUnavailableException(e);
if (e.isPermanent()) {
exchange.setStatusCode(StatusCodes.NOT_FOUND);
} else {
exchange.setStatusCode(StatusCodes.SERVICE_UNAVAILABLE);
}
} finally {
if(servlet != null) {
servlet.release();
}
}
}
@Override
public InstanceHandle<T> createInstance() throws InstantiationException {
return new ImmediateInstanceHandle<>(instance);
}
public InstanceHandle<? extends Servlet> getServlet() {
return instanceHandle;
}