34

I have two sites, both on the same domain, but with different sub-domains.

  • site1.mydomain.example
  • site2.mydomain.example

Once I'm authenticated on each, I look at the cookies included in subsequent request and they are identical for each site.

However, if I log into the first site, and then navigate to the other, I expect my cookie from site 1 to be sent with the request to site2, but this is not the case. Here are the properties of my cookies.

Logging into Site1, this cookie then exists

Name = MySite
Domain =
Has Keys = False
HttpOnly = False
Path = /
Value = 1C41854066B03D8CC5679EA92DE1EF427DAC65D1BA0E672899E27C57245C1F0B7E93AB01B5563363AB4815A8F4BDE9D293FD261E03F8E60B8497ABBA964D8D315CCE1C8DD220C7176E21DC361935CF6
Expires = 1/1/0001 12:00:00 AM

Logging into Site2, these cookies then exists.

Name = MySite
Domain =
Has Keys = False
HttpOnly = False
Path = /
Value =    C8C69F87F993166C4D044D33F21ED96463D5E4EB41E1D986BF508DA0CBD5C2CA7D782F59F3BC96871108997E899FF7401C0D8615705BDB353B56C7E164D2302EE6731F41705016105AD99F4E0578ECD2
Expires = 1/1/0001 12:00:00 AM

I've set the domain on each (doesn't show up in a request cookie as it's only needed on the client). I've made sure my Forms setting for each are identical I've made sure my machine key settings are the same in both web configs.

I'm at a loss on why this isn't working. What is it that a cookie contains that the client will send it for one sub-domain and not the other when they are both using the same auth cookies so far as I can tell?

Please comment if there is more info you'd like to see. I've been struggling with this for two days now. According to this article this should be working.

code added

Here is my config file setting for my authentication. This is used in both sites.

<authentication mode="Forms">
    <forms loginUrl="~/Account/LogOn"
       defaultUrl="~/Home/Index"
       name="MySite"
       protection="All"
       path="/"
       domain="mydomain.example"
       enableCrossAppRedirects="true"
       timeout="2880"
/>

And here is my code to create the cookie in Site1.

//Add a cookie that the Site2 will use for Authentication
var cookie = FormsAuthentication.GetAuthCookie(userName, true);
cookie.Name = "MySite";
cookie.HttpOnly = false;
cookie.Expires = DateTime.Now.AddHours(24);
cookie.Domain = "mydomain.example";
HttpContext.Response.Cookies.Add(cookie);
HttpContext.Response.Redirect(site2Url,true);

UPDATE 2:

I noticed something strange while testing. When I add a cookie to the response for site1, it get's added to this directory... C:\Users\jreddy\AppData\Roaming\Microsoft\Windows\Cookies

When I add a cookie to the response for site, it gets added to this directory... C:\Users\jreddy\AppData\Roaming\Microsoft\Windows\Cookies\Low

That could be my problem. Could it be that one of my sites is included in the local intranet zone?

UPDATE 3: Problem found, solution unknown It seems that my problem has to do with my second site being part of the Local Intranet Zone. If I go to Site1 using Firefox it works, but I have to enter my Windows credentials. If I go thru IE, my credentials are picked up automatically, but the cookies can't be read by site2. I may ask this in another question.

Stephen Ostermiller
  • 23,933
  • 14
  • 88
  • 109
Jeff Reddy
  • 5,551
  • 9
  • 55
  • 88

4 Answers4

20

Set the property of Domain to .mydomain.example in each Cookies of two subdomains websites. Like:

Response.Cookies["test"].Value = "some value";
Response.Cookies["test"].Domain = ".mysite.example";

In Site A:

HttpCookie hc = new HttpCookie("strName", "value");
hc.Domain = ".mydomain.example"; // must start with "."
hc.Expires = DateTime.Now.AddMonths(3);
HttpContext.Current.Response.Cookies.Add(hc);

In Site B:

HttpContext.Current.Request.Cookies["strName"].Value
Stephen Ostermiller
  • 23,933
  • 14
  • 88
  • 109
Mhmd
  • 4,989
  • 3
  • 22
  • 29
  • Does my Domain setting need to be ".mydomain.com" as opposed to "mydomain.com" (decimal leading domain name)? – Jeff Reddy Sep 29 '11 at 12:02
  • I tried that, and it didn't work. I also tried creating a second cookie, holding a random value as opposed to the 'FormsAuthentication' cookie. It isn't picked up by my 2nd site either. – Jeff Reddy Sep 29 '11 at 13:23
  • Jeff: yes "." must be present, and see the update 1 and test that code, :) – Mhmd Sep 29 '11 at 15:10
  • 1
    I tried what you added, almost verbatim, and still no luck. Originally I was trying to share an authentication cookie, but at this point I'll settle for "strName" and "value". When I got to site one, and create that cookie as you suggested, it's always sent in future requests to that site (site1), but site2 never gets it. – Jeff Reddy Sep 29 '11 at 17:23
  • First, i am sure that this code is right and working, i am using it in my projects, second, playing with cookie have many conditions, so make sure that you have cleared the old one, then make sure that cookie is created well by check it in browser with the domain value to ".mydomain.com" and expire enough value, after that the final step reading it by the code i have told you ... tell me in which step you did to solve this problem. REgards – Mhmd Sep 29 '11 at 19:24
  • I'm going to attempt to expire all my cookies. I've been manually deleting them from my local directory. I think the code is correct, but there is something unique to my site that isn't allowing the cookies to be sent in the request for site2. – Jeff Reddy Sep 29 '11 at 19:39
  • use firefox, have a tools to browse cookiees, tell me as i told you if your cookies has been created first :) – Mhmd Sep 29 '11 at 19:45
  • I tried something different. I created a cookie in Site2, and then opened site1. It worked. I copied the code from Site1 into Site2, and I changed only the name and value of the cookie. So the code isn't different. I feel like I'm getting closer, but still not there. – Jeff Reddy Sep 29 '11 at 20:12
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/3911/discussion-between-jeff-reddy-and-bmtu) – Jeff Reddy Sep 29 '11 at 20:17
9

Add new cookie and specify domain like this

HttpCookie cookie = new HttpCookie("cookiename", "value");
cookie.Domain = "domain.example";

For forms authentication set this in web.config

<forms name=".ASPXAUTH"
       loginUrl="login.aspx"
       protection="All"
       timeout="30"
       path="/"
       requireSSL="false"
       domain="domain.example">
</forms>

The cookie will be accessible to all the subdomains.

In order for each domain to decrypt the the cookie, all web.config files must use the same encryption/decryption algorithm and key. (how to create a machine key)

Example:

// do not wrap these values like this in the web.config
// only wrapping for code visibility on SO
<machineKey
  validationKey="21F090935F6E49C2C797F69BBAAD8402ABD2EE0B667A8B44EA7DD4374267A75
                 D7AD972A119482D15A4127461DB1DC347C1A63AE5F1CCFAACFF1B72A7F0A281
                 B"
  decryptionKey="ABAA84D7EC4BB56D75D217CECFFB9628809BDB8BF91CFCD64568A145BE59719
                 F"
  validation="SHA1"
  decryption="AES"
/>

For easier deployments, these values can be stored in a separate file:

<machineKey configSource="machinekey.config"/>

For added security you can also encrypt the machine key for further protection..

Stephen Ostermiller
  • 23,933
  • 14
  • 88
  • 109
Prasanth
  • 3,029
  • 31
  • 44
  • I added the authentication config settings I'm using for both sites, i addition to the cookie creation code. – Jeff Reddy Sep 29 '11 at 12:01
  • I tried adding another cookie to my response in site1, similar to yours. I simply named it test, gave it random value and then made sure I set the domain. Once set, future visits to Site1 give me the cookie, but visits to site2 don't get the cookie. – Jeff Reddy Sep 29 '11 at 13:25
  • See this link http://www.15seconds.com/issue/971108.htm or SO question - http://stackoverflow.com/questions/2172490/asp-net-subdomain-cookie-parent-and-one-subdomain – Prasanth Sep 29 '11 at 17:55
  • I've pulled samples and suggestions from both those sites. Still can't get cookies in site2. – Jeff Reddy Sep 29 '11 at 19:33
  • 1
    For the forms authentication cookie, it's also worth mentioning that machine keys should match if there are multiple applications. In addition, I had to explicitly set the compatibilityMode in order to get things to play nice in IIS8. http://msdn.microsoft.com/en-us/library/system.web.configuration.machinekeysection.compatibilitymode.aspx – Jim Geurts Aug 27 '13 at 21:11
4

If you're using Forms authentication on all of your sub domains, all you need to do is to add domain=".mydomain.example" property to the <forms> node in your web.config

Note the leading period in .mydomain.example

This simple change by itself will make your authentication cookie valid in all sub-domains; no need to manually set any cookies.

Stephen Ostermiller
  • 23,933
  • 14
  • 88
  • 109
roman m
  • 26,012
  • 31
  • 101
  • 133
1

I've created a HttpContext extension method that will write a sub domain safe cookie.

Blog post and discussion

public static class HttpContextBaseExtenstions
{
    public static void SetSubdomainSafeCookie(this HttpContextBase context, string name, string value)
    {
        var domain = String.Empty;

        if (context.Request.IsLocal)
        {
            var domainSegments = context.Request.Url.Host.Split('.');
            domain = "." + String.Join(".", domainSegments.Skip(1));
        }
        else
        {
            domain = context.Request.Url.Host;
        }

        var cookie = new HttpCookie(name, value)
        {
            Domain = domain
        };

        context.Response.SetCookie(cookie);
    }
}

// usage
public class MyController : Controller
{
    public ActionResult Index()
    {
        this.Context.SetSubdomainSafeCookie("id", Guid.NewGuid().ToString());
        return View();
    }
}
Nick
  • 6,366
  • 5
  • 43
  • 62