Skip to content
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

Xamarin Android CookieManager ignores cookies with samesite value set #2284

Closed
MdNaushad opened this issue Oct 10, 2018 · 7 comments
Closed

Comments

@MdNaushad
Copy link

MdNaushad commented Oct 10, 2018

Steps to Reproduce

  1. Create a new Xamarin Forms/Android Project.
  2. In the MainActivity OnCreate, create a cookie by setting the value for samesite as "samesite=lax".
  3. Add the cookie to the CookieManager:
var cookie = new Cookie
            {
                Name = ".WithSameSite.Cookies",
                Value = "13456789jhsvfshvdfjksDg48484751458sfgdfgdfg",
                Domain = ".example.com",
                Path = "/",
                HttpOnly = true,
                Secure = true,
                Expires = DateTime.UtcNow.AddHours(1)
            };
var cookieValue = $"{cookie.Name}={cookie.Value};domain={cookie.Domain};path={cookie.Path};secure;httponly;samesite=lax;";
            CookieManager.Instance.SetCookie("https://www.example.com/", cookieValue);
  1. Try to fetch the cookie :
//fetch cookies with same site
            var fetchCookie = CookieManager.Instance.GetCookie("https://www.example.com/");
            Console.WriteLine($"Cookie fetched:{fetchCookie 

}");

Expected Behavior

The cookie should be fetched

Actual Behavior

The cookie is not getting fetched

Version Information

Log File

@jonathanpeppers
Copy link
Member

@MdNaushad I think we just need to reflect upon your code a little.

A couple points:

  • It looks like you create a System.Net.Cookie object, that is a BCL type (not Android)?
  • It looks like you are calling the Android.WebKit.CookieManager class to set the cookie, which only takes a string?

I'm not sure what using this Cookie object is doing for you? Also you might be running into this semi-colon issue as mentioned here: https://medium.com/@ericluapp/something-might-be-confused-about-cookiemanager-setcookie-422e6e28aacf

I just changed the code to this and it's working for me:

var manager = CookieManager.Instance;
manager.SetCookie ("https://www.example.com/", "abcd=1234");
var cookie = manager.GetCookie ("https://www.example.com/");
Android.Util.Log.Debug ("MyApp", $"Cookie: {cookie}");

I'm not sure this will persist between app launches or not (you didn't mention in your steps). Closing this for now, as I think it is an Android API usage issue and not an issue with Xamarin.Android. If you have further questions about Android APIs, I think StackOverflow would be a better place for those.

Hope this helps, thanks!

@MdNaushad
Copy link
Author

Hey @jonathanpeppers : Thank you for looking into this.
In my issue I have mentioned just the important steps of the flow. To answer your questions:

  • It looks like you create a System.Net.Cookie object, that is a BCL type (not Android)?
    Yes, the project I am using is Xamarin.Forms, I also created a new project to replicate the issue, unfortunately I am not able to attach my test project here.

It looks like you are calling the Android.WebKit.CookieManager class to set the cookie, which only takes a string?

Yes I am using Android.WebKit.CookieManager to set the cookie. The SetCookie method accepts two parameters, first one is URL and second one is Cookie, the cookie has to be string with ";" separated properties.
If you see in this line of code, I am forming a cookie by extracting the values from the System.Net.Cookie object:
var cookieValue = $"{cookie.Name}={cookie.Value};domain={cookie.Domain};path={cookie.Path};secure;httponly;samesite=lax;";
The final cookie looks something like this:
.WithSameSite.Cookies=13456789jhsvfshvdfjksDg48484751458sfgdfgdfg;domain=.example.com;path=/;secure; httponly; samesite=lax;

In the code that you have written, it's working of course because the "samesite=lax;" value is not set for the cookie that you created.
Here is your modified code:

var manager = CookieManager.Instance;
manager.SetCookie ("https://www.example.com/", "abcd=1234;samesite=lax;httponly;secure");
var cookie = manager.GetCookie ("https://www.example.com/");
Android.Util.Log.Debug ("MyApp", $"Cookie: {cookie}");

Can you please try this and let me know if it stills work?

@jonathanpeppers
Copy link
Member

Also you might be running into this semi-colon issue as mentioned here: https://medium.com/@ericluapp/something-might-be-confused-about-cookiemanager-setcookie-422e6e28aacf

Android's API here doesn't like multiple semi-colons at once, take a look at the above article written by a Java/Android dev. I think you are hitting a problem with how to use Android APIs, and this is not a bug in Xamarin.Android, thanks!

@vd3d
Copy link

vd3d commented Jul 8, 2020

I'm not 100% sure my problem is the same, but in my case, I do the following:

  1. [from Xamarin.Android.WebView] I set a cookie with
CookieManager.Instance.SetCookie(cookieDomain, cookieName + "=" + cookieValue);
CookieManager.Instance.Flush();
  1. [from my HTML/Javascript app] The web application do a Javascript call to set a cookie, like this:

document.cookie = cname + "=" + cvalue + expires + ";Secure;path=/";

  1. [from Xamarin.Android.WebView] An finally, I try to read all the cookies like this:

string cookieHeader = CookieManager.Instance.GetCookie(url);

But the cookieHeader does not contains the Javacript-cookie, only the first one !!

@jonathanpeppers
Copy link
Member

@vd3d I think you are having an issue on the JavaScript side, looking at this post:

https://stackoverflow.com/a/16842361

It seems like you need to set document.cookie multiple times for multiple key-value pairs.

I know nothing about JavaScript, though!

image

@vd3d
Copy link

vd3d commented Jul 9, 2020

LOL :-)

The javascript side works perfectly. The in Xamarin, I cannot read all the cookies that are added by the website,
when I do:

string cookieHeader = CookieManager.Instance.GetCookie(url);

I only get my cookies... I don't see all the "AspNet" cookies by example!

@brendanzagaeski
Copy link
Member

This is a little outside the scope of what is typically addressed in GitHub issues for Xamarin.Android because it is part of the upstream Android API behavior rather than anything specific to Xamarin, but note that when using WebView and CookieManager, there are at least 2 pieces required to see cookies that are set via JavaScript.

  1. The WebView must finish loading the URL before the cookies are read. For example, create a custom WebViewClient:

    public class MyWebViewClient : Android.Webkit.WebViewClient
    {
        public override void OnPageFinished(WebView view, string url)
        {
            var cookie = CookieManager.Instance.GetCookie(url);
            Android.Util.Log.Debug("MyApp", $"Cookie: {cookie}");
            base.OnPageFinished(view, url);
        }
    }

    And set it on the WebView:

    webView.SetWebViewClient(new MyWebViewClient());
  2. JavaScript must be enabled for the WebView:

    webView.Settings.JavaScriptEnabled = true;

@ghost ghost locked as resolved and limited conversation to collaborators Jun 7, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants