Modify response header with nginx
Solution 1
"Why is it so darned difficult to modify a response header??"
Some people need to make a living too!
Ah, that wasn't the real question. Damn. Try this
map $upstream_http_x_xsplocation $m_replaceme {
"" "";
"~^.*/page.xsp/(.*)$" "/$1";
"~.*" "";
}
location / {
proxy_pass http://localhost:81/database.nsf/page.xsp/;
proxy_hide_header X-XspLocation;
add_header X-XspLocation $m_replaceme;
}
Tested with nginx/1.14.2
Solution 2
Added always works for me
proxy_hide_header X-XspLocation;
add_header X-XspLocation $m_replaceme always;
D.Bugger
Updated on September 18, 2022Comments
-
D.Bugger over 1 year
I'm trying to configure nginx as a reverse proxy server for a web application on a back-end Domino server. We have 99.9% working, but that last 0.1% is really bugging me.
I'll explain. In some cases, the application returns a partial refresh with a special response header called
X-XspLocation
. If it exists, it contains a url to be redirected to by the client. It's a header generated and used by the XPages environment, my code itself doesn't set or read it. Its value is then:http://localhost:81/database.nsf/page.xsp/ThankYou
and I want it to be just this: /ThankYou
I tried in a million ways, but it seems impossible to alter its value. As soon as I use
proxy_hide_header X-XspLocation;
no new headers can be added usingadd_header
! If I leave the hide out, I get double values in the header, so I know my replacement value is correct. Here's my latest attempt that failed:map $sent_http_x_xsplocation $xsplocation_new { "~http://localhost:81/database.nsf/page.xsp/(.*)" "/$1"; } server { ... location / { proxy_pass http://localhost:81/database.nsf/page.xsp/; # redirect X-XspLocation proxy_hide_header X-XspLocation; add_header X-XspLocation $xsplocation_new; #add_header X-XspLocation2 $xsplocation_new; } }
I even tried with njs to change the header, it probably failed because I don't know how to use js_set or js_content to call a function that doesn't return anything.
Why is it so darned difficult to modify a response header??
The real question is of course: how can I make this work?? Thanks for your assistance!!
More info
In order to prove that the map works, I tested with the following:
location / { proxy_pass http://localhost:81/database.nsf/page.xsp/; # redirect X-XspLocation # proxy_hide_header X-XspLocation; # add_header X-XspLocation $xsplocation_new; add_header X-XspLocation2 $xsplocation_new; }
The result is now that the original header plus the new header
X-XspLocation2
are present, and the 2nd one is exactly what I need inX-XspLocation
.By the way, nginx version: nginx/1.18.0 on Ubuntu 16.04.6 LTS (My client's provider's system, not mine...)
The full censored config file
map $sent_http_x_xsplocation $xsplocation_new { "~http://localhost:81/database.nsf/page.xsp/(.*)" "/$1"; } server { listen 4443 ssl; server_name www.myclient.nl; ssl_certificate /etc/nginx/ssl/www.myclient.nl.pem; ssl_certificate_key /etc/nginx/ssl/www.myclient.nl.pem; # do not allow google to index this website # TODO: remove when going to production add_header X-Robots-Tag "noindex, nofollow, nosnippet, noarchive"; # replace redirects in response header fields Location and Refresh proxy_redirect http://localhost:81/database.nsf/page.xsp/ https://www.myclient.nl:4443/; proxy_redirect http://localhost:81/ https://www.myclient.nl:4443/; # tell domino not to encode the response so we can use sub_filter proxy_set_header Accept-Encoding ""; # substitute response content sub_filter 'localhost:81' 'www.myclient.nl:4443'; sub_filter 'www.myclient.nl' 'www.myclient.nl:4443'; #TODO: remove when going production sub_filter '/database.nsf/page.xsp/' '/'; sub_filter '/database.nsf/' '/other/'; sub_filter_once off; # Domino location = /favicon.ico { access_log off; log_not_found off; proxy_pass http://localhost:81/database.nsf/Images/favicon.ico/%24file/favicon.ico; } # root / homepage location = / { proxy_pass http://localhost:81/database.nsf/page.xsp/HomePage; } #login location /names.nsf { proxy_pass http://localhost:81/names.nsf; } # XPages location /xsp/ { proxy_pass http://localhost:81/xsp/; } location /domjava/ { proxy_pass http://localhost:81/domjava/; } # training location ~* ^/.*-training/(.*) { proxy_pass http://localhost:81/database.nsf/page.xsp/training/$1; } location ~* ^/(.*)-training$ { proxy_pass http://localhost:81/database.nsf/page.xsp/$1; } # IMAGES # image resources - any case insensitive match with 'images' location ~* '/images/(.*)$' { proxy_pass 'http://localhost:81/database.nsf/Images/$1'; } # images referenced from css in file.xsp have this url, redirect to backend correctly location ~* '/file.xsp/images/(.*)$' { proxy_pass 'http://localhost:81/database.nsf/Images/$1'; } # file resources location /file.xsp/ { proxy_pass http://localhost:81/database.nsf/file.xsp/; } # other resources location /other/ { proxy_pass http://localhost:81/database.nsf/; } # all other urls location / { proxy_pass http://localhost:81/database.nsf/page.xsp/; # redirect X-XspLocation #add_header X-XspLocation $xsplocation_new always; proxy_hide_header X-XspLocation; add_header X-XspLocation $xsplocation_new; } }
-
D.Bugger almost 4 yearsIt's always money, isn't it... :-(
-
D.Bugger almost 4 yearsNope, doesn't work. The header X-XspLocation disappears but the new one isn't created. I forgot to mention that most of it works if I add a header, but not for the original header. I'll modify the question.
-
Gerard H. Pille almost 4 yearsDid I forget to mention that I tested it? "Its value is then something like:". It might help to show us an exact value.
-
D.Bugger almost 4 yearsNope. The chances of anything coming from Mars... and still it doesn't work here. I even left out the hide, and changed the header name to X-XspLocation2: no dice.
-
D.Bugger almost 4 yearsI can see if I can anonymize the whole configuration file and post that.
-
Gerard H. Pille almost 4 yearsYou did replace "$sent_http_x..." by "$upstream_http_x..." ?
-
D.Bugger almost 4 yearsOf course, nothing happened. The map I used on $sent_http_x_xsplocation works. It seems to be the proxy_hide_header that doesn't work. Or works too well...
-
Gerard H. Pille almost 4 yearsWithout the hide, the replacement gets appended to the original value, as expected.
-
D.Bugger almost 4 yearsLet us continue this discussion in chat.
-
D.Bugger almost 4 yearsAnd with the hide both headers disappear...
-
D.Bugger almost 4 yearsMost likely the Ubuntu installation is somehow corrupt. Our short term workaround: instead of using the standard XPages call redirectTo, I used getResponse().setHeader with a name of my own and set that to the value I want in X-XspLocation. I added some rules to the nginx config file to move that header to the desired header.
-
Gerard H. Pille almost 3 yearsNog een weekje, en we trekken weer zuidwaarts.
-
D.Bugger almost 3 yearsHet is nu al 34°C hier, niet normaal voor half juni. Goede reis, en houd de neus proper!
-
Gerard H. Pille almost 3 yearsDe météo ziet er bijzonder slecht uit bij jullie, donderdag. Het zal geen plezierritje worden.
-
D.Bugger almost 3 yearsDeze site is redelijk betrouwbaar: meteorama.fr en ik zie niets wat ik echt slecht zou moeten noemen. Vab
-
D.Bugger almost 3 yearsOeps... Vannacht was vreselijk, onweer, 20mm water, storm, rukwinden, zowat het einde der tijden...
-
Gerard H. Pille almost 3 yearsJullie maken er daar wel een gewoonte van. Wegens een fysisch akkefietje vervroegd teruggekeerd, tussen Vienne en Lyon daar een hoeveelheid water over ons gekregen, nog nooit zelf ervaren. Woog natuurlijk niet op tegen wat ze in de Ardennen en Duitsland over zich heen kregen.
-
D.Bugger almost 3 yearsDat was een paar dagen geleden zeker. Het is hier ook wel nat geweest, iets van 30mm op een dag, maar bij Lyon kan het inderdaad flink spoken soms. Hoop dat de terugreis verder zonder incidenten was.
-
Gerard H. Pille almost 3 yearsNul incidenten, en een plezier om eens niet in de blakende zon te moeten rijden - geen liefhebber van airco.
-
D.Bugger almost 3 yearsDa's mooi! Dus een goede vakantie geweest. Nu nog de Covid weg en de tijgermuggen... Ik weet intussen niet meer hoe ik bovenstaand probleem heb opgelost. Fijne zomer verder!