Forum Discussion

johns's avatar
johns
Ret. Employee
Mar 02, 2006

iRule recognize blank space in URI?

Hi, I need to detect blank space in URI and either remove it or rewrite it:

 

 

www.mysite.com/some content/showme.html

 

 

to

 

 

www.mysite.com/some%20content/showme.html

 

 

Current solution in place is only recognizing up to the space so it reads:

 

www.mysite.com/some. and breaks the client request to the server.

 

 

I am thinking if I can find out how BIG-IP can detect the space, I will just replace it with characters that I need in its place.

 

 

Thanks.

27 Replies

  • johns's avatar
    johns
    Ret. Employee
    What about below?

     

     

    when CLIENT_ACCEPTED {

     

    TCP::collect 300

     

    }

     

    when CLIENT_DATA {

     

    set matchedURI [regexp -inline "/vMoD.+HTTP" [TCP::payload]]

     

    if { [string length $matchedURI] > 0 } {

     

    set newURI [getfield [getfield $matchedURI " HTTP" 1] "\{" 2]

     

    log local0. "URI was matched. Result: $newURI"

     

    set preencURI [TCP::payload replace 0 [TCP::payload] $newURI]

     

    set encURI [string map { " " %20} $preencURI]

     

    log local0. "encURI is $encURI"

     

    } else {

     

    log local0. "no match"

     

    set uriRewrite 0

     

    }

     

    }

     

    when HTTP_REQUEST {

     

    if {$uriRewrite == 1} {

     

    HTTP::uri $encURI

     

    log local0. "It worked! [HTTP::uri]"

     

    }

     

    }
  • Lee_Orrick_5554's avatar
    Lee_Orrick_5554
    Historic F5 Account
    John, unRuley is saying to not use the HTTP_REQUEST method at all. If you give the HTTP parser any shot at it, it is going to munge the data. You have the URI rewritten in CLIENT_DATA. Just let it go through to the client now.

     

     

  • johns's avatar
    johns
    Ret. Employee
    So, this means I have to find the URI, replace spaces with %20, then find the offset where "GET /" is and replace the number that equals to string length of the URI between GET / and HTTP/1.0?

     

     

    Does this sound about right?

     

  • johns's avatar
    johns
    Ret. Employee
    Couple of questions, I am collecting TCP data up to about 100 under the assumption that 100 will be enough to grab the URI. The request is coming from mobile phones, and I do not want the BIG-IP to hold the connection open (introducing the delay) in case the request is less than 100. Is this something I should be concerned about?

     

     

    Also, I am thinking of using similar "regexp -inline ".+GET " against TCP::payload to find string up to the URI and calculate the offset, does this look ok?

     

     

    Thanks.
  • johns's avatar
    johns
    Ret. Employee
    I ended up with:

     

     

    when CLIENT_ACCEPTED {

     

    TCP::collect 100

     

    }

     

    when CLIENT_DATA {

     

    Grab characters b/w GET and HTTP version

     

    set matchedURI [regexp -inline "/vMoD.+HTTP" [TCP::payload]]

     

    Find the length of payload up to GET to use as offset

     

     

     

    if { [string length $matchedURI] > 0 } {

     

    Parse the URI and convert spaces to %20

     

    set newURI [getfield [getfield $matchedURI " HTTP" 1] "\{" 2]

     

    set encURI [string map { " " %20} $newURI]

     

    Replace the URI with space with the encoded URI

     

    4 is used as offset, counting "GET ", cound not think of better way

     

    TCP::payload replace 4 [string length $newURI] $encURI

     

    log local0. "encURI is $encURI"

     

    set uriRewrite 1

     

    } else {

     

    set uriRewrite 0

     

    log local0. "no match"

     

    }

     

    }

     

    when HTTP_REQUEST {

     

    verify URI is converted as needed with HTTP parser

     

    if {$uriRewrite == 1} {

     

    log local0. "It worked! [HTTP::uri]"

     

    }

     

    }

     

     

     

     

     

    and it seems to work if I try it with browser (space already encoded since telnet does not seem to let the rule process into HTTP_REQUEST for verification) Would you mind giving me an eyeball on it?

     

     

    Thanks.