use of org.apache.calcite.avatica.util.UnsynchronizedBuffer in project calcite-avatica by apache.
the class ProtobufTranslationImpl method serializeResponse.
@Override
public byte[] serializeResponse(Response response) throws IOException {
// Avoid BAOS for its synchronized write methods, we don't need that concurrency control
UnsynchronizedBuffer out = threadLocalBuffer.get();
try {
Message responseMsg = response.serialize();
// Serialization of the response may be large
if (LOG.isTraceEnabled()) {
LOG.trace("Serializing response '{}'", TextFormat.shortDebugString(responseMsg));
}
serializeMessage(out, responseMsg);
return out.toArray();
} finally {
out.reset();
}
}
use of org.apache.calcite.avatica.util.UnsynchronizedBuffer in project calcite-avatica by apache.
the class AvaticaProtobufHandler method handle.
public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
try (final Context ctx = this.requestTimer.start()) {
// Check if the user is OK to proceed.
if (!isUserPermitted(serverConfig, request, response)) {
LOG.debug("HTTP request from {} is unauthenticated and authentication is required", request.getRemoteAddr());
return;
}
response.setContentType("application/octet-stream;charset=utf-8");
response.setStatus(HttpServletResponse.SC_OK);
if (request.getMethod().equals("POST")) {
final byte[] requestBytes;
// Avoid a new buffer creation for every HTTP request
final UnsynchronizedBuffer buffer = threadLocalBuffer.get();
try (ServletInputStream inputStream = request.getInputStream()) {
requestBytes = AvaticaUtils.readFullyToBytes(inputStream, buffer);
} finally {
buffer.reset();
}
HandlerResponse<byte[]> handlerResponse;
try {
if (null != serverConfig && serverConfig.supportsImpersonation()) {
// If we can't extract a user, need to throw 401 in that case.
String remoteUser = serverConfig.getRemoteUserExtractor().extract(request);
// Invoke the ProtobufHandler inside as doAs for the remote user.
// The doAsRemoteUser call may disallow a user, need to throw 403 in that case.
handlerResponse = serverConfig.doAsRemoteUser(remoteUser, request.getRemoteAddr(), new Callable<HandlerResponse<byte[]>>() {
@Override
public HandlerResponse<byte[]> call() {
return pbHandler.apply(requestBytes);
}
});
} else {
handlerResponse = pbHandler.apply(requestBytes);
}
} catch (RemoteUserExtractionException e) {
LOG.debug("Failed to extract remote user from request", e);
handlerResponse = pbHandler.unauthenticatedErrorResponse(e);
} catch (RemoteUserDisallowedException e) {
LOG.debug("Remote user is not authorized", e);
handlerResponse = pbHandler.unauthorizedErrorResponse(e);
} catch (Exception e) {
LOG.debug("Error invoking request from {}", baseRequest.getRemoteAddr(), e);
// Catch at the highest level of exceptions
handlerResponse = pbHandler.convertToErrorResponse(e);
}
baseRequest.setHandled(true);
response.setStatus(handlerResponse.getStatusCode());
response.getOutputStream().write(handlerResponse.getResponse());
}
}
}
use of org.apache.calcite.avatica.util.UnsynchronizedBuffer in project calcite-avatica by apache.
the class AvaticaJsonHandler method handle.
public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
try (final Context ctx = requestTimer.start()) {
if (!isUserPermitted(serverConfig, request, response)) {
LOG.debug("HTTP request from {} is unauthenticated and authentication is required", request.getRemoteAddr());
return;
}
response.setContentType("application/json;charset=utf-8");
response.setStatus(HttpServletResponse.SC_OK);
if (request.getMethod().equals("POST")) {
// First look for a request in the header, then look in the body.
// The latter allows very large requests without hitting HTTP 413.
String rawRequest = request.getHeader("request");
if (rawRequest == null) {
// Avoid a new buffer creation for every HTTP request
final UnsynchronizedBuffer buffer = threadLocalBuffer.get();
try (ServletInputStream inputStream = request.getInputStream()) {
rawRequest = AvaticaUtils.readFully(inputStream, buffer);
} finally {
// Reset the offset into the buffer after we're done
buffer.reset();
}
}
final String jsonRequest = new String(rawRequest.getBytes("ISO-8859-1"), "UTF-8");
LOG.trace("request: {}", jsonRequest);
HandlerResponse<String> jsonResponse;
try {
if (null != serverConfig && serverConfig.supportsImpersonation()) {
String remoteUser = serverConfig.getRemoteUserExtractor().extract(request);
jsonResponse = serverConfig.doAsRemoteUser(remoteUser, request.getRemoteAddr(), new Callable<HandlerResponse<String>>() {
@Override
public HandlerResponse<String> call() {
return jsonHandler.apply(jsonRequest);
}
});
} else {
jsonResponse = jsonHandler.apply(jsonRequest);
}
} catch (RemoteUserExtractionException e) {
LOG.debug("Failed to extract remote user from request", e);
jsonResponse = jsonHandler.unauthenticatedErrorResponse(e);
} catch (RemoteUserDisallowedException e) {
LOG.debug("Remote user is not authorized", e);
jsonResponse = jsonHandler.unauthorizedErrorResponse(e);
} catch (Exception e) {
LOG.debug("Error invoking request from {}", baseRequest.getRemoteAddr(), e);
jsonResponse = jsonHandler.convertToErrorResponse(e);
}
LOG.trace("response: {}", jsonResponse);
baseRequest.setHandled(true);
// Set the status code and write out the response.
response.setStatus(jsonResponse.getStatusCode());
response.getWriter().println(jsonResponse.getResponse());
}
}
}
use of org.apache.calcite.avatica.util.UnsynchronizedBuffer in project calcite-avatica by apache.
the class ProtobufTranslationImpl method serializeMessage.
void serializeMessage(OutputStream out, Message msg) throws IOException {
// Serialize the protobuf message
UnsynchronizedBuffer buffer = threadLocalBuffer.get();
ByteString serializedMsg;
try {
msg.writeTo(buffer);
// Make a bytestring from it
serializedMsg = UnsafeByteOperations.unsafeWrap(buffer.toArray());
} finally {
buffer.reset();
}
// Wrap the serialized message in a WireMessage
WireMessage wireMsg = WireMessage.newBuilder().setNameBytes(getClassNameBytes(msg.getClass())).setWrappedMessage(serializedMsg).build();
// Write the WireMessage to the provided OutputStream
wireMsg.writeTo(out);
}
use of org.apache.calcite.avatica.util.UnsynchronizedBuffer in project calcite-avatica by apache.
the class ProtobufTranslationImpl method serializeRequest.
@Override
public byte[] serializeRequest(Request request) throws IOException {
// Avoid BAOS for its synchronized write methods, we don't need that concurrency control
UnsynchronizedBuffer out = threadLocalBuffer.get();
try {
Message requestMsg = request.serialize();
// Serialization of the request may be large
if (LOG.isTraceEnabled()) {
LOG.trace("Serializing request '{}'", TextFormat.shortDebugString(requestMsg));
}
serializeMessage(out, requestMsg);
return out.toArray();
} finally {
out.reset();
}
}
Aggregations