On Sun 12 Oct 2008, André Warnier wrote: > <Location /some/url> > > SetHandler jakarta-servlet > SetEnvIf REQUEST_URI "\.(htm|web|css|gif|jpg|js|html?)$" no-jk > > PerlXXXHandler My::Module->some_method > > ... > > </Location> > > ("jakarta-servlet" above means mod_jk --> Tomcat) > (and PerlXXXHandler being any kind of Perl HTTP Handler running soon > enough) > > The Question : > Is it possible, in the PerlXXXHandler, on a request-by-request base, > to "disable" the jakarta-servlet handler, and install the following > instead > > SetHandler modperl > PerlResponseHandler My::Module->some_other_method > > ? > > I know that I can do something like the above for regular static > pages, and I use this already : > $r->handler('modperl'); > $r->set_handlers(PerlAuthzHandler => []); # stop authorization > from running > $r->set_handlers(PerlResponseHandler => \&_send_login_form); > > > However, when I try to do the same in a Location like the above, it > seems that the jakarta-servlet handler runs anyway, and my > PerlResponseHandler is never called.
Does that piece of code run in a /Perl(PostReadRequest|Trans| MapToStorage)Handler/ ? Please, have a look again at the ap_process_request_internal() function in httpd-2.x.y/server/request.c. This function implements almost the complete request cycle (save PostReadRequest, Response and Log). Just after ap_run_translate_name(), that is the PerlTransHandler, you'll see this piece: /* Reset to the server default config prior to running map_to_storage */ r->per_dir_config = r->server->lookup_defaults; if ((access_status = ap_run_map_to_storage(r))) { /* This request wasn't in storage (e.g. TRACE) */ return access_status; } /* Rerun the location walk, which overrides any map_to_storage config. */ if ((access_status = ap_location_walk(r))) { return access_status; } /* Only on the main request! */ if (r->main == NULL) { if ((access_status = ap_run_header_parser(r))) { return access_status; } } ... The line "r->per_dir_config = r->server->lookup_defaults;" resets all request specific configurations applied so far. After that line the request is configured as if no Directory/Location or other container were present in your httpd.conf. Next comes MapToStorage. Here Directory, DirectoryMatch, Files and FilesMatch containers are applied to the request. Then, and this is what I think hits you, comes an ap_location_walk. Here Location containers are applied. So, your SetHandler inside the Location overrides any $r->handler seen before. After the ap_location_walk comes the PerlHeaderParserHandler. But it is skipped for subrequests. A further examination will show you that the next phase that is run by all requests is the PerlTypeHandler just before Fixup. So, move your "$r->handler('modperl');" to one of those and it will work. I prefer Fixup but that is based only on the fact that it is documented as do-what-you-want phase. There are directives that change the handler in the type-checker phase. In fact the AddHandler directive works that way. Mod_mime looks at the file extension and adjusts the handler, e.g "AddHandler cgi-script .pl". So using Fixup your module is the last to kick in. To carry state around use pnotes, notes or subprocess_env. Torsten -- Need professional mod_perl support? Just hire me: [EMAIL PROTECTED]