-
-
Notifications
You must be signed in to change notification settings - Fork 393
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Cookies in 3.0 #506
Comments
I really like everything proposed here. Particularly the idea of My current scenario involves a background hosted service (in asp core) to "login" and persist a Cookie and Controllers that make additional calls to the endpoint with that Cookie. Both places basically end up calling |
I'm curious why not address the underlying cookie issues in httpclient (whatever they may be) with the . Net core team? What does my injection scenario look like for my DAOs. It kind of feels like I will need a service factory and then I make calls only using session? I'm tailing a bit off of @Meberem s question here. Is session thread safe for updates. On a cookie token renewal will the cookie be locked at the appropriate time? There is a challenge here because as soon as the server sends a response and before parsing is complete, a prior token could be expired or invalidated. |
I did my best but have heard nothing back so I'm not going to wait for them. |
@Meberem @rcollette An AspNetCore-specific companion lib is definitely something I'm considering, but I want to get 3.0 released first. Flurl.Http will continue to support a very broad range of platforms, and that's the context of this particular feature, so things like typed clients aren't really relevant to this. Let me know if you see any shortcomings, under the context that it is a platform-agnostic "building block" that may require a little work to marry it to an ASP.NET Core feature. @rcollette It's possible that I'll need to switch to a thread-safe collection such as a |
FlurlRequest.Cookies and FlurlResponse.Cookies more accurately reflect the actual data sent/received in that specific request
This is now available in prerelease 4! https://www.nuget.org/packages/Flurl.Http/3.0.0-pre4 There were enough changes since I first logged this issue that I rewrote the description almost completely. If you've been following this issue I'd encourage you to re-read it. If you are using cookies with Flurl, testing this prerelease is absolutely crucial. It's completely different from 2.x, there's likely going to be some bugs, and it's extremely important to get the behavior right before the full 3.0 release, at which point it'll be too late for breaking changes. I greatly appreciate any and all feedback on this one! |
To be honest, this change disrupted one of the best features of Flurl. I use Flurl in a service invoked via IOC. Ver. 3.0, now requires me to handle explicitly cookies |
@gpcaretti If you post some details of what worked before and doesn't work now, I can probably help you with a smooth transition. Nothing with cookies should be harder than it was before. |
Thank you very much. My post intended that with v. 2.x it was enough to configure Flurl to handle cookies and all was in charge to it. This allowed me to wrap Flurl in a class library with a API such has:
A simple API that I invoked via IOC in different ViewModel of my app:
With v.3 my understanding is I have to create a
|
@gpcaretti Hmm, ok, that's your service interface but it doesn't tell me much about how you're using Flurl. Are you injecting |
FWIW, I had trouble deserializing CookieJar and FlurlCookie with |
@gitfool feel free to log a new issue. It does make sense that persisting a CookieJar should be easy and if it's not maybe there's something that can be done about that. I'm open to suggestions on how. |
I had an initialize such has
Then all methods works in this way:
As you can see, the great thing I liked was that cookies where all "automagic", i.e. if a response set some cookies, the successive request automatically executed with the same cookies. All this thanks to the initial configuration. With v.3 my understanding is I have to create a |
Cookies never worked quite right in 2.x. Although you can get and set them using
FlurlRequest.Cookies
, that's deceiving because they actually live at the client level. This is due to a limitation with the mechanisms from the HttpClient stack. Flurl.Http 3.0 will get it right by turning offHttpClientHandler.UseCookies
and processing the raw headers directly.IFlurlRequest.Cookies
andIFlurlResponse.Cookies
These read-only collections directly reflect the
Cookie
request header andSet-Cookie
response headers for this specific request and response, respectively. Nothing fancy here; if the cookie wasn't sent or received in this specific request, it won't be in these collections.Here's how you can set some per-request cookies manually:
These simply write to the
Cookie
header for this request only.CookieJar
This is where things get a little smarter.
CookieJar
is a special collection type whose contents (FlurlCookie
s) contain the full details received inSet-Cookie
response headers. When aCookieJar
is passed toWithCookies
, you get these additional behaviors:Cookie
header are filtered according to rules involving the origin URL,Domain
andPath
, expiration, etc, per RFC 6265.CookieJar
will be populated/updated with anySet-Cookie
headers present in the response.CookieJar
is well suited to reuse in subsequent requests.In short,
CookieJar
is Flurl's equivalent ofCookieContainer
from the HttpClient stack, with the notable advantage that it's not bound one-to-one with a client or handler.You can create and populate a
CookieJar
(fluently of course):Or, if you don't need to pre-populate it, you can save yourself the trouble of creating it and use an
out
param instead:CookieSession
If passing that
jar
with every request feels like a drag, you can do it implicitly:That base URL passed in the constructor is optional; you can pass full URLs in the
Request
calls, or even a list of segments that will beUrl.Combine
'd together. These semantics are very similar to those ofIFlurlClient.Request
, and if fact, if you are using aFlurlClient
explicitly, you can usenew CookieSession(client)
instead to make sure you're creating requests off that client.Manipulating cookies
Typically, cookies are set/updated via
Set-Cookie
instructions sent by server, and if you use aCookieJar
orCookieSession
as prescribed above, things will just work. But if you do need to manipulate them directly, be aware of these behaviors:WithCookies(jar)
, values relevant to this request are immediately written to theCookies
header. If you manipulate the jar after it is attached to the request and before the request is sent, those changes will not be synchronized with theCookie
header. So it's best to do any initializing/updating of the jar before attaching it to any requests.WithCookie(s)
will overwrite values of the same name set in previous calls, regardless of whether they came from a jar or direct values. But other than overwriting by name, successive calls are additive.CookieJar
, it becomes immutable and you'll get an exception if you try to change it. Usejar.AddOrReplace
to "update" a cookie.Breaking changes
CookiesEnabled
at all settings levels. It doesn't serve any purpose anymore. You're in direct control of sending cookies, you can't prevent a server from sending them in the response headers, and processing theSet-Cookies
headers is done lazily, so there's no overhead involved when you don't need them.Cookies
collection andWithCookie(s)
methods fromFlurlClient
.CookieSession
is the replacement, and it can even be managed as singleton via DI if that's appropriate. If there are legitimate reasons for client-level cookies I could be persuaded to add it back, but I can't think of any.FlurlRequest.Cookies
is a now simple read-only list of Name/Value pairs. This more accurately reflects theCookie
request header, which doesn't contain all the details of theSet-Cookie
response header.WithCookie(s)
is the preferred way to write request cookies. (You could also manipulate theCookie
header directly, but I wouldn't recommended it in most cases.)Cookie
andSet-Cookie
headers are now visible in theHeaders
collections. This is a consequence of disablingHttpClientHandler.UseCookies
, but I tend to like it better because it's a more accurate representation of the actual headers that were sent and received.The text was updated successfully, but these errors were encountered: