Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Introduce possibility to execute query based on data snapshot. Any data modification will mark corresponding pages with a version that will be equal to transaction id in which that particular change was introduced. Also allow count store to track transactions in which changes where introduced. To be able to guarantee that query result is based on a data that was present on query execution start and was not modified while it was running, the engine will verify that all paged that were accessed during query execution have the version that is less or equal that was last closed on a moment when query started. Support for snapshot query execution in CC and HA Snapshot query execution is enabled by 'unsupported.dbms.query.snapshot' setting and number of retries that engine will do while trying to get stable snapshot is controlled by 'unsupported.dbms.query.snapshot.retries'.
- Loading branch information
1 parent
0f01607
commit 3795750
Showing
140 changed files
with
3,204 additions
and
475 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
194 changes: 194 additions & 0 deletions
194
community/cypher/cypher/src/main/java/org/neo4j/cypher/internal/javacompat/EagerResult.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Original file line | Diff line number | Diff line change |
---|---|---|---|
@@ -0,0 +1,194 @@ | |||
/* | |||
* Copyright (c) 2002-2017 "Neo Technology," | |||
* Network Engine for Objects in Lund AB [http://neotechnology.com] | |||
* | |||
* This file is part of Neo4j. | |||
* | |||
* Neo4j is free software: you can redistribute it and/or modify | |||
* it under the terms of the GNU General Public License as published by | |||
* the Free Software Foundation, either version 3 of the License, or | |||
* (at your option) any later version. | |||
* | |||
* This program is distributed in the hope that it will be useful, | |||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
* GNU General Public License for more details. | |||
* | |||
* You should have received a copy of the GNU General Public License | |||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
*/ | |||
package org.neo4j.cypher.internal.javacompat; | |||
|
|||
import java.io.PrintWriter; | |||
import java.util.ArrayList; | |||
import java.util.List; | |||
import java.util.Map; | |||
|
|||
import org.neo4j.graphdb.ExecutionPlanDescription; | |||
import org.neo4j.graphdb.Notification; | |||
import org.neo4j.graphdb.QueryExecutionType; | |||
import org.neo4j.graphdb.QueryStatistics; | |||
import org.neo4j.graphdb.ResourceIterator; | |||
import org.neo4j.graphdb.Result; | |||
|
|||
import static java.lang.System.lineSeparator; | |||
|
|||
/** | |||
* Result produced as result of eager query execution for cases when {@link SnapshotExecutionEngine} is used. | |||
*/ | |||
class EagerResult implements Result | |||
{ | |||
private static final String ITEM_SEPARATOR = ", "; | |||
private final Result originalResult; | |||
private final List<Map<String, Object>> queryResult = new ArrayList<>(); | |||
private int cursor; | |||
|
|||
EagerResult( Result result ) | |||
{ | |||
this.originalResult = result; | |||
} | |||
|
|||
public void consume() | |||
{ | |||
while ( originalResult.hasNext() ) | |||
{ | |||
queryResult.add( originalResult.next() ); | |||
} | |||
} | |||
|
|||
@Override | |||
public QueryExecutionType getQueryExecutionType() | |||
{ | |||
return originalResult.getQueryExecutionType(); | |||
} | |||
|
|||
@Override | |||
public List<String> columns() | |||
{ | |||
return originalResult.columns(); | |||
} | |||
|
|||
@Override | |||
public <T> ResourceIterator<T> columnAs( String name ) | |||
{ | |||
return new EagerResultResourceIterator<>( name ); | |||
} | |||
|
|||
@Override | |||
public boolean hasNext() | |||
{ | |||
return cursor < queryResult.size(); | |||
} | |||
|
|||
@Override | |||
public Map<String,Object> next() | |||
{ | |||
return queryResult.get( cursor++ ); | |||
} | |||
|
|||
@Override | |||
public void close() | |||
{ | |||
// nothing to close. Original result is already closed at this point | |||
} | |||
|
|||
@Override | |||
public QueryStatistics getQueryStatistics() | |||
{ | |||
return originalResult.getQueryStatistics(); | |||
} | |||
|
|||
@Override | |||
public ExecutionPlanDescription getExecutionPlanDescription() | |||
{ | |||
return originalResult.getExecutionPlanDescription(); | |||
} | |||
|
|||
@Override | |||
public String resultAsString() | |||
{ | |||
List<String> columns = originalResult.columns(); | |||
StringBuilder builder = new StringBuilder(); | |||
builder.append( String.join( ITEM_SEPARATOR, columns ) ); | |||
if ( !queryResult.isEmpty() ) | |||
{ | |||
builder.append( lineSeparator() ); | |||
int numberOfColumns = columns.size(); | |||
for ( Map<String,Object> row : queryResult ) | |||
{ | |||
writeRow( columns, builder, numberOfColumns, row ); | |||
builder.append( lineSeparator() ); | |||
} | |||
} | |||
return builder.toString(); | |||
} | |||
|
|||
@Override | |||
public void writeAsStringTo( PrintWriter writer ) | |||
{ | |||
writer.print( resultAsString() ); | |||
} | |||
|
|||
@Override | |||
public void remove() | |||
{ | |||
throw new UnsupportedOperationException( "Not supported" ); | |||
} | |||
|
|||
@Override | |||
public Iterable<Notification> getNotifications() | |||
{ | |||
return originalResult.getNotifications(); | |||
} | |||
|
|||
@Override | |||
public <VisitationException extends Exception> void accept( ResultVisitor<VisitationException> visitor ) | |||
throws VisitationException | |||
{ | |||
for ( Map<String,Object> map : queryResult ) | |||
{ | |||
visitor.visit( new MapRow( map ) ); | |||
} | |||
} | |||
|
|||
private void writeRow( List<String> columns, StringBuilder builder, int numberOfColumns, Map<String,Object> row ) | |||
{ | |||
for ( int i = 0; i < numberOfColumns; i++ ) | |||
{ | |||
builder.append( row.get( columns.get( i ) ) ); | |||
if ( i != numberOfColumns - 1 ) | |||
{ | |||
builder.append( ITEM_SEPARATOR ); | |||
} | |||
} | |||
} | |||
|
|||
private class EagerResultResourceIterator<T> implements ResourceIterator<T> | |||
{ | |||
private final String column; | |||
int cursor; | |||
|
|||
EagerResultResourceIterator( String column ) | |||
{ | |||
this.column = column; | |||
} | |||
|
|||
@Override | |||
public boolean hasNext() | |||
{ | |||
return cursor < queryResult.size(); | |||
} | |||
|
|||
@Override | |||
public T next() | |||
{ | |||
return (T) queryResult.get( cursor++ ).get( column ); | |||
} | |||
|
|||
@Override | |||
public void close() | |||
{ | |||
// Nothing to close. | |||
} | |||
} | |||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.