Custom templates for dotnet new

The .NET Core SDK comes with many templates already installed and ready for you to use. The dotnet new command isn't only the way to use a template, but also how to install and uninstall templates. Starting with .NET Core 2.0, you can create your own custom templates for any type of project, such as an app, service, tool, or class library. You can even create a template that outputs one or more independent files, such as a configuration file.

You can install custom templates from a NuGet package on any NuGet feed, by referencing a NuGet .nupkg file directly, or by specifying a file system directory that contains the template. The template engine offers features that allow you to replace values, include and exclude files, and execute custom processing operations when your template is used.

The template engine is open source, and the online code repository is at dotnet/templating on GitHub. Visit the dotnet/dotnet-template-samples repo for samples of templates. More templates, including templates from third parties, are found at Available templates for dotnet new on GitHub. For more information about creating and using custom templates, see How to create your own templates for dotnet new and the dotnet/templating GitHub repo Wiki.

To follow a walkthrough and create a template, see the Create a custom template for dotnet new tutorial.

.NET default templates

When you install the .NET Core SDK, you receive over a dozen built-in templates for creating projects and files, including console apps, class libraries, unit test projects, ASP.NET Core apps (including Angular and React projects), and configuration files. To list the built-in templates, run the dotnet new command with the -l|--list option:

dotnet new --list

Configuration

A template is composed of the following parts:

  • Source files and folders.
  • A configuration file (template.json).

Source files and folders

The source files and folders include whatever files and folders you want the template engine to use when the dotnet new <TEMPLATE> command is run. The template engine is designed to use runnable projects as source code to produce projects. This has several benefits:

  • The template engine doesn't require you to inject special tokens into your project's source code.
  • The code files aren't special files or modified in any way to work with the template engine. So, the tools you normally use when working with projects also work with template content.
  • You build, run, and debug your template projects just like you do for any of your other projects.
  • You can quickly create a template from an existing project just by adding a ./.template.config/template.json configuration file to the project.

Files and folders stored in the template aren't limited to formal .NET project types. Source files and folders may consist of any content that you wish to create when the template is used, even if the template engine produces just one file as its output.

Files generated by the template can be modified based on logic and settings you've provided in the template.json configuration file. The user can override these settings by passing options to the dotnet new <TEMPLATE> command. A common example of custom logic is providing a name for a class or variable in the code file that's deployed by a template.

template.json

The template.json file is placed in a .template.config folder in the root directory of the template. The file provides configuration information to the template engine. The minimum configuration requires the members shown in the following table, which is sufficient to create a functional template.

Member Type Description
$schema URI The JSON schema for the template.json file. Editors that support JSON schemas enable JSON-editing features when the schema is specified. For example, Visual Studio Code requires this member to enable IntelliSense. Use a value of http://json.schemastore.org/template.
author string The author of the template.
classifications array(string) Zero or more characteristics of the template that a user might use to find the template when searching for it. The classifications also appear in the Tags column when it appears in a list of templates produced by using the dotnet new -l|--list command.
identity string A unique name for this template.
name string The name for the template that users should see.
shortName string A default shorthand name for selecting the template that applies to environments where the template name is specified by the user, not selected via a GUI. For example, the short name is useful when using templates from a command prompt with CLI commands.

The full schema for the template.json file is found at the JSON Schema Store. For more information about the template.json file, see the dotnet templating wiki.

Example

For example, here is a template folder that contains two content files: console.cs and readme.txt. Take notice that there is the required folder named .template.config that contains the template.json file.

└───mytemplate
    │   console.cs
    │   readme.txt
    │
    └───.template.config
            template.json

The template.json file looks like the following:

{
  "$schema": "http://json.schemastore.org/template",
  "author": "Travis Chau",
  "classifications": [ "Common", "Console" ],
  "identity": "AdatumCorporation.ConsoleTemplate.CSharp",
  "name": "Adatum Corporation Console Application",
  "shortName": "adatumconsole"
}

The mytemplate folder is an installable template pack. Once the pack is installed, the shortName can be used with the dotnet new command. For example, dotnet new adatumconsole would output the console.cs and readme.txt files to the current folder.

Packing a template into a NuGet package (nupkg file)

A custom template is packed with the dotnet pack command and a .csproj file. Alternatively, NuGet can be used with the nuget pack command along with a .nuspec file. However, NuGet requires the .NET Framework on Windows and Mono on Linux and MacOS.

The .csproj file is slightly different from a traditional code-project .csproj file. Note the following settings:

  1. The <PackageType> setting is added and set to Template.
  2. The <PackageVersion> setting is added and set to a valid NuGet version number.
  3. The <PackageId> setting is added and set to a unique identifier. This identifier is used to uninstall the template pack and is used by NuGet feeds to register your template pack.
  4. Generic metadata settings should be set: <Title>, <Authors>, <Description>, and <PackageTags>.
  5. The <TargetFramework> setting must be set, even though the binary produced by the template process isn't used. In the example below it's set to netstandard2.0.

A template pack, in the form of a .nupkg NuGet package, requires that all templates be stored in the content folder within the package. There are a few more settings to add to a .csproj file to ensure that the generated .nupkg can be installed as a template pack:

  1. The <IncludeContentInPack> setting is set to true to include any file the project sets as content in the NuGet package.
  2. The <IncludeBuildOutput> setting is set to false to exclude all binaries generated by the compiler from the NuGet package.
  3. The <ContentTargetFolders> setting is set to content. This makes sure that the files set as content are stored in the content folder in the NuGet package. This folder in the NuGet package is parsed by the dotnet template system.

An easy way to exclude all code files from being compiled by your template project is by using the <Compile Remove="**\*" /> item in your project file, inside an <ItemGroup> element.

An easy way to structure your template pack is to put all templates in individual folders, and then each template folder inside of a templates folder that is located in the same directory as your .csproj file. This way, you can use a single project item to include all files and folders in the templates as content. Inside of an <ItemGroup> element, create a <Content Include="templates\**\*" Exclude="templates\**\bin\**;templates\**\obj\**" /> item.

Here is an example .csproj file that follows all of the guidelines above. It packs the templates child folder to the content package folder and excludes any code file from being compiled.

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

  <PropertyGroup>
    <PackageType>Template</PackageType>
    <PackageVersion>1.0</PackageVersion>
    <PackageId>AdatumCorporation.Utility.Templates</PackageId>
    <Title>AdatumCorporation Templates</Title>
    <Authors>Me</Authors>
    <Description>Templates to use when creating an application for Adatum Corporation.</Description>
    <PackageTags>dotnet-new;templates;contoso</PackageTags>
    <TargetFramework>netstandard2.0</TargetFramework>

    <IncludeContentInPack>true</IncludeContentInPack>
    <IncludeBuildOutput>false</IncludeBuildOutput>
    <ContentTargetFolders>content</ContentTargetFolders>
  </PropertyGroup>

  <ItemGroup>
    <Content Include="templates\**\*" Exclude="templates\**\bin\**;templates\**\obj\**" />
    <Compile Remove="**\*" />
  </ItemGroup>

</Project>

The example below demonstrates the file and folder structure of using a .csproj to create a template pack. The MyDotnetTemplates.csproj file and templates folder are both located at the root of a directory named project_folder. The templates folder contains two templates, mytemplate1 and mytemplate2. Each template has content files and a .template.config folder with a template.json config file.

project_folder
│   MyDotnetTemplates.csproj
│
└───templates
    ├───mytemplate1
    │   │   console.cs
    │   │   readme.txt
    │   │
    │   └───.template.config
    │           template.json
    │
    └───mytemplate2
        │   otherfile.cs
        │
        └───.template.config
                template.json

Installing a template

Use the dotnet new -i|--install command to install a package.

To install a template from a NuGet package stored at nuget.org

Use the NuGet package identifier to install a template package.

dotnet new -i <NUGET_PACKAGE_ID>

To install a template from a local nupkg file

Provide the path to a .nupkg NuGet package file.

dotnet new -i <PATH_TO_NUPKG_FILE>

To install a template from a file system directory

Templates can be installed from a template folder, such as the mytemplate1 folder from the example above. Specify the folder path of the .template.config folder. The path to the template directory does not need to be absolute. However, an absolute path is required to uninstall a template that is installed from a folder.

dotnet new -i <FILE_SYSTEM_DIRECTORY>

Get a list of installed templates

The uninstall command, without any other parameters, will list all installed templates.

dotnet new -u

That command returns something similar to the following output:

Template Instantiation Commands for .NET Core CLI

Currently installed items:
  Microsoft.DotNet.Common.ItemTemplates
    Templates:
      global.json file (globaljson)
      NuGet Config (nugetconfig)
      Solution File (sln)
      Dotnet local tool manifest file (tool-manifest)
      Web Config (webconfig)
  Microsoft.DotNet.Common.ProjectTemplates.3.0
    Templates:
      Class library (classlib) C#
      Class library (classlib) F#
      Class library (classlib) VB
      Console Application (console) C#
      Console Application (console) F#
      Console Application (console) VB
...

The first level of items after Currently installed items: are the identifiers used in uninstalling a template. And in the example above, Microsoft.DotNet.Common.ItemTemplates and Microsoft.DotNet.Common.ProjectTemplates.3.0 are listed. If the template was installed by using a file system path, this identifier will the folder path of the .template.config folder.

Uninstalling a template

Use the dotnet new -u|--uninstall command to uninstall a package.

If the package was installed by either a NuGet feed or by a .nupkg file directly, provide the identifier.

dotnet new -u <NUGET_PACKAGE_ID>

If the package was installed by specifying a path to the .template.config folder, use that absolute path to uninstall the package. You can see the absolute path of the template in the output provided by the dotnet new -u command. For more information, see the Get a list of installed templates section above.

dotnet new -u <ABSOLUTE_FILE_SYSTEM_DIRECTORY>

Create a project using a custom template

After a template is installed, use the template by executing the dotnet new <TEMPLATE> command as you would with any other pre-installed template. You can also specify options to the dotnet new command, including template-specific options you configured in the template settings. Supply the template's short name directly to the command:

dotnet new <TEMPLATE>

See also