use of org.wso2.ballerinalang.compiler.semantics.model.types.BMapType in project ballerina by ballerina-lang.
the class PackageActionFunctionAndTypesFilter method populateIterableOperations.
private void populateIterableOperations(SymbolInfo variable, List<SymbolInfo> symbolInfoList) {
BType bType = variable.getScopeEntry().symbol.getType();
if (bType instanceof BArrayType || bType instanceof BMapType || bType instanceof BJSONType || bType instanceof BXMLType || bType instanceof BTableType || bType instanceof BIntermediateCollectionType) {
fillForeachIterableOperation(bType, symbolInfoList);
fillMapIterableOperation(bType, symbolInfoList);
fillFilterIterableOperation(bType, symbolInfoList);
fillCountIterableOperation(symbolInfoList);
if (bType instanceof BArrayType && (((BArrayType) bType).eType.toString().equals("int") || ((BArrayType) bType).eType.toString().equals("float"))) {
fillMinIterableOperation(symbolInfoList);
fillMaxIterableOperation(symbolInfoList);
fillAverageIterableOperation(symbolInfoList);
fillSumIterableOperation(symbolInfoList);
}
// TODO: Add support for Table and Tuple collection
}
}
use of org.wso2.ballerinalang.compiler.semantics.model.types.BMapType in project ballerina by ballerina-lang.
the class SymbolResolver method visit.
public void visit(BLangConstrainedType constrainedTypeNode) {
BType type = resolveTypeNode(constrainedTypeNode.type, env);
BType constraintType = resolveTypeNode(constrainedTypeNode.constraint, env);
if (type.tag == TypeTags.TABLE) {
resultType = new BTableType(TypeTags.TABLE, constraintType, type.tsymbol);
} else if (type.tag == TypeTags.STREAM) {
resultType = new BStreamType(TypeTags.STREAM, constraintType, type.tsymbol);
} else if (type.tag == TypeTags.FUTURE) {
resultType = new BFutureType(TypeTags.FUTURE, constraintType, type.tsymbol);
} else if (type.tag == TypeTags.MAP) {
resultType = new BMapType(TypeTags.MAP, constraintType, type.tsymbol);
} else {
if (!types.checkStructToJSONCompatibility(constraintType) && constraintType != symTable.errType) {
dlog.error(constrainedTypeNode.pos, DiagnosticCode.INCOMPATIBLE_TYPE_CONSTRAINT, type, constraintType);
resultType = symTable.errType;
return;
}
resultType = new BJSONType(TypeTags.JSON, constraintType, type.tsymbol);
}
}
use of org.wso2.ballerinalang.compiler.semantics.model.types.BMapType in project ballerina by ballerina-lang.
the class IterableAnalyzer method validateIterableContext.
public void validateIterableContext(IterableContext context) {
final Operation lastOperation = context.operations.getLast();
final BType expectedType = lastOperation.expectedType;
final BType outputType = lastOperation.resultType;
if (expectedType.tag == TypeTags.VOID && outputType.tag == TypeTags.VOID) {
context.resultType = symTable.noType;
return;
}
if (expectedType.tag == TypeTags.VOID) {
// This error already logged.
return;
}
if (expectedType == symTable.errType) {
context.resultType = symTable.errType;
return;
}
if (outputType.tag == TypeTags.VOID) {
dlog.error(lastOperation.pos, DiagnosticCode.DOES_NOT_RETURN_VALUE, lastOperation.kind);
context.resultType = symTable.errType;
return;
}
// Calculate expected type, if this is an chained iterable operation.
if (outputType.tag == TypeTags.INTERMEDIATE_COLLECTION) {
BIntermediateCollectionType collectionType = (BIntermediateCollectionType) outputType;
final BTupleType tupleType = collectionType.tupleType;
if (expectedType.tag == TypeTags.ARRAY && tupleType.tupleTypes.size() == 1) {
// Convert result into an array.
context.resultType = new BArrayType(tupleType.tupleTypes.get(0));
return;
} else if (expectedType.tag == TypeTags.MAP && tupleType.tupleTypes.size() == 2 && tupleType.tupleTypes.get(0).tag == TypeTags.STRING) {
// Convert result into a map.
context.resultType = new BMapType(TypeTags.MAP, tupleType.tupleTypes.get(1), null);
return;
} else if (expectedType.tag == TypeTags.TABLE) {
// 3. Whether the returned struct is compatible with the constraint struct of the expected type(table)
if (tupleType.getTupleTypes().size() == 1 && tupleType.getTupleTypes().get(0).tag == TypeTags.STRUCT && types.isAssignable(tupleType.getTupleTypes().get(0), ((BTableType) expectedType).constraint)) {
context.resultType = symTable.tableType;
} else {
context.resultType = types.checkType(lastOperation.pos, outputType, ((BTableType) expectedType).constraint, DiagnosticCode.INCOMPATIBLE_TYPES);
}
return;
} else if (expectedType.tag == TypeTags.ANY) {
context.resultType = symTable.errType;
dlog.error(lastOperation.pos, DiagnosticCode.ITERABLE_RETURN_TYPE_MISMATCH, lastOperation.kind);
return;
} else if (expectedType.tag == TypeTags.NONE) {
context.resultType = symTable.noType;
return;
}
}
// Validate compatibility with calculated and expected type.
context.resultType = types.checkType(lastOperation.pos, outputType, expectedType, DiagnosticCode.INCOMPATIBLE_TYPES);
}
use of org.wso2.ballerinalang.compiler.semantics.model.types.BMapType in project ballerina by ballerina-lang.
the class TypeChecker method visit.
public void visit(BLangFieldBasedAccess fieldAccessExpr) {
// First analyze the variable reference expression.
BType actualType = symTable.errType;
BType varRefType = getTypeOfExprInFieldAccess(fieldAccessExpr.expr);
if (fieldAccessExpr.fieldType == FieldType.ALL && varRefType.tag != TypeTags.XML) {
dlog.error(fieldAccessExpr.pos, DiagnosticCode.CANNOT_GET_ALL_FIELDS, varRefType);
}
Name fieldName = names.fromIdNode(fieldAccessExpr.field);
switch(varRefType.tag) {
case TypeTags.STRUCT:
actualType = checkStructFieldAccess(fieldAccessExpr, fieldName, varRefType);
break;
case TypeTags.MAP:
actualType = ((BMapType) varRefType).getConstraint();
break;
case TypeTags.JSON:
BType constraintType = ((BJSONType) varRefType).constraint;
if (constraintType.tag == TypeTags.STRUCT) {
BType fieldType = checkStructFieldAccess(fieldAccessExpr, fieldName, constraintType);
// If the type of the field is struct, treat it as constraint JSON type.
if (fieldType.tag == TypeTags.STRUCT) {
actualType = new BJSONType(TypeTags.JSON, fieldType, symTable.jsonType.tsymbol);
break;
}
}
actualType = symTable.jsonType;
break;
case TypeTags.ENUM:
// Enumerator access expressions only allow enum type name as the first part e.g state.INSTALLED,
BEnumType enumType = (BEnumType) varRefType;
if (fieldAccessExpr.expr.getKind() != NodeKind.SIMPLE_VARIABLE_REF || !((BLangSimpleVarRef) fieldAccessExpr.expr).variableName.value.equals(enumType.tsymbol.name.value)) {
dlog.error(fieldAccessExpr.pos, DiagnosticCode.INVALID_ENUM_EXPR, enumType.tsymbol.name.value);
break;
}
BSymbol symbol = symResolver.lookupMemberSymbol(fieldAccessExpr.pos, enumType.tsymbol.scope, this.env, fieldName, SymTag.VARIABLE);
if (symbol == symTable.notFoundSymbol) {
dlog.error(fieldAccessExpr.pos, DiagnosticCode.UNDEFINED_SYMBOL, fieldName.value);
break;
}
fieldAccessExpr.symbol = (BVarSymbol) symbol;
actualType = fieldAccessExpr.expr.type;
break;
case TypeTags.XML:
if (fieldAccessExpr.lhsVar) {
dlog.error(fieldAccessExpr.pos, DiagnosticCode.CANNOT_UPDATE_XML_SEQUENCE);
break;
}
actualType = symTable.xmlType;
break;
case TypeTags.ERROR:
// Do nothing
break;
default:
dlog.error(fieldAccessExpr.pos, DiagnosticCode.OPERATION_DOES_NOT_SUPPORT_FIELD_ACCESS, varRefType);
}
resultTypes = types.checkTypes(fieldAccessExpr, Lists.of(actualType), this.expTypes);
}
use of org.wso2.ballerinalang.compiler.semantics.model.types.BMapType in project ballerina by ballerina-lang.
the class TypeChecker method visit.
public void visit(BLangIndexBasedAccess indexBasedAccessExpr) {
BType actualType = symTable.errType;
// First analyze the variable reference expression.
checkExpr(indexBasedAccessExpr.expr, this.env, Lists.of(symTable.noType));
BType indexExprType;
BType varRefType = indexBasedAccessExpr.expr.type;
BLangExpression indexExpr = indexBasedAccessExpr.indexExpr;
switch(varRefType.tag) {
case TypeTags.STRUCT:
indexExprType = checkIndexExprForStructFieldAccess(indexExpr);
if (indexExprType.tag == TypeTags.STRING) {
String fieldName = (String) ((BLangLiteral) indexExpr).value;
actualType = checkStructFieldAccess(indexBasedAccessExpr, names.fromString(fieldName), varRefType);
}
break;
case TypeTags.MAP:
indexExprType = checkExpr(indexExpr, this.env, Lists.of(symTable.stringType)).get(0);
if (indexExprType.tag == TypeTags.STRING) {
actualType = ((BMapType) varRefType).getConstraint();
}
break;
case TypeTags.JSON:
BType constraintType = ((BJSONType) varRefType).constraint;
if (constraintType.tag == TypeTags.STRUCT) {
indexExprType = checkIndexExprForStructFieldAccess(indexExpr);
if (indexExprType.tag != TypeTags.STRING) {
break;
}
String fieldName = (String) ((BLangLiteral) indexExpr).value;
BType fieldType = checkStructFieldAccess(indexBasedAccessExpr, names.fromString(fieldName), constraintType);
// If the type of the field is struct, treat it as constraint JSON type.
if (fieldType.tag == TypeTags.STRUCT) {
actualType = new BJSONType(TypeTags.JSON, fieldType, symTable.jsonType.tsymbol);
break;
}
} else {
indexExprType = checkExpr(indexExpr, this.env, Lists.of(symTable.noType)).get(0);
if (indexExprType.tag != TypeTags.STRING && indexExprType.tag != TypeTags.INT) {
dlog.error(indexExpr.pos, DiagnosticCode.INCOMPATIBLE_TYPES, symTable.stringType, indexExprType);
break;
}
}
actualType = symTable.jsonType;
break;
case TypeTags.ARRAY:
indexExprType = checkExpr(indexExpr, this.env, Lists.of(symTable.intType)).get(0);
if (indexExprType.tag == TypeTags.INT) {
actualType = ((BArrayType) varRefType).getElementType();
}
break;
case TypeTags.XML:
if (indexBasedAccessExpr.lhsVar) {
dlog.error(indexBasedAccessExpr.pos, DiagnosticCode.CANNOT_UPDATE_XML_SEQUENCE);
break;
}
checkExpr(indexExpr, this.env).get(0);
actualType = symTable.xmlType;
break;
case TypeTags.ERROR:
// Do nothing
break;
default:
dlog.error(indexBasedAccessExpr.pos, DiagnosticCode.OPERATION_DOES_NOT_SUPPORT_INDEXING, indexBasedAccessExpr.expr.type);
}
resultTypes = types.checkTypes(indexBasedAccessExpr, Lists.of(actualType), this.expTypes);
}
Aggregations