Mod_python Security Considerations
Many of the same security issues that apply to other embedded interpreters apply to mod_python. Here are some brief descriptions. Rather than list the solutions in detail, use them as a basis to search the mailing list or web:
Store sensitive data in modules outside of the DocumentRoot of your site. This prevents modules from being exposed if mod_python isn't running.
- Because the embedded interpreter runs applications as the apache user, all other applications may have access to the same files. This can have serious implications in a multiuser environment, and applies to PHP, SSI, CGI, etc., as well.
- Avoid any kind of dependency on the PATH environment variable. It can easily be changed by other applications, causing your own to fail. If you must call system programs, declare the full path explicitly,
always.
- Debugging information can be essential when developing an application. Take pains to ensure that error messages don't reveal sensitive data if they are returned to the browser. Review your code, and use try/except statements to catch errors when appropriate.
- Learn about Python's mechanisms to restrict what gets exported by a module.
- If your database and application are on the same machine, don't let the database listen on a port exposed to the Internet.
- Understand the quirks of mod_python.publisher if you use it as a handler. For example, add a leading underscore to objects if you do not want them to be directly accessible via HTTP. (4)
_foo = "secret word"
- If using mod_python.publisher and the legacy importer
PythonOption mod_python. (or mod_python version < 3.3), don't use the same name for Python code files (module names) in multiple places. This is because there are bugs in its implementation which can cause cross contamination of modules, the loading of the wrong module and other issues. See: MODPYTHON-9 MODPYTHON-10 MODPYTHON-11
If you use PythonAutoReload, realise that modules are simply reloaded on top of the already loaded modules. This is in part shown in the MODPYTHON-11 bug report. It is mentioned here as a separate item because it means that if you rename a variable/function or remove it, that doesn't actually mean it is no longer accessible. The only way to guarantee that old variables/functions are no longer accessible is to restart Apache. Thus, if you heed (4) and rename variables to have a leading underscore, make sure you restart Apache at the same time.
If multiple people share the same web server, use PythonInterpreter to assign your area of the web site its own instance of the Python interpreter. This isn't fool proof as another user could do the same thing and use the same name. When working though, it will keep your stuff separate from others and avoid them being able to more easily see and fiddle with the internals of your running application.
When using the mod_python.psp handler with PythonDebug On the source code for your PSP pages can be visible by virtue of putting an underscore on the end of the extension. You need to add the .psp_ extension to your AddHandler configuration directive to turn on this feature.
AddHandler mod_python .psp .psp_ PythonHandler mod_python.psp PythonDebug On
It is thus a good idea not to have PythonDebug enabled for production and/or public web site if using mod_python.psp. If you really need PythonDebug to be on, only enable it for requests coming from your own client machine in some way.
If Apache has write access to directories, it can write .pyc files into the directories for modules loaded. This extension isn't generally protected and people can download the ".pyc" files and potentially work out what your code is. Use something like:
<Files *.pyc> deny from all </Files>
Depending on platform, you may have to block access to .pyo files as well.
<Files *.pyo> deny from all </Files>
Use the FilesMatch directive to disallow access to important types of files, such as *.pyc, *.pyo, *~, etc.
- Turn off automatic directory indexing for Apache on directories which use mod_python. This is generally applicable to any web site, but potentially more so for mod_python if you forget to do (3). Thus don't use "Indexes" option.
If using an extension such as ".html" with AddHandler to map to handler code in actual directory, ensure you block access to ".py" extension if need be.
<Files *.py> deny from all </Files>
- Don't store backup files where they can be accessed via HTTP. Honestly, I'm sure I could gather about a thousand db passwords in a day if I simply created a bot that crawled dynamically driven sites
and appended ~ to every file name it finds.
PythonDebug in general can reveal stack traces to a client when something goes wrong. In the worst case, this may reveal secret information.
- Try to avoid putting source code in actual directories visible to Apache. Especially do not put sensitive information in such files. The reason here is that it only takes one mistake in Apache configuration and all your code would be visible.
- When writing a custom handler and returning apache.DECLINED, make sure you understand what it does. Specifically, it will cause the builtin default Apache handler to still run, which will serve up static files. Like above, you may need to deny access to certain files as a result.