[SOLVED]Automatic rewrite /wordpress/?

I’ve been failing the following problem for a few days:

In addition to UCS DC server, various member servers are installed. Wordpress has been running on one of these for some time.
HAproxy runs on another UCS member server, which is the perfect running gateway for all remote accesses. Basically, all external access runs smoothly.

But remote access to a single application on a separate internal FreeBSD server with XigmaNAS only works partially. The error is strange:
First access: the WebGUI on the FreeBSD is called up and the menu is completly displayed (possibly previous password query also ok).
Further accesses:
If a submenu is now called up by the WebGUI, then the URl is always entered after the domain name “/wordpress/” (but never with local access, everything is ok there).

I just can’t figured out which program or script put “/wordpress/” into the path !

A trace in HAproxy + on the FreeBSD server (Lighttpd) show that the HTTP request sent by the HAproxy is completely OK. FreeBSD also arrives in the HTTP request.

Feb 20 13:09:03 ucs-xxxx haproxy[14350]: PHPSESSID=2115 “GET /xig/ HTTP/1.1”[capture.req.hdr(1) 109.41.x,yz:30602 [20/Feb/2020:13:09:01.600] https-in~ xig_servers/nas 0/0/55/1432/1530 200 22120 - - --VN 1/1/0/1/0 0/0 {PHPSESSID=2115|Is Host NAS|Not Host Wordpress|Is Cookie NAS|Not Cookie Wordpress} “GET /xig/ HTTP/1.1”]
2020-02-20 13:09:01: (connections.c.772) fd: 9 request-len: 557 \nGET / HTTP/1.1\r\nHost: DOMAIN.com\r\nAccept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8\r\nCookie: PHPSESSID=2115b82aed91273b1a6e5c9f08d5a1b1; _ga=GA1.2.1716885048.1581926246; _pk_id.14.2479=6a1f9d93739cfb66.1581613477.3.1581767789.1581767342.\r\nUser-Agent: Mozilla/5.0 (iPhone; CPU iPhone OS 13_3 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/13.0.4 Mobile/15E148 Safari/604.1\r\nAccept-Language: de-de\r\nAccept-Encoding: gzip, deflate, br\r\nX- Forwarded-Proto: http\r\nX-Forwarded-Proto: https\r\nX-Forwarded-For: 109.41.x,yz\r\n\r\n
> 2020-02-20 13:09:01: (response.c.435) – splitting Request-URI
> 2020-02-20 13:09:01: (response.c.436) Request-URI : /
> 2020-02-20 13:09:01: (response.c.437) URI-scheme : https
> 2020-02-20 13:09:01: (response.c.438) URI-authority : DOMAIN.com
> 2020-02-20 13:09:01: (response.c.439) URI-path (raw) : /
> 2020-02-20 13:09:01: (response.c.440) URI-path (clean): /
> 2020-02-20 13:09:01: (response.c.441) URI-query :
> 2020-02-20 13:09:01: (mod_access.c.177) – mod_access_uri_handler called
> 2020-02-20 13:09:01: (response.c.586) – before doc_root
> 2020-02-20 13:09:01: (response.c.587) Doc-Root : /usr/local/www
> 2020-02-20 13:09:01: (response.c.588) Rel-Path : /
> 2020-02-20 13:09:01: (response.c.589) Path :
> 2020-02-20 13:09:01: (response.c.631) – after doc_root
> 2020-02-20 13:09:01: (response.c.632) Doc-Root : /usr/local/www
> 2020-02-20 13:09:01: (response.c.633) Rel-Path : /
> 2020-02-20 13:09:01: (response.c.634) Path : /usr/local/www/
> 2020-02-20 13:09:01: (response.c.658) – logical -> physical
> 2020-02-20 13:09:01: (response.c.659) Doc-Root : /usr/local/www
> 2020-02-20 13:09:01: (response.c.660) Basedir : /usr/local/www
> 2020-02-20 13:09:01: (response.c.661) Rel-Path : /
> 2020-02-20 13:09:01: (response.c.662) Path : /usr/local/www/
> 2020-02-20 13:09:01: (response.c.674) – handling physical path
> 2020-02-20 13:09:01: (response.c.675) Path : /usr/local/www/
> 2020-02-20 13:09:01: (response.c.682) – handling subrequest
> 2020-02-20 13:09:01: (response.c.683) Path : /usr/local/www/
> 2020-02-20 13:09:01: (response.c.684) URI : /
> 2020-02-20 13:09:01: (response.c.685) Pathinfo :
> 2020-02-20 13:09:01: (mod_indexfile.c.159) – handling the request as Indexfile
> 2020-02-20 13:09:01: (mod_indexfile.c.160) URI : /
> 2020-02-20 13:09:01: (mod_access.c.177) – mod_access_uri_handler called
> 2020-02-20 13:09:01: (gw_backend.c.2416) handling it in mod_gw
> 2020-02-20 13:09:01: (mod_openssl.c.1762) SSL: -1 5 54 Connection reset by peer
> 2020-02-20 13:09:02: (response.c.113) Response-Header: \nHTTP/1.1 200 OK\r\nExpires: Thu, 19 Nov 1981 08:52:00 GMT\r\nCache-Control: no-store, no-cache, must-revalidate\r\nPragma: no-cache\r\nContent-Type: text/html; charset=UTF-8\r\nTransfer-Encoding: chunked\r\nDate: Thu, 20 Feb 2020 12:09:02 GMT\r\nServer: WebGUI\r\n\r\n

(without “>” = HAproxy; with “>” = FreeBSD with the WebGUI)
So in the header response of the FreeBSD is only “/” in the URI.

If the submenu is now called up in the WebGUI, the log contain:

Feb 20 13:09:07 ucs-xxxx haproxy[14350]: wp-settings-ti “GET /wordpress/ HTTP/1.1”[capture.req.hdr(1) 109.41.x,yz:9158 [20/Feb/2020:13:09:07.373] https-in~ xig_servers/nas 0/0/16/1/17 404 466 - - --VN 1/1/0/1/0 0/0 {wp-settings-ti|Not Host NAS|Is Host Wordpress|Is Cookie NAS|Not Cookie Wordpress} “GET /wordpress/ HTTP/1.1”]
2020-02-20 13:09:07: (connections.c.772) fd: 9 request-len: 634 \nGET /wordpress/ HTTP/1.1\r\nHost: DOMAIN.com\r\nAccept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8\r\nCookie: wp-settings-time-6=1578216400; PHPSESSID=2115b82aed91273b1a6e5c9f08d5a1b1; _ga=GA1.2.1716885048.1581926246; _pk_id.14.2479=6a1f9d93739cfb66.1581613477.3.1581767789.1581767342.\r\nUser-Agent: Mozilla/5.0 (iPhone; CPU iPhone OS 13_3 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/13.0.4 Mobile/15E148 Safari/604.1\r\nAccept-Language: de-de\r\nReferer: https://DOMAIN.com/xig/\r\nAccept-Encoding: gzip, deflate, br\r\nX-Forwarded-Proto: http\r\nX-Forwarded-Proto: https\r\nX-Forwarded-For: 109.41.x,yz\r\n\r\n
> 2020-02-20 13:09:07: (response.c.435) – splitting Request-URI
> 2020-02-20 13:09:07: (response.c.436) Request-URI : /wordpress/
> 2020-02-20 13:09:07: (response.c.437) URI-scheme : https
> 2020-02-20 13:09:07: (response.c.438) URI-authority : DOMAIN.com
> 2020-02-20 13:09:07: (response.c.439) URI-path (raw) : /wordpress/
> 2020-02-20 13:09:07: (response.c.440) URI-path (clean): /wordpress/
> 2020-02-20 13:09:07: (response.c.441) URI-query :
> 2020-02-20 13:09:07: (mod_access.c.177) – mod_access_uri_handler called
> 2020-02-20 13:09:07: (response.c.586) – before doc_root
> 2020-02-20 13:09:07: (response.c.587) Doc-Root : /usr/local/www
> 2020-02-20 13:09:07: (response.c.588) Rel-Path : /wordpress/
> 2020-02-20 13:09:07: (response.c.589) Path :
> 2020-02-20 13:09:07: (response.c.631) – after doc_root
> 2020-02-20 13:09:07: (response.c.632) Doc-Root : /usr/local/www
> 2020-02-20 13:09:07: (response.c.633) Rel-Path : /wordpress/
> 2020-02-20 13:09:07: (response.c.634) Path : /usr/local/www/wordpress/
> 2020-02-20 13:09:07: (response.c.658) – logical -> physical
> 2020-02-20 13:09:07: (response.c.659) Doc-Root : /usr/local/www
> 2020-02-20 13:09:07: (response.c.660) Basedir : /usr/local/www
> 2020-02-20 13:09:07: (response.c.661) Rel-Path : /wordpress/
> 2020-02-20 13:09:07: (response.c.662) Path : /usr/local/www/wordpress/
> 2020-02-20 13:09:07: (response.c.674) – handling physical path
> 2020-02-20 13:09:07: (response.c.675) Path : /usr/local/www/wordpress/
> 2020-02-20 13:09:07: (response.c.150) – file not found
> 2020-02-20 13:09:07: (response.c.151) Path : /usr/local/www/wordpress/
> 2020-02-20 13:09:07: (response.c.113) Response-Header: \nHTTP/1.1 404 Not Found\r\nContent-Type: text/html\r\nContent-Length: 341\r\nDate: Thu, 20 Feb 2020 12:09:07 GMT\r\nServer: WebGUI\r\n\r\n

The request header of the HAproxy now contains “/wordpress” and the PHP SessionID is deleted.

I can not find out which program or script inserts the path “/ wordpress” there.
According to the log, FreeBSD - WebGUI sends the Uri “/” (ie no path specification) back in the last response header. So it can’t be the FreeBSD server.
Why “/wordpress/” arrives in the HAproxy is completely unclear.

I have deactivated the Apache service on all UCS servers (including the proxy) as a test + stopped all Docker apps at the same time -> no change!

Here is the HAproxy.cfg (completely reduced to the essential entries):

global
log /dev/log local0
log /dev/log local1 notice
chroot /var/lib/haproxy
stats socket /run/haproxy/admin.sock mode 660 level admin
stats timeout 30s
user haproxy
group haproxy
daemon

 Default SSL material locations

ca-base /etc/ssl/certs
crt-base /etc/ssl/private

 # Default ciphers to use on SSL-enabled listening sockets.
 # For more information, see ciphers(1SSL). This list is from:
 #  https://hynek.me/articles/hardening-your-web-servers-ssl-ciphers/
 # An alternative list with additional directives can be obtained from
 #  https://mozilla.github.io/server-side-tls/ssl-config-generator/?server=haproxy
ssl-default-bind-ciphers ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:RSA+AESGCM:RSA+AES:!aNULL:!MD5:!DSS
ssl-default-bind-options no-sslv3
tune.ssl.default-dh-param 2048

defaults
log global
mode http

Start manual additions - defaults section

    option forwardfor
   #option http-server-close

    stats enable
    stats uri /haproxystats
    stats realm Haproxy\ Statistics
    stats auth yyyyyyy:xxxxxx
    ### End manual additions - defaults section

option httplog
log-format “%ci:%cp [%tr] %ft %b/%s %TR/%Tw/%Tc/%Tr/%Ta %ST %B %CC %CS %tsc %ac/%fc/%bc/%sc/%rc %sq/%bq %hr %hs %{+Q}r”
option dontlognull
timeout connect 5000
timeout client 50000
timeout server 50000
# option httpclose
errorfile 400 /etc/haproxy/errors/400.http
errorfile 403 /etc/haproxy/errors/403.http
errorfile 408 /etc/haproxy/errors/408.http
errorfile 500 /etc/haproxy/errors/500.http
errorfile 502 /etc/haproxy/errors/502.http
errorfile 503 /etc/haproxy/errors/503.http
errorfile 504 /etc/haproxy/errors/504.http

Start manual additions - proxy section

frontend https-in
bind *:80
reqadd X-Forwarded-Proto:\ http
bind *:443 ssl crt /etc/haproxy/cert/haproxy.pem
reqadd X-Forwarded-Proto:\ https

redirect scheme https if !{ ssl_fc } ## global switch to SSL

###  Debug - config special log format 
## ================================
##http-request capture req.hdr(Host) len 128

http-request capture req.hdr(Cookie) len 14
log-format “%[capture.req.hdr(0)] %{+Q}r[capture.req.hdr(1) %ci:%cp [%tr] %ft %b/%s %TR/%Tw/%Tc/%Tr/%Ta %ST %B %CC %CS %tsc %ac/%fc/%bc/%sc/%rc %sq/%bq %hr %hs %{+Q}r]”
## ================================

## -----------------------------
## Define hosts: criteria subdir 
## -----------------------------

acl is_host_nas path_beg /xig /xig/

 ## Debug - check cookies and write in log
 ## ======================================

http-request set-var(req.is_host_nas) str(“Not Host NAS”)

http-request set-var(req.is_host_nas) str(“Is Host NAS”) if is_host_nas

acl cookie_nas req.cook(SERVERID) -m str XIG1

http-request set-var(req.cookie_nas) str(“Not Cookie NAS”)

http-request set-var(req.cookie_nas) str(“Is Cookie NAS”) if cookie_nas

http-request capture var(req.is_host_nas) len 24
http-request capture var(req.cookie_nas) len 24
## ======================================

 ## ------------------------------
 ## figure out which backend to use
 ## -------------------------------
 ## 1st host + path

use_backend xig_servers if is_host_nas

 ## 2nd cookie

use_backend xig_servers if cookie_nas

 ## default

default_backend portal_servers

backend xig_servers ## FreeBSD - WebGUI
cookie SERVERID insert indirect nocache
http-request set-path %[path,regsub(^/xig/?,/)]
server nas FreeBSD.server.local:443 ssl verify none check cookie XIG1

backend portal_servers ## default
http-request set-path /
server portal ucs-DC.server.local:443 ssl verify none check

End manual additions - proxy section

Is an entry automatically created somewhere during the installation of Wordpress, which possibly controls the “/wordpress/”?

Does anyone have an idea where I could still search?

I couldn´t fix the problem with the URL path, but I found a workaround…

To get a criterion for HAproxy, which server to call, I have now simply set up a subdomain.
This now works perfectly.