On 26.02.2013 19:41, Jochen Wißmann wrote:
> Hello,
> 
> i am trying to find an easy way to determine from the http-client side,
> which  AJP13-worker handled my request.
> So my basic idea is to use mod_header to add mod_jk`s env-variable
> JK_WORKER_NAME to the Header of the http-response.
> I tried to get something like this working:
> 
> httpd.conf:
> ...
> Header add TC-Server "%{JK_WORKER_NAME}e"
> ...
> 
> All my previous attempts resulted in http-responses looking like this:
> 
> < HTTP/1.1 200 OK
> < Set-Cookie: ARPT=LRWQXVS110.160.11.26CKMLQ; path=/
> < Date: Tue, 26 Feb 2013 18:25:31 GMT
> < Server: Apache/2.2.22 (Unix) mod_jk/1.2.36 mod_ssl/2.2.22
> OpenSSL/0.9.8x DAV/2
> < Set-Cookie: JSESSIONID=A4052BF60BA2007F0B0F47E2699AFDE.liferay0; Path=/
> < Set-Cookie: GUEST_LANGUAGE_ID=en_US; Expires=Wed, 26-Feb-2014 18:25:31
> GMT; Path=/
> < Set-Cookie: COOKIE_SUPPORT=true; Expires=Wed, 26-Feb-2014 18:25:31
> GMT; Path=/
> < Liferay-Portal: Liferay Portal Community Edition 6.0.6 CE (Bunyan /
> Build 6006 / February 17, 2011)
> < ETag: "838b4ae2"
> < Content-Length: 8043
> < X-Server-Ip: 110.160.11.26
> < TC-Server: (null)
> < Content-Type: text/html;charset=utf-8
> 
> Why do i get "TC-Server: (null)" ?
> Using the Variable JK_WORKER_NAME to log the worker's name via
> mod_log_config works fine.
> 
> Am i missing something? Is it even possible to access the env-variable
> JK_WORKER_NAME with module mod_header?
> Could anyone please help?
> Thanks!

mod_jk respects the environment variable JK_WORKER_NAME when choosing a
target worker, but it does not set it.

mod_jk only sets a note with name JK_WORKER_NAME, which is different
from an env var. The "n" in your log format means "note".

Unfortunately most variable use supported in Apache config is for env
vars, not for notes, so you can't directly set the header from a note.

There are two things you can experiment with:

a) using an undocumented mod_rewrite feature to try to copy the note
into an env var and then using that env var to set the header

or

b) not using the normal JkMount or uriworkermap.properties way of
defining the workers responsible for handling the URIs, but instead
using mod_rewrite via setting the env var JK:WORKER_NAME

Ad a)

Works roughly like that (untested):

RewriteCond %{ENV:JK_WORKER_NAME} (.*)
RewriteRule . - [ENV=WORKER:%1]

Note 1: the undocumented feature of mod_rewrite is, that
%{ENV:JK_WORKER_NAME} first looks for a note named "JK_WORKER_NAME" and
only if it doesn't find it for an env var.

Note 2: The RewriteRule now sets a new env var "WORKER" to the captured
value of the note. lease choose a new variable name here, not
"JK_WORER_NAME".

Now we add

Header add TC-Server-Ip "%{WORKER}e"

If you choose another name as "WORKER" for the new env var in the
RewriteRule, please adjust here as well.

Finally: if it doesn't work, try again by placing the Rewrite lines in a
<Directory></Directory> block. Don't forget to switch

RewriteEngine On

Ad b)

You can use mod_rewrite to set the env var JK_WORKER_NAME (now it is
important to use that name). mod_jk will then route the request to that
worker and since you had set the env var yourself, you can also copy it
to a header.

RewriteRule ^/c - [ENV=JK_WORKER_NAME:liferay]
RewriteRule ^/c/.* - [ENV=JK_WORKER_NAME:liferay]
RewriteRule ^/group - [ENV=JK_WORKER_NAME:liferay]
RewriteRule ^/group/.* - [ENV=JK_WORKER_NAME:liferay]

etc.

and then

Header add TC-Server-Ip "%{JK_WORKER_NAME}e"

Final remarks:

Your config does not really warrant this effort: you only have one
worker name, so what do you expect in the header? I'm asking, because if
you are using a load balancer worker (assumed name "lb") in your real
config, and it has sub workers for example "node1" and "node2" then
JK_WORKER_NAME will always be "lb". To actually get the chosen sub
worker, only recipe 1 has a chance to work. You would there replace
JK_WORJER_NAME in the RewriteCond by JK_WORKER_ROUTE. Unfortunately I
think that the route note is not set before the request actually gets
forwarded and that is to late for mod_rewrite to be able to copy it in
an env var.

In that case (load balancer and you want to know the chosen lb sub
worker) we would either need to add something to mod_jk, or allow
mod_headers to also support notes, or write a special small module.

Having written all that, I think the following patch to mod_headers
would be best. It simply adds support for notes to mod_headers (%{xxx}n
notation):

Index: modules/metadata/mod_headers.c
===================================================================
--- modules/metadata/mod_headers.c      (revision 1449529)
+++ modules/metadata/mod_headers.c      (working copy)
@@ -200,6 +200,16 @@
         return "(null)";
 }

+static const char *header_request_note(request_rec *r, char *a)
+{
+    const char *s = apr_table_get(r->notes,a);
+
+    if (s)
+        return unwrap_header(r->pool, s);
+    else
+        return "(null)";
+}
+
 static const char *header_request_ssl_var(request_rec *r, char *name)
 {
     if (header_ssl_lookup) {
@@ -853,6 +863,7 @@
     register_format_tag_handler("D", (const void
*)header_request_duration);
     register_format_tag_handler("t", (const void *)header_request_time);
     register_format_tag_handler("e", (const void *)header_request_env_var);
+    register_format_tag_handler("n", (const void *)header_request_note);
     register_format_tag_handler("s", (const void *)header_request_ssl_var);

     return OK;

You should be able to apply it to a 2.2 mod_headers, recompile and be
done. Not a standard feature though.

Regards,

Rainer

P.S.: Grüße von Bonn nach Bonn

---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org
For additional commands, e-mail: users-h...@tomcat.apache.org

Reply via email to