dotnet / aspnetcore

ASP.NET Core is a cross-platform .NET framework for building modern cloud-based web applications on Windows, Mac, or Linux.
https://asp.net
MIT License
35.43k stars 10.01k forks source link

[Announcement] HttpResponse body infrastructure changes #12635

Closed Tratcher closed 3 years ago

Tratcher commented 5 years ago

TLDR: The infrastructure backing HttpResponse bodies has changed. If you're using HttpResponse directly you should not need to make any code changes. Read further if you were wrapping or replacing HttpResponse.Body or accessing HttpContext.Features.

Version: 3.0.0-preview8

Background: HttpContext, HttpRequest, HttpResponse are backed by an abstraction called Features. This allows functionality to be provided by different components in the pipeline without wrapping the entire HttpContext.

In 2.x there are three APIs associated with the response body: IHttpResponseFeature.Body, IHttpSendFileFeature.SendFileAsync, and IHttpBufferingFeature.DisableResponseBuffering, but the later two were rarely implemented or used.

Over the course of 3.0 several new response body APIs were added: IHttpResponseBodyPipeFeature IHttpResponseStartFeature.StartAsync IHttpResponseCompleteFeature.CompleteAsync

Problem: With so many APIs it became too hard for middleware to properly intercept the response body. It was also hard for calling code to rely on those features being present on all servers.

Fix: Consolidate the response body APIs onto a single new feature interface IHttpResponseBodyFeature. HttpResponse has been updated accordingly, and each server has been updated to provide at least a minimal implementation for all of these APIs. We'll iterate to provide more fully featured implementations in each server but that won't require any more API changes.

Note if you replace HttpResponse.Body it will now replace the entire IHttpResponseBodyFeature with a wrapper around your given stream using StreamResponseBodyFeature to provide default implementations for all of the expected APIs. Setting back the original stream will undo this change. https://github.com/aspnet/AspNetCore/blob/4aebd29abca80242f5ff9e89e07d4f1b28788a44/src/Http/Http/src/Internal/DefaultHttpResponse.cs#L67-L89

Breaking change https://github.com/aspnet/AspNetCore/pull/12328

Obsolete existing 2.x APIs IHttpResponseFeature.Body IHttpSendFileFeature IHttpBufferingFeature

Deleted feature interfaces that were introduced earlier in 3.0. IHttpResponseBodyPipeFeature IHttpResponseStartFeature IHttpResponseCompleteFeature

In a future major release we plan to refactor the request body features as well https://github.com/aspnet/AspNetCore/issues/12620.

Joel-S-Black commented 4 years ago

What nuget package is StreamResponseBodyFeature in? I downloaded Microsoft.AspNetCore.Http.Features, but I cannot resolve the reference.

Tratcher commented 4 years ago

StreamResponseBodyFeature isn't in a nuget package, it's in the shared framework. https://github.com/dotnet/aspnetcore/blob/3132e5c6cee173bc025f36b2cfa3c53161370ca1/src/Http/Http/src/StreamResponseBodyFeature.cs#L16

https://docs.microsoft.com/en-us/aspnet/core/migration/22-to-30?view=aspnetcore-3.1&tabs=visual-studio#framework-reference

Joel-S-Black commented 4 years ago

I was not able to get a reference for StreamResponseBodyFeature to resolve by simply upgrading the framework version. I had to install Microsoft.Aspnetcore.Own nuget package, version 3.0.0. Oddly enough, the IHttpResponseBodyFeature resolved just fine with netstandard2.1 framework version.

davidfowl commented 4 years ago

ASP.NET Core 3.x isnt' available via NuGet packages https://docs.microsoft.com/en-us/aspnet/core/migration/22-to-30?view=aspnetcore-3.1&tabs=visual-studio#migrate-libraries-via-multi-targeting

Joel-S-Black commented 4 years ago

Correct. Allow me to rephrase: the namespace Microsoft.Aspnetcore.Http would not resolve for class StreamResponseBodyFeature when I posted the origin question. After changing the targeting of my csproj to netcoreapp3.1, the project still would not build. I then pulled in the Microsoft.Aspnetcore.Http.Features nuget package. No resolution. After purging my nuget cache, cleaning, and rebuilding to no avail, I asked my budget question. While waiting on the response, I began installing nuget packages based off of this repo that whose name started with "Microsoft.Aspnetcore" which should touch middleware. When the reference would not resolve, I'd uninstall that package and look for the next one that appeared to be based on this repo.

I'm happy to report that the class "StreamResponseBodyFeature" resolved once I installed the "Microsoft.Aspnetcore.Owin, version 3" nuget package. I would have thought that class would have been included in the "Microsoft.Aspnetcore.Http", but it would not resolve.

To make sure of my conclusion, I uninstalled the Owin package and confirmed the project would not build. After reinstalling the package, I brought the project below netcoreapp3 and confirmed that the project would not build.

So, my conclusion is that the class "StreamResponseBodyFeature" can only be used in a project targeting netcoreapp3 with "Microsoft.Aspnetcore.Owin", >= v3.0.0

Sincerely,

Joel Black


From: David Fowler notifications@github.com Sent: Friday, May 22, 2020 1:57 AM To: dotnet/aspnetcore aspnetcore@noreply.github.com Cc: Joel Black jllblk@hotmail.com; Comment comment@noreply.github.com Subject: Re: [dotnet/aspnetcore] [Announcement] HttpResponse body infrastructure changes (#12635)

ASP.NET Core 3.x isnt' available via NuGet packages https://docs.microsoft.com/en-us/aspnet/core/migration/22-to-30?view=aspnetcore-3.1&tabs=visual-studio#migrate-libraries-via-multi-targeting

— You are receiving this because you commented. Reply to this email directly, view it on GitHubhttps://github.com/dotnet/aspnetcore/issues/12635#issuecomment-632525057, or unsubscribehttps://github.com/notifications/unsubscribe-auth/AB6XZTRAVFALRNQEM4O42OTRSYO7BANCNFSM4IHHTFYA.

davidfowl commented 4 years ago

So, my conclusion is that the class "StreamResponseBodyFeature" can only be used in a project targeting netcoreapp3 with "Microsoft.Aspnetcore.Owin", >= v3.0.0

You need to target netcoreapp3.x for sure but you also need to add a <FrameworkReference Include="Microsoft.AspNetCore.App" /> to the project. Refer to the doc I linked as it explains how to write class libraries that use ASP.NET Core.

ASP.NET Core 3.0 only works on .NET Core.

Tratcher commented 4 years ago

The Microsoft.Aspnetcore.Owin package isn't required, but it would pull in the FrameworkReference for you.

Joel-S-Black commented 4 years ago

David, thanks for that link. Although I had read that page prior, I did not realize that FrameworkReferences were actually a thing (When I have previously read csprojs, I had thought that all things appearing to reference a name space was the same type of reference). Tratcher, thank you for your clarifying comment as well, it helped me to reconcile what I could see with what you were saying. I'm curious how I managed to get along so long not knowing that FrameworkReferences were a thing (since 2018)..

This would appear to be the documentation on FrameworkReferences: https://docs.microsoft.com/en-us/dotnet/core/packages .

In conclusion, the answer to my question about what nuget package to use make sure when using .net core 3 that you have '<"FrameworkReference Include="Microsoft.AspNetCore.App" />' in a project file ItemGroup tag.

jkotalik commented 3 years ago

Closing as this is already stable and has been in more than on release.