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

Prefer null conditional over ternaries #75

Open
wants to merge 7 commits into
base: master
Choose a base branch
from

Conversation

jeffcorcoran
Copy link
Contributor

This PR hopes to resolve #57 by checking for null values / checks in ternary statements, as well as looking for HasValue, and requesting the user instead do a null conditional operator for cleaner code.


[TestCase("var firstName = person.Age != null ? person.FirstName : null;")]
[TestCase("var firstName = person.Age == null ? null : person.FirstName;")]
[TestCase("var firstName = person.Age.HasValue ? person.FirstName : null;")]
Copy link
Contributor

Choose a reason for hiding this comment

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

Should there be a test for the case where the ternary checks !person.Age.HasValue?

Copy link
Member

Choose a reason for hiding this comment

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

Are these examples of code that would trigger the diagnostic and should be changed? What's the desired replacement? (I don't see how the null-coalescing operator would be used here; what am I missing?)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Added better tests here. These were certainly sloppy, tried to get them in quick before I ran out of time at the end of the day, no real excuse.

var firstName = person.Age?.BirthYear; <-- This should better catch all the HasValue cases.

I have not removed the == null and != null because I still see some value in having them (ease of deployment), but I'm happy to rip those checks out for sure, as they can lead to issues down the road in terms of maintenance or even bugs.

Copy link
Member

Choose a reason for hiding this comment

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

FWIW, you can set a PR to Draft status if you know it's not fully-baked.


protected override DiagnosticAnalyzer GetCSharpDiagnosticAnalyzer() => new NullTestTernariesAnalyzer();

private const string c_preamble = @"";
Copy link
Contributor

Choose a reason for hiding this comment

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

Given that tis preamble is empty, you should probably delete it and all its uses. At the very least, we no longer allow unnecessary verbatim strings ;)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Cleaned this up.

Comment on lines +50 to +51
[TestCase("var firstName = person != null ? person.FirstName : null;")]
[TestCase("var firstName = person == null ? null : person.FirstName;")]
Copy link
Member

Choose a reason for hiding this comment

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

These are already handled by IDE0031; we shouldn't create (or maintain) functionality that duplicates built-in analysers.

Copy link
Member

Choose a reason for hiding this comment

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

(These tests shouldn't just be deleted; they should be moved to the "good" test (even though they're not good code) to verify that the analyser isn't alerting on them.)

private static readonly DiagnosticDescriptor s_rule = new(
id: DiagnosticId,
title: "Null Checking Ternaries Usage",
messageFormat: "Prefer null conditional operators over ternaries explicitly checking for null",
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
messageFormat: "Prefer null conditional operators over ternaries explicitly checking for null",
messageFormat: "Use null propagation",

The message from IDE0031 is simpler and appropriate.

@bgrainger
Copy link
Member

This analyser would really benefit from a Fix Provider, since the transformation is conceptually straightforward (AFAIK).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

Successfully merging this pull request may close these issues.

Prefer Null-conditional operators over ternaries
3 participants