Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixing completion in async foreach/using #23960

Merged
merged 3 commits into from
Jan 19, 2018

Conversation

jcouv
Copy link
Member

@jcouv jcouv commented Dec 28, 2017

The keyword await should be offered for completion after using and foreach.
Also, var and new should be appropriately offered in using await ($$ and foreach await (var i in $$.

@jcouv jcouv added this to the 16.0 milestone Dec 28, 2017
@jcouv jcouv self-assigned this Dec 28, 2017
@jcouv jcouv requested a review from a team as a code owner December 28, 2017 23:54
@jcouv jcouv added the New Feature - Async Streams Async Streams label Dec 29, 2017
@jcouv
Copy link
Member Author

jcouv commented Jan 2, 2018

@dotnet/roslyn-ide for review. Thanks

1 similar comment
@jcouv
Copy link
Member Author

jcouv commented Jan 3, 2018

@dotnet/roslyn-ide for review. Thanks

@jcouv
Copy link
Member Author

jcouv commented Jan 5, 2018

@dotnet/roslyn-ide for review. Thanks


if (previous.IsKind(SyntaxKind.AwaitKeyword))
{
var beforeAwait = previous.GetPreviousToken(includeSkipped: true);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would assume this would check that the 'await' parsed as a part of a statement vs. just checking previous token. You sure don't want "using await" at the start of a file (i.e. namespace using) triggering this.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(and yes, it looks like the previous check also has a bug. 😄)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From another PR, I understand that recommending keywords a little loosely isn't bad.
#24089
Are you saying they both should be tightened?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems like this shouldnt' be necessary. Instead of:

                 var previous = token.GetPreviousToken(includeSkipped: true);
                 if (previous.IsKind(SyntaxKind.ForKeyword) ||
                     previous.IsKind(SyntaxKind.ForEachKeyword) ||
                     previous.IsKind(SyntaxKind.UsingKeyword))
                  {
                      return true;
                  }

We should jsut check the parent node kind.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i.e. if we have an open paren, see if the parent of it is a BaseForeachStatementSyntax, ForStatementSyntax, or a UsingStatementSyntax.

@@ -2363,6 +2375,14 @@ public static bool IsLabelContext(this SyntaxTree syntaxTree, int position, Canc
return true;
}

// using await ( |
if (token.IsKind(SyntaxKind.OpenParenToken) &&
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we can just update the previous test to see if the open paren parent is a UsingStatementSyntax.

@CyrusNajmabadi
Copy link
Member

FYI: that code was written at a time when syntax trees were still in flux, and it wasn't clear if we had parent pointers or not. So it was trying to be as token oriented as possible. That's a lot less necessary now, and we can def go with the simpler forms where we just check the parent of a token.

@jcouv jcouv removed the 3 - Working label Jan 13, 2018
@@ -51,6 +51,11 @@ protected override bool IsValidContext(int position, CSharpSyntaxContext context
return true;
}

if (context.TargetToken.IsKind(SyntaxKind.UsingKeyword, SyntaxKind.ForEachKeyword))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

note: this will mean 'await' may be offered after 'using' at the top level. That's probably not waht we want. can you filter out that case and add a test. (note: maybe we do want it, because of script... not sure).

public static bool IsParentKind(this SyntaxNode node, SyntaxKind kind1, SyntaxKind kind2, SyntaxKind kind3, SyntaxKind kind4)
{
return node != null && IsKind(node.Parent, kind1, kind2, kind3, kind4);
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit, use =>

@jcouv
Copy link
Member Author

jcouv commented Jan 18, 2018

@jasonmalinowski Any other feedback?

@jasonmalinowski
Copy link
Member

Anybody from @dotnet/roslyn-ide can review this one.

@jcouv jcouv merged commit 2e83b53 into dotnet:features/async-streams Jan 19, 2018
@jcouv jcouv deleted the async-ide branch January 19, 2018 17:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants