pyodbc是否支持使用AD访问令牌而不是用户/密码连接到Azure SQL DB?

时间:2020-04-06 22:07:29

标签: azure azure-active-directory azure-sql-database

当前,我使用设备代码凭据来访问Azure AD。

device_code_credential = DeviceCodeCredential(
        azure_client_id,
        tenant_id=azure_tenant_id,
        authority=azure_authority_uri)

但是我仍然需要使用Azure帐户用户名/密码来连接到Azure SQL服务器

driver = 'ODBC Driver 17 for SQL Server'
db_connection_string = f'DRIVER={driver};SERVER={server};' \
    f'DATABASE={database};UID={user_name};PWD={password};'\
    f'Authentication=ActiveDirectoryPassword;'\
    'Encrypt=yes;TrustServerCertificate=no;Connection Timeout=30;'
connector = pyodbc.connect(db_connection_string)

在Linux / MacOS下的python中,有什么方法可以允许我使用device_code_credential和access_token连接到Azure SQL服务器吗?

https://github.com/mkleehammer/pyodbc/issues/228

我只有这个链接,而且似乎没有用。

有人有一个可以正常工作的样品吗?

2 个答案:

答案 0 :(得分:2)

您可以参考本教程:AzureAD/azure-activedirectory-library-for-python: Connect to Azure SQL Database

可以通过ADAL Python从Azure Active Directory(AAD)获取令牌来连接到Azure SQL数据库。我们目前尚未为其提供完整的示例,但是本文概述了一些关键要素。

  1. 您按照Connecting using Access Token的说明进行操作 设置您的应用程序。还有另一篇类似的博客文章here
  2. 您的SQL管理员需要将应用注册的权限添加到 您尝试访问的特定数据库。查看详细信息 此博客帖子Token-based authentication support for Azure SQL DB using Azure AD auth,作者Mirek H Sztajno。
  3. 在两个文档中都没有特别强调 以上,但您需要使用https://database.windows.net/作为 资源字符串。请注意,您需要保留斜线, 否则,发行的令牌将不起作用。
  4. 将以上配置输入ADAL Python的Client Credentials sample
  5. 获得访问令牌后,请使用它in this way in pyodbc 连接到SQL数据库。

这适用于AAD访问令牌。如上面的链接所述,在Python 2.x中,示例代码用于扩展令牌并在其前面加上长度:

token = "eyJ0eXAiOi...";
exptoken = "";
for i in token:
    exptoken += i;
    exptoken += chr(0);
tokenstruct = struct.pack("=i", len(exptoken)) + exptoken;
conn = pyodbc.connect(connstr, attrs_before = { 1256:bytearray(tokenstruct) });

3.x由于令人讨厌的字符/字节拆分而只涉及到更多一点:

token = b"eyJ0eXAiOi...";
exptoken = b"";
for i in token:
    exptoken += bytes({i});
    exptoken += bytes(1);
tokenstruct = struct.pack("=i", len(exptoken)) + exptoken;
conn = pyodbc.connect(connstr, attrs_before = { 1256:tokenstruct });

(SQL_COPT_SS_ACCESS_TOKEN为1256;它特定于msodbcsql驱动程序,因此pyodbc没有定义它,并且可能不会。)

希望这会有所帮助。

答案 1 :(得分:1)

您可以通过以下方式获取令牌

from azure.identity import DeviceCodeCredential

# Recommended to allocate a new ClientID in your tenant.
AZURE_CLI_CLIENT_ID = "04b07795-8ddb-461a-bbee-02f9e1bf7b46"
credential = DeviceCodeCredential(client_id=AZURE_CLI_CLIENT_ID)
databaseToken = credential.get_token('https://database.windows.net/.default')

然后按照Leon Yue的答案所述,将databaseToken.token用作AAD访问令牌。