Question Details

No question body available.

Tags

c# .net static-analysis nullable-reference-types

Answers (3)

July 9, 2026 Score: 3 Rep: 31,455 Quality: Medium Completeness: 50%

I prefer to add a verification method:

[MemberNotNullWhen(true, nameof(Obj))]
public bool IsValid
{
    get
    {
        Debug.Assert(Obj != null);
        return true;
    }
}

public static void Test() { A WithObj = MakeAWithObj(); if(WithObj.IsValid) { var Warning = WithObj.Obj.GetHashCode(); } }

It is actually easy to understand why the attribute cannot be applied to static methods, as it cannot answer the question of "whose member?".

July 9, 2026 Score: 1 Rep: 8,106 Quality: Low Completeness: 50%

On my static method, it seems to do nothing, and the warning still results.

The attribute still works, however, when you are applying it to a static method it will be just for static members initiation:

public class Container {
    private static string uniqueIdentifier; // must be initialized.

// would get warning here if we didn't use MemberNotNull static Container(){ Helper(); }

[MemberNotNull(nameof(uniqueIdentifier))] private static void Helper() { _uniqueIdentifier = DateTime.Now.Ticks.ToString(); } }

To me it's logical or at least consistent that instance helper methods are responsible for instance members and static helper methods for static members.

July 9, 2026 Score: 0 Rep: 426 Quality: Low Completeness: 60%

Warning "CS8602" is triggered by the fact that property Obj has a nullable type object?. Unless whenever you use it with a null-forgiving operator !, dereferencing such type always triggers such warning by IntelliSense.

So, for step 1, change its type to object. This immediately gets rid of CS8602.

public object Obj { get; private set; }

But the new problem is that you need to initialize it privately. We can do that by these more steps:

  1. Add a private 1-argument constructor so only your static factory method can call it, like so:
private A(object x) => Obj = x;
  1. Change the static factory method (you don't need that attribute) to call that private constructor:
public static A MakeAWithObj() => new A(new object());

That way, WithObj.Obj.GetHashCode() will be free of that warning because Visual Studio IntelliSense knows WithObj.Obj has a non-null type.

The suggested revised code:

public sealed class A
{
    public object Obj { get; private set; }

private A(object x) => Obj = x;

public static A MakeAWithObj() => new A(new object());

public static void Test() { A WithObj = MakeAWithObj(); int Warning = WithObj.Obj.GetHashCode(); } }

Note

This changes your design of the Obj property type from object? to object. If your project does not allow such change, I would suggest you follow @shingo's approach. However, according to the fact that you have jumped through the hoops using private setter / static factory method to ensure the property will never be null after the object itself is constructed, I don't see a reason why not explicitly defining the proper type to reflect this fact. This ensures the property type is consistent to its behavior and responsibility. Sometimes an easier approach is more maintainable than a complicated one.

PS

Simply just change the property type from object? to object without using the 1-argument private constructure in static factory method would not work. That would cause a new warning at the property definition:

public sealed class A
{
    public object Obj { get; private set; }
    //            ^^^ CS8618: "Non-nullable variable must contain a non-null value when exiting constructor. Consider declaring it as nullable."

[MemberNotNull(nameof(Obj))] // This has no effect public static A MakeAWithObj() => new() { Obj = new() };

public static void Test() { A WithObj = MakeAWithObj(); int Warning = WithObj.Obj.GetHashCode(); } }

Why adding a 1-argument constructor avoids the warning: With that constructor added, and it is the only constructor, IntelliSense thinks in your code you have only 1 place to initialize the object content, and in that constructor it has given the property an initial non-null value, hence the analysis concludes that the property will not have a null value later. Without any constructor, the static analyzer does not have such guarantee. It is not smart enough to analyze the run-time behavior inside static factory method's code.

PPS

OP's original code shows no constructor and thus adding a 1-argument constructor is suggested to solve the problem. Such constructor simply copies the argument to Obj thus we can initialize it indirectly in the static factory method. However, if the code already contains multiple constructors and some of them do not initialize the property, then they will be flagged with the same warning.