Forum Discussion

Ritchie-T's avatar
Ritchie-T
Icon for Nimbostratus rankNimbostratus
Sep 16, 2020
Solved

http to https redirect on single VIP using a port list consisting of port 80 and 443

Hi there,

 

In the past I have had 2 virtual servers when wanting to redirect from HTTP to HTTPS. One on port 80 with the built in "_sys_https_redirect" irule, then another on port 443 for the redirect to land on.

 

Since the introduction of "Shared Objects ›› Port Lists" I have attempted to have one virtual server and have it listen on port 80 and 443. This does work as expected until I add on the https redirect irule. This then breaks https connections to the VIP.

 

I have attempted to catch only the port 80 requets and redirect them in an attempt to not interfere with the 443 requests that do not need redirecting. Initially I attempted the below:

 

when HTTP_REQUEST {

  if { [TCP::local_port] == 80 } {

    HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]

  }

}

 

 

This failed to identify the traffic. From what I can understand it is because the virtual server has an SSL client profile attached which stops the http traffic even being identified, which it needs for the https connections. I was able to find a way to identify the http traffic by disabling SSL a below:

 

when CLIENT_ACCEPTED {

  if { [TCP::local_port] == 80 } {

  log local0.notice "Port 80 connection hit"

    SSL::disable

  }

}

 

 

I can see in the logs this is being hit. The problem I have is that I cannot do the HTTP::redirect if using the "when CLIENT_ACCEPTED", but I cannot identify the port 80 traffic if using the "when HTTP_REQUEST".

 

Kind of stuck with the 2 not talking to each other in the same irule.

 

Has anybody else come across this problem?

 

Many thanks

  • Do you have Non-SSL Connections enabled in your clientSSL profile?

6 Replies

  • Do you have Non-SSL Connections enabled in your clientSSL profile?

  • Hi

     

    I think what you are trying to achieve is not possible. If you want to simplify, you could create a VS listening on port 80 on the wildcard address 0.0.0.0 with the _sys_https_redirect irule. Any request going to that VS, will be redirected to the relevant HTTPS Virtual Server.

     

    Would that match your requirement ?

     

    Yoann

     

  • Thanks for the reply Yoann. I doubt this would work due to the DNS names having to point to a particular IP. I could not direct port 80 traffic to a different address and 443 to another.

     

    I always thought it was a messy config to have duplicate VIPs for every https redirect. I was hoping that the port lists would offer a cleaner setup.

     

    If it is not possible then I can always go back to the previous design.

     

    I will keep having a play. Thanks for your help.

     

    Ritchie

  • Agreed, but if you create a VS that listens on 0.0.0.0:80, this would respond to ANY IP address. Or you can be a bit more precise let's say : 192.168.10.0/24:80 to restrict that to a full network.

     

    But make sure this does not confilct with other use case on your infrastructure :)

     

    Then you only have one VIP for HTTPS 192.168.10.1:443.

  • The problem is with DNS still though. If http://www.mywebsite.com has a DNS record of 1.2.3.4 then the redirect for https://www.mywebsite.com will still go to 1.2.3.4 because DNS is not port specific.

  • Excellent. Jason!

     

    I did not know that was an option. With Non-SSL Connections enabled in the client SSL profile I do not need to disable the SSL for port 80 requests anymore under "when CLIENT_ACCEPTED". This leaves me free to process the irule using only "when HTTP_REQUEST". I had to tweak the irule slightly from my original post, but the below works a charm 👍

     

    when HTTP_REQUEST {

      if { [TCP::local_port] == 80 } {

      if {[HTTP::has_responded]}{return}

        HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]

        event disable

      }

    }