Enabling Client Certificate Authentication in Sun Web Server 7.0 reverse proxy server and origin server


For this I have setup two Sun Java System Web Server 7.0 update 6instances. One acting as a reverse proxy and the other origin serverthat serves the request. Enabled SSL and client authentication on both these instances. Sent SSL requests with client certificates from a test client.

Changes made in Reverse Proxy Web Server Instance


In obj.conf I have add "map" SAF so that all requests are redirected to origin server. In real world situation you can if you want redirect only certain requests depending on your requirements.
AuthTrans fn="match-browser" browser="*MSIE*" ssl-unclean-shutdown="true" NameTrans fn="map" from="/" name="reverse-proxy-/" to="/" ... Service fn="proxy-retrieve" method="*" Route fn="set-origin-server" server="https://test.sun.com:4444" ...

In server.xml I have added "ssl" element in http-listener, added server certificate nickname (if its different from "Server-Cert") and set client authentication as "required" :



http-listener-1 3333 test.sun.com test Server-Cert-Reverse-Proxy-Server required In server.xml I have also modified access log format so that we can see what is happening
../logs/access %Ses->client.ip% %Req->vars.auth-user% [%SYSDATE%] "%Req->reqpb.clf-request%" %Req->srvhdrs.clf-status% %Req->srvhdrs.content-length% %Ses->client.cipher% %Req->vars.auth-cert%
Changes made in Origin Server Web Server Instance


In server.xml I have added "ssl" element in http-listener, added servercertificate nickname (if its different from "Server-Cert") and setclient authentication as "required" :
http-listener-1 4444 test.sun.com Server-Cert-Reverse-Proxy-Server required test
In server.xml I have also modified access log format so that we can see what is happening
../logs/access %Ses->client.ip% %Req->vars.auth-user% [%SYSDATE%] "%Req->reqpb.clf-request%" %Req->srvhdrs.clf-status% %Req->srvhdrs.content-length% %Ses->client.cipher% %Req->vars.auth-cert% %Req->headers.proxy-auth-cert%
Created a test.html file that should be served when the client requests for it :

$cat ../docs/test.html This is test.html on origin server
Installed Server Certificates in both Web Server instances


I created self signed certificate in reverse proxy server.

$cd /https-test/config $rm *.db $../../bin/certutil -N -d . $../../bin/certutil -S -d . -n Server-Cert-Reverse-Proxy-Server -s "CN=test.sun.com" -x -t "CT,CT,CT" $../../bin/certutil -L -d . Certificate Nickname Trust Attributes SSL,S/MIME,JAR/XPIServer-Cert-Reverse-Proxy-Server CTu,Cu,Cu
For convenience I copied these *.db to origin server instance config directory, and hence used the same server certificate in origin server. In real world use a new server certificate for origin server.

Test Client I used

I used "tstclnt" which is bundled with NSS-NSPR binaries in bin directory. Note that I used the server certificate of reverse proxy server as client certificate because I am too lazy to create more certificates. In real world use a proper client certificate.

Created a test request file :

$cat > sslreq.dat GET /test.html HTTP/1.0^M ^M
Sent request to the reverse proxy server

$tstclnt -h test.sun.com -p 3333 -n Server-Cert-Reverse-Proxy-Server -d https-test/config -c n -v -o -f < sslreq.dat tstclnt: connecting to test.sun.com:3333 (address=xxx.xxx.xxx.xxx)... tstclnt: stdin read 27 bytes tstclnt: Writing 27 bytes to server tstclnt: SSL version 3.1 using 128-bit RC4 with 160-bit SHA1 MAC tstclnt: Server Auth: 1024-bit RSA, Key Exchange: 1024-bit RSA subject DN: CN=test.sun.com issuer DN: CN=test.sun.com... tstclnt: Read from server 350 bytes HTTP/1.1 200 OK Server: Sun-Java-System-Web-Server/7.0 Date: Fri, 18 Sep 2009 10:59:13 GMT Content-type: text/html Last-modified: Thu, 17 Sep 2009 10:44:10 GMT Content-length: 35 Etag: "23-4ab212fa" Accept-ranges: bytes Via: 1.1 https-test Proxy-agent: Sun-Java-System-Web-Server/7.0 Connection: close This is test.html on origin server...
tstclnt: exiting with return code 0
You can see the request is being served from origin server.

I have used in this test client cipher "n" which is SSL3 RSA WITH RC4 128 SHA because I know this cipher that is enabled in Sun Web Server 7.0 update 6. I cansee that at the time of server startup when run infinest. You can use other ciphers as well.


Access log of Reverse Proxy Web Server shows the certificate

$cat ../logs/accessformat=%Ses->client.ip% %Req->vars.auth-user% [%SYSDATE%] "%Req->reqpb.clf-request%" %Req->srvhdrs.clf-status% %Req->srvhdrs.content-length% %Ses->client.cipher% %Req->vars.auth-cert%xxx.xxx.xxx.xxx - [18/Sep/2009:16:29:13 +0530] "GET /test.html HTTP/1.0" 200 35 RC4 MIIBujCCASOgAwIBAgIFAI566gYwDQYJKo...fBqhD710VkFmO ScYjWBxZe1vhnTbu/NexX4NqLsZG9So= Note cipher is RC4.

Access log of origin server shows the certificate

$cat ../logs/access format=%Ses->client.ip% %Req->vars.auth-user% [%SYSDATE%] "%Req->reqpb.clf-request%" %Req->srvhdrs.clf-status% %Req->srvhdrs.content-length% %Ses->client.cipher% %Req->vars.auth-cert%%Req->headers.proxy-auth-cert% xxx.xxx.xxx.xxx - [18/Sep/2009:16:29:13 +0530] "GET /test.html HTTP/1.1" 200 35 RC4 MIIBujCCASOgAwIBAgIFAI566gYwDQYJKo...fBqhD710VkFmO ScYjWBxZe1vhnTbu/NexX4NqLsZG9So=MIIBujCCASOgAwIBAgIFAI566gYwDQYJKo. ..fBqhD710VkFmOScYjWBxZe1vhnTbu/NexX4NqLsZG9So= Note that as expected in origin-server, rq->headers pblock has the certificate in "proxy-auth-cert". Reverse proxy server sends the certificate to origin server in this header.


References
More...