如何使用应用服务对 Azure Functions 应用进行身份验证/授权?
Posted
技术标签:
【中文标题】如何使用应用服务对 Azure Functions 应用进行身份验证/授权?【英文标题】:How can I authenticate/authorize an Azure functions app with an app service? 【发布时间】:2017-11-07 07:54:25 【问题描述】:我有一个 Azure 应用服务 以及一个 functions 应用(我目前正在学习 Azure,如果有其他方法可以实现我想要的,我愿意建议)。应用服务包含一个简单的表,我想与一个应用同步(它已经在工作),并且我想实现一个函数,其中包含一个填充简单表的 blob 存储输入绑定或计时器触发器。
由于似乎没有简单表的输出绑定,我遵循this answer 并使用MobileServiceClient
实现了访问。
MobileServiceClient client = new MobileServiceClient("https://my-app.azurewebsites.net");
var table = client.GetTable<MyTableClass>();
await table.InsertAsync(myObject);
只要表是公开可写的,它就可以工作,但是当它可以匿名读取时它当然不起作用,但只有经过身份验证的用户才可写。为了验证我的功能,我创建了一个 Azure Active Directory 并为该 AD 中的应用程序创建了一个 API 密钥,然后我尝试通过
验证MobileServiceClient
await client.LoginAsync(MobileServiceAuthenticationProvider.WindowsAzureActiveDirectory,
new JObject "access_token", "<my API key>");
但这并没有成功。我总是收到错误
请求无法完成。 (未经授权)。
显然这行不通(以这种方式使用 API 密钥实际上只是在黑暗中拍摄),但我不确定如何从我的函数应用程序中完成身份验证。我知道当我在应用程序中使用MobileServiceClient
时,我可以将用户重定向到登录,但这(显然)不适用于函数。
如何使用现有应用服务验证我的函数,以便写入不可匿名写入的表?
【问题讨论】:
【参考方案1】:应用服务无法通过 API 密钥进行简单访问,但访问应用服务需要通过 Active Directory 进行完整身份验证。为此,可以使用 ADAL (Active Directory Access Library)。
AuthenticationContext
ADAL 定义了AuthenticationContext
类,它是使用 Active Directory 进行身份验证的助手。先新建一个AuthenticationContext
var authenticationContext = new AuthenticationContext("https://login.microsoftonline.com/<Directory ID>");
您可以通过访问 Azure 门户中的 Azure Active Directory 找到 Directory ID
,然后从 Azure Active Directory 菜单打开 属性。在属性菜单中有一个包含Directory ID
的文本框。
使用 Azure Active Directory 进行身份验证
您现在可以使用身份验证
var authenticationResult = await authenticationContext.AcquireTokenAsync(
"https://batch.core.windows.net/",
new ClientCredential("<app ID>", "<app secret>"));
我假设已经有 一个已注册的应用程序。要获取应用 ID,请访问 Azure Active Directory → 应用注册 → ,您可以在其中找到应用程序 ID(也在 Properties 下)。
接下来,您必须为应用创建密钥。因此访问 Azure Active Directory → 应用注册 →
MobileServiceClient
最后一步是创建MobileServiceClient
。由于 UI 登录不可用,我们必须手动创建登录用户(请参阅here)。
MobileServiceClient client = new MobileServiceClient("https://my-app.azurewebsites.net");
client.CurrentUser = new MobileServiceUser("Foo:123456789");
client.CurrentUser.MobileServiceAuthenticationToken = authenticationResult.AccessToken;
现在MobileServiceClient
已通过身份验证并可以使用。
进一步阅读
https://docs.microsoft.com/en-us/azure/active-directory/develop/active-directory-protocols-oauth-service-to-service
https://docs.microsoft.com/en-us/azure/active-directory/develop/active-directory-authentication-scenarios#web-application-to-web-api
https://docs.microsoft.com/en-us/dotnet/api/microsoft.identitymodel.clients.activedirectory.authenticationcontext?view=azure-dotnet
https://docs.microsoft.com/en-us/azure/batch/batch-aad-auth
【讨论】:
【参考方案2】:您可以使用托管服务身份向应用服务验证您的功能。
您的应用程序可以像自己一样与其他 Azure 服务进行通信 使用托管的 Azure Active Directory 标识。
您可以在此处查看如何启用和使用托管标识:
https://docs.microsoft.com/en-us/azure/app-service/app-service-managed-service-identity
希望这会有所帮助!
【讨论】:
我无法尝试,但从我读到的内容看来,我似乎仍然需要请求身份验证令牌(不是使用 ADAL,而是使用AzureServiceTokenProvider
),因此我真的不明白这如何使事情变得更简单(除了不必自己找出租户 ID 和应用程序密码)。
此解决方案是官方支持的跨多个 Azure 服务“作为服务”执行请求的方式。您标记了自己的答案,但甚至没有尝试实施正确的方法……对我来说似乎很可疑,并且会引导人们找到错误的解决方案。
这是不是受支持的方式,而是一种预览 - 相应的库也是如此。无论如何,我没有标记我的解决方案,因为我看到指向未来支持的方式有其存在和被承认的权利。以上是关于如何使用应用服务对 Azure Functions 应用进行身份验证/授权?的主要内容,如果未能解决你的问题,请参考以下文章
Azure基础:何时使用Azure Functions无服务器计算(11)
如何从 Azure 移动应用服务调用 HTTP(Azure Functions)?