我想使用托管身份(即连接到Visual Studio的用户的身份,而不是在我的连接字符串中提供UserId和密码)从在调试中的计算机上执行的Azure函数中查询Azure SQL数据库。
我在Microsoft文档上遵循了this tutorial,因此我的Azure SQL Server拥有一个AD用户作为admin,这使我可以授予我使用Azure Function Identity和其中的用户创建的Azure AD组的权限(db_datareader) (以及我在Azure中部署的Function App)。
如果我在Azure功能中在Azure中部署和运行,它可以查询我的数据库,并且一切正常。但是,当我在本地运行Azure函数时,出现以下错误:
用户'NT AUTHORITY \ ANONYMOUS LOGON'登录失败。
我的函数的代码如下:
public async Task<IActionResult> Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = "test")] HttpRequest req,
ILogger log)
{
log.LogInformation("C# HTTP trigger function processed a request.");
using (var connection = new SqlConnection(Environment.GetEnvironmentVariable("sqlConnectionString")))
{
connection.AccessToken = await (new AzureServiceTokenProvider()).GetAccessTokenAsync("https://database.windows.net");
log.LogInformation($"Access token : {connection.AccessToken}");
try
{
await connection.OpenAsync();
var rows = await connection.QueryAsync<Test>("select top 10 * from TestTable");
return new OkObjectResult(rows);
}
catch (Exception e)
{
throw e;
}
}
}
该代码正确检索了令牌,该错误发生在第await connection.OpenAsync()
行。
如果在Azure Data Studio中使用与连接到Visual Studio的用户相同的用户打开数据库(该用户是具有数据库权限的AD组的成员),则可以连接和查询数据库而没有任何问题。
这是已知问题还是我在这里遗漏了什么?
答案 0 :(得分:0)
您本地计算机的IP地址是否列入白名单?
https://docs.microsoft.com/en-us/azure/sql-database/sql-database-firewall-configure
答案 1 :(得分:0)
尝试了特定的情况后,我测试了很多方法来尝试使其在本地运行。这不起作用,给出的错误信息与您相同。
当可能的解决方案出现时,我与一些人进行了讨论。我测试了它:它有效!
在我的情况下,主要问题是我的订阅(和我的用户)是一个Microsoft帐户(Outlook)。因此,您需要在tenantId
调用中指定GetAccessTokenAsync()
。
显然,对于托管身份,您不必指定tenantId
。对于用户,最好明确指定它。如果是个人MS帐户,则必须指定该帐户。
我的代码(某种):
var tokenProvider = new AzureServiceTokenProvider();
using (var connection = new SqlConnection(CONNECTIONSTRING))
using (var command = new SqlCommand(QUERY, connection))
{
connection.AccessToken = await tokenProvider.GetAccessTokenAsync("https://database.windows.net/", "<YOUR_TENANT_ID>");
await connection.OpenAsync();
var result = (await command.ExecuteScalarAsync()).ToString();
return new OkObjectResult(result);
}
此解决方案已经过测试,并且在指定tenantId
(或目录ID,租户的GUID)和'onmicrosoft'名称(xxx.onmicrosoft.com
)时都可以使用。