@Override
    protected void load() {
        //recordId can be null when in batchMode
        if (this.recordId != null && this.properties.isEmpty()) {
            this.sqlgGraph.tx().readWrite();
            if (this.sqlgGraph.getSqlDialect().supportsBatchMode() && this.sqlgGraph.tx().getBatchManager().isStreaming()) {
                throw new IllegalStateException("streaming is in progress, first flush or commit before querying.");
            }

            //Generate the columns to prevent 'ERROR: cached plan must not change result type" error'
            //This happens when the schema changes after the statement is prepared.
            @SuppressWarnings("OptionalGetWithoutIsPresent")
            EdgeLabel edgeLabel = this.sqlgGraph.getTopology().getSchema(this.schema).orElseThrow(() -> new IllegalStateException(String.format("Schema %s not found", this.schema))).getEdgeLabel(this.table).orElseThrow(() -> new IllegalStateException(String.format("EdgeLabel %s not found", this.table)));
            StringBuilder sql = new StringBuilder("SELECT\n\t");
            sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes("ID"));
            appendProperties(edgeLabel, sql);
            List<VertexLabel> outForeignKeys = new ArrayList<>();
            for (VertexLabel vertexLabel : edgeLabel.getOutVertexLabels()) {
                outForeignKeys.add(vertexLabel);
                sql.append(", ");
                if (vertexLabel.hasIDPrimaryKey()) {
                    String foreignKey = vertexLabel.getSchema().getName() + "." + vertexLabel.getName() + Topology.OUT_VERTEX_COLUMN_END;
                    sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes(foreignKey));
                } else {
                    int countIdentifier = 1;
                    for (String identifier : vertexLabel.getIdentifiers()) {
                        PropertyColumn propertyColumn = vertexLabel.getProperty(identifier).orElseThrow(
                                () -> new IllegalStateException(String.format("identifier %s column must be a property", identifier))
                        );
                        PropertyType propertyType = propertyColumn.getPropertyType();
                        String[] propertyTypeToSqlDefinition = this.sqlgGraph.getSqlDialect().propertyTypeToSqlDefinition(propertyType);
                        int count = 1;
                        for (String ignored : propertyTypeToSqlDefinition) {
                            if (count > 1) {
                                sql.append(sqlgGraph.getSqlDialect().maybeWrapInQoutes(vertexLabel.getFullName() + "." + identifier + propertyType.getPostFixes()[count - 2] + Topology.OUT_VERTEX_COLUMN_END));
                            } else {
                                //The first column existVertexLabel no postfix
                                sql.append(sqlgGraph.getSqlDialect().maybeWrapInQoutes(vertexLabel.getFullName() + "." + identifier + Topology.OUT_VERTEX_COLUMN_END));
                            }
                            if (count++ < propertyTypeToSqlDefinition.length) {
                                sql.append(", ");
                            }
                        }
                        if (countIdentifier++ < vertexLabel.getIdentifiers().size()) {
                            sql.append(", ");
                        }
                    }
                }
            }
            List<VertexLabel> inForeignKeys = new ArrayList<>();
            for (VertexLabel vertexLabel : edgeLabel.getInVertexLabels()) {
                sql.append(", ");
                inForeignKeys.add(vertexLabel);
                if (vertexLabel.hasIDPrimaryKey()) {
                    String foreignKey = vertexLabel.getSchema().getName() + "." + vertexLabel.getName() + Topology.IN_VERTEX_COLUMN_END;
                    sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes(foreignKey));
                } else {
                    int countIdentifier = 1;
                    for (String identifier : vertexLabel.getIdentifiers()) {
                        PropertyColumn propertyColumn = vertexLabel.getProperty(identifier).orElseThrow(
                                () -> new IllegalStateException(String.format("identifier %s column must be a property", identifier))
                        );
                        PropertyType propertyType = propertyColumn.getPropertyType();
                        String[] propertyTypeToSqlDefinition = this.sqlgGraph.getSqlDialect().propertyTypeToSqlDefinition(propertyType);
                        int count = 1;
                        for (String ignored : propertyTypeToSqlDefinition) {
                            if (count > 1) {
                                sql.append(sqlgGraph.getSqlDialect().maybeWrapInQoutes(vertexLabel.getFullName() + "." + identifier + propertyType.getPostFixes()[count - 2] + Topology.IN_VERTEX_COLUMN_END));
                            } else {
                                //The first column existVertexLabel no postfix
                                sql.append(sqlgGraph.getSqlDialect().maybeWrapInQoutes(vertexLabel.getFullName() + "." + identifier + Topology.IN_VERTEX_COLUMN_END));
                            }
                            if (count++ < propertyTypeToSqlDefinition.length) {
                                sql.append(", ");
                            }
                        }
                        if (countIdentifier++ < vertexLabel.getIdentifiers().size()) {
                            sql.append(", ");
                        }
                    }
                }
            }
            sql.append("\nFROM\n\t");
            sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes(this.schema));
            sql.append(".");
            sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes(EDGE_PREFIX + this.table));
            sql.append(" WHERE ");
            //noinspection Duplicates
            if (edgeLabel.hasIDPrimaryKey()) {
                sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes("ID"));
                sql.append(" = ?");
            } else {
                int count = 1;
                for (String identifier : edgeLabel.getIdentifiers()) {
                    sql.append(this.sqlgGraph.getSqlDialect().maybeWrapInQoutes(identifier));
                    sql.append(" = ?");
                    if (count++ < edgeLabel.getIdentifiers().size()) {
                        sql.append(" AND ");
                    }

                }
            }
            if (this.sqlgGraph.getSqlDialect().needsSemicolon()) {
                sql.append(";");
            }
            Connection conn = this.sqlgGraph.tx().getConnection();
            if (logger.isDebugEnabled()) {
                logger.debug(sql.toString());
            }
            try (PreparedStatement preparedStatement = conn.prepareStatement(sql.toString())) {
                if (edgeLabel.hasIDPrimaryKey()) {
                    preparedStatement.setLong(1, this.recordId.sequenceId());
                } else {
                    int count = 1;
                    for (Comparable identifierValue : this.recordId.getIdentifiers()) {
                        preparedStatement.setObject(count++, identifierValue);
                    }
                }
                ResultSet resultSet = preparedStatement.executeQuery();
                if (resultSet.next()) {
                    loadResultSet(resultSet, inForeignKeys, outForeignKeys);
                }
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
    }
@ Override protected void load ( ) { if ( this . recordId != null && this . properties . isEmpty ( ) ) { this . sqlgGraph . tx ( ) . readWrite ( ) ; if ( this . sqlgGraph . getSqlDialect ( ) . supportsBatchMode ( ) && this . sqlgGraph . tx ( ) . getBatchManager ( ) . isStreaming ( ) ) { throw new IllegalStateException ( "streaming is in progress, first flush or commit before querying." ) ; } @ SuppressWarnings ( "OptionalGetWithoutIsPresent" ) EdgeLabel edgeLabel = this . sqlgGraph . getTopology ( ) . getSchema ( this . schema ) . orElseThrow ( ( ) -> new IllegalStateException ( String . format ( "Schema %s not found" , this . schema ) ) ) . getEdgeLabel ( this . table ) . orElseThrow ( ( ) -> new IllegalStateException ( String . format ( "EdgeLabel %s not found" , this . table ) ) ) ; StringBuilder sql = new StringBuilder ( "SELECT\n\t" ) ; sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( "ID" ) ) ; appendProperties ( edgeLabel , sql ) ; List < VertexLabel > outForeignKeys = new ArrayList < > ( ) ; for ( VertexLabel vertexLabel : edgeLabel . getOutVertexLabels ( ) ) { outForeignKeys . add ( vertexLabel ) ; sql . append ( ", " ) ; if ( vertexLabel . hasIDPrimaryKey ( ) ) { String foreignKey = vertexLabel . getSchema ( ) . getName ( ) + "." + vertexLabel . getName ( ) + Topology . OUT_VERTEX_COLUMN_END ; sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( foreignKey ) ) ; } else { int countIdentifier = 1 ; for ( String identifier : vertexLabel . getIdentifiers ( ) ) { PropertyColumn propertyColumn = vertexLabel . getProperty ( identifier ) . orElseThrow ( ( ) -> new IllegalStateException ( String . format ( "identifier %s column must be a property" , identifier ) ) ) ; PropertyType propertyType = propertyColumn . getPropertyType ( ) ; String [ ] propertyTypeToSqlDefinition = this . sqlgGraph . getSqlDialect ( ) . propertyTypeToSqlDefinition ( propertyType ) ; int count = 1 ; for ( String ignored : propertyTypeToSqlDefinition ) { if ( count > 1 ) { sql . append ( sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( vertexLabel . getFullName ( ) + "." + identifier + propertyType . getPostFixes ( ) [ count - 2 ] + Topology . OUT_VERTEX_COLUMN_END ) ) ; } else { sql . append ( sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( vertexLabel . getFullName ( ) + "." + identifier + Topology . OUT_VERTEX_COLUMN_END ) ) ; } if ( count ++ < propertyTypeToSqlDefinition . length ) { sql . append ( ", " ) ; } } if ( countIdentifier ++ < vertexLabel . getIdentifiers ( ) . size ( ) ) { sql . append ( ", " ) ; } } } } List < VertexLabel > inForeignKeys = new ArrayList < > ( ) ; for ( VertexLabel vertexLabel : edgeLabel . getInVertexLabels ( ) ) { sql . append ( ", " ) ; inForeignKeys . add ( vertexLabel ) ; if ( vertexLabel . hasIDPrimaryKey ( ) ) { String foreignKey = vertexLabel . getSchema ( ) . getName ( ) + "." + vertexLabel . getName ( ) + Topology . IN_VERTEX_COLUMN_END ; sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( foreignKey ) ) ; } else { int countIdentifier = 1 ; for ( String identifier : vertexLabel . getIdentifiers ( ) ) { PropertyColumn propertyColumn = vertexLabel . getProperty ( identifier ) . orElseThrow ( ( ) -> new IllegalStateException ( String . format ( "identifier %s column must be a property" , identifier ) ) ) ; PropertyType propertyType = propertyColumn . getPropertyType ( ) ; String [ ] propertyTypeToSqlDefinition = this . sqlgGraph . getSqlDialect ( ) . propertyTypeToSqlDefinition ( propertyType ) ; int count = 1 ; for ( String ignored : propertyTypeToSqlDefinition ) { if ( count > 1 ) { sql . append ( sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( vertexLabel . getFullName ( ) + "." + identifier + propertyType . getPostFixes ( ) [ count - 2 ] + Topology . IN_VERTEX_COLUMN_END ) ) ; } else { sql . append ( sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( vertexLabel . getFullName ( ) + "." + identifier + Topology . IN_VERTEX_COLUMN_END ) ) ; } if ( count ++ < propertyTypeToSqlDefinition . length ) { sql . append ( ", " ) ; } } if ( countIdentifier ++ < vertexLabel . getIdentifiers ( ) . size ( ) ) { sql . append ( ", " ) ; } } } } sql . append ( "\nFROM\n\t" ) ; sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( this . schema ) ) ; sql . append ( "." ) ; sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( EDGE_PREFIX + this . table ) ) ; sql . append ( " WHERE " ) ; if ( edgeLabel . hasIDPrimaryKey ( ) ) { sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( "ID" ) ) ; sql . append ( " = ?" ) ; } else { int count = 1 ; for ( String identifier : edgeLabel . getIdentifiers ( ) ) { sql . append ( this . sqlgGraph . getSqlDialect ( ) . maybeWrapInQoutes ( identifier ) ) ; sql . append ( " = ?" ) ; if ( count ++ < edgeLabel . getIdentifiers ( ) . size ( ) ) { sql . append ( " AND " ) ; } } } if ( this . sqlgGraph . getSqlDialect ( ) . needsSemicolon ( ) ) { sql . append ( ";" ) ; } Connection conn = this . sqlgGraph . tx ( ) . getConnection ( ) ; if ( logger . isDebugEnabled ( ) ) { logger . debug ( sql . toString ( ) ) ; } try ( PreparedStatement preparedStatement = conn . prepareStatement ( sql . toString ( ) ) ) { if ( edgeLabel . hasIDPrimaryKey ( ) ) { preparedStatement . setLong ( 1 , this . recordId . sequenceId ( ) ) ; } else { int count = 1 ; for ( Comparable identifierValue : this . recordId . getIdentifiers ( ) ) { preparedStatement . setObject ( count ++ , identifierValue ) ; } } ResultSet resultSet = preparedStatement . executeQuery ( ) ; if ( resultSet . next ( ) ) { loadResultSet ( resultSet , inForeignKeys , outForeignKeys ) ; } } catch ( SQLException e ) { throw new RuntimeException ( e ) ; } } }
TODO this needs optimizing, an edge created in the transaction need not go to the db to load itself again