For more information regarding the security incident at F5, the actions we are taking to address it, and our ongoing efforts to protect our customers, click here.

Forum Discussion

nmaynard's avatar
nmaynard
Icon for Altocumulus rankAltocumulus
Nov 15, 2025
Solved

Strict header Insertion

Howdy!   Incredibly new to the F5 world, and trying to learn fast after the last F5 SME left.   Here's my issue: Our organization currently has a static page being served up directly on the F5. ...
  • F5_Design_Engineer's avatar
    Nov 19, 2025

    nmaynard​ 

     

    You’re running into a very common issue: when you use `HTTP::respond` in an iRule, you completely generate the full response, meaning F5 won’t automatically add additional headers afterward. 

    So if you want HSTS (or any other header) applied, you must include it directly inside the HTTP::respond command that sends the content.

    Also, you can’t use `HTTP_RESPONSE` or `HTTP_RESPONSE_RELEASE` here because there is no server response coming back—you are short-circuiting the request and generating the response directly on the F5. 

    That means `HTTP_RESPONSE` will never fire.

    To solve this situation

    Add the HSTS header directly in your `HTTP::respond` commands, like this:

    ```
    when HTTP_REQUEST {
        set hsts_header {Strict-Transport-Security "max-age=31536000; includeSubDomains; preload"}

        switch [HTTP::uri] {
            "/" {
                HTTP::respond 200 \
                    content [ifile get webpage_ifile] \
                    "Content-Type" "text/html" \
                    $hsts_header
            }

            "/mainpage.png" {
                HTTP::respond 200 \
                    content [ifile get mainpage_ifile] \
                    "Content-Type" "image/png" \
                    $hsts_header
            }

            "/favicon.ico" {
                HTTP::respond 200 \
                    content [ifile get favicon_ifile] \
                    "Content-Type" "image/x-icon" \
                    $hsts_header
            }
        }
    }
    ```

    This will work as the HSTS header is inserted at the moment the response is generated.
    Since the F5 is creating the response internally, this is the only chance to add the header.


    Make sure this is HTTPS-only

    HSTS must only be applied to HTTPS responses.

    If this iRule applies on an HTTP virtual server, you should either redirect HTTP to HTTPS first or add a protocol check.

    You can do this once with a small TCL variable

    As shown, using a `set` for the header at the top avoids repeating long strings.

    If you want to enforce TLS-only redirect

    Add this at the top:

    ```
    if { [TCP::local_port] == 80 } {
        HTTP::respond 301 Location "https://[HTTP::host][HTTP::uri]"
        return
    }
    ```

     

    I usually prefer using an HTTP Profile instead of iRule

    If your VIP is HTTPS and you want HSTS globally, you can simply:

    1. Go to:

    ```
    Local Traffic → Profiles → HTTP → <your HTTP Profile>
    ```

    2. Set:

    ```
    HSTS = Enabled
    Max Age = 31536000
    Include Subdomains = Checked
    ```

    This is cleaner and doesn't need iRules.

    However, since you're generating the response via `HTTP::respond`, the rule still overrides everything—so adding the header directly in the rule is required unless you switch to standard server responses.


    So here is the summary

    `HTTP::respond` bypasses the normal response pipeline.

    Therefore, you must add `Strict-Transport-Security` in the same command that generates the response.

    Your updated iRule as above will satisfy the security scan.

    let me now for any further assistance.

    F5 Design Engineer