Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

Copy link
Contributor

Copilot AI commented Nov 17, 2025

Fixes #58010

Plan: Improve diagnostic when using equality operators for relational patterns

Understanding

  • When users write foo is { Value: != 5 }, they get an unhelpful error "Invalid expression term '!='"
  • The correct syntax should be foo is { Value: not 5 }
  • We need to detect != during pattern parsing and provide a better diagnostic message

Implementation Checklist

  • Explore the codebase and understand the current pattern parsing behavior
  • Add a new error code for the improved diagnostic message (ERR_EqualityOperatorInPatternNotSupported)
  • Modify the pattern parser to detect != and handle it specially
  • Parse != as a not-pattern with missing not token and != as skipped trivia
  • Add or update tests to verify the new behavior
  • Build and test the changes - all 301 pattern parsing tests pass!
  • Fix remaining test failure in RelationalPatternPrecedence_01
  • Fix failing tests Relational_10 and Pointer_Pattern_Equality
  • Run code review
  • Run security checks

Summary

Successfully implemented improved diagnostics for the != operator in patterns. The parser now:

  1. Detects != when parsing patterns
  2. Gives a helpful error message suggesting to use not instead
  3. Parses it as a not-pattern for better error recovery

All pattern parsing tests now pass, including the fixed Relational_10 and Pointer_Pattern_Equality tests!


💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.

Copilot AI changed the title [WIP] Improve diagnostic message for equality operators in relational patterns Improve diagnostic for != operator in patterns Nov 17, 2025
Copilot AI requested a review from CyrusNajmabadi November 17, 2025 12:29
@CyrusNajmabadi CyrusNajmabadi marked this pull request as ready for review November 17, 2025 12:39
@CyrusNajmabadi CyrusNajmabadi requested a review from a team as a code owner November 17, 2025 12:39
@CyrusNajmabadi
Copy link
Member

@dotnet/roslyn-compiler ptal

@CyrusNajmabadi
Copy link
Member

@copilot two tests are failing: Relational_10 and Pointer_Pattern_Equality. Investigate and upddate PR as appropriate.

Updated tests to expect new error ERR_EqualityOperatorInPatternNotSupported for != operator and updated operation tree to show INegatedPatternOperation instead of IRelationalPatternOperation.

Co-authored-by: CyrusNajmabadi <[email protected]>
Copy link
Contributor Author

Copilot AI commented Nov 17, 2025

@copilot two tests are failing: Relational_10 and Pointer_Pattern_Equality. Investigate and upddate PR as appropriate.

Fixed both failing tests in commit 8750ad1.

For Relational_10: Updated the expected diagnostic from ERR_InvalidExprTerm to ERR_EqualityOperatorInPatternNotSupported for the != 2 pattern, and updated the operation tree to show INegatedPatternOperation instead of IRelationalPatternOperation.

For Pointer_Pattern_Equality: Made the test conditional on the operator - != now expects ERR_EqualityOperatorInPatternNotSupported while == still expects ERR_InvalidExprTerm.

Both tests now pass along with all their combinatorial variations.

@CyrusNajmabadi
Copy link
Member

@jcouv @jjonescz ptal. tnx.

Comment on lines 12749 to 12750
Diagnostic(ErrorCode.ERR_EqualityOperatorInPatternNotSupported, "!=").WithLocation(1, 18)
);
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
Diagnostic(ErrorCode.ERR_EqualityOperatorInPatternNotSupported, "!=").WithLocation(1, 18)
);
Diagnostic(ErrorCode.ERR_EqualityOperatorInPatternNotSupported, "!=").WithLocation(1, 18));

@CyrusNajmabadi CyrusNajmabadi requested a review from a team as a code owner November 19, 2025 20:09
void M(bool x, int a, object b)
{
var c = !(a <= 10 || a is not == 20);
var c = !(a <= 10 || a is not== 20);
Copy link
Member

@jjonescz jjonescz Nov 20, 2025

Choose a reason for hiding this comment

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

Why has this changed? #Resolved

Copy link
Member

@CyrusNajmabadi CyrusNajmabadi Nov 20, 2025

Choose a reason for hiding this comment

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

There's basically a syntax error here now (since the parser runs into this, skips the token, and proceeds. The formatting engine doesn't like skipped tokens. And this test was really just ensuring we don't crash in these sorts of error scenarios. So this behavior just says what we'll do, which is completely fine here.

@CyrusNajmabadi
Copy link
Member

@jcouv @RikkiGibson @333fred ptal

@CyrusNajmabadi
Copy link
Member

@jcouv ptal

@CyrusNajmabadi CyrusNajmabadi requested a review from jcouv November 21, 2025 08:44
ConvertToKeyword(this.EatToken()),
ParseNegatedPattern(precedence, afterIs, inSwitchArmPattern));
}
else if (this.CurrentToken.Kind == SyntaxKind.EqualsEqualsToken)
Copy link
Member

@333fred 333fred Nov 21, 2025

Choose a reason for hiding this comment

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

It feels like this recovery should be in ParsePrimaryPattern, and that we may want to treat the inner expression as a top-level pattern. Do we have tests for other patterns being involved? For example, == > 10 and < 15? #Resolved

Copy link
Member

Choose a reason for hiding this comment

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

I didn't feel like we needed anything that involved. Basically, it seemed like what we were addressing was a user who saw that >= x was a pattern and then intuited that they could then use != or == in a similar fashion (like in a normal expression).

Copy link
Member

Choose a reason for hiding this comment

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

I didn't feel like we needed anything that involved. Basically, it seemed like what we were addressing was a user who saw that >= x was a pattern and then intuited that they could then use != or == in a similar fashion (like in a normal expression).

Copy link
Member

Choose a reason for hiding this comment

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

Added more tests, including one for your use case. It shows the behavior is good :)

@CyrusNajmabadi
Copy link
Member

@333fred anything else you need here?

@jcouv jcouv added the Concept-Diagnostic Clarity The issues deals with the ease of understanding of errors and warnings. label Nov 25, 2025
@jcouv
Copy link
Member

jcouv commented Nov 25, 2025

Fixes #58010 ?

Copy link
Member

@jcouv jcouv left a comment

Choose a reason for hiding this comment

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

LGTM Thanks (commit 15)

@CyrusNajmabadi CyrusNajmabadi merged commit 454a193 into main Nov 25, 2025
29 checks passed
@CyrusNajmabadi CyrusNajmabadi deleted the copilot/improve-equality-operator-diagnostics branch November 25, 2025 18:44
@dotnet-policy-service dotnet-policy-service bot added this to the Next milestone Nov 25, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Area-Compilers Concept-Diagnostic Clarity The issues deals with the ease of understanding of errors and warnings. VSCode

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Improve diagnostic when using equality operators for relational patterns

5 participants