util_current_location (public)

 util_current_location

Defined in packages/acs-tcl/tcl/utilities-procs.tcl

This function behaves like [ad_conn location], since it returns the location string of the current request in the form protocol://hostname?:port? but it honors the "Host:" header field (when the client addressed the server with a hostname different to the default one from the server configuration file) and therefore as well the host-node mapping. If the "Host" header field is missing or empty this function falls back to [ad_conn location].

Returns:
the current location in the form "protocol://hostname?:port?"
See Also:

Partial Call Graph (max 5 caller/called nodes):
%3 test_ad_dom_sanitize_html ad_dom_sanitize_html (test acs-tcl) util_current_location util_current_location test_ad_dom_sanitize_html->util_current_location test_get_insecure_location get_insecure_location (test acs-tcl) test_get_insecure_location->util_current_location test_sync_http_get_document sync_http_get_document (test acs-authentication) test_sync_http_get_document->util_current_location ad_conn ad_conn (public) util_current_location->ad_conn ad_url ad_url (public) util_current_location->ad_url apm_package_id_from_key apm_package_id_from_key (public) util_current_location->apm_package_id_from_key parameter::get parameter::get (public) util_current_location->parameter::get security::validated_host_header security::validated_host_header (public) util_current_location->security::validated_host_header ad_dom_sanitize_html ad_dom_sanitize_html (public) ad_dom_sanitize_html->util_current_location ad_html_qualify_links ad_html_qualify_links (public) ad_html_qualify_links->util_current_location ad_returnredirect ad_returnredirect (public) ad_returnredirect->util_current_location packages/acs-subsite/www/members/member-state-change.tcl packages/acs-subsite/ www/members/member-state-change.tcl packages/acs-subsite/www/members/member-state-change.tcl->util_current_location rp_filter rp_filter (private) rp_filter->util_current_location

Testcases:
sync_http_get_document, get_insecure_location, ad_dom_sanitize_html
Source code:

    #
    # Compute util_current_location only once per request and cache
    # the result per thread.
    #
    if {[info exists ::__util_current_location]} {
        return $::__util_current_location
    }

    #
    # In case we have no connection return the location based on the
    # configured kernel parameters. This will be the same value for
    # all (maybe host-node mapped) subsites, so probably one should
    # parameterize this function with a subsite value and compute the
    # result in the non-connected based on the subsite_id.
    #
    if {![ns_conn isconnected]} {
        return [ad_url]
    }

    set default_port(http) 80
    set default_port(https) 443
    set default_port(udp) 8000

    #
    # The package parameter "SuppressHttpPort" might be set when the
    # server is behind a proxy to hide the internal port.
    #
    set suppress_port [parameter::get  -package_id [apm_package_id_from_key acs-tcl]  -parameter SuppressHttpPort  -default 0]
    #
    # Obtain the information from ns_conn based on the actual driver
    # handling the current request.  The obtained variables "proto",
    # "hostname" and "port" will be the default and might be
    # overwritten by more specific information.
    #
    if {![util::split_location [ns_conn location] proto hostname port]} {
        ns_log Error "util_current_location got invalid information from driver '[ns_conn location]'"
        # provide fallback info
        set hostname [ns_info hostname]
        set proto ""
    }
    if {$proto eq ""} {
        set proto http
        set port  $default_port($proto)
    }

    if { [ad_conn behind_proxy_p] } {
        #
        # We are running behind a proxy
        #
        if {[ad_conn behind_secure_proxy_p]} {
            #
            # We know, the request was an HTTPS request
            #
            set proto https
        }
        #
        # reset to the default port
        #
        set port $default_port($proto)
    }

    #
    # If we want to allow developers to access the backend server
    # directly (not via the proxy), the clause above does not fire,
    # although "ReverseProxyMode" was set, since there is no
    # "X-Forwarded-For".  The usage of "SuppressHttpPort" would not
    # allow this use case.
    #

    #
    # In case the "Host:" header field was provided, use the "hostame"
    # and maybe the "port" from there (this has the highest priority)
    #
    set Host [security::validated_host_header]
    #ns_log notice "util_current_location validated host header <$Host>"
    if {$Host ne ""} {
        util::split_host $Host hostname Host_port
        if {$Host_port ne ""} {
            set port $Host_port
        }
    } else {
        ns_log notice "ignore non-existing or untrusted host header, fall back to <$hostname>"
    }

    #
    # We have all information, return the data...
    #
    if {$suppress_port || $port eq $default_port($proto) || $port eq ""} {
        set result ${proto}://${hostname}
    } else {
        set result ${proto}://${hostname}:${port}
    }

    set ::__util_current_location $result
    #ns_log notice "util_current_location returns <$result> based on hostname <$hostname>"
    return $result
XQL Not present:
PostgreSQL, Oracle
Generic XQL file:
packages/acs-tcl/tcl/utilities-procs.xql

[ hide source ] | [ make this the default ]
Show another procedure: