static OProperty<?> buildPropery( String propName, EdmType type, Object value, String invalidCharacterReplacement) throws TransformationException, SQLException, IOException { if (!(type instanceof EdmSimpleType)) { if (type instanceof EdmCollectionType) { EdmCollectionType collectionType = (EdmCollectionType) type; EdmType componentType = collectionType.getItemType(); Builder<OObject> b = OCollections.newBuilder(componentType); if (value instanceof Array) { value = ((Array) value).getArray(); } int length = java.lang.reflect.Array.getLength(value); for (int i = 0; i < length; i++) { Object o = java.lang.reflect.Array.get(value, i); OProperty p = buildPropery("x", componentType, o, invalidCharacterReplacement); if (componentType instanceof EdmSimpleType) { b.add(OSimpleObjects.create((EdmSimpleType) componentType, p.getValue())); } else { throw new AssertionError("Multi-dimensional arrays are not yet supported."); // b.add((OCollection)p.getValue()); } } return OProperties.collection(propName, collectionType, b.build()); } throw new AssertionError("non-simple types are not yet supported"); } EdmSimpleType expectedType = (EdmSimpleType) type; if (value == null) { return OProperties.null_(propName, expectedType); } Class<?> sourceType = DataTypeManager.getRuntimeType(value.getClass()); Class<?> targetType = DataTypeManager.getDataTypeClass( ODataTypeManager.teiidType(expectedType.getFullyQualifiedTypeName())); if (sourceType != targetType) { Transform t = DataTypeManager.getTransform(sourceType, targetType); if (t == null && BlobType.class == targetType) { if (sourceType == ClobType.class) { return OProperties.binary(propName, ClobType.getString((Clob) value).getBytes()); } if (sourceType == SQLXML.class) { return OProperties.binary(propName, ((SQLXML) value).getString().getBytes()); } } value = DataTypeManager.convertToRuntimeType(value, true); value = t != null ? t.transform(value, targetType) : value; value = replaceInvalidCharacters(expectedType, value, invalidCharacterReplacement); if (value instanceof BinaryType) { value = ((BinaryType) value).getBytesDirect(); } return OProperties.simple(propName, expectedType, value); } value = replaceInvalidCharacters(expectedType, value, invalidCharacterReplacement); return OProperties.simple(propName, expectedType, value); }
private static void buildFunctionImports(MetadataStore metadataStore, List<Builder> edmSchemas) { for (Schema schema : metadataStore.getSchemaList()) { EdmSchema.Builder odataSchema = findSchema(edmSchemas, schema.getName()); EdmEntityContainer.Builder entityContainer = findEntityContainer(edmSchemas, schema.getName()); // procedures for (Procedure proc : schema.getProcedures().values()) { EdmFunctionImport.Builder edmProcedure = EdmFunctionImport.newBuilder(); edmProcedure.setName(proc.getName()); String httpMethod = "POST"; for (ProcedureParameter pp : proc.getParameters()) { if (pp.getName().equals("return")) { httpMethod = "GET"; edmProcedure.setReturnType( ODataTypeManager.odataType(pp.getDatatype().getRuntimeTypeName())); continue; } EdmFunctionParameter.Builder param = EdmFunctionParameter.newBuilder(); param.setName(pp.getName()); param.setType(ODataTypeManager.odataType(pp.getDatatype().getRuntimeTypeName())); if (pp.getType() == ProcedureParameter.Type.In) { param.setMode(Mode.In); } else if (pp.getType() == ProcedureParameter.Type.InOut) { param.setMode(Mode.InOut); } else if (pp.getType() == ProcedureParameter.Type.Out) { param.setMode(Mode.Out); } param.setNullable(pp.getNullType() == NullType.Nullable); edmProcedure.addParameters(param); } // add a complex type for return resultset. ColumnSet<Procedure> returnColumns = proc.getResultSet(); if (returnColumns != null) { httpMethod = "GET"; EdmComplexType.Builder complexType = EdmComplexType.newBuilder(); complexType.setName(proc.getName() + "_" + returnColumns.getName()); complexType.setNamespace(schema.getName()); for (Column c : returnColumns.getColumns()) { EdmProperty.Builder property = EdmProperty.newBuilder(c.getName()) .setType(ODataTypeManager.odataType(c.getDatatype().getRuntimeTypeName())) .setNullable(c.getNullType() == NullType.Nullable); if (c.getDatatype() .getRuntimeTypeName() .equals(DataTypeManager.DefaultDataTypes.STRING)) { property .setFixedLength(c.isFixedLength()) .setMaxLength(c.getLength()) .setUnicode(true); } complexType.addProperties(property); } odataSchema.addComplexTypes(complexType); edmProcedure.setIsCollection(true); edmProcedure.setReturnType( EdmCollectionType.newBuilder() .setCollectionType(complexType) .setKind(CollectionKind.Collection)); } edmProcedure.setHttpMethod(httpMethod); entityContainer.addFunctionImports(edmProcedure); } } }
private static void buildEntityTypes( MetadataStore metadataStore, List<EdmSchema.Builder> edmSchemas) { for (Schema schema : metadataStore.getSchemaList()) { List<EdmEntitySet.Builder> entitySets = new ArrayList<EdmEntitySet.Builder>(); List<EdmEntityType.Builder> entityTypes = new ArrayList<EdmEntityType.Builder>(); for (Table table : schema.getTables().values()) { KeyRecord primaryKey = table.getPrimaryKey(); List<KeyRecord> uniques = table.getUniqueKeys(); if (primaryKey == null && uniques.isEmpty()) { LogManager.logDetail( LogConstants.CTX_ODATA, ODataPlugin.Util.gs(ODataPlugin.Event.TEIID16002, table.getFullName())); continue; } EdmEntityType.Builder entityType = EdmEntityType.newBuilder().setName(table.getName()).setNamespace(schema.getName()); // adding key if (primaryKey != null) { for (Column c : primaryKey.getColumns()) { entityType.addKeys(c.getName()); } } else { for (Column c : uniques.get(0).getColumns()) { entityType.addKeys(c.getName()); } } // adding properties for (Column c : table.getColumns()) { EdmProperty.Builder property = EdmProperty.newBuilder(c.getName()) .setType(ODataTypeManager.odataType(c.getDatatype().getRuntimeTypeName())) .setNullable(c.getNullType() == NullType.Nullable); if (c.getDatatype() .getRuntimeTypeName() .equals(DataTypeManager.DefaultDataTypes.STRING)) { property.setFixedLength(c.isFixedLength()).setMaxLength(c.getLength()).setUnicode(true); } entityType.addProperties(property); } // entity set one for one entity type EdmEntitySet.Builder entitySet = EdmEntitySet.newBuilder().setName(table.getName()).setEntityType(entityType); entityType.setNamespace(schema.getName()); entitySets.add(entitySet); // add enitity types for entity schema entityTypes.add(entityType); } // entity container is holder entity sets, association sets, function imports EdmEntityContainer.Builder entityContainer = EdmEntityContainer.newBuilder() .setName(schema.getName()) .setIsDefault(false) .addEntitySets(entitySets); // build entity schema EdmSchema.Builder modelSchema = EdmSchema.newBuilder() .setNamespace(schema.getName()) .addEntityTypes(entityTypes) .addEntityContainers(entityContainer); edmSchemas.add(modelSchema); } }
@Override public BaseResponse executeCall(String sql, List<SQLParam> parameters, EdmType returnType) { ConnectionImpl connection = null; try { LogManager.logDetail(LogConstants.CTX_ODATA, "Teiid-Query:", sql); // $NON-NLS-1$ connection = getConnection(); final CallableStatementImpl stmt = connection.prepareCall(sql); int i = 1; if (returnType != null && returnType.isSimple()) { stmt.registerOutParameter( i++, JDBCSQLTypeInfo.getSQLType( ODataTypeManager.teiidType(returnType.getFullyQualifiedTypeName()))); } if (!parameters.isEmpty()) { for (SQLParam param : parameters) { stmt.setObject(i++, param.value, param.sqlType); } } boolean results = stmt.execute(); if (results) { final ResultSet rs = stmt.getResultSet(); OCollection.Builder resultRows = OCollections.newBuilder( (EdmComplexType) ((EdmCollectionType) returnType).getItemType()); while (rs.next()) { int idx = 1; List<OProperty<?>> row = new ArrayList<OProperty<?>>(); Iterator<EdmProperty> props = ((EdmComplexType) ((EdmCollectionType) returnType).getItemType()) .getProperties() .iterator(); while (props.hasNext()) { EdmProperty prop = props.next(); row.add( buildPropery( prop.getName(), prop.getType(), rs.getObject(idx++), invalidCharacterReplacement)); } OComplexObject erow = OComplexObjects.create( (EdmComplexType) ((EdmCollectionType) returnType).getItemType(), row); resultRows.add(erow); } String collectionName = returnType.getFullyQualifiedTypeName(); collectionName = collectionName.replace("(", "_"); // $NON-NLS-1$ //$NON-NLS-2$ collectionName = collectionName.replace(")", "_"); // $NON-NLS-1$ //$NON-NLS-2$ return Responses.collection(resultRows.build(), null, null, null, collectionName); } if (returnType != null) { Object result = stmt.getObject(1); OProperty prop = buildPropery("return", returnType, result, invalidCharacterReplacement); // $NON-NLS-1$ return Responses.property(prop); } return null; } catch (Exception e) { throw new ServerErrorException(e.getMessage(), e); } finally { if (connection != null) { try { connection.close(); } catch (SQLException e) { } } } }