[mod_python] Current Working Directory not set?

Sean Jamieson sean at barriescene.com
Fri Jan 27 17:48:13 EST 2006


...and I completely forgot about decorators, I'm going to come up with 
something later, to make this more sane using a decorator.


Sean Jamieson wrote:

> Thanks for all the options Graham.
>
> I've come up with the following code template, if anyone see anything 
> obviously wrong/bad please let me know:
> import os
> import sys
> from mod_python import apache, util
> from kid import Template
>
> # this file's current directory
> __dir__ = os.path.dirname( __file__ )
>
> # set the templates path under this file's directory
> __templates__ = os.path.join( __dir__, "templates" )
>
> def index( req ): _page='index'
>    req.content_type = 'text/html'
>    ## function body ##
>    return Template( file=os.path.join( __templates__, '%s_%s.kid' % 
> (__name__, _page) ), **vars() )
>
>
> I'm expecting someone might say something about my use of **vars().
> The overall result of my return Template(..) statement is that it will 
> match [script's dir]/templates/[script name]_[function name].kid
>
> Comments?
>
> Sean
>
> Graham Dumpleton wrote:
>
>>
>> On 28/01/2006, at 6:53 AM, Sean Jamieson wrote:
>>
>>> Hello everybody,
>>> I don't know if there's already been a discussion about this, it 
>>> seems like a small but obvious issue.
>>
>>
>>
>> Many times. ;-)
>>
>>> The current working directory does not apear to be set when a 
>>> mod_python.publisher script runs; or rather it's set to "/" which is 
>>> not useful. This becomes quite a pain, as I'm forced to do many 
>>> things to work around it.
>>
>>
>>
>> As someone else said, working directory can't be changed because of 
>> multithreading
>> abilities of mod_python.
>>
>>> i.e.
>>> 1) I've started using kid templates, and I have to use:
>>>     Template( file=req.document_root().'template.kid', ... )
>>> or
>>>    Template( 
>>> file=req.document_root().'project_dir/templates/template.kid', ... )
>>> rather then the more natural:
>>>    Template( file='templates/template.kid )
>>> this should find the 'templates' directory in the same directory as 
>>> the running script
>>
>>
>>
>> Don't use req.document_root(). Instead, in that specific Python code 
>> file,
>> include at global scope:
>>
>>   import os
>>   __here__ = os.path.dirname(__file__)
>>   __templates__ = os.path.join(__here__,"templates")
>>
>> That will give you the directory that file is located in, in a handy 
>> variable
>> which you can then use.
>>
>>     Template( file=os.path.join(__templates__,"template.kid") )
>>
>> This is only useful though if all your publisher handlers are in the 
>> one directory.
>> If you have stuff spread over subdirectories, you start having to use 
>> relative
>> paths as appropriate in subdirectory handler files.
>>
>>   import os
>>   __here__ = os.path.dirname(__file__)
>>   __templates__ = os.path.join(__here__,"..","templates")
>>
>> Thus, you may be better off doing something like:
>>
>>   def _templates(req,path):
>>     return os.path.join(req.hlist.directory,"templates",path)
>>
>>   ...
>>
>>     Template( file=_template("template.kid") )
>>
>> The req.hlist.directory variable will be set to the directory for 
>> which PythonHandler
>> is specified, thus giving you a root anchor point which you can use 
>> to describe all
>> paths relative to. Doing this means you have more flexibility as far 
>> as moving code
>> files around between directories without having to modify code.
>>
>> The other reference point you might use is:
>>
>>   def _templates(req,path):
>>     directory = os.path.dirname(req.filename)
>>     return os.path.join(directory,path)
>>
>>   ...
>>
>>     Template( file=_template("templates/template.kid") )
>>
>> The req.filename object is similar to using __file__ for most cases, 
>> but getting the
>> information from the request object instead.
>>
>> You might even create your own derived class from Kid's Template 
>> class so you can
>> pass it a 'req' object and relative template file path and have that 
>> derived class
>> constructor do the calculation of where the file is relative to 
>> PythonHandler root
>> or req.filename.
>>
>> In other words, to be more transparent, the template system would 
>> need to know about
>> the environment it is used in.
>>
>>> 2) I have to fully qualify imports from the document root, as the 
>>> document root is added to sys.modules, but the current directory is 
>>> not. So, if I'm in a subdirectory under the document root I have to do:
>>>    import project_dir.subpackage.module
>>> when the current directory is 'project_dir'. This is silly, I should 
>>> be able to import something in, or under, the current working 
>>> directory:
>>>    import subpackage.module
>>
>>
>>
>> If these packages contain reusable code used across various pages and 
>> don't have
>> actual code in them for generating pages, it is not a good idea to 
>> put them under
>> your document root. This is because with the right URL they may be 
>> able to be
>> invoked by a remote user because of publishers automatic mapping. 
>> Thus you need to
>> be very careful.
>>
>> If they do contain code for generating pages, you should not be using 
>> "import"
>> to access them as at the same time they could be getting loaded by 
>> publisher using
>> a different module loading system which will cause various problems.
>>
>> As suggested by someone else, look at using "apache.import_module()".
>>
>>> I would have to do some hack involving seperating the dirname of 
>>> __file__ and adding it to sys.modules
>>
>>
>>
>> I think you must have meant into sys.path. Same above, Modifying 
>> sys.path directly
>> in mod_python is not usually a good idea either. The use of 
>> PythonHandler will
>> automatically put that root directory in sys.path for you without 
>> having to resort
>> to using PythonPath. This all assumes you have already set PythonPath 
>> explicitly
>> and aren't using Location directive instead of Directory directive to 
>> specify context
>> in which mod_python is used.
>>
>> Graham
>>
>>
>>
>
> _______________________________________________
> Mod_python mailing list
> Mod_python at modpython.org
> http://mailman.modpython.org/mailman/listinfo/mod_python
>
>



More information about the Mod_python mailing list