Forum Discussion

DJDX21_252164's avatar
Mar 17, 2016
Solved

iRule to rewrite cookie domain to toplevel domain

I have to domains, 1. xyz.abc.com 2. xyz.abbc.com Now when I am trying to change the domain of the cookie at the toplevel the below iRule isn't working.

 

when HTTP_RESPONSE { set a ".abc.com" set b ".abbc.local" foreach mycookie [HTTP::cookie names] { set cookieDomain [HTTP::cookie domain $mycookie] if {$cookieDomain contains $a } { HTTP::cookie domain $mycookie $a } elseif {$cookieDomain contains $b } { HTTP::cookie domain $mycookie $b } } }

 

There is no response of the iRule.

 

Expected:

 

cookie domain for xyz.abc.com should be .abc.com and for xyz.abbc.com should be .abbc.com

 

Help?

 

  • Finally I was able to set the cookie domain to toplevel by using the following iRule. Cookies are set to toplevel domain now by using HTTP::host and comparing directly with the domain values I have. What do you think about the following iRule? Any flaws?

    when HTTP_REQUEST {
        log local0. "Cookie names in received request: [HTTP::cookie names] from IP: [IP::local_addr]"
       set httphost [HTTP::host]
    }
    
    when HTTP_RESPONSE { 
        foreach mycookie [HTTP::cookie names] { 
         log local0. "Host : $httphost"
            if { $httphost ends_with ".abc.com" } { 
                HTTP::cookie domain $mycookie ".abc.com"
            } elseif { $httphost ends_with ".abbc.com" } { 
                HTTP::cookie domain $mycookie ".abbc.com"
            } else {
              log local0. "Not a single cookie domain matched :"
            }
        } 
    }
    

17 Replies

  • Lets get the easy questions out of the way. Do you have an HTTP profile attached? Also, if this is HTTPS do you have a client SSL profile attached?

     

  • I think he could not use such iRules HTTP functions if he did not had http profile applied, but better if DJDX21 can confirm that point, and good point pointing with eventual HTTPS.

    DJDX21, according to your example, you have entered:

    set b ".abbc.local"
    

    instead of:

    set b ".abbc.com"
    

    Likely, if your problem does not come from missing http or ssl client profiles, your if statements most probably never match. You can simply check that with logging like for instance:

    when HTTP_REQUEST {
        log local0. "Cookie names in received request: [HTTP::cookie names] from IP: [IP::local_addr]"
    }
    
    when HTTP_RESPONSE { 
        set a ".abc.com" 
        set b ".abbc.com" 
    
        foreach mycookie [HTTP::cookie names] { 
            set cookieDomain [HTTP::cookie domain $mycookie] 
    
            if { $cookieDomain contains $a } { 
                log local0. "Cookie domain matched: $a"
                HTTP::cookie domain $mycookie $a 
            } 
            elseif { $cookieDomain contains $b } { 
                log local0. "Cookie domain matched: $a"
                HTTP::cookie domain $mycookie $b 
            }
            else {
                log local0. "Not a single cookie domain matched :/"
            }
        } 
    }
    

    Note I did not test this iRule on real traffic but only validates the compilation on a VM.

    Good luck

    • DJDX21_252164's avatar
      DJDX21_252164
      Icon for Cirrus rankCirrus
      Thanks will try logging and yes I have profile attached and HTTPS enabled. Thanks!
    • DJDX21_252164's avatar
      DJDX21_252164
      Icon for Cirrus rankCirrus
      @Sylvain. Thanks for the advice I tried logging and it seems "Not a single cookie domain matched :\" But it should match because when for only abc.com works. when HTTP_RESPONSE { foreach mycookie [HTTP::cookie names] { HTTP::cookie domain $mycookie ".abc.com" } }
  • But it should match because when for only abc.com works

     

    What do you mean?

     

    Can you please post the output of the log of when HTTP_REQUEST statement? And also the content of $mycookie variable? (add it into you log statements) One last thing, I would suggest to use end_with function (or similar) instead of contains (https://devcentral.f5.com/wiki/iRules.ends_with.ashx) since you're targeting the end of cookie domain value.

     

    • DJDX21_252164's avatar
      DJDX21_252164
      Icon for Cirrus rankCirrus
      Cookie names in received request: ASP.NET_SessionId .AB.DOMAIN.ID .AB.QA.CCM.99 from IP: *.*.*.* : Not a single cookie domain matched :/
  • And the value of $mycookie in each if statement. Please use below code as I just noticed I made a copy/paste mistake in the log of the second if statement (the one for $b):

     

    when HTTP_REQUEST {
        log local0. "Cookie domain in received request: [HTTP::cookie names] from IP: [IP::local_addr]"
    }
    
    when HTTP_RESPONSE { 
        set a ".abc.com" 
        set b ".abbc.com" 
    
        foreach mycookie [HTTP::cookie names] { 
            set cookieDomain [HTTP::cookie domain $mycookie] 
            log local0. "==> cookieDomain value is : $cookieDomain"
    
           if { $cookieDomain contains $a } { 
                log local0. "Cookie domain matched: $a"
                HTTP::cookie domain $mycookie $a 
            } 
            elseif { $cookieDomain contains $b } { 
                log local0. "Cookie domain matched: $b"
                HTTP::cookie domain $mycookie $b 
            } else {
                log local0. "Not a single cookie domain matched :/"
            }
    
        } 
    }

    We definitively need to have a clear idea of the value of $cookieDomain to make a correct match on it.

     

    • DJDX21_252164's avatar
      DJDX21_252164
      Icon for Cirrus rankCirrus
      Yeah, I rectified it before paste. the if statement is matching now. Cookie names in received request: ASP.NET_SessionId .AB.DOMAIN.ID .AB.QA.CCM.99 from IP: *.*.*.* Cookie domain matched: .abc.com But the domain is still not getting set I can still see xyz.abc.com
  • So what gives the logging in your logs of:

    log local0. "==> cookieDomain value is : $cookieDomain"`
    

    $cookieDomain value is not the same as cookie name dumps. We need to be sure what there is in this variable.

    • DJDX21_252164's avatar
      DJDX21_252164
      Icon for Cirrus rankCirrus
      : ==> cookieDomain value is : : Not a single cookie domain matched : Nothing is getting in cookieDomian, but then how was it going in if block. Just fyi: when HTTP_RESPONSE { foreach mycookie [HTTP::cookie names] { HTTP::cookie domain $mycookie ".abc.com" } } This works perfect but nothing works when if is applied.
  • When you do not use the if statements, you insert/replace domain cookie because you do not question about $cookieDomain value. That's why it's working.

     

    The if statement are not working just because there is nothing into $cookieDomain variable. So the they always return "fasle" and you end up into the final else (the one logging Not a single cookie domain matched :/)

     

    It would help if you could post HTTP headers into the response (name and value, eventually values anonymized) since it seems you want to rewrite domain cookie in responses. You can use developer tool in Chrome or Firefox to do that (F12 and network console), or a tcpdump or any other solution you like.

     

    I have the feeling you're not using the correct cookie statement (ie. HTTP::cookie domain in your iRule) but I can be wrong. Having clear listing of HTTP headers in responses would be definitively helpful.

     

  • Finally I was able to set the cookie domain to toplevel by using the following iRule. Cookies are set to toplevel domain now by using HTTP::host and comparing directly with the domain values I have. What do you think about the following iRule? Any flaws?

    when HTTP_REQUEST {
        log local0. "Cookie names in received request: [HTTP::cookie names] from IP: [IP::local_addr]"
       set httphost [HTTP::host]
    }
    
    when HTTP_RESPONSE { 
        foreach mycookie [HTTP::cookie names] { 
         log local0. "Host : $httphost"
            if { $httphost ends_with ".abc.com" } { 
                HTTP::cookie domain $mycookie ".abc.com"
            } elseif { $httphost ends_with ".abbc.com" } { 
                HTTP::cookie domain $mycookie ".abbc.com"
            } else {
              log local0. "Not a single cookie domain matched :"
            }
        } 
    }
    
    • Sylvain_85827's avatar
      Sylvain_85827
      Icon for Cirrus rankCirrus
      Just remember when you go live with iRule to remove all log entries and the final else that will become useless. when HTTP_REQUEST { set httphost [HTTP::host] } when HTTP_RESPONSE { foreach mycookie [HTTP::cookie names] { if { $httphost ends_with ".abc.com" } { HTTP::cookie domain $mycookie ".abc.com" } elseif { $httphost ends_with ".abbc.com" } { HTTP::cookie domain $mycookie ".abbc.com" } } }
  • Finally I was able to set the cookie domain to toplevel by using the following iRule. Cookies are set to toplevel domain now by using HTTP::host and comparing directly with the domain values I have. What do you think about the following iRule? Any flaws?

    when HTTP_REQUEST {
        log local0. "Cookie names in received request: [HTTP::cookie names] from IP: [IP::local_addr]"
       set httphost [HTTP::host]
    }
    
    when HTTP_RESPONSE { 
        foreach mycookie [HTTP::cookie names] { 
         log local0. "Host : $httphost"
            if { $httphost ends_with ".abc.com" } { 
                HTTP::cookie domain $mycookie ".abc.com"
            } elseif { $httphost ends_with ".abbc.com" } { 
                HTTP::cookie domain $mycookie ".abbc.com"
            } else {
              log local0. "Not a single cookie domain matched :"
            }
        } 
    }
    
    • Sylvain_85827's avatar
      Sylvain_85827
      Icon for Cirrus rankCirrus
      Just remember when you go live with this iRule to remove all log entries and the final else statement that will become useless.