On Wed, Aug 15, 2012 at 1:59 PM, Ethan Jucovy <[email protected]> wrote:
> On Wed, Aug 15, 2012 at 1:34 PM, Christopher Nelson
> <[email protected]> wrote:
>> ... My object model is kind of messy.  I have, very
>> roughly, something like:
>>
>>     class TracPM:
>>          def start(self, task):
>>              ...do something to get start out of task...
>>          def finish(self, task):
>>              ...do something to get finish out of task...
>>
>> which is then called like:
>>
>>     for t in tasks:
>>         start = pm.start(t)
>>
>> If I create TracPM.__get__() that doesn't relate to the start date, it
>> relates to the TracPM class.  I guess what I need to do is:
>>
>>  * Create a ScheduleDate (or PMDate or something) class
>>  * Give it __get__ and __set__ (and __delete__?) methods
>>  * Make the dates in the task instances of that class
>>  * Where I currently do "s = pm.start(t)" I'd do "s = t.start" (which
>> would invoke the getter) and elsewhere I could do "t.start =
>> <somedate>" to set it.
>>
>> Does that sound right?
>
> Not quite -- you don't define __get__ and __set__ methods.  You define
> methods with any name, and then magically turn them into a property (which
> is a pair of setter/getter methods that magically act like an attribute
> instead) using the built-in property() function (or the alternate
> decorator-based spelling Olemis pointed out)
>
> The problem in your case is that your getter is a function which takes one
> argument -- because, as you say, it's actually a getter of a property on the
> task, not on the TracPM class.  That means that you can't define the
> property on the TracPM class.  Instead you would define the getter and
> setter methods on whatever class "task" is an instance of, and then access
> it like `foo = self.task.start; self.task.start = datetime(...)`.

Right.  But I could create a pmDate class that had getter and setter
methods and pass that around.

> But if "task" is a Trac ticket, or some other class whose definition you
> don't control, then you can't really do that either.

A task is a hash of ticket attributes, not quite a whole ticket.
Right now, my TracPM code adds a '_calc_start' entry to the dictionary
so `TracPM.start(t)` really just masks the name of the index with
something not a lot more complicated than `return t['_calc_start']`.

My thought is that if TracPM did something like:

 t['_start'] = pmDate('start')
 t['_finish'] = pmDate('finish')

then the caller could do

   for t in tasks:
      start = t['_start'] # Invoke the getter

and my internal code could do:

   t['_start'] = somedate # Invoke the setter

Am I still off base?


> At that point I guess
> the "most elegant" way to deal with the problem would be by wrapping the
> ticket in another class that adds the "start" and "finish" properties with
> their getters and setters:
>
> class TracPMTask(object):
>   def __init__(self, task):
>     self.task = task
>   def _get_start(self):
>     return however_you_do_this(self.task)
>   def _set_start(self, start_datetime):
>     however_you_do_that(self.task, start_datetime)
>   start = property(_get_start, _set_start)
>
> ...which you would use like:
>
> for t in tasks:
>   start = TracPMTask(t).start
>   TracPMTask(t).new_start = datetime.datetime.now()
>
> ...but, as you can see, this is now a pretty big departure from how you're
> already doing things,

I'm willing to write off a false start to start doing it right.  There
are only a handful of uses in a couple of classes so fixing it now is
easy.

> and also begins to obfuscate what's going on more than
> it helps.  So really, in your case, the "most Pythonic" thing to do is
> probably to just keep it simple, and define a TracPM.set_start(self, task,
> new_start) method -- then you don't have to change any of your code, and
> it's totally clear to a reader what's going on.  It's perfectly idiomatic
> Python as long as you don't call the method setStart :-)

Gawd, I had embedded underscores!

-- 
A: Top-posting.
Q: What is the most annoying thing in e-mail?

-- 
You received this message because you are subscribed to the Google Groups "Trac 
Development" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/trac-dev?hl=en.

Reply via email to