The question of .NET Core’s viability for use in a production application comes up often in my perusing of the various dotnet watering holes.

The answer is almost always something along the lines of:

Well, .NET Core is stable, but many important libraries have not yet been ported to a netstandard and so can only be used with .NET Framework.

One popular follow-up to this is that you are more than welcome to target your ASP.NET Core application at the “full framework” so that you can use the libraries you need. Once said libraries become netstandard compatible, you can then target .NET Core and most of your code-base will likely still be intact.

I decided to give this a shot.

In search for some good instructions, I came upon our friend Jon Hilton’s series post Use ASP.NET Core against .NET 4.6 (thanks Jon!).

It seems he was writing this in response to the same question of production-readiness I mentioned earlier.

Now, as you may have heard, gone are the days of our beloved project.json file in favor of our old friend, the .csproj project file.

Jon explains how to update the older project file quite clearly, so I have adapted his instruction to fit the new file type and structure.

We’ll start with a new .NET Core command line application for simplicity, but first, do you have the latest preview4 version of the .NET Core SDK?

If not, you’ll still be using the old project file type. You can run:

dotnet --info

from the command line to check your version. It should read 1.0.0-preview4-004233 at the time of this writing.

Get it from here.

Now, let’s build! First, the usual:

dotnet new

will generate both a Program.cs hello world program and a supporting .csproj file that is named after the folder we ran the command from.

Mine looks like this:

<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="15.0">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp1.0</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <Compile Include="**\*.cs" />
    <EmbeddedResource Include="**\*.resx" />
  </ItemGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.NETCore.App" Version="1.0.1" />
  </ItemGroup>

</Project>

A quick dotnet restore and dotnet run will display “Hello World!” as we expect.

Okay, now adapting Jon’s instructions, we need to change the target framework to net461 for .NET Framework 4.6.1 (make sure you have that version on your machine first!)

We also need to remove the reference to Microsoft.NETCore.App since we will no longer need that.

Our new file looks like this:

<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="15.0">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net461</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <Compile Include="**\*.cs" />
    <EmbeddedResource Include="**\*.resx" />
  </ItemGroup>

</Project>

Looks good.

Now, if we try to restore this with dotnet restore and then dotnet run, we get a nasty blood-red error.

RuntimeIdentifier must be set for .NETFramework executables. Consider RuntimeIdentifier=win7-x86 or RuntimeIdentifier=win7-x64.

Mostly helpful, but how do we actually set it?

An extra line of XML will do the trick (found here). Make sure you use the correct identifier for your system. This is needed for compilation so that it knows which native assets to use.

Now our file should look like this:

<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="15.0">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net461</TargetFramework>
    <RuntimeIdentifier>win7-x64</RuntimeIdentifier>
  </PropertyGroup>

  <ItemGroup>
    <Compile Include="**\*.cs" />
    <EmbeddedResource Include="**\*.resx" />
  </ItemGroup>

</Project>

Looks great!

A final dotnet restore and dotnet run on the command line and the lovely “Hello World!” output signifies we are now successfully targeting full framework.

At this point you are free to reference any .NET Framework 4.6.1 compatible library. You will NOT be cross-platform, however. Once the library is ported to .NET Standard, you can reverse these instructions.

Thanks again, @jonhilt for the excellent guide!