Présentation de l’espace de noms Microsoft.Data.SqlClient

Télécharger ADO.NET

L’espace de noms Microsoft.Data.SqlClient est essentiellement une nouvelle version de l’espace de noms System.Data.SqlClient. Microsoft.Data.SqlClient conserve généralement la même API et la compatibilité descendante avec System.Data.SqlClient. Pour la plupart des applications, il est simple de migrer de System.Data.SqlClient vers Microsoft.Data.SqlClient. Ajoutez une dépendance NuGet à Microsoft.Data.SqlClient et mettez à jour les références et instructions using à Microsoft.Data.SqlClient.

Il existe quelques différences dans les API moins utilisées par rapport à System.Data.SqlClient qui peuvent affecter certaines applications. Pour connaître ces différences, consultez l’aide-mémoire sur le portage.

Informations de référence sur l'API

Les détails de l’API Microsoft.Data.SqlClient sont disponibles dans le navigateur d’API .NET.

Notes de publication pour Microsoft.Data.SqlClient 5.2

Nouvelles fonctionnalités de la version 5.2

  • Ajout de la prise en charge de SqlDiagnosticListener sur .NET Standard. #1931
  • Ajout de la nouvelle propriété RowsCopied64 à SqlBulkCopy. #2004 Pour en savoir plus
  • Ajout d'une nouvelle API AccessTokenCallBack à SqlConnection. #1260 Pour en savoir plus
  • Ajout de la prise en charge de l'option SuperSocketNetLib de registre pour le chiffrement sur .NET sur Windows. #2047
  • Ajout de la prise en charge de SqlBatch sur .NET 6+ #1825, #2223 En savoir plus
  • Ajout de la prise en charge de l'authentification des identités de charge de travail #2159, #2264
  • Ajout de la prise en charge de la localisation sur .NET #2210
  • Ajout de la prise en charge du classement géorgien #2194
  • Ajout de la prise en charge des systèmes avec primauté des octets de poids fort (big-endian) #2170
  • Ajout de la prise en charge de .NET 8 #2230
  • Ajout d'une version explicite pour les principales dépendances de version .NET sur System.Runtime.Caching 8.0.0, System.Configuration.ConfigurationManager 8.0.0 et System.Diagnostics.DiagnosticSource 8.0.0 #2303
  • Ajout de la possibilité de générer des symboles de débogage dans un fichier de package distinct #2137

Ajout de la nouvelle propriété RowsCopied64 à SqlBulkCopy

SqlBulkCopy a une nouvelle propriété RowsCopied64 qui prend en charge les types valeur long.

Notez que le comportement existant SqlBulkCopy.RowsCopied n'est pas modifié. Lorsque la valeur dépasse int.MaxValue, RowsCopied peut retourner un nombre négatif.

Exemple d'utilisation :

    using (SqlConnection srcConn = new SqlConnection(srcConstr))
    using (SqlCommand srcCmd = new SqlCommand("select top 5 * from employees", srcConn))
    {
        srcConn.Open();
        using (DbDataReader reader = srcCmd.ExecuteReader())
        {
            using (SqlBulkCopy bulkcopy = new SqlBulkCopy(dstConn))
            {
                bulkcopy.DestinationTableName = dstTable;
                SqlBulkCopyColumnMappingCollection ColumnMappings = bulkcopy.ColumnMappings;

                ColumnMappings.Add("EmployeeID", "col1");
                ColumnMappings.Add("LastName", "col2");
                ColumnMappings.Add("FirstName", "col3");

                bulkcopy.WriteToServer(reader);
                long rowsCopied = bulkcopy.RowsCopied64;
            }
        }
    }

Ajout de la nouvelle propriété AccessTokenCallBack à SqlConnection

SqlConnection prend en charge TokenCredential l'authentification en introduisant une nouvelle propriété AccessTokenCallBack en tant que délégué Func<SqlAuthenticationParameters, CancellationToken,Task<SqlAuthenticationToken>> pour retourner un jeton d'accès d'authentification fédéré.

Exemple d'utilisation :

using Microsoft.Data.SqlClient;
using Azure.Identity;

const string defaultScopeSuffix = "/.default";
string connectionString = GetConnectionString();
DefaultAzureCredential credential = new();
using SqlConnection connection = new(connectionString);

connection.AccessTokenCallback = async (authParams, cancellationToken) =>
{
    string scope = authParams.Resource.EndsWith(defaultScopeSuffix)
        ? authParams.Resource
        : $"{authParams.Resource}{defaultScopeSuffix}";
    AccessToken token = await cred.GetTokenAsync(
        new TokenRequestContext([scope]),
        cancellationToken);

    return new SqlAuthenticationToken(token.Token, token.ExpiresOn);
}

connection.Open();
Console.WriteLine("ServerVersion: {0}", connection.ServerVersion);
Console.WriteLine("State: {0}", connection.State);

SqlBatch API

Exemple d'utilisation :

using Microsoft.Data.SqlClient;

class Program
{
    static void Main()
    {
        string str = "Data Source=(local);Initial Catalog=Northwind;"
        + "Integrated Security=SSPI;Encrypt=False";
        RunBatch(str);
    }

    static void RunBatch(string connString)
    {
        using var connection = new SqlConnection(connString);
        connection.Open();

        var batch = new SqlBatch(connection);

        const int count = 10;
        const string parameterName = "parameter";
        for (int i = 0; i < count; i++)
        {
            var batchCommand = new SqlBatchCommand($"SELECT @{parameterName} as value");
            batchCommand.Parameters.Add(new SqlParameter(parameterName, i));
            batch.BatchCommands.Add(batchCommand);
        }

        // Optionally Prepare
        batch.Prepare();

        var results = new List<int>(count);
        using (SqlDataReader reader = batch.ExecuteReader())
        {
            do
            {
                while (reader.Read())
                {
                    results.Add(reader.GetFieldValue<int>(0));
                }
            } while (reader.NextResult());
        }
        Console.WriteLine(string.Join(", ", results));
    }
}

Prise en charge de la plateforme cible 5.2

  • .NET Framework 4.6.2+ (Windows x86, Windows x64)
  • .NET 6.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le référentiel GitHub : Notes de publication 5.2.

Changements cassants dans la version 5.1

  • Fin de la prise en charge de .NET Core 3.1 #1704 #1823

Nouvelles fonctionnalités de la version 5.1

  • Ajout de la prise en charge de DateOnly et TimeOnly pour la valeur SqlParameter et GetFieldValue. #1813
  • Ajout de la prise en charge de TLS 1.3 pour .NET Core et SNI Native. #1821
  • Ajout du paramètre ServerCertificate pour Encrypt=Mandatory ou Encrypt=Strict. #1822 Pour en savoir plus
  • Ajout de la prise en charge de Windows ARM64 lors du ciblage de .NET Framework. #1828

Certificat de serveur

La valeur par défaut du paramètre de connexionServerCertificate est une chaîne vide. Lorsque Encrypt est défini sur Mandatory ou Strict, ServerCertificate peut être utilisé pour spécifier sur le système de fichiers un chemin de fichier de certificat correspondant au certificat TLS/SSL du serveur. Le certificat spécifié doit correspondre exactement pour être valide. Les formats de certificat acceptés sont PEM, DER et CER. Voici un exemple d’utilisation :

"Data Source=...;Encrypt=Strict;ServerCertificate=C:\\certificates\\server.cer"

Prise en charge de la plateforme cible 5.1

  • .NET Framework 4.6.2+ (Windows x86, Windows x64)
  • .NET 6.0+ (Windows x86, Windows x64, Windows ARM64, Windows Azure Resource Manager, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub 5.1 Release Notes.

Notes de publication pour Microsoft.Data.SqlClient 5.0

Changements cassants dans la version 5.0

  • Annulation de la prise en charge de .NET Framework 4.6.1 #1574
  • Ajout d’une dépendance au package Microsoft.SqlServer.Server. Cette nouvelle dépendance peut entraîner des conflits d’espace de noms si votre application référence cet espace de noms et a toujours des références de package (directes ou indirectes) à System.Data.SqlClient à partir de .NET Core.
  • Classes annulées de l’espace de noms Microsoft.Data.SqlClient.Server et remplacées par des types pris en charge à partir du package Microsoft.SqlServer.Server .#1585. Les classes et les enums affectées sont les suivantes :
    • Microsoft.Data.SqlClient.Server.IBinarySerialize -> Microsoft.SqlServer.Server.IBinarySerialize
    • Microsoft.Data.SqlClient.Server.InvalidUdtException -> Microsoft.SqlServer.Server.InvalidUdtException
    • Microsoft.Data.SqlClient.Server.SqlFacetAttribute -> Microsoft.SqlServer.Server.SqlFacetAttribute
    • Microsoft.Data.SqlClient.Server.SqlFunctionAttribute -> Microsoft.SqlServer.Server.SqlFunctionAttribute
    • Microsoft.Data.SqlClient.Server.SqlMethodAttribute -> Microsoft.SqlServer.Server.SqlMethodAttribute
    • Microsoft.Data.SqlClient.Server.SqlUserDefinedAggregateAttribute -> Microsoft.SqlServer.Server.SqlUserDefinedAggregateAttribute
    • Microsoft.Data.SqlClient.Server.SqlUserDefinedTypeAttribute -> Microsoft.SqlServer.Server.SqlUserDefinedTypeAttribute
    • (enum) Microsoft.Data.SqlClient.Server.DataAccessKind -> Microsoft.SqlServer.Server.DataAccessKind
    • (enum) Microsoft.Data.SqlClient.Server.Format -> Microsoft.SqlServer.Server.Format
    • (enum) Microsoft.Data.SqlClient.Server.SystemDataAccessKind -> Microsoft.SqlServer.Server.SystemDataAccessKind

Nouvelles fonctionnalités de la version 5.0

  • Ajout de la prise en charge de TDS8. Pour utiliser TDS 8, les utilisateurs doivent spécifier Encrypt=Strict dans la chaîne de connexion. #1608 Pour en savoir plus
  • Ajout de la prise en charge de la spécification du SPN de serveur et du SPN du serveur de basculement sur la connexion. #1607 Pour en savoir plus
  • Ajout de la prise en charge des alias lors du ciblage de .NET Core sur Windows. #1588 Pour en savoir plus
  • Ajout de SqlDataSourceEnumerator. #1430, En savoir plus
  • Ajout d’un nouveau commutateur AppContext pour supprimer les avertissements TLS non sécurisés. #1457, En savoir plus

Sécurité améliorée de TDS 8

Pour utiliser TDS 8, spécifiez Encrypt=Strict dans la chaîne de connexion. Le mode strict désactive TrustServerCertificate (toujours traité comme False en mode Strict). HostNameInCertificate a été ajouté pour aider certains scénarios en mode Strict. TDS 8 commence et poursuit toutes les communications de serveur à l’intérieur d’une connexion TLS sécurisée et chiffrée.

De nouvelles valeurs Encrypt ont été ajoutées pour clarifier le comportement de chiffrement de connexion. Encrypt=Mandatory équivaut à Encrypt=True et chiffre les connexions pendant la négociation de connexion TDS. Encrypt=Optional est équivalent et Encrypt=False chiffre uniquement la connexion si le serveur indique au client que le chiffrement est requis pendant la négociation de connexion TDS.

Pour plus d’informations sur le chiffrement des connexions au serveur, consultez Chiffrement et validation de certificat.

HostNameInCertificate peut être spécifié dans la chaîne de connexion lors de l’utilisation d’alias pour se connecter avec le chiffrement à un serveur qui a un certificat de serveur portant un nom différent ou un autre nom d’objet que le nom utilisé par le client pour identifier le serveur (alias DNS, par exemple). Exemple d’utilisation : HostNameInCertificate=MyDnsAliasName

SPN du serveur

Lorsque vous vous connectez dans un environnement qui a une topographie de domaine/forêt unique, vous pouvez avoir des exigences spécifiques pour les SPN de serveur. Les paramètres de chaîne de connexion ServerSPN (SPN du serveur) et FailoverServerSPN (SPN du serveur de basculement) peuvent être utilisés pour remplacer les SPN de serveur générés automatiquement et utilisés lors de l’authentification intégrée dans un environnement de domaine.

Support pour les alias SQL

Les utilisateurs peuvent configurer des alias à l’aide du Gestionnaire de configuration SQL Server. Ces alias sont stockés dans le Registre Windows et sont déjà pris en charge lors du ciblage de .NET Framework. Cette version prend en charge les alias lors du ciblage de .NET ou .NET Core sur Windows.

Support de l’énumérateur de source de données SQL

Fournit un mécanisme pour énumérer toutes les instances disponibles de SQL Server dans le réseau local.

using Microsoft.Data.Sql;
static void Main()  
  {  
    // Retrieve the enumerator instance and then the data.  
    SqlDataSourceEnumerator instance =  
      SqlDataSourceEnumerator.Instance;  
    System.Data.DataTable table = instance.GetDataSources();  
  
    // Display the contents of the table.  
    DisplayData(table);  
  
    Console.WriteLine("Press any key to continue.");  
    Console.ReadKey();  
  }  
  
  private static void DisplayData(System.Data.DataTable table)  
  {  
    foreach (System.Data.DataRow row in table.Rows)  
    {  
      foreach (System.Data.DataColumn col in table.Columns)  
      {  
        Console.WriteLine("{0} = {1}", col.ColumnName, row[col]);  
      }  
      Console.WriteLine("============================");  
    }  
  }  

Supprimer les avertissements TLS non sécurisés

Un avertissement de sécurité est généré sur la console si la version TLS inférieure à 1.2 est utilisée pour négocier avec le serveur. Cet avertissement peut être supprimé sur la connexion SQL en Encrypt = false activant le commutateur AppContext suivant au démarrage de l’application :

Switch.Microsoft.Data.SqlClient.SuppressInsecureTLSWarning

Support de la plateforme cible 5.0

  • .NET Framework 4.6.2+ (Windows x86, Windows x64)
  • .NET Core 3.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le référentiel GitHub : Notes de publication 5.0.

Notes de publication pour Microsoft.Data.SqlClient 4.1

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 4.1.

Nouvelles fonctionnalités de la version 4.1

Introduire le protocole d’attestation None

Un nouveau protocole d’attestation nommé None est autorisé dans la chaîne de connexion. Ce protocole permet aux utilisateurs de renoncer à l’attestation d’enclave pour les enclaves VBS. Lorsque ce protocole est défini, la propriété URL d’attestation d’enclave est facultative.

Exemple de chaîne de connexion :

//Attestation protocol NONE with no URL
"Data Source = {server}; Initial Catalog = {db}; Column Encryption Setting = Enabled; Attestation Protocol = None;"

Prise en charge de la plateforme cible 4.1

  • .NET Framework 4.6.1+ (Windows x86, Windows x64)
  • .NET Core 3.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Notes de publication pour Microsoft.Data.SqlClient 4.0

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 4.0.

Changements cassants dans la version 4.0

  • Modification de la propriété de chaîne de connexion de Encrypt à true par défaut. #1210 Pour en savoir plus
  • Le pilote lève désormais SqlException remplaçant AggregateException pour les modes d’authentification Active Directory.répertoire. #1213
  • Suppression de la propriété de connexion obsolète Asynchronous Processing de .NET Framework. #1148
  • Suppression du commutateur de sécurité Configurable Retry Logic. #1254 Pour en savoir plus
  • Fin de la prise en charge de .NET Core 2.1 #1272
  • [.NET Framework] Aucune exception n’est levée si un ID d’utilisateur est fourni dans la chaîne de connexion dans le cadre de l’authentification Active Directory Integrated. #1359

Nouvelles fonctionnalités de la version 4.0

Chiffrer la valeur par défaut définie sur true

La valeur par défaut du paramètre de connexion Encrypt est passée de false à true. Avec l’utilisation croissante des bases de données cloud et la nécessité de s’assurer que ces connexions sont sécurisées, il est temps de procéder à ce changement cassant de compatibilité descendante.

S’assurer que les connexions échouent quand le chiffrement est requis

Dans les scénarios où les bibliothèques de chiffrement client étaient désactivées ou indisponibles, il était possible d’établir des connexions non chiffrées quand Encrypt était défini sur true ou quand le serveur nécessitait un chiffrement.

Commutateur AppContext pour l’utilisation des protocoles par défaut du système

TLS 1.3 n’est pas pris en charge par le pilote. Par conséquent, il a été supprimé de la liste des protocoles pris en charge par défaut. Les utilisateurs peuvent revenir à l’utilisation forcée des protocoles clients du système d’exploitation. Pour cela, activez le commutateur App Context suivant :

Switch.Microsoft.Data.SqlClient.UseSystemDefaultSecureProtocols

Activer la liaison de paramètres optimisée

Microsoft.Data.SqlClient introduit une nouvelle API SqlCommand, EnableOptimizedParameterBinding pour améliorer les performances des requêtes avec un grand nombre de paramètres. Elle est désactivée par défaut. Si elle prend la valeur true, les noms de paramètres ne sont pas envoyés au SQL Server quand la commande est exécutée.

public class SqlCommand
{
    public bool EnableOptimizedParameterBinding { get; set; }
}

Supprimer le commutateur de sécurité de logique de nouvelle tentative configurable

Le commutateur App Context « Switch.Microsoft.Data.SqlClient.EnableRetryLogic » n’est plus nécessaire pour utiliser la fonctionnalité de logique de nouvelle tentative configurable. La fonctionnalité est désormais prise en charge en production. Le comportement par défaut de la fonctionnalité reste une stratégie sans nouvelle tentative. Il doit être remplacé par les applications clientes pour activer les nouvelles tentatives.

Prise en charge des instances partagées SqlLocalDb

Les instances partagées SqlLocalDb sont désormais prises en charge lors de l’utilisation de l’indication SNI managée.

  • Scénarios possibles :
    • (localdb)\. (se connecte à l’instance par défaut de SqlLocalDb)
    • (localdb)\<named instance>
    • (localdb)\.\<shared instance name> (* prise en charge récemment ajoutée)

Prise en charge de GetFieldValueAsync<T> et GetFieldValue<T> pour les types XmlReader, TextReader, Stream

Les types XmlReader, TextReader, Stream sont désormais pris en charge lors de l’utilisation de GetFieldValueAsync<T> et GetFieldValue<T>.

Exemple d'utilisation :

using (SqlConnection connection = new SqlConnection(connectionString))
{
    using (SqlCommand command = new SqlCommand(query, connection))
    {
        connection.Open();
        using (SqlDataReader reader = await command.ExecuteReaderAsync())
        {
            if (await reader.ReadAsync())
            {
                using (Stream stream = await reader.GetFieldValueAsync<Stream>(1))
                {
                    // Continue to read from stream
                }
            }
        }
    }
}

Prise en charge de la plateforme cible 4.0

  • .NET Framework 4.6.1+ (Windows x86, Windows x64)
  • .NET Core 3.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Notes de publication pour Microsoft.Data.SqlClient 3.0

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 3.0.

Changements cassants dans la version 3.0

  • La version minimale prise en charge de .NET Framework est passée à v4.6.1. .NET Framework v4.6.0 n’est plus pris en charge. #899
  • La propriété de connexion User Id requiert désormais Client Id au lieu de Object Id pour l’identité managée affectée par l’utilisateur #1010 En savoir plus
  • SqlDataReader retourne maintenant une valeur DBNull au lieu d’un byte[] vide. Le comportement hérité peut être activé en définissant le commutateur AppContext Switch.Microsoft.Data.SqlClient.LegacyRowVersionNullBehavior #998 En savoir plus

Nouvelles fonctionnalités de la version 3.0

Logique de nouvelle tentative configurable

Cette nouvelle fonctionnalité introduit une prise en charge configurable pour les applications clientes afin de réessayer en cas d’erreurs « transitoires » ou « reproductibles ». La configuration peut être effectuée par le biais de fichiers de configuration de code ou d’application, et les opérations de nouvelle tentative peuvent être appliquées à l’ouverture d’une connexion ou à l’exécution d’une commande. Cette fonctionnalité est désactivée par défaut et est actuellement en préversion. Pour permettre cette prise en charge, les applications clientes doivent activer le commutateur de sûreté suivant :

AppContext.SetSwitch("Switch.Microsoft.Data.SqlClient.EnableRetryLogic", true);

Une fois que le commutateur .NET AppContext est activé, une stratégie de logique de nouvelle tentative peut être définie pour SqlConnection et SqlCommand indépendamment, ou ensemble à l’aide de différentes options de personnalisation.

De nouvelles API publiques sont introduites dans SqlConnection et SqlCommand pour l’inscription d’une implémentation SqlRetryLogicBaseProvider personnalisée :

public SqlConnection
{
    public SqlRetryLogicBaseProvider RetryLogicProvider;
}

public SqlCommand
{
    public SqlRetryLogicBaseProvider RetryLogicProvider;
}

Vous trouverez des exemples d’utilisation d’API ici :

using Microsoft.Data.SqlClient;

/// Detecting retriable exceptions is a vital part of the retry pattern.
/// Before applying retry logic it is important to investigate exceptions and choose a retry provider that best fits your scenario.
/// First, log your exceptions and find transient faults.
/// The purpose of this sample is to illustrate how to use this feature and the condition might not be realistic.
class RetryLogicSample
{
    private const string DefaultDB = "Northwind";
    private const string CnnStringFormat = "Server=localhost; Initial Catalog={0}; Integrated Security=true; pooling=false;";
    private const string DropDatabaseFormat = "DROP DATABASE {0}";

    // For general use
    private static SqlConnection s_generalConnection = new SqlConnection(string.Format(CnnStringFormat, DefaultDB));

    static void Main(string[] args)
    {
        // 1. Define the retry logic parameters
        var options = new SqlRetryLogicOption()
        {
            NumberOfTries = 5,
            MaxTimeInterval = TimeSpan.FromSeconds(20),
            DeltaTime = TimeSpan.FromSeconds(1)
        };

        // 2. Create a retry provider
        var provider = SqlConfigurableRetryFactory.CreateExponentialRetryProvider(options);

        // define the retrying event to report the execution attempts
        provider.Retrying += (object s, SqlRetryingEventArgs e) =>
            {
                int attempts = e.RetryCount + 1;
                Console.ForegroundColor = ConsoleColor.Yellow;
                Console.WriteLine($"attempt {attempts} - current delay time:{e.Delay} \n");
                Console.ForegroundColor = ConsoleColor.DarkGray;
                if (e.Exceptions[e.Exceptions.Count - 1] is SqlException ex)
                {
                    Console.WriteLine($"{ex.Number}-{ex.Message}\n");
                }
                else
                {
                    Console.WriteLine($"{e.Exceptions[e.Exceptions.Count - 1].Message}\n");
                }

                // It is not a good practice to do time-consuming tasks inside the retrying event which blocks the running task.
                // Use parallel programming patterns to mitigate it.
                if (e.RetryCount == provider.RetryLogic.NumberOfTries - 1)
                {
                    Console.WriteLine("This is the last chance to execute the command before throwing the exception.");
                    Console.WriteLine("Press Enter when you're ready:");
                    Console.ReadLine();
                    Console.WriteLine("continue ...");
                }
            };

        // Open the general connection.
        s_generalConnection.Open();

        try
        {
            // Assume the database is being created and other services are going to connect to it.
            RetryConnection(provider);
        }
        catch
        {
            // exception is thrown if connecting to the database isn't successful.
            throw;
        }
    }

    private static void ExecuteCommand(SqlConnection cn, string command)
    {
        using var cmd = cn.CreateCommand();
        cmd.CommandText = command;
        cmd.ExecuteNonQuery();
    }

    private static void RetryConnection(SqlRetryLogicBaseProvider provider)
    {
        // Change this if you already have a database with the same name in your database.
        string dbName = "Invalid_DB_Open";

        // Create a connection to an invalid database.
        using var cnn = new SqlConnection(string.Format(CnnStringFormat, dbName));
        // 3. Assign the `provider` to the connection
        cnn.RetryLogicProvider = provider;
        Console.WriteLine($"Connecting to the [{dbName}] ...");
        // Manually execute the following command in SSMS to create the invalid database while the SqlConnection is attempting to connect to it.
        // >> CREATE DATABASE Invalid_DB_Open;
        Console.WriteLine($"Manually, run the 'CREATE DATABASE {dbName};' in the SQL Server before exceeding the {provider.RetryLogic.NumberOfTries} attempts.");
        // the connection tries to connect to the database 5 times
        Console.WriteLine("The first attempt, before getting into the retry logic.");
        cnn.Open();
        Console.WriteLine($"Connected to the [{dbName}] successfully.");

        cnn.Close();

        // Drop it after test
        ExecuteCommand(s_generalConnection, string.Format(DropDatabaseFormat, dbName));
        Console.WriteLine($"The [{dbName}] is removed.");
    }
}
/// Detecting retriable exceptions is a vital part of the retry pattern.
/// Before applying retry logic it is important to investigate exceptions and choose a retry provider that best fits your scenario.
/// First, log your exceptions and find transient faults.
/// The purpose of this sample is to illustrate how to use this feature and the condition might not be realistic.

    private const string DefaultDB = "Northwind";
    private const string CnnStringFormat = "Server=localhost; Initial Catalog={0}; Integrated Security=true; pooling=false;";
    private const string DropDatabaseFormat = "DROP DATABASE {0}";
    private const string CreateDatabaseFormat = "CREATE DATABASE {0}";

    // For general use
    private static SqlConnection s_generalConnection = new SqlConnection(string.Format(CnnStringFormat, DefaultDB));

    static void Main(string[] args)
    {
        // 1. Define the retry logic parameters
        var options = new SqlRetryLogicOption()
        {
            NumberOfTries = 5,
            MaxTimeInterval = TimeSpan.FromSeconds(20),
            DeltaTime = TimeSpan.FromSeconds(1),
            AuthorizedSqlCondition = null,
            // error number 3702 : Cannot drop database "xxx" because it is currently in use.
            TransientErrors = new int[] {3702}
        };

        // 2. Create a retry provider
        var provider = SqlConfigurableRetryFactory.CreateExponentialRetryProvider(options);

        // define the retrying event to report execution attempts
        provider.Retrying += (object s, SqlRetryingEventArgs e) =>
            {
                int attempts = e.RetryCount + 1;
                Console.ForegroundColor = ConsoleColor.Yellow;
                Console.WriteLine($"attempt {attempts} - current delay time:{e.Delay} \n");
                Console.ForegroundColor = ConsoleColor.DarkGray;
                if (e.Exceptions[e.Exceptions.Count - 1] is SqlException ex)
                {
                    Console.WriteLine($"{ex.Number}-{ex.Message}\n");
                }
                else
                {
                    Console.WriteLine($"{e.Exceptions[e.Exceptions.Count - 1].Message}\n");
                }

                // It is not good practice to do time-consuming tasks inside the retrying event which blocks the running task.
                // Use parallel programming patterns to mitigate it.
                if (e.RetryCount == provider.RetryLogic.NumberOfTries - 1)
                {
                    Console.WriteLine("This is the last chance to execute the command before throwing the exception.");
                    Console.WriteLine("Press Enter when you're ready:");
                    Console.ReadLine();
                    Console.WriteLine("continue ...");
                }
            };

        // Open a general connection.
        s_generalConnection.Open();

        try
        {
            // Assume the database is creating and other services are going to connect to it.
            RetryCommand(provider);
        }
        catch
        {
            s_generalConnection.Close();
            // exception is thrown if connecting to the database isn't successful.
            throw;
        }
        s_generalConnection.Close();
    }

    private static void ExecuteCommand(SqlConnection cn, string command)
    {
        using var cmd = cn.CreateCommand();
        cmd.CommandText = command;
        cmd.ExecuteNonQuery();
    }

    private static void FindActiveSessions(SqlConnection cnn, string dbName)
    {
        using var cmd = cnn.CreateCommand();
        cmd.CommandText = "DECLARE @query NVARCHAR(max) = '';" + Environment.NewLine +
            $"SELECT @query = @query + 'KILL ' + CAST(spid as varchar(50)) + ';' FROM sys.sysprocesses WHERE dbid = DB_ID('{dbName}')" + Environment.NewLine +
            "SELECT @query AS Active_sessions;";
        var reader = cmd.ExecuteReader();
        if (reader.Read())
        {
            Console.ForegroundColor = ConsoleColor.Green;
            Console.Write($">> Execute the '{reader.GetString(0)}' command in SQL Server to unblock the running task.");
            Console.ResetColor();
        }
        reader.Close();
    }
var RetryLogicOption = new SqlRetryLogicOption()
{
    NumberOfTries = 5,
    // Declare the error number 102 as a transient error to apply the retry logic when it occurs.
    TransientErrors = new int[] { 102 },
    // When a SqlCommand executes out of a transaction, 
    // the retry logic will apply if it contains a 'select' keyword.
    AuthorizedSqlCondition = x => string.IsNullOrEmpty(x)
            || Regex.IsMatch(x, @"\b(SELECT)\b", RegexOptions.IgnoreCase),
    DeltaTime = TimeSpan.FromSeconds(1),
    MaxTimeInterval = TimeSpan.FromSeconds(60),
    MinTimeInterval = TimeSpan.FromSeconds(3)
};

De nouvelles sections de configuration ont également été ajoutées pour effectuer la même inscription à partir de fichiers de configuration, sans avoir à modifier le code existant :

<section name="SqlConfigurableRetryLogicConnection"
            type="Microsoft.Data.SqlClient.SqlConfigurableRetryConnectionSection, Microsoft.Data.SqlClient"/>

<section name="SqlConfigurableRetryLogicCommand"
            type="Microsoft.Data.SqlClient.SqlConfigurableRetryCommandSection, Microsoft.Data.SqlClient"/>

Voici un exemple simple d’utilisation des nouvelles sections de configuration dans les fichiers de configuration :

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <configSections>
    <section name="SqlConfigurableRetryLogicConnection"
             type="Microsoft.Data.SqlClient.SqlConfigurableRetryConnectionSection, Microsoft.Data.SqlClient"/>
    <section name="SqlConfigurableRetryLogicCommand"
             type="Microsoft.Data.SqlClient.SqlConfigurableRetryCommandSection, Microsoft.Data.SqlClient"/>

    <section name="AppContextSwitchOverrides"
             type="Microsoft.Data.SqlClient.AppContextSwitchOverridesSection, Microsoft.Data.SqlClient"/>
  </configSections>

  <!--Enable safety switch in .NET Core-->
  <AppContextSwitchOverrides value="Switch.Microsoft.Data.SqlClient.EnableRetryLogic=true"/>

  <!--Retry method for SqlConnection-->
  <SqlConfigurableRetryLogicConnection retryMethod ="CreateFixedRetryProvider" numberOfTries ="3" deltaTime ="00:00:10" maxTime ="00:00:30"
                                    transientErrors="40615" />

  <!--Retry method for SqlCommand containing SELECT queries-->
  <SqlConfigurableRetryLogicCommand retryMethod ="CreateIncrementalRetryProvider" numberOfTries ="5" deltaTime ="00:00:10" maxTime ="00:01:10"
                                    authorizedSqlCondition="\b(SELECT)\b" transientErrors="102, 4060, 0"/>
</configuration>

Les applications peuvent également implémenter leur propre fournisseur de la classe de base SqlRetryLogicBaseProvider et l’inscrire auprès de SqlConnection/SqlCommand.

Compteurs d’événements

Les compteurs suivants sont désormais disponibles pour les applications ciblant .NET Core 3.1+ et .NET Standard 2.1+ :

Name Nom complet Description
active-hard-connections Connexions actives réelles actuellement établies aux serveurs Nombre de connexions actuellement ouvertes aux serveurs de base de données.
hard-connects Taux de connexion réel aux serveurs Nombre de connexions ouvertes aux serveurs de base de données par seconde.
hard-disconnects Taux de déconnexion réel des serveurs Nombre de déconnexions des serveurs de base de données par seconde.
active-soft-connects Connexions actives récupérées à partir du pool de connexions Nombre de connexions déjà ouvertes consommées à partir du pool de connexions.
soft-connects Taux de connexions récupérées à partir du pool de connexions Nombre de connexions consommées à partir du pool de connexions par seconde.
soft-disconnects Taux de connexions retournées au pool de connexions Nombre de connexions retournées au pool de connexions par seconde.
number-of-non-pooled-connections Nombre de connexions n’utilisant pas de regroupement de connexions Nombre de connexions actives qui ne sont pas regroupées.
number-of-pooled-connections Nombre de connexions gérées par le pool de connexions Nombre de connexions actives gérées par l’infrastructure de pools de connexions.
number-of-active-connection-pool-groups Nombre de chaînes de connexion uniques actives Nombre de groupes uniques et actifs du pool de connexions. Ce compteur s’appuie sur le nombre de chaînes de connexion uniques trouvées dans AppDomain.
number-of-inactive-connection-pool-groups Nombre de chaînes de connexion uniques en attente de nettoyage Nombre de groupes marqués pour le nettoyage du pool de connexions unique. Ce compteur s’appuie sur le nombre de chaînes de connexion uniques trouvées dans AppDomain.
number-of-active-connection-pools Nombre de pools de connexions actifs Nombre total de regroupements de connexions.
number-of-inactive-connection-pools Nombre de pools de connexions inactifs Nombre de pools de connexions inactifs sans activité récente et en attente de suppression.
number-of-active-connections Nombre de connexions actives Nombre de connexions actives en cours d’utilisation.
number-of-free-connections Nombre de connexions prêtes dans le pool de connexions Nombre de connexions ouvertes disponibles pour une utilisation dans les pools de connexions.
number-of-stasis-connections Nombre de connexions actuellement en préparation Nombre de connexions actuellement en attente de l’achèvement d’une action et qui ne sont pas disponibles pour une utilisation par l’application.
number-of-reclaimed-connections Nombre de connexions récupérées à partir du nettoyage de la mémoire Nombre de connexions récupérées par le nettoyage de la mémoire alors que ni Close ni Dispose n’a été appelée par l’application. Remarque La fermeture ou la suppression explicite des connexions nuit aux performances.

Ces compteurs peuvent être utilisés avec les outils CLI globaux de .NET Core : dotnet-counters et dotnet-trace dans Windows ou Linux et PerfView dans Windows, en utilisant Microsoft.Data.SqlClient.EventSource comme nom de fournisseur. Pour plus d’informations, consultez Récupérer les valeurs des compteurs d’événements.

dotnet-counters monitor Microsoft.Data.SqlClient.EventSource -p
PerfView /onlyProviders=*Microsoft.Data.SqlClient.EventSource:EventCounterIntervalSec=1 collect

Présentation de la dépendance Azure Identity

Microsoft.Data.SqlClient dépend désormais de la bibliothèque Azure.Identity pour acquérir des jetons pour les modes d’authentification « Identité managée Active Directory/MSI » et « Principal de service Azure Directory ». Ce changement apporte les modifications suivantes à la surface d’exposition publique :

  • Changement cassant
    La propriété de connexion « ID d’utilisateur » requiert désormais « ID client » et non « ID d’objet » pour « Identité managée affectée par l’utilisateur ».
  • API publique
    Nouvelle propriété publique en lecture seule : SqlAuthenticationParameters.ConnectionTimeout
  • Dépendance
    Azure.Identity v1.3.0

Améliorations du suivi d’événements dans SNI.dll

Les versions Microsoft.Data.SqlClient.SNI (dépendance sur .NET Framework) et Microsoft.Data.SqlClient.SNI.runtime (dépendance sur .NET Core/Standard) ont été mises à jour vers v3.0.0-preview1.21104.2. Le suivi d’événements dans SNI.dll n’est plus activé par le biais d’une application cliente. Il suffit d’abonner une session au fournisseur Microsoft.Data.SqlClient.EventSource par le biais d’outils tels que xperf ou perfview. Pour plus d’informations, consultez Prise en charge du suivi d’événements dans Native SNI.

Activation du comportement Null de version de ligne

SqlDataReader retourne une valeur DBNull au lieu d’un byte[] vide. Pour permettre le comportement hérité, vous devez activer le commutateur AppContext suivant au démarrage de l’application : "Switch.Microsoft.Data.SqlClient.LegacyRowVersionNullBehavior"

Support pour l’authentification Microsoft Entra par défaut

Remarque

Bien que Microsoft Entra ID soit le nouveau nom d’Azure Active Directory (Azure AD) pour empêcher l’interruption des environnements existants, Azure AD reste toujours dans certains éléments codés en dur, tels que les champs d’interface utilisateur, les fournisseurs de connexions, les codes d’erreur et cmdlets. Dans cet article, les deux noms sont interchangeables.

Ce PR introduit une nouvelle méthode d’authentification SQL, Active Directory par défaut. Ce mode d’authentification élargit les possibilités d’authentification des utilisateurs avec Microsoft Entra ID, en étendant les solutions de connexion à l’environnement client, Visual Studio Code, Visual Studio, Azure CLI, etc.

Avec ce mode d’authentification, le pilote acquiert un jeton en transmettant « DefaultAzureCredential » à partir de la bibliothèque Azure Identity pour obtenir un jeton d’accès. Ce mode tente d’utiliser ces types d’informations d’identification pour obtenir un jeton d’accès dans l’ordre suivant :

  • EnvironmentCredential
    • Active l’authentification avec Microsoft Entra ID à l’aide du client et du secret, ou du nom d’utilisateur et du mot de passe, des détails configurés dans les variables d’environnement suivantes : AZURE_TENANT_ID, AZURE_CLIENT_ID, AZURE_CLIENT_SECRET, AZURE_CLIENT_CERTIFICATE_PATH, AZURE_USERNAME, AZURE_PASSWORD (Plus d’informations)
  • ManagedIdentityCredential
    • Tente l’authentification avec Microsoft Entra ID à l’aide d’une identité managée qui a été affectée à l’environnement de déploiement. L’« ID client » d’une « identité managée affectée par l’utilisateur » est lu à partir de la propriété de connexion « Identifiant utilisateur ».
  • SharedTokenCacheCredential
    • Procède à l’authentification à l’aide de jetons dans le cache local partagé entre les applications Microsoft.
  • VisualStudioCredential
    • Assure l’authentification avec Microsoft Entra ID à l’aide de données provenant de Visual Studio
  • VisualStudioCodeCredential
    • Active l’authentification avec Microsoft Entra ID à l’aide de données de Visual Studio Code.
  • AzureCliCredential
    • Active l’authentification avec Microsoft Entra ID à l’aide d’Azure CLI pour obtenir un jeton d’accès.

InteractiveBrowserCredential est désactivé dans l’implémentation de pilote « Active Directory par défaut » et « Active Directory interactive » est la seule option disponible pour acquérir un jeton à l’aide de l’authentification MFA/interactive.*

Aucune autre option de personnalisation n’est disponible pour le moment.

Améliorations apportées à l’inscription du fournisseur de magasin de clés principales personnalisé

Microsoft.Data.SqlClient offre désormais davantage de contrôle sur l’emplacement d’accès des fournisseurs de magasins de clés principales dans une application pour mieux prendre en charge les applications multilocataires et leur utilisation du chiffrement/déchiffrement de colonne. Les API suivantes sont introduites pour permettre l’inscription de fournisseurs de magasins de clés principales personnalisés sur des instances de SqlConnection et SqlCommand :

public class SqlConnection
{
    public void RegisterColumnEncryptionKeyStoreProvidersOnConnection(IDictionary<string, SqlColumnEncryptionKeyStoreProvider> customProviders)
}
public class SqlCommand 
{
    public void RegisterColumnEncryptionKeyStoreProvidersOnCommand(IDictionary<string, SqlColumnEncryptionKeyStoreProvider> customProviders)
}

L’API statique sur SqlConnection, autrement dit SqlConnection.RegisterColumnEncryptionKeyStoreProviders pour inscrire globalement des fournisseurs de magasins de clés principales personnalisés, continue à être prise en charge. Le cache de clés de chiffrement de colonne géré globalement s’applique uniquement aux fournisseurs inscrits globalement.

Priorité d’inscription des fournisseurs de magasins de clés principales de colonne

Les fournisseurs de magasins de clés principales de colonne intégrés qui sont disponibles pour le magasin de certificats Windows, le magasin CNG et CSP sont préinscrits. Aucun fournisseur ne doit être inscrit sur l’instance de connexion ni de commande si l’un des fournisseurs de magasins de clés principales de colonne intégrés est nécessaire.

Les fournisseurs de magasins de clés principales personnalisés peuvent être inscrits auprès du pilote dans trois couches différentes. Le niveau global est tel qu’il est actuellement. Les nouvelles inscriptions de niveau par connexion et par commande sont initialement vides et peuvent être définies plusieurs fois.

La priorité des trois inscriptions est la suivante :

  • L’inscription par commande est vérifiée si elle n’est pas vide.
  • Si l’inscription par commande est vide, l’inscription par connexion est vérifiée si elle n’est pas vide.
  • Si l’inscription par connexion est vide, l’inscription globale est vérifiée.

Une fois qu’un fournisseur de magasin de clés a été trouvé au niveau d’une inscription, le pilote ne revient PAS aux autres inscriptions pour rechercher un fournisseur. Si des fournisseurs sont inscrits, mais que le fournisseur approprié est introuvable à un niveau, une exception est levée. Elle ne contient que les fournisseurs inscrits dans l’inscription vérifiée.

Priorité du cache de clés de chiffrement de colonne

Le pilote ne met pas en cache les clés de chiffrement de colonne des fournisseurs de magasins de clés personnalisés inscrits à l’aide des nouvelles API au niveau de l’instance. Les fournisseurs de magasins de clés doivent implémenter leur propre cache pour améliorer les performances. Le pilote désactive le cache local de clés de chiffrement de colonne implémenté par les fournisseurs de magasins de clés personnalisés si l’instance de fournisseur est inscrite dans le pilote au niveau global.

Une nouvelle API a également été introduite dans la classe de base SqlColumnEncryptionKeyStoreProvider pour définir la durée de vie du cache :

public abstract class SqlColumnEncryptionKeyStoreProvider
{
    // The default value of Column Encryption Key Cache Time to Live is 0.
    // Provider's local cache is disabled for globally registered providers.
    // Custom key store provider implementation must include column encryption key cache to provide caching support to locally registered providers.
    public virtual TimeSpan? ColumnEncryptionKeyCacheTtl { get; set; } = new TimeSpan(0);
}

Préférence d’adresse IP

Une nouvelle propriété de connexion IPAddressPreference est introduite pour spécifier la préférence de la famille d’adresses IP pour le pilote lors de l’établissement de connexions TCP. Si Transparent Network IP Resolution (dans .NET Framework) ou Multi Subnet Failover a la valeur true, ce paramètre n’a aucun effet. Voici les trois valeurs acceptées pour cette propriété :

  • IPv4First

    • Il s’agit de la valeur par défaut. Le pilote utilise d’abord les adresses IPv4 résolues. S’il est impossible de se connecter à aucune d’entre elles, il tente les adresses IPv6 résolues.
  • IPv6First

    • Le pilote utilise d’abord les adresses IPv6 résolues. S’il est impossible de se connecter à aucune d’entre elles, il tente les adresses IPv4 résolues.
  • UsePlatformDefault

    • Le pilote essaie les adresses IP dans l’ordre de réception de la réponse de résolution DNS.

Prise en charge de la plateforme cible 3.0

  • .NET Framework 4.6.1+ (Windows x86, Windows x64)
  • .NET Core 2.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Notes de publication de Microsoft.Data.SqlClient 2.1

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 2.1.

Nouvelles fonctionnalités de la version 2.1

Support multiplateforme pour Always Encrypted

Microsoft.Data.SqlClient v2.1 étend le support d’Always Encrypted sur les plateformes suivantes :

Support Always Encrypted Support Always Encrypted avec enclave sécurisée Framework cible Version Microsoft.Data.SqlClient Système d’exploitation
Oui Oui .NET Framework 4.6+ 1.1.0+ Windows
Oui Oui .NET Core 2.1+ 2.1.0+1 Windows, Linux, macOS
Oui Non 2 .NET Standard 2.0 2.1.0+ Windows, Linux, macOS
Oui Oui .NET Standard 2.1+ 2.1.0+ Windows, Linux, macOS

Notes

1 Avant Microsoft.Data.SqlClient version v2.1, Always Encrypted est pris en charge uniquement sur Windows. 2 Always Encrypted avec enclaves sécurisés n’est pas pris en charge sur .NET Standard 2.0.

Authentification à l’aide du flux de code d’appareil Microsoft Entra

Microsoft.Data.SqlClient v2.1 fournit le support de l’authentification « Flux de code d’appareil » avec MSAL.NET. Documentation de référence : Flux de l’octroi de l’autorisation d’appareil OAuth2.0

Exemple de chaîne de connexion :

Server=<server>.database.windows.net; Authentication=Active Directory Device Code Flow; Database=Northwind;Encrypt=True

L’API suivante permet la personnalisation du mécanisme de rappel du flux de code de l’appareil :

public class ActiveDirectoryAuthenticationProvider
{
    // For .NET Framework, .NET Core and .NET Standard targeted applications
    public void SetDeviceCodeFlowCallback(Func<DeviceCodeResult, Task> deviceCodeFlowCallbackMethod)
}

Authentification à l’aide d’une identité managée Microsoft Entra

Microsoft.Data.SqlClient v2.1 introduit la prise en charge de l’authentification Microsoft Entra à l’aide des identités managées.

Les mots clé d’authentification suivants sont pris en charge :

  • Identité managée Active Directory
  • Active Directory MSI (pour la compatibilité des pilotes inter MS SQL)

Exemples de chaînes de connexion :

// For System Assigned Managed Identity
"Server={serverURL}; Authentication=Active Directory MSI; Encrypt=True; Initial Catalog={db};"

// For System Assigned Managed Identity
"Server={serverURL}; Authentication=Active Directory Managed Identity; Initial Catalog={db};"

// For User Assigned Managed Identity
"Server={serverURL}; Authentication=Active Directory MSI; Encrypt=True; User Id={ObjectIdOfManagedIdentity}; Initial Catalog={db};"

// For User Assigned Managed Identity
"Server={serverURL}; Authentication=Active Directory Managed Identity; Encrypt=True; User Id={ObjectIdOfManagedIdentity}; Initial Catalog={db};"

Améliorations concernant l’authentification interactive Microsoft Entra

Microsoft.Data.SqlClient v2.1 ajoute les API suivantes pour personnaliser l’expérience d’authentification Microsoft Entra interactive :

public class ActiveDirectoryAuthenticationProvider
{
    // For .NET Framework targeted applications only
    public void SetIWin32WindowFunc(Func<IWin32Window> iWin32WindowFunc);

    // For .NET Standard targeted applications only
    public void SetParentActivityOrWindowFunc(Func<object> parentActivityOrWindowFunc);

    // For .NET Framework, .NET Core and .NET Standard targeted applications
    public void SetAcquireAuthorizationCodeAsyncCallback(Func<Uri, Uri, CancellationToken, Task<Uri>> acquireAuthorizationCodeAsyncCallback);

    // For .NET Framework, .NET Core and .NET Standard targeted applications
    public void ClearUserTokenCache();
}

section de configuration SqlClientAuthenticationProviders

Microsoft.Data.SqlClient v2.1 introduit une nouvelle section de configuration, SqlClientAuthenticationProviders (un clone du SqlAuthenticationProviders existant). La section de configuration existante, SqlAuthenticationProviders, est toujours prise en charge à des fins de compatibilité descendante lorsque le type approprié est défini.

La nouvelle section permet aux fichiers config d’application de contenir à la fois une section SqlAuthenticationProviders pour System.Data.SqlClient et une section SqlClientAuthenticationProviders pour Microsoft.Data.SqlClient.

Authentification Microsoft Entra à l’aide d’un ID client d’application

Microsoft.Data.SqlClient v2.1 introduit le support de la transmission d’un ID client d’application définie par l’utilisateur à la bibliothèque d’authentification Microsoft. L’ID client d’application est utilisé lors de l’authentification avec Microsoft Entra ID.

Les nouvelles API suivantes sont introduites :

  1. Un nouveau constructeur a été introduit dans ActiveDirectoryAuthenticationProvider:\
    [S’applique à toutes les plateformes .NET (.NET Framework, .NET Core et .NET Standard)]

    public ActiveDirectoryAuthenticationProvider(string applicationClientId)
    

    Usage :

    string APP_CLIENT_ID = "<GUID>";
    SqlAuthenticationProvider customAuthProvider = new ActiveDirectoryAuthenticationProvider(APP_CLIENT_ID);
    SqlAuthenticationProvider.SetProvider(SqlAuthenticationMethod.ActiveDirectoryInteractive, customAuthProvider);
    
    using (SqlConnection sqlConnection = new SqlConnection("<connection_string>")
    {
        sqlConnection.Open();
    }
    
  2. Une nouvelle propriété de configuration a été introduite sous SqlAuthenticationProviderConfigurationSection et SqlClientAuthenticationProviderConfigurationSection:\
    [S’applique à .NET Framework et .NET Core]

    internal class SqlAuthenticationProviderConfigurationSection : ConfigurationSection
    {
        ...
        [ConfigurationProperty("applicationClientId", IsRequired = false)]
        public string ApplicationClientId => this["applicationClientId"] as string;
    }
    
    // Inheritance
    internal class SqlClientAuthenticationProviderConfigurationSection : SqlAuthenticationProviderConfigurationSection
    { ... }
    

    Usage :

    <configuration>
        <configSections>
            <section name="SqlClientAuthenticationProviders"
                             type="Microsoft.Data.SqlClient.SqlClientAuthenticationProviderConfigurationSection, Microsoft.Data.SqlClient" />
        </configSections>
        <SqlClientAuthenticationProviders applicationClientId ="<GUID>" />
    </configuration>
    
    <!--or-->
    
    <configuration>
        <configSections>
            <section name="SqlAuthenticationProviders"
                             type="Microsoft.Data.SqlClient.SqlAuthenticationProviderConfigurationSection, Microsoft.Data.SqlClient" />
        </configSections>
        <SqlAuthenticationProviders applicationClientId ="<GUID>" />
    </configuration>
    

Support de la classification des données v2

Microsoft.Data.SqlClient v2.1 introduit le support des informations de « classement de la sensibilité » de la classification des données. Les nouvelles API suivantes sont maintenant disponibles :

public class SensitivityClassification
{
    public SensitivityRank SensitivityRank;
}

public class SensitivityProperty
{
    public SensitivityRank SensitivityRank;
}

public enum SensitivityRank
{
    NOT_DEFINED = -1,
    NONE = 0,
    LOW = 10,
    MEDIUM = 20,
    HIGH = 30,
    CRITICAL = 40
}

ID de processus serveur pour un actif SqlConnection

MicrosoftData. SqlClient v2.1 introduit une nouvelle propriété SqlConnection, ServerProcessId, sur une connexion active.

public class SqlConnection
{
    // Returns the server process Id (SPID) of the active connection.
    public int ServerProcessId;
}

Support du suivi des traces dans Native SNI

Microsoft.Data.SqlClient v2.1 étend l’implémentation SqlClientEventSource existante pour activer le suivi d’événements dans SNI.dll. Les événements doivent être capturés à l’aide d’un outil tel que Xperf.

Pour activer le suivi, envoyez une commande à SqlClientEventSource :

// Enables trace events:
EventSource.SendCommand(eventSource, (EventCommand)8192, null);

// Enables flow events:
EventSource.SendCommand(eventSource, (EventCommand)16384, null);

// Enables both trace and flow events:
EventSource.SendCommand(eventSource, (EventCommand)(8192 | 16384), null);

Propriété de chaîne de connexion « Délai d’attente de la commande »

Microsoft.Data.SqlClient v2.1 introduit la propriété de chaîne de connexion « Délai d’attente de la commande » pour remplacer la valeur par défaut de 30 secondes. Le délai d’attente pour les commandes individuelles peut être substitué à l’aide de la propriété CommandTimeout sur SqlCommand.

Exemples de chaînes de connexion :

"Server={serverURL}; Initial Catalog={db}; Encrypt=True; Integrated Security=true; Command Timeout=60"

Suppression de symboles de Native SNI

Avec Microsoft.Data.SqlClient v2.1, nous avons supprimé les symboles introduits dans v2.0.0 de Microsoft.Data.SqlClient.SNI. Runtime NuGet à partir de v2.1.1. Les symboles publics sont désormais publiés sur le serveur de symboles Microsoft pour les outils tels que BinSkim qui requièrent l’accès aux symboles publics.

Liaison à la source des symboles Microsoft.Data.SqlClient

À compter de Microsoft.Data.SqlClient v2.1, les symboles Microsoft.Data.SqlClient sont liés à la source et publiés sur le serveur de symboles Microsoft pour une expérience de débogage améliorée sans avoir besoin de télécharger le code source.

Prise en charge de la plateforme cible 2.1

  • .NET Framework 4.6+ (Windows x86, Windows x64)
  • .NET Core 2.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Notes de publication de Microsoft.Data.SqlClient 2.0

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 2.0.

Changements cassants dans la version 2.0

  • Le modificateur d’accès de l’interface du fournisseur d’enclave SqlColumnEncryptionEnclaveProvider (public) a été remplacé par internal.
  • Les constantes de la classe SqlClientMetaDataCollectionNames ont été mises à jour pour refléter les modifications apportées à SQL Server.
  • Le pilote effectue maintenant une validation du certificat de serveur lorsque le serveur SQL Server cible applique le chiffrement TLS (comportement par défaut pour les connexions Azure).
  • SqlDataReader.GetSchemaTable() retourne maintenant une DataTable vide à la place de null.
  • Le pilote effectue maintenant un arrondi d’échelle décimale, calqué sur le comportement de SQL Server. À des fins de compatibilité descendante, le comportement de troncation précédent peut être activé à l’aide d’un commutateur AppContext.
  • Dans le cas des applications .NET Framework qui consomment Microsoft.Data.SqlClient, les fichiers SNI.dll, auparavant téléchargés dans les dossiers bin\x64 et bin\x86, sont maintenant nommés Microsoft.Data.SqlClient.SNI.x64.dll et Microsoft.Data.SqlClient.SNI.x86.dll, et téléchargés dans le répertoire bin.
  • À des fins de cohérence, de nouveaux synonymes des propriétés de chaîne de connexion remplacent les anciennes propriétés lors de l’extraction de la chaîne de connexion auprès de SqlConnectionStringBuilder. En savoir plus

Nouvelles fonctionnalités de la version 2.0

Ont été introduites dans Microsoft.Data.SqlClient 2.0 les nouvelles fonctionnalités suivantes.

Résilience des échecs DNS

Le pilote met maintenant en cache les adresses IP issues de toutes les connexions réussies dans un point de terminaison SQL Server qui prend en charge la fonctionnalité. En cas d’échec de la résolution DNS lors d’une tentative de connexion, il s’efforce d’établir une connexion à l’aide d’une adresse IP en cache, s’il en existe une pour ce serveur.

Suivi EventSource

Cette version introduit la prise en charge de la capture des journaux de suivi d’événements pour les applications de débogage. Pour capturer ces événements, les applications clientes doivent les détecter dans l’implémentation EventSource de SqlClient :

Microsoft.Data.SqlClient.EventSource

Pour plus d’informations, consultez Guide pratique pour activer le suivi d’événements dans SqlClient.

Activation de la mise en réseau gérée sur Windows

Un nouveau commutateur AppContext, « Switch.Microsoft.Data.SqlClient.UseManagedNetworkingOnWindows » , permet d’utiliser une implémentation SNI managée sur Windows à des fins de test et de débogage. Il modifie le comportement du pilote de façon à utiliser une indication SNI gérée dans les projets .NET Core 2.1 (et versions ultérieures) et .NET Standard 2.0 (et versions ultérieures) sur Windows, éliminant ainsi toutes les dépendances de la bibliothèque Microsoft.Data.SqlClient vis-à-vis de bibliothèques natives.

AppContext.SetSwitch("Switch.Microsoft.Data.SqlClient.UseManagedNetworkingOnWindows", true);

Pour obtenir la liste complète des commutateurs disponibles dans le pilote, consultez Commutateurs AppContext dans SqlClient.

Activation du comportement de troncation décimale

Tout comme SQL Server, le pilote arrondit par défaut l’échelle de données décimale. À des fins de compatibilité descendante, vous pouvez définir le commutateur AppContext Switch.Microsoft.Data.SqlClient.TruncateScaledDecimal sur true.

AppContext.SetSwitch("Switch.Microsoft.Data.SqlClient.TruncateScaledDecimal", true);

Nouveaux synonymes des propriétés de chaîne de connexion

De nouveaux synonymes ont été ajoutés pour les propriétés de chaîne de connexion existantes suivantes afin d’éviter toute confusion liée à l’espacement entre les propriétés comportant plusieurs mots. Les anciens noms de propriétés restent pris en charge à des fins de compatibilité descendante. Toutefois, les nouvelles propriétés de chaîne de connexion sont désormais incluses lors de l’extraction de la chaîne de connexion auprès de SqlConnectionStringBuilder.

Propriété de chaîne de connexion existante Nouveau synonyme
ApplicationIntent Intention de l'application
ConnectRetryCount Nombre de nouvelles tentatives de connexion
ConnectRetryInterval Intervalle avant nouvelle tentative de connexion
PoolBlockingPeriod Période de blocage du pool
MultipleActiveResultSets Jeux MARS (Multiple Active Result Set)
MultiSubnetFailover Basculement de plusieurs sous-réseaux
TransparentNetworkIPResolution Résolution transparente d’adresses IP réseau
TrustServerCertificate Faire confiance au certificat de serveur

Propriété SqlBulkCopy RowsCopied

La propriété RowsCopied fournit un accès en lecture seule au nombre de lignes traitées dans l’opération de copie en bloc en cours. Cette valeur n’est pas nécessairement égale au nombre final de lignes ajoutées à la table de destination.

Remplacement de Connection.Open

Le comportement par défaut de SqlConnection.Open() peut être écrasé pour désactiver le délai de dix secondes et les tentatives de connexion automatiques déclenchées par des erreurs temporaires.

using SqlConnection sqlConnection = new SqlConnection("Data Source=(local);Integrated Security=true;Initial Catalog=AdventureWorks;");
sqlConnection.Open(SqlConnectionOverrides.OpenWithoutRetry);

Notes

Notez que ce remplacement ne s’applique qu’à SqlConnection.Open() et non à SqlConnection.OpenAsync().

Prise en charge du nom d’utilisateur pour le mode interactif Active Directory

Un nom d’utilisateur peut être spécifié dans la chaîne de connexion avec le mode d’authentification interactive Microsoft Entra pour .NET Framework et .NET Core.

Définissez un nom d’utilisateur à l’aide de la propriété de chaîne de connexion User ID ou UID :

"Server=<server name>; Database=<db name>; Authentication=Active Directory Interactive; User Id=<username>;Encrypt=True;"

Indicateurs d’ordre pour SqlBulkCopy

Des indicateurs d’ordre peuvent être spécifiés pour améliorer les performances des opérations de copie en bloc sur les tables avec index cluster. Pour plus d’informations, consultez la section Opérations de copie en bloc.

Modification des dépendances SNI

Microsoft.Data.SqlClient (.NET Core et .NET Standard) sur Windows dépend maintenant de Microsoft.Data.SqlClient.SNI.runtime, et non plus de runtime.native.System.Data.SqlClient.SNI. La nouvelle dépendance ajoute la prise en charge de la plateforme ARM à celle des plateformes déjà prises en charge (ARM64, x64 et x86) sur Windows.

Prise en charge de la plateforme cible 2.0

  • .NET Framework 4.6+ (Windows x86, Windows x64)
  • .NET Core 2.1+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Windows ARM64, Windows ARM, Linux, macOS)

Notes de publication de Microsoft.Data.SqlPackage 1.1.0

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 1.1.

Nouvelles fonctionnalités de la version 1.1

Always Encrypted avec enclaves sécurisées

Always Encrypted est disponible à partir de Microsoft SQL Server 2016. Les enclaves sécurisées sont disponibles à partir de Microsoft SQL Server 2019. La fonctionnalité d’enclave ne peut être utilisée que si les chaînes de connexion incluent le protocole d’attestation et l’URL d’attestation requis. Par exemple :

"Attestation Protocol=HGS;Enclave Attestation Url=<attestation_url_for_HGS>"

Pour plus d'informations, consultez les pages suivantes :

Prise en charge de la plateforme cible 1.1

  • .NET Framework 4.6+ (Windows x86, Windows x64)
  • .NET Core 2.1+ (Windows x86, Windows x64, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Linux, macOS)

Notes de publication pour Microsoft.Data.SqlPackage 1.0

La version initiale de l’espace de noms Microsoft.Data.SqlClient offre plus de fonctionnalités que l’espace de noms System.Data.SqlClient existant.

Les notes de publication complètes, y compris les dépendances, sont disponibles dans le dépôt GitHub : Notes de publication 1.0.

Nouvelles fonctionnalités de la version 1.0

Nouvelles fonctionnalités de .NET Framework 4.7.2 System.Data.SqlClient

  • Classification des données : disponible dans Azure SQL Database et Microsoft SQL Server 2019.

  • Support UTF-8 : disponible dans Microsoft SQL Server 2019.

Nouvelles fonctionnalités de .NET Core 2.2 System.Data.SqlClient

  • Classification des données : disponible dans Azure SQL Database et Microsoft SQL Server 2019.

  • Support UTF-8 : disponible dans Microsoft SQL Server 2019.

  • Authentification : mode d’authentification du mot de passe Active Directory.

Classification des données

La classification des données apporte un nouvel ensemble d’API exposant la sensibilité des données en lecture seule et des informations de classification sur les objets récupérés par le biais de SqlDataReader lorsque la source sous-jacente prend en charge la fonctionnalité et contient des métadonnées sur la sensibilité et la classification des données. Consultez l’exemple d’application dans Découverte et classification des données dans SqlClient.

public class SqlDataReader
{
    public Microsoft.Data.SqlClient.DataClassification.SensitivityClassification SensitivityClassification
}

namespace Microsoft.Data.SqlClient.DataClassification
{
    public class ColumnSensitivity
    {
        public System.Collections.ObjectModel.ReadOnlyCollection<Microsoft.Data.SqlClient.DataClassification.SensitivityProperty> SensitivityProperties
    }
    public class InformationType
    {
        public string Id
        public string Name
    }
    public class Label
    {
        public string Id
        public string Name
    }
    public class SensitivityClassification
    {
        public System.Collections.ObjectModel.ReadOnlyCollection<Microsoft.Data.SqlClient.DataClassification.ColumnSensitivity> ColumnSensitivities
        public System.Collections.ObjectModel.ReadOnlyCollection<Microsoft.Data.SqlClient.DataClassification.InformationType> InformationTypes
        public System.Collections.ObjectModel.ReadOnlyCollection<Microsoft.Data.SqlClient.DataClassification.Label> Labels
    }
    public class SensitivityProperty
    {
        public Microsoft.Data.SqlClient.DataClassification.InformationType InformationType
        public Microsoft.Data.SqlClient.DataClassification.Label Label
    }
}

Prise en charge d’UTF-8

La prise en charge d’UTF-8 ne nécessite aucun changement du code de l’application. Ces modifications SqlClient optimisent la communication client-serveur lorsque le serveur prend en charge l’encodage UTF-8 et que le classement de la colonne sous-jacente est en UTF-8. Consultez la section UTF-8 sous Nouveautés de SQL Server 2019.

Always Encrypted avec enclaves sécurisées

En général, la documentation existante qui utilise System.Data.SqlClient sur .NET Framework et les fournisseurs de magasin de clés principales de colonne intégrés doivent désormais fonctionner également avec .NET Core.

Développer à l’aide d’Always Encrypted avec le fournisseur de données .NET Framework

Always Encrypted : Protéger les données sensibles et stocker les clés de chiffrement dans le magasin de certificats Windows

Authentification

Vous pouvez spécifier différents modes d’authentification à l’aide de l’option de chaîne de connexion Authentification. Pour plus d’informations, consultez la documentation de SqlAuthenticationMethod.

Notes

Les fournisseurs de magasins de clés personnalisés, comme le fournisseur d’Azure Key Vault, devront être mis à jour pour prendre en charge Microsoft.Data.SqlClient. De même, les fournisseurs d’enclaves devront également être mis à jour pour prendre en charge Microsoft.Data.SqlClient. Always Encrypted est pris en charge uniquement sur les cibles .NET Framework et .NET Core. Il n’est pas pris en charge sur .NET Standard dans la mesure où certaines dépendances de chiffrement manquent dans .NET Standard.

Prise en charge de la plateforme cible 1.0

  • .NET Framework 4.6+ (Windows x86, Windows x64)
  • .NET Core 2.1+ (Windows x86, Windows x64, Linux, macOS)
  • .NET Standard 2.0+ (Windows x86, Windows x64, Linux, macOS)