use of org.ballerinalang.connector.api.BallerinaConnectorException in project ballerina by ballerina-lang.
the class WebSocketServerConnectorListener method onMessage.
@Override
public void onMessage(WebSocketInitMessage webSocketInitMessage) {
HTTPCarbonMessage msg = new HTTPCarbonMessage(((DefaultWebSocketInitMessage) webSocketInitMessage).getHttpRequest());
Map<String, String> pathParams = new HashMap<>();
WebSocketService wsService = WebSocketDispatcher.findService(servicesRegistry, pathParams, webSocketInitMessage, msg);
BStruct serviceEndpoint = BLangConnectorSPIUtil.createBStruct(wsService.getResources()[0].getResourceInfo().getServiceInfo().getPackageInfo().getProgramFile(), PROTOCOL_PACKAGE_HTTP, WEBSOCKET_ENDPOINT);
BStruct serverConnector = WebSocketUtil.createAndGetBStruct(wsService.getResources()[0]);
serverConnector.addNativeData(WebSocketConstants.WEBSOCKET_MESSAGE, webSocketInitMessage);
serverConnector.addNativeData(WebSocketConstants.WEBSOCKET_SERVICE, wsService);
serviceEndpoint.setRefField(SERVICE_ENDPOINT_CONNECTION_INDEX, serverConnector);
serviceEndpoint.setRefField(3, new BMap());
serverConnector.addNativeData(WEBSOCKET_ENDPOINT, serviceEndpoint);
Map<String, String> upgradeHeaders = webSocketInitMessage.getHeaders();
BMap<String, BString> bUpgradeHeaders = new BMap<>();
upgradeHeaders.forEach((key, value) -> bUpgradeHeaders.put(key, new BString(value)));
serviceEndpoint.setRefField(4, bUpgradeHeaders);
Resource onUpgradeResource = wsService.getResourceByName(WebSocketConstants.RESOURCE_NAME_ON_UPGRADE);
if (onUpgradeResource != null) {
Semaphore semaphore = new Semaphore(0);
AtomicBoolean isResourceExeSuccessful = new AtomicBoolean(false);
BStruct inRequest = BLangConnectorSPIUtil.createBStruct(WebSocketUtil.getProgramFile(wsService.getResources()[0]), PROTOCOL_PACKAGE_HTTP, HttpConstants.REQUEST);
BStruct inRequestEntity = BLangConnectorSPIUtil.createBStruct(WebSocketUtil.getProgramFile(wsService.getResources()[0]), org.ballerinalang.mime.util.Constants.PROTOCOL_PACKAGE_MIME, Constants.ENTITY);
BStruct mediaType = BLangConnectorSPIUtil.createBStruct(WebSocketUtil.getProgramFile(wsService.getResources()[0]), org.ballerinalang.mime.util.Constants.PROTOCOL_PACKAGE_MIME, Constants.MEDIA_TYPE);
BStruct cacheControlStruct = BLangConnectorSPIUtil.createBStruct(WebSocketUtil.getProgramFile(wsService.getResources()[0]), PROTOCOL_PACKAGE_HTTP, REQUEST_CACHE_CONTROL);
RequestCacheControlStruct requestCacheControl = new RequestCacheControlStruct(cacheControlStruct);
HttpUtil.populateInboundRequest(inRequest, inRequestEntity, mediaType, msg, requestCacheControl);
List<ParamDetail> paramDetails = onUpgradeResource.getParamDetails();
BValue[] bValues = new BValue[paramDetails.size()];
bValues[0] = serviceEndpoint;
bValues[1] = inRequest;
WebSocketDispatcher.setPathParams(bValues, paramDetails, pathParams, 2);
Tracer tracer = TraceManagerWrapper.newTracer(null, false);
upgradeHeaders.entrySet().stream().filter(c -> c.getKey().startsWith(TraceConstants.TRACE_PREFIX)).forEach(e -> tracer.addProperty(e.getKey(), e.getValue()));
Executor.submit(onUpgradeResource, new CallableUnitCallback() {
@Override
public void notifySuccess() {
isResourceExeSuccessful.set(true);
semaphore.release();
}
@Override
public void notifyFailure(BStruct error) {
ErrorHandlerUtils.printError("error: " + BLangVMErrors.getPrintableStackTrace(error));
semaphore.release();
}
}, null, tracer, bValues);
try {
semaphore.acquire();
if (isResourceExeSuccessful.get() && !webSocketInitMessage.isCancelled() && !webSocketInitMessage.isHandshakeStarted()) {
WebSocketUtil.handleHandshake(wsService, null, serverConnector);
}
} catch (InterruptedException e) {
throw new BallerinaConnectorException("Connection interrupted during handshake");
}
} else {
WebSocketUtil.handleHandshake(wsService, null, serverConnector);
}
}
use of org.ballerinalang.connector.api.BallerinaConnectorException in project ballerina by ballerina-lang.
the class HttpDispatcher method populateAndGetEntityBody.
private static BValue populateAndGetEntityBody(HttpResource httpResource, BStruct inRequest, BStruct inRequestEntity, BType entityBodyType) throws IOException {
HttpUtil.populateEntityBody(null, inRequest, inRequestEntity, true);
switch(entityBodyType.getTag()) {
case TypeTags.STRING_TAG:
StringDataSource stringDataSource = EntityBodyHandler.constructStringDataSource(inRequestEntity);
EntityBodyHandler.addMessageDataSource(inRequestEntity, stringDataSource);
return stringDataSource != null ? new BString(stringDataSource.getMessageAsString()) : null;
case TypeTags.JSON_TAG:
BJSON bjson = EntityBodyHandler.constructJsonDataSource(inRequestEntity);
EntityBodyHandler.addMessageDataSource(inRequestEntity, bjson);
return bjson;
case TypeTags.XML_TAG:
BXML bxml = EntityBodyHandler.constructXmlDataSource(inRequestEntity);
EntityBodyHandler.addMessageDataSource(inRequestEntity, bxml);
return bxml;
case TypeTags.BLOB_TAG:
BlobDataSource blobDataSource = EntityBodyHandler.constructBlobDataSource(inRequestEntity);
EntityBodyHandler.addMessageDataSource(inRequestEntity, blobDataSource);
return new BBlob(blobDataSource != null ? blobDataSource.getValue() : new byte[0]);
case TypeTags.STRUCT_TAG:
bjson = EntityBodyHandler.constructJsonDataSource(inRequestEntity);
EntityBodyHandler.addMessageDataSource(inRequestEntity, bjson);
try {
return JSONUtils.convertJSONToStruct(bjson, (BStructType) entityBodyType);
} catch (NullPointerException ex) {
throw new BallerinaConnectorException("cannot convert payload to struct type: " + entityBodyType.getName());
}
}
return null;
}
use of org.ballerinalang.connector.api.BallerinaConnectorException in project ballerina by ballerina-lang.
the class HttpDispatcher method findService.
protected static HttpService findService(HTTPServicesRegistry servicesRegistry, HTTPCarbonMessage inboundReqMsg) {
try {
Map<String, HttpService> servicesOnInterface = servicesRegistry.getServicesInfoByInterface();
String rawUri = (String) inboundReqMsg.getProperty(HttpConstants.TO);
inboundReqMsg.setProperty(HttpConstants.RAW_URI, rawUri);
Map<String, Map<String, String>> matrixParams = new HashMap<>();
String uriWithoutMatrixParams = URIUtil.extractMatrixParams(rawUri, matrixParams);
inboundReqMsg.setProperty(HttpConstants.TO, uriWithoutMatrixParams);
inboundReqMsg.setProperty(HttpConstants.MATRIX_PARAMS, matrixParams);
URI validatedUri = getValidatedURI(uriWithoutMatrixParams);
// Most of the time we will find service from here
String basePath = servicesRegistry.findTheMostSpecificBasePath(validatedUri.getPath(), servicesOnInterface);
if (basePath == null) {
inboundReqMsg.setProperty(HttpConstants.HTTP_STATUS_CODE, 404);
throw new BallerinaConnectorException("no matching service found for path : " + validatedUri.getRawPath());
}
HttpService service = servicesOnInterface.get(basePath);
setInboundReqProperties(inboundReqMsg, validatedUri, basePath);
return service;
} catch (Throwable e) {
throw new BallerinaConnectorException(e.getMessage());
}
}
use of org.ballerinalang.connector.api.BallerinaConnectorException in project ballerina by ballerina-lang.
the class HttpResourceDispatcher method findResource.
public static HttpResource findResource(HttpService service, HTTPCarbonMessage inboundRequest) throws BallerinaConnectorException {
String method = (String) inboundRequest.getProperty(HttpConstants.HTTP_METHOD);
String subPath = (String) inboundRequest.getProperty(HttpConstants.SUB_PATH);
subPath = sanitizeSubPath(subPath);
Map<String, String> resourceArgumentValues = new HashMap<>();
try {
HttpResource resource = service.getUriTemplate().matches(subPath, resourceArgumentValues, inboundRequest);
if (resource != null) {
inboundRequest.setProperty(HttpConstants.RESOURCE_ARGS, resourceArgumentValues);
inboundRequest.setProperty(HttpConstants.RESOURCES_CORS, resource.getCorsHeaders());
return resource;
} else {
if (method.equals(HttpConstants.HTTP_METHOD_OPTIONS)) {
handleOptionsRequest(inboundRequest, service);
} else {
inboundRequest.setProperty(HttpConstants.HTTP_STATUS_CODE, 404);
throw new BallerinaConnectorException("no matching resource found for path : " + inboundRequest.getProperty(HttpConstants.TO) + " , method : " + method);
}
return null;
}
} catch (URITemplateException e) {
throw new BallerinaConnectorException(e.getMessage());
}
}
use of org.ballerinalang.connector.api.BallerinaConnectorException in project ballerina by ballerina-lang.
the class HttpService method buildHttpService.
public static HttpService buildHttpService(Service service) {
HttpService httpService = new HttpService(service);
Annotation serviceConfigAnnotation = getHttpServiceConfigAnnotation(service);
if (serviceConfigAnnotation == null) {
log.debug("serviceConfig not specified in the Service instance, using default base path");
// service name cannot start with / hence concat
httpService.setBasePath(HttpConstants.DEFAULT_BASE_PATH.concat(httpService.getName()));
} else {
Struct serviceConfig = serviceConfigAnnotation.getValue();
httpService.setBasePath(serviceConfig.getStringField(BASE_PATH_FIELD));
httpService.setCompression(serviceConfig.getEnumField(COMPRESSION_FIELD));
httpService.setCorsHeaders(CorsHeaders.buildCorsHeaders(serviceConfig.getStructField(CORS_FIELD)));
httpService.setWebSocketUpgradeConfig(serviceConfig.getStructField(WEBSOCKET_UPGRADE_FIELD));
}
List<HttpResource> resources = new ArrayList<>();
for (Resource resource : httpService.getBallerinaService().getResources()) {
HttpResource httpResource = HttpResource.buildHttpResource(resource, httpService);
try {
httpService.getUriTemplate().parse(httpResource.getPath(), httpResource, new HttpResourceElementFactory());
} catch (URITemplateException | UnsupportedEncodingException e) {
throw new BallerinaConnectorException(e.getMessage());
}
resources.add(httpResource);
}
httpService.setResources(resources);
httpService.setAllAllowedMethods(DispatcherUtil.getAllResourceMethods(httpService));
return httpService;
}
Aggregations