{
  "$type": "site.standard.document",
  "canonicalUrl": "https://johnnyreilly.com/posts/nullable-reference-types-csharp-strictnullchecks",
  "description": "C# introduces nullable reference types similar to TypeScripts `strictNullChecks`. Enabling raises warnings and solves null reference risks.",
  "path": "/posts/nullable-reference-types-csharp-strictnullchecks",
  "publishedAt": "2020-12-20T00:00:00.000Z",
  "site": "at://did:plc:yy3apqjlms24kso7ahn7lbmb/site.standard.publication/3mova7c4nho2b",
  "tags": [
    "c#"
  ],
  "textContent": "'Tis the season to play with new compiler settings! I'm a very keen TypeScript user and have been merrily using strictNullChecks since it shipped. I was dimly aware that Cwas also getting a similar feature by the name of nullable reference types.\n\n\n\nIt's only now that I've got round to taking at look at this marvellous feature. I thought I'd share what moving to nullable reference types looked like for me; and what code changes I found myself making as a consequence.\n\nTurning on nullable reference types\n\nTo turn on nullable reference types in a Cproject you should pop open the .csproj file and ensure it contains a <Nullable>enable</Nullable>. So if you had a .NET Core 3.1 codebase it might look like this:\n\nWhen you compile from this point forward, possible null reference types are reported as warnings. Consider this C#:\n\nA dotnet build results in this:\n\nYou see the two \"Possible null reference return.\" warnings? Bingo\n\nFail the build with WarningsAsErrors\n\nThis is good - information is being surfaced up. But it's a warning. I could ignore it. I like compilers to get really up in my face and force me to make a change. I'm not into warnings; I'm into errors. Know what works for you. If you're similarly minded, you can upgrade nullable reference warnings to errors by tweaking the .csproj a touch further. Add yourself a <WarningsAsErrors>nullable</WarningsAsErrors> element. So maybe your .csproj now looks like this:\n\nAnd a dotnet build will result in this:\n\nYay! Errors!\n\nWhat do they mean?\n\n\"Possible null reference return\" isn't the clearest of errors. What does that actually amount to? Well, it amounts to the compiler saying \"you're a liar! (maybe)\". Let's look again at the code where this error is reported:\n\nWe're getting that error reported where we're returning null and where we're returning User.Identity.Name which _may_ be null. And we're getting that because as far as the compiler is concerned string has changed. Before we turned on nullable reference types the compiler considered string to mean string _OR_null. Now, string means string.\n\nThis is the same sort of behaviour as TypeScripts strictNullChecks. With TypeScript, before you turn on strictNullChecks, as far as the compiler is concerned, string means string_OR_null_OR_undefined (JavaScript didn't feel one null-ish value was enough and so has two - don't ask). Once strictNullChecks is on, string means string.\n\nIt's a lot clearer. And that's why the compiler is getting antsy. The method signature is string, but it can see null potentially being returned. It doesn't like it. By and large that's good. We want the compiler to notice this as that's the entire point. We want to catch accidental nulls before they hit a user. This is _great_! However, what do you do if have a method (as we do) that legitimately returns a string or null?\n\nWidening the type to include null\n\nWe change the signature from this:\n\nTo this:\n\nThat's right, the simple addition of ? marks a reference type (like a string) as potentially being null. Adding that means that we're potentially returning null, but we're sure about it; there's intention here - it's not accidental. Wonderful!",
  "title": "Nullable reference types; CSharp's very own strictNullChecks"
}