diff --git a/idea/src/org/jetbrains/jet/JetNodeTypes.java b/idea/src/org/jetbrains/jet/JetNodeTypes.java index 72960eeca32..295abc076ca 100644 --- a/idea/src/org/jetbrains/jet/JetNodeTypes.java +++ b/idea/src/org/jetbrains/jet/JetNodeTypes.java @@ -36,7 +36,6 @@ public interface JetNodeTypes { JetNodeType CLASS_BODY = new JetNodeType("CLASS_BODY", JetClassBody.class); JetNodeType IMPORT_DIRECTIVE = new JetNodeType("IMPORT_DIRECTIVE", JetImportDirective.class); - JetNodeType IMPORTED = new JetNodeType("IMPORTED"); // TODO: ??? JetNodeType NAMESPACE_BODY = new JetNodeType("NAMESPACE_BODY", JetNamespaceBody.class); JetNodeType MODIFIER_LIST = new JetNodeType("MODIFIER_LIST", JetModifierList.class); JetNodeType ATTRIBUTE_ANNOTATION = new JetNodeType("ATTRIBUTE_ANNOTATION", JetAttributeAnnotation.class); @@ -46,6 +45,7 @@ public interface JetNodeTypes { JetNodeType VALUE_ARGUMENT = new JetNodeType("VALUE_ARGUMENT", JetArgument.class); JetNodeType TYPE_REFERENCE = new JetNodeType("TYPE_REFERENCE", JetTypeReference.class); JetNodeType LABELED_TUPLE_ENTRY = new JetNodeType("LABELED_TUPLE_ENTRY"); + JetNodeType LABELED_TUPLE_TYPE_ENTRY = new JetNodeType("LABELED_TUPLE_TYPE_ENTRY"); JetNodeType USER_TYPE = new JetNodeType("USER_TYPE", JetUserType.class); JetNodeType TUPLE_TYPE = new JetNodeType("TUPLE_TYPE", JetTupleType.class); diff --git a/idea/src/org/jetbrains/jet/lang/parsing/JetExpressionParsing.java b/idea/src/org/jetbrains/jet/lang/parsing/JetExpressionParsing.java index cf895b63986..12bdb8e8c91 100644 --- a/idea/src/org/jetbrains/jet/lang/parsing/JetExpressionParsing.java +++ b/idea/src/org/jetbrains/jet/lang/parsing/JetExpressionParsing.java @@ -1218,8 +1218,15 @@ public class JetExpressionParsing extends AbstractJetParsing { } /* - * "(" expression ")" // see tupleLiteral - * "(" expression{","} ")" + * tupleLiteral // Ambiguity when after a SimpleName (infix call). In this case (e) is treated as an expression in parentheses + * // to put a tuple, write write ((e)) + * : "(" ((SimpleName "=")? expression){","} ")" + * ; + * + * expression + * : "(" expression ")" + * ; + * * TODO: duplication with valueArguments (but for the error messages) */ private void parseParenthesizedExpressionOrTuple() { @@ -1237,7 +1244,16 @@ public class JetExpressionParsing extends AbstractJetParsing { errorAndAdvance("Expecting a tuple entry (expression)"); } - parseExpression(); + if (at(IDENTIFIER) && lookahead(1) == EQ) { + PsiBuilder.Marker entry = mark(); + advance(); // IDENTIFIER + advance(); // EQ + tuple = true; + parseExpression(); + entry.done(LABELED_TUPLE_ENTRY); + } else { + parseExpression(); + } if (!at(COMMA)) break; advance(); // COMMA diff --git a/idea/src/org/jetbrains/jet/lang/parsing/JetParsing.java b/idea/src/org/jetbrains/jet/lang/parsing/JetParsing.java index 9017a295662..92f6ba1315c 100644 --- a/idea/src/org/jetbrains/jet/lang/parsing/JetParsing.java +++ b/idea/src/org/jetbrains/jet/lang/parsing/JetParsing.java @@ -1274,7 +1274,7 @@ public class JetParsing extends AbstractJetParsing { advance(); // IDENTIFIER advance(); // COLON parseTypeRef(); - labeledEntry.done(LABELED_TUPLE_ENTRY); + labeledEntry.done(LABELED_TUPLE_TYPE_ENTRY); } else if (TYPE_REF_FIRST.contains(tt())) { parseTypeRef(); diff --git a/idea/testData/psi/TupleTypes.txt b/idea/testData/psi/TupleTypes.txt index 06dfc0df69c..fa779bf8618 100644 --- a/idea/testData/psi/TupleTypes.txt +++ b/idea/testData/psi/TupleTypes.txt @@ -61,7 +61,7 @@ JetFile: TupleTypes.jet TYPE_REFERENCE TUPLE_TYPE PsiElement(LPAR)('(') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('x') PsiWhiteSpace(' ') PsiElement(COLON)(':') @@ -71,7 +71,7 @@ JetFile: TupleTypes.jet PsiElement(IDENTIFIER)('Int') PsiElement(COMMA)(',') PsiWhiteSpace(' ') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('y') PsiWhiteSpace(' ') PsiElement(COLON)(':') @@ -188,7 +188,7 @@ JetFile: TupleTypes.jet PsiWhiteSpace(' ') TUPLE_TYPE PsiElement(LPAR)('(') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('x') PsiWhiteSpace(' ') PsiElement(COLON)(':') @@ -206,7 +206,7 @@ JetFile: TupleTypes.jet PsiElement(IDENTIFIER)('Int') PsiElement(COMMA)(',') PsiWhiteSpace(' ') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('y') PsiWhiteSpace(' ') PsiElement(COLON)(':') diff --git a/idea/testData/psi/TupleTypes_ERR.txt b/idea/testData/psi/TupleTypes_ERR.txt index b12d633b8f0..51e85e39481 100644 --- a/idea/testData/psi/TupleTypes_ERR.txt +++ b/idea/testData/psi/TupleTypes_ERR.txt @@ -60,7 +60,7 @@ JetFile: TupleTypes_ERR.jet TYPE_REFERENCE TUPLE_TYPE PsiElement(LPAR)('(') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('x') PsiWhiteSpace(' ') PsiElement(COLON)(':') @@ -186,7 +186,7 @@ JetFile: TupleTypes_ERR.jet PsiWhiteSpace(' ') TUPLE_TYPE PsiElement(LPAR)('(') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('x') PsiWhiteSpace(' ') PsiElement(COLON)(':') @@ -204,7 +204,7 @@ JetFile: TupleTypes_ERR.jet PsiElement(IDENTIFIER)('Int') PsiElement(COMMA)(',') PsiWhiteSpace(' ') - LABELED_TUPLE_ENTRY + LABELED_TUPLE_TYPE_ENTRY PsiElement(IDENTIFIER)('y') PsiWhiteSpace(' ') PsiElement(COLON)(':') diff --git a/idea/testData/psi/TuplesWithLabeledEntries.jet b/idea/testData/psi/TuplesWithLabeledEntries.jet new file mode 100644 index 00000000000..8e1ee98d58a --- /dev/null +++ b/idea/testData/psi/TuplesWithLabeledEntries.jet @@ -0,0 +1,2 @@ +val foo = (a = 3) +val foo = (a = 3, a) \ No newline at end of file diff --git a/idea/testData/psi/TuplesWithLabeledEntries.txt b/idea/testData/psi/TuplesWithLabeledEntries.txt new file mode 100644 index 00000000000..b1f0de58d24 --- /dev/null +++ b/idea/testData/psi/TuplesWithLabeledEntries.txt @@ -0,0 +1,41 @@ +JetFile: TuplesWithLabeledEntries.jet + NAMESPACE + PROPERTY + PsiElement(val)('val') + PsiWhiteSpace(' ') + PsiElement(IDENTIFIER)('foo') + PsiWhiteSpace(' ') + PsiElement(EQ)('=') + PsiWhiteSpace(' ') + TUPLE + PsiElement(LPAR)('(') + LABELED_TUPLE_ENTRY + PsiElement(IDENTIFIER)('a') + PsiWhiteSpace(' ') + PsiElement(EQ)('=') + PsiWhiteSpace(' ') + INTEGER_CONSTANT + PsiElement(INTEGER_LITERAL)('3') + PsiElement(RPAR)(')') + PsiWhiteSpace('\n') + PROPERTY + PsiElement(val)('val') + PsiWhiteSpace(' ') + PsiElement(IDENTIFIER)('foo') + PsiWhiteSpace(' ') + PsiElement(EQ)('=') + PsiWhiteSpace(' ') + TUPLE + PsiElement(LPAR)('(') + LABELED_TUPLE_ENTRY + PsiElement(IDENTIFIER)('a') + PsiWhiteSpace(' ') + PsiElement(EQ)('=') + PsiWhiteSpace(' ') + INTEGER_CONSTANT + PsiElement(INTEGER_LITERAL)('3') + PsiElement(COMMA)(',') + PsiWhiteSpace(' ') + REFERENCE_EXPRESSION + PsiElement(IDENTIFIER)('a') + PsiElement(RPAR)(')') \ No newline at end of file