5

I wrote a WSGI application which I need to deploy to a server, however I've been given a server that already has mod_python installed.

I am not allowed to remove mod_python since there are some mod_python applications running on it already.

One option I considered was installing mod_wsgi alongside mod_python, however I went through sources and found that was a bad idea. Apparently mod_wsgi and mod_python don't mix well.

Another option I considered was installing mod_fastcgi and deploying it using fastcgi.

I would love to hear if someone has a better idea which doesn't break the current mod_python applications running on the server.

user868459
  • 288
  • 1
  • 3
  • 8
  • Turns out that since the server was on UBuntu, python is compiled as a linked library, so I could just apt-get install mod_wsgi alongside it, and it works like a charm. – user868459 Oct 27 '11 at 17:48

4 Answers4

3

You can use mod_python and mod_wsgi together so long as same Python version and mod_python not linked against a static Python library.

Run the 'ldd' command on the mod_python.so file:

ldd mod_python.so

to find out if it links to libpythonX.Y.so. Build mod_wsgi to use same Python version, ensuring it is similarly linked against same libpythonX.Y.so.


UPDATE

Version 4.X of mod_wsgi now explicitly refuses to start if mod_python is also loaded. In order for mod_python and mod_wsgi to be used together, certain features of mod_wsgi had to be crippled. As mod_python is now very old, not meaningfully updated, has various problems with it and should not be used for anything new, no longer trying to support them being used together.

Graham Dumpleton
  • 57,726
  • 6
  • 119
  • 134
2

Here's an idea (that needs fleshing out, and that maybe won't work):

Here's what I would start with:

from mod_python import apache
from wsgiref.handlers import BaseHandler

class MyWSGIHandler(BaseHandler):
    def __init__(self, apachereq):
        BaseHandler.__init__(self)
        self.apachereq = apachereq

    def _write(self, data):
        self.apachereq.write(data)

    # override the other required methods of BaseHandler, see
    # http://docs.python.org/library/wsgiref.html#wsgiref.handlers.BaseHandler

wsgi_app = create_your_wsgi_app()

def handler(req):
    wsgi_handler = MyWSGIHandler(req)
    wsgi_handler.run(wsgi_app)
    return apache.OK

IDEA 2 (pretty hackish):

You could in your handler code also use the werkzeug wsgi testing module to pass a request to the WSGI app, get a werkzeug response back and then write that response to apache.

Something like:

from mod_python import apache
from werkzeug.test import Client
from werkzeug.wrappers import BaseResponse

wsgi_app = create_your_wsgi_app()

def handler(req):
    c = Client(wsgi_app, BaseResponse)
    resp = c.get(somehow_get_the_url_from(req)) # or c.post if it's a POST request
    req.write(resp.data) # ... and find a way to write the headers as well
    return apache.OK
codeape
  • 97,830
  • 24
  • 159
  • 188
  • the first idea sounds promising. The second idea is pretty hackyish but cool :) Would this affect performance of the web application, this proxying through a mod_python handler. Im also concerned about the overhead of the creation of a new MyWSGIHandler and then calling wsgi_handler.run method. Sounds like it will be doing a lot of work on each request? – user868459 Oct 25 '11 at 05:15
  • I don't believe performance would be a problem, but only testing will tell if it will fly. Creating an object is not a big overhead. The docs say that a ``BaseHandler`` object is meant to handle one request only. – codeape Oct 25 '11 at 08:27
  • A quote from [this blog post](http://adam.gomaa.us/blog/2007/aug/1/five-things-i-hate-about-django/index.html): "mod_python can run WSGI apps". But the author does not explain how. Perhaps there is an existing solution that does what you want? – codeape Oct 25 '11 at 11:02
1

The best solution might be to use mod_proxy and run the Python web app in a different webserver.

Mike Graham
  • 73,987
  • 14
  • 101
  • 130
  • thanks but I have to use this webserver with mod_python on it. – user868459 Oct 25 '11 at 05:13
  • But perhaps you could use a Python-based server, like ``wsgiref.sample_server`` or [werkzeug's](http://werkzeug.pocoo.org/docs/serving/)? – codeape Oct 25 '11 at 08:50
  • @user868459, I'm not suggesting that you don't. Apache's mod_proxy lets you serve a website with a different server process and route through Apache. You're not _not_ using your current Apache server. You're just using something else as well. – Mike Graham Oct 26 '11 at 14:51
0

After some googling, I found this:

How to set up mod_python for use as a WSGI server

The following now works using Apache2, with mpm_winnt and prefork! Other versions and MPM's may give radically different results. If you've got a little time and experience, please try this latest version with prefork on Linux, and any other Multi-Processing Modules you favor.

codeape
  • 97,830
  • 24
  • 159
  • 188