use of org.teiid.language.Expression in project teiid by teiid.
the class InfinispanUpdateVisitor method visit.
@Override
public void visit(Update obj) {
this.operationType = OperationType.UPDATE;
append(obj.getTable());
if (obj.getWhere() != null) {
buffer.append(Tokens.SPACE).append(SQLConstants.Reserved.WHERE).append(Tokens.SPACE);
append(obj.getWhere());
// Can't use the original where string because it is designed for the document model querying
this.whereClause = obj.getWhere();
}
// table that update issued for
Table table = obj.getTable().getMetadataObject();
if (!table.equals(getParentTable())) {
this.nested = true;
}
// read the properties
try {
InfinispanDocument targetDocument = buildTargetDocument(table, false);
int elementCount = obj.getChanges().size();
for (int i = 0; i < elementCount; i++) {
Column column = obj.getChanges().get(i).getSymbol().getMetadataObject();
if (isPartOfPrimaryKey(column.getName())) {
throw new TranslatorException(InfinispanPlugin.Event.TEIID25019, InfinispanPlugin.Util.gs(InfinispanPlugin.Event.TEIID25019, column.getName()));
}
Expression expr = obj.getChanges().get(i).getValue();
Object value = resolveExpressionValue(expr);
// this.updatePayload.put(getName(column), value);
updateDocument(targetDocument, column, value);
}
this.insertPayload = targetDocument;
} catch (TranslatorException e) {
this.exceptions.add(e);
}
}
use of org.teiid.language.Expression in project teiid by teiid.
the class SubstringFunctionModifier method translate.
@Override
public List<?> translate(Function function) {
this.modify(function);
if (function.getParameters().size() != 3) {
return null;
}
// case when length > LENGTH(string) - start + 1 then LENGTH(string) - start + 1 case when length > 0 then length end
Expression forLength = function.getParameters().get(2);
List<SearchedWhenClause> clauses = new ArrayList<SearchedWhenClause>(2);
Boolean isNegative = null;
if (forLength instanceof Literal) {
Literal l = (Literal) forLength;
int value = (Integer) l.getValue();
isNegative = value < 0;
}
Function length = new Function(SourceSystemFunctions.LENGTH, Arrays.asList(function.getParameters().get(0)), TypeFacility.RUNTIME_TYPES.INTEGER);
Expression from = function.getParameters().get(1);
SearchedCase adjustedFrom = new SearchedCase(Arrays.asList(new SearchedWhenClause(new Comparison(from, length, Operator.GT), new Function(SourceSystemFunctions.ADD_OP, Arrays.asList(length, new Literal(1, TypeFacility.RUNTIME_TYPES.INTEGER)), TypeFacility.RUNTIME_TYPES.INTEGER))), from, TypeFacility.RUNTIME_TYPES.INTEGER);
function.getParameters().set(1, adjustedFrom);
Expression maxLength = new Function(SourceSystemFunctions.SUBTRACT_OP, Arrays.asList(length, new Function(SourceSystemFunctions.SUBTRACT_OP, Arrays.asList(adjustedFrom, new Literal(1, TypeFacility.RUNTIME_TYPES.INTEGER)), TypeFacility.RUNTIME_TYPES.INTEGER)), TypeFacility.RUNTIME_TYPES.INTEGER);
clauses.add(new SearchedWhenClause(new Comparison(forLength, maxLength, Operator.GT), maxLength));
Expression defaultExpr = null;
if (isNegative == null) {
clauses.add(new SearchedWhenClause(new Comparison(forLength, new Literal(0, TypeFacility.RUNTIME_TYPES.INTEGER), Operator.GT), forLength));
} else if (isNegative) {
// TODO: could be done in the rewriter
return Arrays.asList(new Literal(null, TypeFacility.RUNTIME_TYPES.STRING));
} else {
defaultExpr = forLength;
}
SearchedCase sc = new SearchedCase(clauses, defaultExpr, TypeFacility.RUNTIME_TYPES.INTEGER);
function.getParameters().set(2, sc);
return null;
}
use of org.teiid.language.Expression in project teiid by teiid.
the class InfinispanUpdateExecution method performInsert.
@SuppressWarnings("unchecked")
private void performInsert(final InfinispanUpdateVisitor visitor, Table table, final RemoteCache<Object, Object> cache, boolean upsert, TeiidTableMarsheller marshaller) throws TranslatorException {
Insert insert = (Insert) this.command;
if (visitor.isNestedOperation()) {
InfinispanDocument previous = null;
if (visitor.getIdentity() != null) {
previous = (InfinispanDocument) cache.get(visitor.getIdentity());
}
if (insert.getParameterValues() != null) {
throw new TranslatorException(InfinispanPlugin.Util.gs(InfinispanPlugin.Event.TEIID25017, table.getName(), visitor.getParentTable().getName()));
}
if (previous == null) {
throw new TranslatorException(InfinispanPlugin.Util.gs(InfinispanPlugin.Event.TEIID25009, table.getName(), visitor.getIdentity()));
}
String childName = ProtobufMetadataProcessor.getMessageName(visitor.getQueryTable());
previous.addChildDocument(childName, visitor.getInsertPayload().getChildDocuments(childName).get(0));
if (upsert) {
previous = (InfinispanDocument) cache.replace(visitor.getIdentity(), previous);
} else {
previous = (InfinispanDocument) cache.put(visitor.getIdentity(), previous);
}
this.updateCount++;
} else {
if (insert.getParameterValues() == null) {
insertRow(cache, visitor.getIdentity(), visitor.getInsertPayload(), upsert);
this.updateCount++;
} else {
boolean putAll = false;
if (this.executionContext.getSourceHint() != null) {
putAll = this.executionContext.getSourceHint().indexOf("use-putall") != -1;
}
// bulk insert
int batchSize = this.executionContext.getBatchSize();
Iterator<? extends List<Expression>> args = (Iterator<? extends List<Expression>>) insert.getParameterValues();
while (true) {
Map<Object, InfinispanDocument> rows = visitor.getBulkInsertPayload(insert, batchSize, args);
if (rows.isEmpty()) {
break;
}
if (putAll) {
BulkInsert bi = new UsePutAll(cache);
bi.run(rows, false);
} else {
BulkInsert bi = new OneAtATime(cache);
bi.run(rows, upsert);
}
this.updateCount += rows.size();
}
}
}
}
use of org.teiid.language.Expression in project teiid by teiid.
the class LocateFunctionModifier method modify.
/**
* Returns a version of <code>function</code> suitable for executing at the
* data source.
* <p>
* For example:
* <ul>
* <code>locate('a', 'abcdefg') ---> LOCATE('a', 'abcdefg')</code><br />
* <code>locate('a', 'abcdefg', 1) ---> LOCATE('a', 'abcdefg', 1)</code><br />
* <code>locate('a', 'abcdefg', 1) ---> INSTR('abcdefg', 'a', 1)</code><br />
* <code>locate('a', 'abcdefg', -5) ---> INSTR('abcdefg', 'a', 1)</code><br />
* <code>locate('a', 'abcdefg', 1) ---> FINDSTR('a', 'abcdefg', 1)</code><br />
* <code>locate('a', 'abcdefg', myCol) ---> LOCATE('a', 'abcdefg', CASE WHEN myCol < 1 THEN 1 ELSE myCol END)</code>
* </ul>
*
* @param function the LOCATE function that may need to be modified
*/
public void modify(Function function) {
super.modify(function);
List<Expression> args = function.getParameters();
Expression searchStr = args.get(0);
Expression sourceStr = args.get(1);
// if startIndex was given then we may need to do additional work
if (args.size() > 2) {
args.set(2, ensurePositiveStartIndex(args.get(2)));
}
if (sourceStringFirst) {
args.set(0, sourceStr);
args.set(1, searchStr);
}
}
use of org.teiid.language.Expression in project teiid by teiid.
the class ModFunctionModifier method translate.
@Override
public List<?> translate(Function function) {
List<Expression> expressions = function.getParameters();
Class<?> type = function.getType();
if (supportedTypes.contains(type)) {
modify(function);
return null;
}
// x % y => x - sign(x) * floor(abs(x / y)) * y
Function divide = langFactory.createFunction(SourceSystemFunctions.DIVIDE_OP, new ArrayList<Expression>(expressions), type);
Function abs = langFactory.createFunction(SourceSystemFunctions.ABS, Arrays.asList(divide), type);
Function floor = langFactory.createFunction(SourceSystemFunctions.FLOOR, Arrays.asList(abs), type);
Function sign = langFactory.createFunction(SourceSystemFunctions.SIGN, Arrays.asList(expressions.get(0)), type);
List<? extends Expression> multArgs = Arrays.asList(sign, floor, langFactory.createFunction(SourceSystemFunctions.ABS, Arrays.asList(expressions.get(1)), type));
Function mult = langFactory.createFunction(SourceSystemFunctions.MULTIPLY_OP, multArgs, type);
List<Expression> minusArgs = Arrays.asList(expressions.get(0), mult);
return Arrays.asList(langFactory.createFunction(SourceSystemFunctions.SUBTRACT_OP, minusArgs, type));
}
Aggregations