问题描述
我目前正在将 R Shiny 应用程序部署到 Azure 应用程序服务,并通过 Active Directory 集成限制访问(这似乎在后台使用了 Azure easyauth 代理).
I am currently deploying an R Shiny app to Azure App Service, and restricting access via Active Directory integration (which seems to use the Azure easyauth proxy under the hood).
当我部署 rocker/shiny:3.6.0
或 rocker/shiny:4.0.0
容器以简单地查看hello world"时页面部署成功.
When I deploy the rocker/shiny:3.6.0
or rocker/shiny:4.0.0
container to simply see the "hello world" page the deployment is successful.
当我打开 Active Directory 身份验证时,网站挂起,然后返回 500
.
When I turn on Active Directory Authentication, the website hangs, then returns a 500
.
我在此消息的底部附上了错误日志,但我认为它没有任何关于我可以控制的事情的有用信息.
I have attached the error log at the bottom of this message, but I don't think it has any useful information with respect to things I have control over.
进一步调查表明,如果我部署 rocker:shiny:3.5.2
或更低版本,一切都会按预期工作.如果我部署 rocker/shiny:3.6.0
或更高版本,我得到一个 500
并且网站挂起.
Further investigation shows that if I deploy rocker:shiny:3.5.2
or below, everything works as expected. If I deploy rocker/shiny:3.6.0
or above, I get a 500
and the website hangs.
部署 rocker/shiny:3.5.3
会导致这些问题中报告的症状:
Deploying rocker/shiny:3.5.3
results in the symptoms reported in these questions:
所以我很确定根本原因是不同的.
So I am fairly sure the root cause is different.
对我来说,这表明 rocker/shiny:3.6.0
包及更高版本的更改导致身份验证停止工作,但恐怕这是我的调试能力停止的地方!
To me this indicates changes in the rocker/shiny:3.6.0
packages and above which is stopping the authentication from working, but I am afraid this is where my debugging ability stops!
我的问题是 - 我真的做错了什么吗?这是一个已知问题吗?我该如何报告(以及向谁报告?!).
My questions are - am I actually just doing something wrong, is this a known issue, and how do I report it (and to who?!).
感谢您的帮助,
阿基尔
fail: Middleware[0]
Unhandled exception in request pipeline: System.Net.Http.HttpRequestException: An error occurred while sending the request.
---> System.IO.IOException: The response ended prematurely.
at System.Net.Http.HttpConnection.FillAsync()
at System.Net.Http.HttpConnection.ReadNextResponseHeaderLineAsync(Boolean foldedHeadersAllowed)
at System.Net.Http.HttpConnection.SendAsyncCore(HttpRequestMessage request, CancellationToken cancellationToken)
--- End of inner exception stack trace ---
at System.Net.Http.HttpConnection.SendAsyncCore(HttpRequestMessage request, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionPool.SendWithNtConnectionAuthAsync(HttpConnection connection, HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionPool.SendWithRetryAsync(HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
at System.Net.Http.HttpClient.FinishSendAsyncUnbuffered(Task`1 sendTask, HttpRequestMessage request, CancellationTokenSource cts, Boolean disposeCts)
at Microsoft.Azure.AppService.MiddlewareShim.Startup.ForwardRequestAsync(HttpContext context) in /EasyAuth/Middleware.Host/Startup.cs:line 197
at Microsoft.Azure.AppService.MiddlewareShim.Startup.OnRequest(HttpContext context) in /EasyAuth/Middleware.Host/Startup.cs:line 151
fail: Microsoft.AspNetCore.Server.Kestrel[13]
Connection id "...", Request id "...": An unhandled exception was thrown by the application.
System.Net.Http.HttpRequestException: An error occurred while sending the request.
---> System.IO.IOException: The response ended prematurely.
at System.Net.Http.HttpConnection.FillAsync()
at System.Net.Http.HttpConnection.ReadNextResponseHeaderLineAsync(Boolean foldedHeadersAllowed)
at System.Net.Http.HttpConnection.SendAsyncCore(HttpRequestMessage request, CancellationToken cancellationToken)
--- End of inner exception stack trace ---
at System.Net.Http.HttpConnection.SendAsyncCore(HttpRequestMessage request, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionPool.SendWithNtConnectionAuthAsync(HttpConnection connection, HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionPool.SendWithRetryAsync(HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
at System.Net.Http.HttpClient.FinishSendAsyncUnbuffered(Task`1 sendTask, HttpRequestMessage request, CancellationTokenSource cts, Boolean disposeCts)
at Microsoft.Azure.AppService.MiddlewareShim.Startup.ForwardRequestAsync(HttpContext context) in /EasyAuth/Middleware.Host/Startup.cs:line 197
at Microsoft.Azure.AppService.MiddlewareShim.Startup.OnRequest(HttpContext context) in /EasyAuth/Middleware.Host/Startup.cs:line 151
at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequests[TContext](IHttpApplication`1 application
推荐答案
存在一个已知问题,即某些最新版本的节点(或其他一些网络服务器)的标头最大容量为 8KB.
There is a known issue where some recent versions of node (or some other webservers) has a maximum capacity of 8KB for headers.
当您启用 EasyAuth 时,它会在请求中添加一些较大的标头.
When you enable EasyAuth, it adds some large headers to the request.
要克服这个问题,您可以使用以下两种解决方案中的一种:
To overcome this, you can use on of the 2 solutions:
1.使用 WEBSITE_AUTH_DISABLE_IDENTITY_FLOW
应用设置
1. Use WEBSITE_AUTH_DISABLE_IDENTITY_FLOW
App Settings
当此变量设置为 true
时,它会禁用分配线程主体身份,这将删除添加到请求中的最大标头之一 X-MS-CLIENT-PRINCIPAL
,通常由 .NET Framework 和 Function 应用程序使用.
When this variable is set to true
it disables assigning the thread principal identity, which will remove one of the largest headers added to the request X-MS-CLIENT-PRINCIPAL
, which is generally used by .NET Framework and Function apps.
但是,它包含与 id_token 相同的声明.一个 Base64 编码的 JSON 对象,我们可以对其进行解码以获取信息.如果您想直接访问 id_token JWT,可以使用 X-MS-TOKEN-AAD-ID-TOKEN
标头.
However, it contains the same claims as the id_token. A Base64-encoded JSON object that we can decode to get the information. If you want access to the id_token JWT directly, you can use X-MS-TOKEN-AAD-ID-TOKEN
header.
参考:https://github.com/cgillum/easyauth/wiki/Advanced-Application-设置
2.提高标头大小的限制
这可以使用 NODE_OPTIONS
变量来完成,如以下 github 问题 这里.
This can be done using the NODE_OPTIONS
variable, as described in the following github issue here.
示例:NODE_OPTIONS=--max-http-header-size=16384
这篇关于Azure 应用服务上的 R Shiny 应用与 Active Directory 集成的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!