Skip to content

Instantly share code, notes, and snippets.

@progandy progandy/README.md Secret
Last active Feb 14, 2019

Embed
What would you like to do?
mod_proxy_handler for apache 2.4

mod_proxy_handler

This module for apache 2.4 allows you to use e.g. mod_proxy_fcgi in AddHandler or SetHandler directives.

Compile and install the module with apxs:

apxs -i -a -c mod_proxy_handler.c

Example:

Send php files to php-fpm running on a TCP socket:

# set handler for php
LoadModule proxy_handler_module modules/mod_proxy_handler.so
<FilesMatch \.php$>
    SetHandler "proxy:fcgi://127.0.0.1:9000/"
</FilesMatch>

# configuration for phpmyadmin package in archlinux 
Alias /phpmyadmin "/usr/share/webapps/phpMyAdmin"
<Directory "/usr/share/webapps/phpMyAdmin">
    DirectoryIndex index.html index.php
    AllowOverride All
    Options FollowSymlinks
    Require all granted
</Directory>
/*
* Copyright 2014 Andreas Bosch
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "httpd.h"
#include "http_config.h"
#include "http_protocol.h"
#include "ap_config.h"
#include "apr_strings.h"
#include "http_request.h"
static int proxy_handler_handler(request_rec *r)
{
// This function is adapted from a patch to mod_proxy
// http://svn.apache.org/viewvc?view=revision&revision=1573626
if (r->filename && !r->proxyreq) {
/* We may have forced the proxy handler via config or .htaccess */
if (r->handler &&
strncmp(r->handler, "proxy:", 6) == 0 &&
strncmp(r->filename, "proxy:", 6) != 0) {
r->proxyreq = PROXYREQ_REVERSE;
r->filename = apr_pstrcat(r->pool, r->handler, r->filename, NULL);
apr_table_setn(r->notes, "rewrite-proxy", "1");
r->handler = "proxy-server";
// always return declined since we do some weird stuff:
// we modify the request in a handler
return DECLINED;
}
}
return DECLINED;
}
static void proxy_handler_register_hooks(apr_pool_t *p)
{
static const char * const aszSucc[] = { "mod_proxy.c", NULL };
ap_hook_handler(proxy_handler_handler, NULL, aszSucc, APR_HOOK_REALLY_FIRST);
}
/* Dispatch list for API hooks */
module AP_MODULE_DECLARE_DATA proxy_handler_module = {
STANDARD20_MODULE_STUFF,
NULL, /* create per-dir config structures */
NULL, /* merge per-dir config structures */
NULL, /* create per-server config structures */
NULL, /* merge per-server config structures */
NULL, /* table of config file commands */
proxy_handler_register_hooks /* register hooks */
};
@RafaelKa

This comment has been minimized.

Copy link

commented May 6, 2014

Hey folks, if you want to use UDS then make it as follows:

Send php files to php-fpm running on a UDS socket:

# set handler for php
LoadModule proxy_handler_module modules/mod_proxy_handler.so
<FilesMatch \.php$>
    SetHandler "proxy:unix:/path/to/socket.sock|fcgi://./"
</FilesMatch>

tested on SVN 2.4.10 candidate

@inthl

This comment has been minimized.

Copy link

commented May 9, 2014

what modules are required for this? I am testing the module with 2.4.9 and apache is unable to process any request due to AH01144: No protocol handler was valid for the URL. I have mod_proxy and mod_proxy_http as well as mod_proxy_fcgi loaded

@dzuelke

This comment has been minimized.

Copy link

commented Jun 2, 2014

@RafaelKa did you (or anyone else) try this with rewrites? When rewriting to path info, e.g. RewriteRule (.*) index.php/$1, it doesn't work; FPM says no input file specified...

@Tragen

This comment has been minimized.

Copy link

commented Sep 2, 2014

I like this module. But why is it so much slower than using ProxyPassMatch?
After the page php page is parsed, it takes nearly 2 seconds until I get the result in my browser.
With ProxyPassMatch it is shown immediately.

@valmirselmani

This comment has been minimized.

Copy link

commented Nov 13, 2014

This script helped me a lot, thanks progandy! I just have one problem, if I type a url with a non-existent php file it still goes through the proxy instead of ignoring it and it doesn't use the standard 404 error document from apache. Anyone had the same problem?

OS: RedHat 6
PHP: 5.5.18
Apache: 2.4.6

@BtbN

This comment has been minimized.

Copy link

commented Nov 24, 2014

It is slow because it opens a new connection to php-fpm on every request, instead of reusing an existing pool like ProxyPass(Match) does.
This can be workarounded by setting up a dummy worker for the same proxy url as explained here:
http://httpd.apache.org/docs/2.4/mod/mod_proxy.html#workers

An example configuration could be:

ProxyPass /dummyproxy unix:/path/to/socket.sock|fcgi://./ connectiontimeout=5 timeout=30
<Location /dummyproxy>
    Require all denied
</Location>
AddHandler proxy:unix:/path/to/socket.sock|fcgi://./ .php

It is important that the URLs to the proxy match, in order for them to use the same worker.

Also, i just noticed that support for this was merged into Apache 2.4.10. So if you are running at least that version, you don't need this module anymore. See http://httpd.apache.org/docs/2.4/mod/mod_proxy.html#handler

@butesa

This comment has been minimized.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.