File transforms and variable substitution reference

Last Update: 7/18/2017

Some tasks, such as the Azure App Service Deploy task version 3 and later and the IIS Web App Deploy task, allow users to configure the package based on the environment specified.

This configuration is specified in the File Transform and Variable Substitution Options section of the settings for the tasks. The transformation and substitution options are:

XML Transformation

XML transformation supports transforming the configuration files (*.config files) by following Web.config Transformation Syntax and is based on the environment to which the web package will be deployed. This option is useful when you want to add, remove or modify configurations for different environments. Transformation will be applied for other configuration files including Console or Windows service application configuration files (for example, FabrikamService.exe.config).

Configuration transform file naming conventions

XML transformation will be run on the *.config file for transformation configuration files named *.Release.config or *.<Environment>.config and will be executed in the following order:

  1. *.Release.config (for example, fabrikam.Release.config)
  2. *.<Environment>.config (for example, fabrikam.Production.config)

For example, if your package contains the following files:

  • Web.config
  • Web.Debug.config
  • Web.Release.config
  • Web.Production.config

and your environment name is Production, the transformation is applied for Web.config with Web.Release.config followed by Web.Production.config.

XML transformation example

  1. Create a Web Application package with the necessary configuration and transform files. For example, use the following configuration files:

    Configuration file

    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
      <connectionStrings>
        <add name="DefaultConnection" connectionString="Data Source=(LocalDb)\\MSDB;DbFilename=aspcore-local.mdf;" />
      </connectionStrings>
      <appSettings>
        <add key="webpages:Version" value="3.0.0.0" />
        <add key="webpages:Enabled" value="false" />
      </appSettings>
      <system.web>
        <authentication mode="None" />
        <compilation targetFramework="4.5" debug="true" />
      </system.web>
    </configuration>
    

    Transform file

    <?xml version="1.0"?>
    <configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
        <connectionStrings>
          <add name="MyDB"
            connectionString="Data Source=ReleaseSQLServer;Initial Catalog=MyReleaseDB;Integrated Security=True"
            xdt:Transform="Insert" />
        </connectionStrings>
      <appSettings>
        <add xdt:Transform="Replace" xdt:Locator="Match(key)" key="webpages:Enabled" value="true" />
      </appSettings>
      <system.web>
        <compilation xdt:Transform="RemoveAttributes(debug)" />
      </system.web>
    </configuration>
    

    This example transform configuration file does three things:

    • It adds a new database connection string inside the ConnectionStrings element.
    • It modifies value of Webpages:Enabled inside the appSettings element.
    • It removes the debug attribute from the compilation element inside the System.Web element.

    For more information, see Web.config Transformation Syntax for Web Project Deployment Using Visual Studio

  2. Create a release definition with an environment named Release.

  3. Add an Azure App Service Deploy task and set (tick) the XML transformation option.

    Release definition for XML transformation

  4. Save the release definition and start a new release.

  5. Open the Web.config file to see the transformations from Web.Release.config.

    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
      <connectionStrings>
        <add name="DefaultConnection" connectionString="Data Source=(LocalDb)\\MSDB;DbFilename=aspcore-local.mdf;" />
      <add name="MyDB" connectionString="Data Source=ReleaseSQLServer;Initial Catalog=MyReleaseDB;Integrated Security=True" /></connectionStrings>
      <appSettings>
        <add key="webpages:Version" value="3.0.0.0" />
        <add key="webpages:Enabled" value="true" />
      </appSettings>
      <system.web>
        <authentication mode="None" />
        <compilation targetFramework="4.5" />
      </system.web>
    </configuration>
    

Note:

  • You can use this technique to create a default package and deploy it to multiple environments.

  • XML transformation takes effect only when the configuration file and transform file reside within the same folder inside the specified package.

  • Set the Copy to Output Directory property for the configuration transform files to Copy If Newer.

  • By default, MSBuild applies the transformation as it generates the web package by if the <DependentUpon> element is already present in the transform file in the *.csproj file. In such cases, the Azure App Service Deploy task will fail because there is no further transformation applied on the Web.config file. Therefore, it is recommended that the <DependentUpon> element is removed from all the transform files to disable any build-time configuration when using XML transformation.

    ...
    <Content Include="Web.Debug.config">
       <DependentUpon>Web.config</DependentUpon>
    </Content>
    <Content Include="Web.Release.config">
       <DependentUpon>Web.config</DependentUpon>
    </Content>
    ...
    

XML variable substitution

This feature enables you to modify configuration settings in configuration files inside web packages. In this way, the same package can be configured based on the environment to which it will be deployed.

Variable substitution takes effect only on the applicationSettings, appSettings, connectionStrings, and configSections elements of configuration files.

XML variable substitution example

As an example, consider the task of changing the following values in Web.config:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
    <configSection>
        <section name="entityFramework" />
    </configSection>
    <connectionStrings>
        <!-- Change connectionString in this line: --> 
        <add name="DefaultConnection" connectionString="Data Source=(LocalDB)\\LocalDB;FileName=Local.mdf" />
    </connectionStrings>
    <appSettings>
        <add key="ClientValidationEnabled" value="true" />
        <add key="UnobstructiveJavascriptEnabled" value="true" />
        <!-- Change AdminUserName in this line: --> 
        <add key="AdminUserName" value="__AdminUserName__" />
        <!-- Change AdminPassword in this line: --> 
        <add key="AdminPassword" value="__AdminPasword__" />
    </appSettings>
    <entityFramework>
        <defaultConnectionFactory type="System.Data.Entity.LocalDbConnectionFactory">
            <parameters></parameters>
        </defaultConnectionFactory>
        <providers>
            <!-- Change invariantName in this line: --> 
            <provider invariantName="System.Data.SqlClient" type="System.Data.Entity.SqlServer" />
        </providers>
    </entityFramework>
</configuration>

  1. Create a release definition with an environment named Release.

  2. Add an Azure App Service Deploy task and set (tick) the XML variable substitution option.

    Release definition for XML variable substitution

  3. Define the required values in release definition variables

    Release definition variables XML variable substitution

  4. Save the release definition and start a new release.

  5. Open the Web.config file to see the variable substitutions.

    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
        <configSection>
            <section name="entityFramework" />
        </configSection>
        <connectionStrings>
            <add name="DefaultConnection" connectionString="Data Source=(ProdDB)\\MSSQLProdDB;AttachFileName=Local.mdf" />
        </connectionStrings>
        <appSettings>
            <add key="ClientValidationEnabled" value="true" />
            <add key="UnobstructiveJavascriptEnabled" value="true" />
            <add key="AdminUserName" value="ProdAdminName" />
            <add key="AdminPassword" value="*password_masked_for_display*" />
        </appSettings>
        <entityFramework>
            <defaultConnectionFactory type="System.Data.Entity.LocalDbConnectionFactory">
                <parameters></parameters>
            </defaultConnectionFactory>
            <providers>
                <provider invariantName="System.Data.SqlClientExtension" type="System.Data.Entity.SqlServer" />
            </providers>
        </entityFramework>
    </configuration>
    

Note:

  • By default, ASP.NET applications have a default parameterized connection attribute. These values are overridden only in the parameters.xml file inside the web package.

  • Because substitution occurs before deployment, the user can override the values in Web.config using parameters.xml (inside the web package) or a setparameters file.

JSON variable substitution

This feature substitutes values in the JSON configuration files. It overrides the values in the specified JSON configuration files (for example, appsettings.json) with the values matching names of release definition and environment variables.

To substitute variables in specific JSON files, provide newline-separated list of JSON files. Files names must be specified relative to the root folder. For example, if your package has in this structure:

/WebPackage(.zip)
  /---- content
    /----- website
      /---- appsetttings.json
      /---- web.config
      /---- [other folders] 
  /--- archive.xml
  /--- systeminfo.xml

and you want to substitute values in appsettings.json, enter the relative path from the root folder; for example content/website/appsettings.json. Alternatively, use wildcard patterns to search for specific JSON files. For example, **/appsettings.json returns the relative path and name of files named appsettings.json.

JSON variable substitution example

As an example, consider the task of overriding values in this JSON file:

{
  "Data": {
    "DefaultConnection": {
      "ConnectionString": "Data Source=(LocalDb)\\MSDB;AttachDbFilename=aspcore-local.mdf;"
    },
    "DebugMode": "enabled",
    "DBAccess": {
      "Admininstrators": ["Admin-1", "Admin-2"],
      "Users": ["Vendor-1", "vendor-3"]
    },
    "FeatureFlags": {
      "Preivew": [
        {
          "newUI": "AllAccounts"
        },
        {
          "NewWelcomeMessage": "Newusers"
        }
      ]
    }
  }
}

The task is to override the values of ConnectionString, DebugMode, the first of the Users values, and NewWelcomeMessage at the respective places within the JSON file hierarchy.

  1. Create a release definition with an environment named Release.

  2. Add an Azure App Service Deploy task and enter a newline-separated list of JSON files to substitute the variable values in the JSON variable substitution textbox. Files names must be relative to the root folder. You can use wildcards to search for JSON files. For example: **/*.json means substitute values in all the JSON files within the package.

    Release definition for JSON variable substitution

  3. Define the required substitution values in release definition or environment variables.

    Release definition variables JSON variable substitution

  4. Save the release definition and start a new release.

  5. After the transformation, the JSON will contain the following:

    {
      "Data": {
        "DefaultConnection": {
          "ConnectionString": "Data Source=(prodDB)\\MSDB;AttachDbFilename=prod.mdf;"
        },
        "DebugMode": "disabled",
        "DBAccess": {
          "Admininstrators": ["Admin-1", "Admin-2"],
          "Users": ["Admin-3", "vendor-3"]
        },
        "FeatureFlags": {
          "Preivew": [
            {
              "newUI": "AllAccounts"
            },
            {
              "CoolDialog": "AllAccounts"
            }
          ]
        }
      }
    }
    '''
    
    
    

Note:

  • To substitute values in nested levels of the file, concatenate the names with a period (.) in hierarchical order.

  • A JSON object may contain an array whose values can be referenced by their index. For example, to substitute the first value in the Users array shown above, use the variable name DBAccess.Users.0. To update the value in NewWelcomeMessage, use the variable name FeatureFlags.Preview.1.NewWelcomeMessage.

  • Only String substitution is supported for JSON variable substitution.

  • Substitution is supported for only UTF-8 and UTF-16 LE encoded files.

  • If the file specification you enter does not match any file, the task will fail.

  • Variable name matching is case-sensitive.