Skip to content

Commit

Permalink
Fix prepared statements with named parameters
Browse files Browse the repository at this point in the history
  • Loading branch information
gartens committed Sep 25, 2023
1 parent 9c5b746 commit 95b4621
Show file tree
Hide file tree
Showing 2 changed files with 14 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,9 @@

package org.polypheny.db.protointerface;

import com.google.common.collect.ImmutableBiMap;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import lombok.Getter;
Expand All @@ -30,41 +27,43 @@
public class NamedValueProcessor {

// matches tags such as :name
private static final Pattern PLACEHOLDER_PATTERN = Pattern.compile( "(?<!')(:[\\w]*)(?!')" );
private static final Pattern PLACEHOLDER_PATTERN = Pattern.compile( "(?<!'):([\\w]*)(?!')" );
private static final String REPLACEMENT_CHARACTER = "?";
@Getter
private String processedQuery;
@Getter
private ImmutableBiMap<String, Integer> namedIndexes;
private final List<String> replacements = new ArrayList<>();


public NamedValueProcessor( String statement ) {
this.processStatement( statement );
}


public void processStatement( String statement ) {
HashMap<String, Integer> indexByName = new HashMap<>();
AtomicInteger valueIndex = new AtomicInteger();
private void processStatement( String statement ) {
Matcher matcher = PLACEHOLDER_PATTERN.matcher( statement );
if ( !matcher.find() ) {
this.processedQuery = statement;
return;
}
StringBuilder stringBuilder = new StringBuilder();
String currentGroup = matcher.group( 1 );
do {
replacements.add( matcher.group( 1 ) );
matcher.appendReplacement( stringBuilder, REPLACEMENT_CHARACTER );
indexByName.put( currentGroup, valueIndex.getAndIncrement() );
} while ( matcher.find() );
matcher.appendTail( stringBuilder );
this.processedQuery = stringBuilder.toString();
this.namedIndexes = ImmutableBiMap.copyOf( indexByName );
}


public List<PolyValue> transformValueMap( Map<String, PolyValue> values ) {
List<PolyValue> image = new ArrayList<>();
values.forEach( ( key, value ) -> image.set( namedIndexes.get( key ), value ) );
for ( String placeholder : replacements ) {
PolyValue value = values.get( placeholder );
if ( value == null ) {
throw new RuntimeException( "Missing named parameter: " + placeholder );
}
image.add( values.get( placeholder ) );
}
return image;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -64,11 +64,8 @@ public StatementResult execute( Map<String, PolyValue> values, int fetchSize ) t
statement = client.getCurrentOrCreateNewTransaction().createStatement();
}
List<PolyValue> valueList = namedValueProcessor.transformValueMap( values );
long index = 0;
for ( PolyValue value : valueList ) {
if ( value != null ) {
statement.getDataContext().addParameterValues( index++, null, List.of( value ) );
}
for ( int i = 0; i < valueList.size(); i++ ) {
statement.getDataContext().addParameterValues( i, null, List.of( valueList.get( i ) ) );
}
StatementProcessor.implement( this );
return StatementProcessor.executeAndGetResult( this, fetchSize );
Expand Down

0 comments on commit 95b4621

Please sign in to comment.