@Override public void upsertStreamProperty( DataRequest request, String entityETag, InputStream streamContent, NoContentResponse response) throws ODataLibraryException, ODataApplicationException { UpdateResponse updateResponse = null; EdmProperty edmProperty = request.getUriResourceProperty().getProperty(); try { ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); Update update = visitor.updateStreamProperty(edmProperty, streamContent); updateResponse = getClient().executeUpdate(update, visitor.getParameters()); } catch (SQLException | TeiidException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } if (updateResponse != null && updateResponse.getUpdateCount() > 0) { response.writeNoContent(); } else { response.writeNotModified(); } }
@Override public void crossJoin(DataRequest request, List<String> entitySetNames, ODataResponse response) throws ODataLibraryException, ODataApplicationException { final ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, true, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); try { Query query = visitor.selectQuery(); BaseResponse queryResponse = executeQuery(request, request.isCountRequest(), visitor, query); ContextURL.Builder builder = new ContextURL.Builder().asCollection().entitySetOrSingletonOrType("Edm.ComplexType"); EdmComplexResponse complexResponse = EdmComplexResponse.getInstance(request, builder.build(), false, response); sendResults(request, visitor, queryResponse, complexResponse); } catch (Exception e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } }
private UpdateResponse performInsert( String rawURI, UriInfo uriInfo, EdmEntityType entityType, Entity entity) throws SQLException, TeiidException { ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, rawURI, this.serviceMetadata, this.nameGenerator); visitor.visit(uriInfo); Insert command = visitor.insert(entityType, entity, null, this.prepared); return getClient().executeUpdate(command, visitor.getParameters()); }
private void sendResults( final DataRequest request, final ODataSQLBuilder visitor, final BaseResponse queryResponse, EntitySetResponse response) throws ODataApplicationException, SerializerException { if (request.getPreference(ODATA_MAXPAGESIZE) != null) { response.writeHeader( PREFERENCE_APPLIED, ODATA_MAXPAGESIZE + "=" + request.getPreference(ODATA_MAXPAGESIZE)); // $NON-NLS-1$ } EntityCollectionResponse result = (EntityCollectionResponse) queryResponse; if (result.getNextToken() != null) { try { String nextUri = request.getODataRequest().getRawBaseUri() + request.getODataRequest().getRawODataPath() + "?" + buildNextToken( request.getODataRequest().getRawQueryPath(), result.getNextToken()); result.setNext(new URI(nextUri)); } catch (URISyntaxException e) { throw new ODataApplicationException(e.getMessage(), 500, Locale.getDefault(), e); } catch (MalformedURLException e) { throw new ODataApplicationException(e.getMessage(), 500, Locale.getDefault(), e); } } response.writeReadEntitySet(visitor.getContext().getEdmEntityType(), result); }
private QueryCommand buildSubquery(Expression projected) { Criteria criteria = null; for (ForeignKey fk : this.childTable.getForeignKeys()) { if (fk.getPrimaryKey().getParent().equals(this.parent)) { List<String> refColumns = fk.getReferenceColumns(); if (refColumns == null) { refColumns = ODataSQLBuilder.getColumnNames(childTable.getPrimaryKey().getColumns()); } List<String> pkColumns = ODataSQLBuilder.getColumnNames(parent.getPrimaryKey().getColumns()); List<Criteria> critList = new ArrayList<Criteria>(); for (int i = 0; i < refColumns.size(); i++) { critList.add( new CompareCriteria( new ElementSymbol(pkColumns.get(i), this.parentGroup), CompareCriteria.EQ, new ElementSymbol(refColumns.get(i), this.childGroup))); } criteria = critList.get(0); for (int i = 1; i < critList.size(); i++) { criteria = new CompoundCriteria(CompoundCriteria.AND, criteria, critList.get(i)); } } } Select s1 = new Select(); s1.addSymbol(projected); From f1 = new From(); f1.addGroup(this.childGroup); Query q1 = new Query(); q1.setSelect(s1); q1.setFrom(f1); q1.setCriteria(criteria); return q1; }
@Override public void deleteEntity(DataRequest request, String entityETag, EntityResponse response) throws ODataLibraryException, ODataApplicationException { // TODO: need to match entityETag. checkETag(entityETag); UpdateResponse updateResponse = null; try { ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); Delete delete = visitor.delete(); updateResponse = getClient().executeUpdate(delete, visitor.getParameters()); } catch (SQLException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } if (updateResponse != null && updateResponse.getUpdateCount() > 0) { response.writeDeletedEntityOrReference(); } else { // since DELETE is idempotent same response as otherwise success operation. response.writeDeletedEntityOrReference(); } }
@Override public void upsertEntity( DataRequest request, Entity entity, boolean merge, String entityETag, EntityResponse response) throws ODataLibraryException, ODataApplicationException { final ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, true, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); final EntityCollectionResponse queryResponse; try { Query query = visitor.selectQuery(); queryResponse = (EntityCollectionResponse) executeQuery(request, request.isCountRequest(), visitor, query); } catch (Exception e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } if (!queryResponse.getEntities().isEmpty()) { updateEntity(request, entity, merge, entityETag, response); } else { createEntity(request, entity, response); } }
private <T extends ServiceResponse> void invokeOperation( final OperationRequest request, OperationParameterValueProvider parameters, T response) throws ODataApplicationException, ODataLibraryException { checkExpand(request.getUriInfo().asUriInfoResource()); final ODataSQLBuilder visitor = new ODataSQLBuilder( odata, getClient().getMetadataStore(), this.prepared, true, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.setOperationParameterValueProvider(parameters); visitor.visit(request.getUriInfo()); final OperationResponseImpl queryResponse; try { if (visitor.getContext() instanceof NoDocumentNode) { NoDocumentNode cdn = (NoDocumentNode) visitor.getContext(); ProcedureReturn procReturn = cdn.getProcedureReturn(); queryResponse = new OperationResponseImpl(procReturn); getClient().executeCall(cdn.getQuery(), visitor.getParameters(), procReturn, queryResponse); } else { Query query = visitor.selectQuery(); queryResponse = (OperationResponseImpl) executeQuery(request, request.isCountRequest(), visitor, query); } } catch (Throwable e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } /* try { MetadataStore store = getClient().getMetadataStore(); ProcedureSQLBuilder builder = new ProcedureSQLBuilder(store.getSchema(schemaName), request); ProcedureReturn procedureReturn = builder.getReturn(); result = new OperationResponseImpl(procedureReturn); getClient().executeCall(builder.buildProcedureSQL(), builder.getSqlParameters(), procedureReturn, result); } catch (SQLException e) { throw new ODataApplicationException(e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (TeiidException e) { throw new ODataApplicationException(e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } */ final OperationResponseImpl operationResult = queryResponse; response.accepts( new ServiceResponseVisior() { @Override public void visit(PropertyResponse response) throws ODataLibraryException, ODataApplicationException { Property property = (Property) operationResult.getResult(); Object value = property.getValue(); if (value instanceof SQLXML || value instanceof Blob || value instanceof Clob) { try { handleLobResult(getClient().getProperty(Client.CHARSET), value, response); } catch (SQLException e) { LogManager.logDetail(LogConstants.CTX_ODATA, e); response.writeServerError(true); } } else { response.writeProperty(request.getReturnType().getType(), property); } } }); }
@Override public void updateEntity( DataRequest request, Entity entity, boolean merge, String entityETag, EntityResponse response) throws ODataLibraryException, ODataApplicationException { // TODO: need to match entityETag. checkETag(entityETag); UpdateResponse updateResponse = null; if (merge) { try { ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); EdmEntityType entityType = request.getEntitySet().getEntityType(); Update update = visitor.update(entityType, entity, this.prepared); updateResponse = getClient().executeUpdate(update, visitor.getParameters()); } catch (SQLException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (TeiidException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } } else { // delete, then insert String txn = startTransaction(); boolean success = false; try { // build insert first as it could fail to validate ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); EdmEntityType entityType = request.getEntitySet().getEntityType(); List<UriParameter> keys = request.getKeyPredicates(); Insert command = visitor.insert(entityType, entity, keys, this.prepared); // run delete ODataSQLBuilder deleteVisitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), this.prepared, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); deleteVisitor.visit(request.getUriInfo()); Delete delete = deleteVisitor.delete(); updateResponse = getClient().executeUpdate(delete, deleteVisitor.getParameters()); // run insert updateResponse = getClient().executeUpdate(command, visitor.getParameters()); commit(txn); success = true; } catch (SQLException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (TeiidException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } finally { if (!success) { rollback(txn); } } } if (updateResponse != null && updateResponse.getUpdateCount() > 0) { response.writeUpdatedEntity(); } else { response.writeNotModified(); } }
@Override public void createEntity(DataRequest request, Entity entity, EntityResponse response) throws ODataLibraryException, ODataApplicationException { EdmEntityType entityType = request.getEntitySet().getEntityType(); String txn; try { txn = getClient().startTransaction(); } catch (SQLException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } boolean success = false; try { List<ExpandNode> expands = new ArrayList<TeiidServiceHandler.ExpandNode>(); UpdateResponse updateResponse = performDeepInsert( request.getODataRequest().getRawBaseUri(), request.getUriInfo(), entityType, entity, expands); if (updateResponse != null && updateResponse.getUpdateCount() == 1) { ODataSQLBuilder visitor = new ODataSQLBuilder( this.odata, getClient().getMetadataStore(), true, false, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); Query query = visitor.selectWithEntityKey( entityType, entity, updateResponse.getGeneratedKeys(), expands); LogManager.logDetail( LogConstants.CTX_ODATA, null, "created entity = ", entityType.getName(), " with key=", query.getCriteria().toString()); // $NON-NLS-1$ //$NON-NLS-2$ EntityCollectionResponse result = new EntityCollectionResponse( request.getODataRequest().getRawBaseUri(), visitor.getContext()); getClient().executeSQL(query, visitor.getParameters(), false, null, null, null, 1, result); if (!result.getEntities().isEmpty()) { entity = result.getEntities().get(0); String location = EntityResponse.buildLocation( request.getODataRequest().getRawBaseUri(), entity, request.getEntitySet().getName(), entityType); entity.setId(new URI(location)); } response.writeCreatedEntity(request.getEntitySet(), entity); } else { response.writeNotModified(); } getClient().commit(txn); success = true; } catch (SQLException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (URISyntaxException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (TeiidException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } catch (EdmPrimitiveTypeException e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } finally { if (!success) { try { getClient().rollback(txn); } catch (SQLException e1) { // ignore } } } }
private BaseResponse executeQuery( final ServiceRequest request, boolean countRequest, final ODataSQLBuilder visitor, Query query) throws SQLException { if (countRequest) { return getClient().executeCount(query, visitor.getParameters()); } else { String pageSize = getPageSize(request); QueryResponse result = new EntityCollectionResponse( request.getODataRequest().getRawBaseUri(), visitor.getContext()); if (visitor.getContext() instanceof CrossJoinNode) { result = new CrossJoinResult( request.getODataRequest().getRawBaseUri(), (CrossJoinNode) visitor.getContext()); } else if (visitor.getContext() instanceof ComplexDocumentNode) { ComplexDocumentNode cdn = (ComplexDocumentNode) visitor.getContext(); result = new OperationResponseImpl(cdn.getProcedureReturn()); } getClient() .executeSQL( query, visitor.getParameters(), visitor.includeTotalSize(), visitor.getSkip(), visitor.getTop(), visitor.getNextToken(), Integer.parseInt(pageSize), result); return result; } }
@Override public <T extends ServiceResponse> void read(final DataRequest request, T response) throws ODataLibraryException, ODataApplicationException { final ODataSQLBuilder visitor = new ODataSQLBuilder( odata, getClient().getMetadataStore(), this.prepared, true, request.getODataRequest().getRawBaseUri(), this.serviceMetadata, this.nameGenerator); visitor.visit(request.getUriInfo()); final BaseResponse queryResponse; try { Query query = visitor.selectQuery(); queryResponse = executeQuery(request, request.isCountRequest(), visitor, query); } catch (Throwable e) { throw new ODataApplicationException( e.getMessage(), HttpStatusCode.INTERNAL_SERVER_ERROR.getStatusCode(), Locale.getDefault(), e); } response.accepts( new ServiceResponseVisior() { public void visit(CountResponse response) throws ODataLibraryException, ODataApplicationException { org.teiid.odata.api.CountResponse cr = (org.teiid.odata.api.CountResponse) queryResponse; response.writeCount(cr.getCount()); } public void visit(PrimitiveValueResponse response) throws ODataLibraryException, ODataApplicationException { EntityCollection entitySet = (EntityCollection) queryResponse; Entity entity = entitySet.getEntities().get(0); EdmProperty edmProperty = request.getUriResourceProperty().getProperty(); Property property = entity.getProperty(edmProperty.getName()); if (property == null) { response.writeNotFound(true); } else if (property.getValue() == null) { response.writeNoContent(true); } response.write(property.getValue()); } public void visit(PropertyResponse response) throws ODataLibraryException, ODataApplicationException { EntityCollection entitySet = (EntityCollection) queryResponse; if (!entitySet.getEntities().isEmpty()) { Entity entity = entitySet.getEntities().get(0); EdmProperty edmProperty = request.getUriResourceProperty().getProperty(); Property property = entity.getProperty(edmProperty.getName()); response.writeProperty(edmProperty.getType(), property); } else { response.writeNotFound(true); } } public void visit(StreamResponse response) throws ODataLibraryException, ODataApplicationException { EntityCollectionResponse entitySet = (EntityCollectionResponse) queryResponse; EdmProperty edmProperty = request.getUriResourceProperty().getProperty(); Object value = entitySet.getStream(edmProperty.getName()); if (value == null) { response.writeNoContent(true); } else { try { handleLobResult(getClient().getProperty(Client.CHARSET), value, response); } catch (SQLException e) { LogManager.logDetail(LogConstants.CTX_ODATA, e); response.writeServerError(true); } } } public void visit(EntityResponse response) throws ODataLibraryException, ODataApplicationException { EntityCollection entitySet = (EntityCollection) queryResponse; if (entitySet.getEntities().isEmpty()) { if (visitor.hasNavigation()) { response.writeNoContent(true); } else { response.writeNotFound(true); } } else { response.writeReadEntity( visitor.getContext().getEdmEntityType(), entitySet.getEntities().get(0)); } } public void visit(EntitySetResponse response) throws ODataLibraryException, ODataApplicationException { sendResults(request, visitor, queryResponse, response); } }); }