Conectar-se ao SQL do Azure com a autenticação Microsoft Entra e o SqlClient

Aplicável a: .NET Framework .NET .NET Standard

Baixar ADO.NET

Este artigo descreve como se conectar a fontes de dados do SQL do Azure usando a autenticação do Microsoft Entra em um aplicativo .NET com o SqlClient.

Observação

Embora o Microsoft Entra ID seja o novo nome do Azure Active Directory (Azure AD), para evitar a interrupção de ambientes existentes, o Azure AD ainda permanecerá em alguns elementos codificados, como campos de interface do usuário, provedores de conexão, códigos de erro e cmdlets. Neste artigo, os dois nomes são intercambiáveis.

Visão geral

A autenticação do Microsoft Entra usa identidades no Microsoft Entra ID para acessar fontes de dados do SQL do Azure, como o Banco de Dados SQL do Azure, a Instância Gerenciada de SQL do Azure e o Azure Synapse Analytics. O namespace Microsoft.Data.SqlClient permite que aplicativos cliente especifiquem as credenciais do Microsoft Entra em diferentes modos de autenticação quando estão se conectando à instância gerenciada de SQL do Azure. Para usar a autenticação Microsoft Entra com SQL do Azure, é necessário configurar e gerenciar a autenticação Microsoft Entra com SQL do Azure.

Quando você define a propriedade de conexão Authentication na cadeia de conexão, o cliente pode escolher um modo de autenticação preferencial do Microsoft Entra de acordo com o valor fornecido:

  • A versão mais antiga do Microsoft.Data.SqlClient dá suporte a Active Directory Password para o .NET Framework, .NET Core e .NET Standard. Ela também dá suporte à autenticação Active Directory Integrated e Active Directory Interactive para o .NET Framework.

  • A partir do Microsoft.Data.SqlClient 2.0.0, o suporte à autenticação Active Directory Integrated e Active Directory Interactive foi estendido para o .NET Framework, .NET Core e .NET Standard.

    Um novo modo de autenticação Active Directory Service Principal também foi adicionado no SqlClient 2.0.0. Ele usa a ID do cliente e o segredo de uma identidade de entidade de serviço para realizar a autenticação.

  • Mais modos de autenticação foram adicionados no Microsoft.Data.SqlClient 2.1.0, incluindo Active Directory Device Code Flow e Active Directory Managed Identity (também conhecido como Active Directory MSI). Esses novos modos permitem que o aplicativo adquira um token de acesso para se conectar ao servidor.

Para obter informações sobre a autenticação do Microsoft Entra além do que as seções a seguir descrevem, consulte Usar a autenticação do Microsoft Entra.

Configuração da autenticação do Microsoft Entra

Quando o aplicativo está se conectando a fontes de dados do SQL do Azure usando a autenticação do Microsoft Entra, ele precisa fornecer um modo de autenticação válido. A tabela a seguir lista os modos de autenticação com suporte. O aplicativo especifica um modo usando a propriedade de conexão Authentication na cadeia de conexão.

Valor Descrição Versão do Microsoft.Data.SqlClient
Senha do Active Directory Autenticar com o nome de usuário e a senha de uma identidade do Microsoft Entra 1.0+
Integrado ao Active Directory Autenticar com a identidade do Microsoft Entra usando a Autenticação Integrada do Windows (IWA) 2.0.0+1
Interativa do Active Directory Autentique com a identidade do Microsoft Entra usando a autenticação interativa 2.0.0+1
Entidade de serviço do Active Directory Autenticar com uma entidade de serviço do Microsoft Entra, usando seu ID de cliente e segredo 2.0.0+
Fluxo de código de dispositivo do Active Directory Autentique com uma identidade do Microsoft Entra usando o modo de Fluxo de código de dispositivo 2.1.0+
Identidade gerenciada do Active Directory,
MSI do Active Directory
Autentique-se usando uma identidade gerenciada atribuída pelo sistema ou atribuída pelo usuário do Microsoft Entra. 2.1.0+
Active Directory Padrão Execute uma autenticação com uma identidade do Microsoft Entra usando mecanismos sem senha e não interativos, incluindo: Identidades Gerenciadas, o Visual Studio Code, o Visual Studio, a CLI do Azure etc. 3.0.0+
Identidade de carga de trabalho do Active Directory Autentique-se com uma identidade do Microsoft Entra usando uma Identidade Gerenciada Atribuída pelo Usuário federada para se conectar ao Banco de Dados SQL a partir de ambientes de cliente do Azure que habilitaram o suporte para a Identidade de Carga de Trabalho. 5.2.0+

1 Antes do Microsoft.Data.SqlClient 2.0.0, os modos de autenticação Active Directory Integrated e Active Directory Interactive eram compatíveis somente com o .NET Framework.

Usando autenticação de senha

O modo de autenticação Active Directory Password dá suporte à autenticação para fontes de dados do Azure com o Microsoft Entra ID para usuários nativos ou federados do Microsoft Entra. Quando você estiver usando esse modo, as credenciais do usuário deverão ser fornecidas na cadeia de conexão. O exemplo a seguir mostra como usar a autenticação Active Directory Password.

// Use your own server, database, user ID, and password.
string ConnectionString = @"Server=demo.database.windows.net; Authentication=Active Directory Password; Encrypt=True; Database=testdb; User Id=user@domain.com; Password=***";

using (SqlConnection conn = new SqlConnection(ConnectionString)) {
    conn.Open();
}

Como usar a autenticação integrada

Para usar o modo de autenticação Active Directory Integrated, você deve ter uma instância do Active Directory local que tenha ingressado no Microsoft Entra ID na nuvem. Você pode federar usando os AD FS (Serviços de Federação do Active Directory), por exemplo.

Com esse modo, quando você estiver conectado a um computador conectado ao domínio, poderá acessar as fontes de dados do SQL do Azure sem que as credenciais sejam solicitadas. Não é possível especificar o nome de usuário e a senha na cadeia de conexão para aplicativos .NET Framework. Nos aplicativos .NET Core e .NET Standard, o nome de usuário é opcional na cadeia de conexão. Não é possível definir a propriedade Credential de SqlConnection nesse modo.

O snippet de código a seguir é um exemplo de quando a autenticação Active Directory Integrated está em uso.

// Use your own server and database.
string ConnectionString1 = @"Server=demo.database.windows.net; Authentication=Active Directory Integrated; Encrypt=True; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString1)) {
    conn.Open();
}

// User ID is optional for .NET Core and .NET Standard.
string ConnectionString2 = @"Server=demo.database.windows.net; Authentication=Active Directory Integrated; Encrypt=True; Database=testdb; User Id=user@domain.com";

using (SqlConnection conn = new SqlConnection(ConnectionString2)) {
    conn.Open();
}

Usando a autenticação interativa

A autenticação Active Directory Interactive dá suporte à tecnologia de autenticação multifator para se conectar a fontes de dados do SQL do Azure. Se você fornecer esse modo de autenticação na cadeia de conexão, uma tela de autenticação do Azure será exibida e solicitará que o usuário insira credenciais válidas. Não é possível especificar a senha na cadeia de conexão.

Não é possível definir a propriedade Credential de SqlConnection nesse modo. Com o Microsoft.Data.SqlClient 2.0.0 e posterior, é possível usar o nome de usuário na cadeia de conexão quando se está no modo interativo.

O exemplo a seguir mostra como usar a autenticação Active Directory Interactive.

// Use your own server, database, and user ID.
// User ID is optional.
string ConnectionString1 = @"Server=demo.database.windows.net; Authentication=Active Directory Interactive; Encrypt=True; Database=testdb; User Id=user@domain.com";

using (SqlConnection conn = new SqlConnection(ConnectionString1)) {
    conn.Open();
}

// User ID is not provided.
string ConnectionString2 = @"Server=demo.database.windows.net; Authentication=Active Directory Interactive; Encrypt=True; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString2)) {
    conn.Open();
}

Usar a autenticação de entidade de serviço

No modo de autenticação Active Directory Service Principal, o aplicativo cliente pode se conectar a fontes de dados do SQL do Azure fornecendo a ID do cliente e o segredo de uma identidade de entidade de serviço. A autenticação de entidade de serviço envolve:

  1. Configuração de um registro de aplicativo com um segredo.
  2. Concessão de permissões para o aplicativo na instância do Banco de Dados SQL do Azure.
  3. Conexão com a credencial correta.

O exemplo a seguir mostra como usar a autenticação Active Directory Service Principal.

// Use your own server, database, app ID, and secret.
string ConnectionString = @"Server=demo.database.windows.net; Authentication=Active Directory Service Principal; Encrypt=True; Database=testdb; User Id=AppId; Password=secret";

using (SqlConnection conn = new SqlConnection(ConnectionString)) {
    conn.Open();
}

Usar a autenticação de Fluxo de código do dispositivo

Com a MSAL.NET (Biblioteca de Autenticação da Microsoft para .NET), a autenticação Active Directory Device Code Flow permite que o aplicativo cliente se conecte a fontes de dados do SQL do Azure em dispositivos e sistemas operacionais que não têm um navegador da Web interativo. A autenticação interativa será executada em outro dispositivo. Para saber mais sobre a autenticação de fluxo de código de dispositivo, confira Fluxo de código do dispositivo OAuth 2.0.

Quando esse modo estiver em uso, não será possível definir a propriedade Credential de SqlConnection. Além disso, o nome de usuário e a senha não devem ser especificados na cadeia de conexão.

O trecho de código a seguir é um exemplo de uso da autenticação Active Directory Device Code Flow.

Observação

O tempo limite para Active Directory Device Code Flow é padrão para a configuração de Connect Timeout conexão. Especifique um Connect Timeout que forneça tempo suficiente para percorrer o processo de autenticação de fluxo de código do dispositivo.

// Use your own server and database and increase Connect Timeout as needed for device code flow.
string ConnectionString = @"Server=demo.database.windows.net; Authentication=Active Directory Device Code Flow; Encrypt=True; Database=testdb; Connect Timeout=180;";

using (SqlConnection conn = new SqlConnection(ConnectionString)) {
    conn.Open();
}

Usar autenticação de identidade gerenciada

A autenticação com identidades gerenciadas para recursos do Azure é o método de autenticação recomendado para acesso programático ao SQL. Um aplicativo cliente pode usar a identidade gerenciada atribuída pelo usuário ou pelo sistema de um recurso para autenticar no SQL com o Microsoft Entra ID, fornecendo a identidade e usando-a para obter tokens de acesso. Esse método elimina a necessidade de gerenciar credenciais e segredos e pode simplificar o gerenciamento do acesso.

Há dois tipos de identidades gerenciadas:

  • A identidade gerenciada atribuída pelo sistema é criada como parte de um recurso do Azure (como sua instância gerenciada de SQL ou o servidor lógico) e compartilha o ciclo de vida desse recurso. As identidades atribuídas pelo sistema só podem ser associadas a um único recurso do Azure.
  • Uma identidade gerenciada atribuída pelo usuário é criada como um recurso autônomo do Azure. Ela pode ser atribuída a uma ou mais instâncias de um serviço do Azure.

Para saber mais sobre identidades gerenciadas, confira Sobre as identidades gerenciadas para recursos do Azure.

Desde o Microsoft.Data.SqlClient 2.1.0, o driver dá suporte à autenticação para o Banco de Dados SQL do Azure, o Azure Synapse Analytics e a Instância Gerenciada de SQL do Azure adquirindo tokens de acesso por meio de identidade gerenciada. Para usar essa autenticação, especifique Active Directory Managed Identity ou Active Directory MSI na cadeia de conexão; nenhuma senha será necessária. Também não é possível definir a propriedade Credential de SqlConnection nesse modo.

Para usar uma identidade gerenciada atribuída pelo usuário, será preciso obter a ID do cliente da identidade gerenciada ao usar o Microsoft.Data.SqlClient v3.0 ou posterior. Caso esteja usando o Microsoft.Data.SqlClient v2.1, será preciso obter a ID de objeto da identidade gerenciada.

O exemplo a seguir mostra como usar a autenticação Active Directory Managed Identity com uma identidade gerenciada atribuída pelo sistema.

// For system-assigned managed identity
// Use your own values for Server and Database.
string ConnectionString1 = @"Server=demo.database.windows.net; Authentication=Active Directory Managed Identity; Encrypt=True; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString1)) {
    conn.Open();
}

string ConnectionString2 = @"Server=demo.database.windows.net; Authentication=Active Directory MSI; Encrypt=True; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString2)) {
    conn.Open();
}

O exemplo a seguir mostrará uma autenticação de Active Directory Managed Identity usando uma identidade gerenciada atribuída pelo usuário com o Microsoft.Data.SqlClient v3.0 ou posterior.

// For user-assigned managed identity
// Use your own values for Server, Database, and User Id.

// With Microsoft.Data.SqlClient v3.0+
string ConnectionString1 = @"Server=demo.database.windows.net; Authentication=Active Directory Managed Identity; Encrypt=True; User Id=ClientIdOfManagedIdentity; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString1)) {
    conn.Open();
}

// With Microsoft.Data.SqlClient v3.0+
string ConnectionString2 = @"Server=demo.database.windows.net; Authentication=Active Directory MSI; Encrypt=True; User Id=ClientIdOfManagedIdentity; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString2)) {
    conn.Open();
}

O exemplo a seguir mostrará uma autenticação de Active Directory Managed Identity usando uma identidade gerenciada atribuída pelo usuário com o Microsoft.Data.SqlClient v2.1.

// For user-assigned managed identity
// Use your own values for Server, Database, and User Id.

// With Microsoft.Data.SqlClient v2.1
string ConnectionString1 = @"Server=demo.database.windows.net; Authentication=Active Directory Managed Identity; Encrypt=True; User Id=ObjectIdOfManagedIdentity; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString1)) {
    conn.Open();
}

// With Microsoft.Data.SqlClient v2.1
string ConnectionString2 = @"Server=demo.database.windows.net; Authentication=Active Directory MSI; Encrypt=True; User Id=ObjectIdOfManagedIdentity; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString2)) {
    conn.Open();
}

Usar autenticação padrão

Disponível a partir da versão 3.0, esse modo de autenticação amplia as possibilidades de autenticação do usuário. Este modo estende as soluções de logon para o ambiente do cliente, o Visual Studio Code, o Visual Studio, a CLI do Azure etc.

Com esse modo de autenticação, o driver obtém um token passando "DefaultAzureCredential" da biblioteca do Azure Identity para adquirir um token de acesso. Esse modo tenta usar esses tipos de credenciais para obter um token de acesso no pedido. O conjunto de credenciais varia de acordo com a versão da biblioteca Azure Identity usada. As diferenças específicas da versão são observadas na lista. Para conhecer o comportamento específico da versão do Azure Identity, confira a documentação da API do Azure.Identity.

  • EnvironmentCredential
    • Permite executar uma autenticação no Microsoft Entra ID usando um cliente e um segredo ou um nome de usuário e uma senha. Os detalhes estão configurados nestas variáveis de ambiente: AZURE_TENANT_ID, AZURE_CLIENT_ID, AZURE_CLIENT_SECRET, AZURE_CLIENT_CERTIFICATE_PATH, AZURE_USERNAME, AZURE_PASSWORD (mais detalhes)
  • WorkloadIdentityCredential
    • Habilita a autenticação de ID de carga de trabalho do Microsoft Entra no Kubernetes e em outros hosts com suporte à identidade de carga de trabalho. Para obter mais informações, consulte Identidades de Carga de Trabalho do Microsoft Entra. Disponível a partir da versão 1.10 do Azure Identity e Microsoft.Data.SqlClient 5.1.4.
  • ManagedIdentityCredential
    • Tenta executar uma autenticação no Microsoft Entra ID usando uma identidade gerenciada atribuída ao ambiente de implantação. É possível ler a "ID do cliente" da "Identidade Gerenciada Atribuída pelo Usuário" na Propriedade de conexão da "ID de usuário" .
  • SharedTokenCacheCredential
    • Executa uma autenticação usando tokens compartilhados entre aplicativos da Microsoft no cache local.
  • VisualStudioCredential
    • Habilita a autenticação com Microsoft Entra ID usando dados do Visual Studio
  • VisualStudioCodeCredential
    • Habilita a autenticação com o Microsoft Entra ID usando dados do Visual Studio Code.
  • AzurePowerShellCredential
    • Permite a autenticação no Microsoft Entra ID usando o Azure PowerShell. Disponível a partir da versão 1.6 do Azure Identity e Microsoft.Data.SqlClient 5.0.
  • AzureCliCredential
    • Habilita a autenticação com Microsoft Entra ID usando a CLI do Azure para obter um token de acesso.
  • AzureDeveloperCliCredential
    • Habilita a autenticação com o Microsoft Entra ID usando a Azure Developer CLI para obter um token de acesso. Disponível a partir da versão 1.10 do Azure Identity e Microsoft.Data.SqlClient 5.1.4.

Observação

A opção InteractiveBrowserCredential está desabilitada na implementação do driver do "Active Directory Padrão". Além disso, "Active Directory Interativo" é a única opção disponível para obter um token usando uma autenticação MFA/Interativa.

No momento, não há outras opções de personalização disponíveis.

O exemplo a seguir mostrará de que modo usar uma autenticação do Active Directory Padrão.

// Use your own server, database
string ConnectionString = @"Server=demo.database.windows.net; Authentication=Active Directory Default; Encrypt=True; Database=testdb;";

using (SqlConnection conn = new SqlConnection(ConnectionString)) {
    conn.Open();
}

Usando a autenticação de identidade de cargas de trabalho

A partir da versão 5.2, assim como acontece com identidades gerenciadas, o modo de autenticação de identidade de cargas de trabalho usa o valor do parâmetro User Id na cadeia de conexão para sua ID de cliente, se especificado. Mas, ao contrário da identidade gerenciada, WorkloadIdentityCredentialOptions padroniza seu valor a partir de variáveis de ambiente: AZURE_TENANT_ID, AZURE_CLIENT_ID e AZURE_FEDERATED_TOKEN_FILE. No entanto, somente a ID do cliente pode ser sobrescrita pela cadeia de conexão.

O exemplo a seguir demonstra uma autenticação de Active Directory Workload Identity usando uma identidade gerenciada atribuída pelo usuário com o Microsoft.Data.SqlClient v5.2 ou posterior.

// Use your own values for Server, Database, and User Id.
// With Microsoft.Data.SqlClient v5.2+
string ConnectionString = @"Server=demo.database.windows.net; Authentication=Active Directory Workload Identity; Encrypt=True; User Id=ClientIdOfManagedIdentity; Database=testdb";

using (SqlConnection conn = new SqlConnection(ConnectionString)) {
    conn.Open();
}

Personalização da autenticação do Microsoft Entra

Além de usar a autenticação do Active Directory incorporada ao driver, o Microsoft.Data.SqlClient 2.1.0 e posterior fornece aos aplicativos a opção de personalizar a autenticação do Microsoft Entra. A personalização é baseada na classe ActiveDirectoryAuthenticationProvider, que é derivada da classe abstrata SqlAuthenticationProvider.

Durante a autenticação do Microsoft Entra, o aplicativo cliente pode definir sua própria classe ActiveDirectoryAuthenticationProvider ao:

  • Usar um método de retorno de chamada personalizado.
  • Passar uma ID do cliente de aplicativo para a biblioteca MSAL por meio do driver SqlClient a fim de buscar tokens de acesso.

O exemplo a seguir mostra como usar um retorno de chamada personalizado quando a autenticação Active Directory Device Code Flow está em uso.

using System;
using System.Threading.Tasks;
using Microsoft.Identity.Client;
using Microsoft.Data.SqlClient;

namespace CustomAuthenticationProviderExamples
{
    public class Program
    {
        public static void Main()
        {
            SqlAuthenticationProvider authProvider = new ActiveDirectoryAuthenticationProvider(CustomDeviceFlowCallback);
            SqlAuthenticationProvider.SetProvider(SqlAuthenticationMethod.ActiveDirectoryDeviceCodeFlow, authProvider);
            using (SqlConnection sqlConnection = new SqlConnection("Server=<myserver>.database.windows.net;Authentication=Active Directory Device Code Flow;Database=<db>;"))
            {
                sqlConnection.Open();
                Console.WriteLine("Connected successfully!");
            }
        }

        private static Task CustomDeviceFlowCallback(DeviceCodeResult result)
        {
            // Provide custom logic to process result information and read device code.
            Console.WriteLine(result.Message);
            return Task.FromResult(0);
        }
    }
}

Com uma classe ActiveDirectoryAuthenticationProvider personalizada, uma ID do cliente de aplicativo definida pelo usuário pode ser passada para o SqlClient quando um modo de autenticação do Microsoft Entra com suporte está em uso. Os modos de autenticação do Microsoft Entra com suporte incluem Active Directory Password, Active Directory Integrated, Active Directory Interactive, Active Directory Service Principal e Active Directory Device Code Flow.

A ID do cliente de aplicativo também é configurável por meio de SqlAuthenticationProviderConfigurationSection ou SqlClientAuthenticationProviderConfigurationSection. A propriedade de configuração applicationClientId aplica-se ao .NET Framework 4.6+ e ao .NET Core 2.1+.

O snippet de código a seguir é um exemplo de uso de uma classe ActiveDirectoryAuthenticationProvider personalizada com uma ID do cliente de aplicativo definida pelo usuário quando a autenticação Active Directory Interactive está em uso.

using System;
using Microsoft.Data.SqlClient;

namespace CustomAuthenticationProviderExamples
{
    public class Program
    {
        public static void Main()
        {
            // Supported for all authentication modes supported by ActiveDirectoryAuthenticationProvider
            ActiveDirectoryAuthenticationProvider provider = new ActiveDirectoryAuthenticationProvider("<application_client_id>");
            if (provider.IsSupported(SqlAuthenticationMethod.ActiveDirectoryInteractive))
            {
                SqlAuthenticationProvider.SetProvider(SqlAuthenticationMethod.ActiveDirectoryInteractive, provider);
            }
            
            using (SqlConnection sqlConnection = new SqlConnection("Server=<myserver>.database.windows.net;Authentication=Active Directory Interactive;Database=<db>;"))
            {
                sqlConnection.Open();
                Console.WriteLine("Connected successfully!");
            }
        }
    }
}

O exemplo a seguir mostra como definir uma ID do cliente de aplicativo por meio de uma seção de configuração.

<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>

Suporte para um provedor de autenticação SQL personalizado

Com mais flexibilidade, o aplicativo cliente também pode usar seu próprio provedor de autenticação do Microsoft Entra em vez de usar a classe ActiveDirectoryAuthenticationProvider. O provedor de autenticação personalizado precisa ser uma subclasse de SqlAuthenticationProvider com métodos substituídos. Ele deve registrar o provedor personalizado, substituindo um ou mais dos métodos de autenticação Active Directory* existentes.

O exemplo a seguir mostra como usar um novo provedor para a autenticação Active Directory Device Code Flow.

using System;
using System.Threading.Tasks;
using Microsoft.Identity.Client;
using Microsoft.Data.SqlClient;

namespace CustomAuthenticationProviderExamples
{
    /// <summary>
    /// Example demonstrating creating a custom device code flow authentication provider and attaching it to the driver.
    /// This is helpful for applications that wish to override the Callback for the Device Code Result implemented by the SqlClient driver.
    /// </summary>
    public class CustomDeviceCodeFlowAzureAuthenticationProvider : SqlAuthenticationProvider
    {
        public override async Task<SqlAuthenticationToken> AcquireTokenAsync(SqlAuthenticationParameters parameters)
        {
            string clientId = "my-client-id";
            string clientName = "My Application Name";
            string s_defaultScopeSuffix = "/.default";

            string[] scopes = new string[] { parameters.Resource.EndsWith(s_defaultScopeSuffix) ? parameters.Resource : parameters.Resource + s_defaultScopeSuffix };

            IPublicClientApplication app = PublicClientApplicationBuilder.Create(clientId)
                .WithAuthority(parameters.Authority)
                .WithClientName(clientName)
                .WithRedirectUri("https://login.microsoftonline.com/common/oauth2/nativeclient")
                .Build();

            AuthenticationResult result = await app.AcquireTokenWithDeviceCode(scopes,
                    deviceCodeResult => CustomDeviceFlowCallback(deviceCodeResult)).ExecuteAsync();
            return new SqlAuthenticationToken(result.AccessToken, result.ExpiresOn);
        }

        public override bool IsSupported(SqlAuthenticationMethod authenticationMethod) => authenticationMethod.Equals(SqlAuthenticationMethod.ActiveDirectoryDeviceCodeFlow);

        private Task CustomDeviceFlowCallback(DeviceCodeResult result)
        {
            Console.WriteLine(result.Message);
            return Task.FromResult(0);
        }
    }

    public class Program
    {
        public static void Main()
        {
            // Register our custom authentication provider class to override Active Directory Device Code Flow
            SqlAuthenticationProvider.SetProvider(SqlAuthenticationMethod.ActiveDirectoryDeviceCodeFlow, new CustomDeviceCodeFlowAzureAuthenticationProvider());
            using (SqlConnection sqlConnection = new SqlConnection("Server=<myserver>.database.windows.net;Authentication=Active Directory Device Code Flow;Database=<db>;"))
            {
                sqlConnection.Open();
                Console.WriteLine("Connected successfully!");
            }
        }
    }
}

Além de melhorar a experiência de autenticação Active Directory Interactive, o Microsoft.Data.SqlClient 2.1.0 e posterior fornece as seguintes APIs para aplicativos cliente a fim de personalizar as autenticações de fluxo de código de dispositivo e interativa.

public class ActiveDirectoryAuthenticationProvider
{
    // For .NET Framework targeted applications only
    // Sets a reference to the current System.Windows.Forms.IWin32Window that triggers the browser to be shown. 
    // Used to center the browser pop-up onto this window.
    public void SetIWin32WindowFunc(Func<IWin32Window> iWin32WindowFunc);

    // For .NET Standard targeted applications only
    // Sets a reference to the ViewController (if using Xamarin.iOS), Activity (if using Xamarin.Android) IWin32Window, or IntPtr (if using .NET Framework). 
    // Used for invoking the browser for Active Directory Interactive authentication.
    public void SetParentActivityOrWindowFunc(Func<object> parentActivityOrWindowFunc);

    // For .NET Framework, .NET Core, and .NET Standard targeted applications
    // Sets a callback method that's invoked with a custom web UI instance that will let the user sign in with Azure AD, present consent if needed, and get back the authorization code. 
    // Applicable when working with Active Directory Interactive authentication.
    public void SetAcquireAuthorizationCodeAsyncCallback(Func<Uri, Uri, CancellationToken, Task<Uri>> acquireAuthorizationCodeAsyncCallback);

    // For .NET Framework, .NET Core, and .NET Standard targeted applications
    // Clears cached user tokens from the token provider.
    public static void ClearUserTokenCache();
}

Confira também