Re: [Repoze-dev] repoze.tm wishlist

2008-07-15 Thread Chris McDonough
Chris McDonough wrote:
> So, long story short, I've been afraid to release *either* repoze.tm or 
> repoze.tm2 until I had the time to sort all that out.  I'd still rather not 
> release either to PyPI but I'll go ahead and create a release of "repoze.tm2" 
> in 
> an index on dist.repoze.org (which will also contain the transaction package).

Done.  I release repoze.tm2 1.0a2 and created an index for it on 
dist.repoze.org:

bin/easy_install -i http://dist.repoze.org/tm2/dev/simple repoze.tm2


___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-15 Thread Chris McDonough
Alberto Valverde wrote:
>> Hi Alberto,
>>
>> Thanks!  I applied a slightly modified version of this patch:
>>
>> http://lists.repoze.org/pipermail/repoze-checkins/2008-July/001088.html
>>
>> The code can be checked out from http://svn.repoze.org/repoze.tm2/trunk/ .
> 
> Awesome, thanks :)
> 
> I'll remove my temporary implementation from rum and use repoze.tm2 now
> instead and tell you how it goes... Then I'll take ata sb at integrating
> it in turbogears2 (this is why I'm cross-posting to tg-trunk)
> 
> BTW, where can I tell pkg_resources to pull repoze.tm2 as a distribution's
> requirement from? Are you planning to register it at PyPI like everyone
> else does? ;)

Our release situation is a little complicated right now.  There's another 
version named "repoze.tm" that is used by "repoze.zope2".  The difference 
between repoze.tm and repoze.tm2 is that repoze.tm depends not only on 
"transaction" but also on all of ZODB ("transaction" is a package that up until 
recently always shipped as part of ZODB).

It's appropriate for "repoze.zope2" to depend on ZODB, and thus for it to use 
repoze.tm wholesale, not trying to use a standalone "transaction" package.  But 
it's our intent to retire "repoze.tm" and start to use repoze.tm2 for all of 
our 
projects.  But that requires a couple days worth of development to tease apart 
ZODB dependencies our releases of Zope2 so it can use separate "ZODB" and 
"transaction" packages.  And each version of Zope would need to be tested to 
make sure this works, which is probably another day or two worth of effort.  We 
just haven't done the work.

So, long story short, I've been afraid to release *either* repoze.tm or 
repoze.tm2 until I had the time to sort all that out.  I'd still rather not 
release either to PyPI but I'll go ahead and create a release of "repoze.tm2" 
in 
an index on dist.repoze.org (which will also contain the transaction package).

- C


___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Chris McDonough
Chris McDonough wrote:
> Hi Alberto,
> 
> Thanks!  I applied a slightly modified version of this patch:

... which after I look at the checkin message, was wrong. ;-)

Fixed via 
http://lists.repoze.org/pipermail/repoze-checkins/2008-July/001089.html

- C

___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Chris McDonough
Hi Alberto,

Thanks!  I applied a slightly modified version of this patch:

http://lists.repoze.org/pipermail/repoze-checkins/2008-July/001088.html

The code can be checked out from http://svn.repoze.org/repoze.tm2/trunk/ .

Thanks again,

- C




Alberto Valverde wrote:
> Chris McDonough wrote:
>> (...)
 There is an existing pattern for this if you can get a hold of the
 transaction
 object itself in app code:  transaction.doom()
>>> This is good for the cases where the middleware stacked below repoze.tm
>>> knows about the transaction, but worthless otherwise.
>> Any app code can doom the current transaction, actually by an import
>> and a couple of function calls:
>>
>> import transaction
>> transaction.get().doom()
>>
>> "t" is a transaction.Transaction object then representing the current
>> transaction.  It is effectively a "thread local" (although it's not a
>> Python threading.local, as the transaction package was created before
>> that existed).
> 
> I was thinking more about some thirdparty middleware (outside TG's
> code-base, hence we can't tell it to doom the transaction) which used
> the response status to signal an error and doesn't want to deal with
> transactions because it doens't need them.  This imaginary middleware
> needs to be stacked below TM however since I want TM to wrap several
> apps (eg: 'forked' with a URLMap) but only one of these needs the
> imaginary middleware in its branch since if it were above TM it would
> affect both of them.
> 
> It has just occurred to me that we could still wrap this troublesome
> middleware with yet another middleware that turned this HTTP error back
> into an exception (or simply doom the transaction) but I think that the
> hook you proposed would make things simpler since TG2 could configure TM
> with this behavior by default so users who want to cherry pick their
> middleware pieces don't get bitten by, for example, 403 responses
> silently committing whatever objects have been created until the auth.
> framework determined the user didn't have the credentials.
> 
> As I've said, this bug happened to me and I found it pretty obscure
> since all I got was a report by a co-worker who was testing the app that
> said: "I tried to delete a mailbox I wasn't supposed to delete and the
> app told me I couldn't, but then I looked back and it wasn't there!"
> 
 If that's not convenient, how about a way to define a "commit veto"
 hook?
 Then
 you could do whatever you liked with the environ, status, or response
 headers to
 determine that you shouldn't commit. An implementation might be:

 def commit_veto(environ, status, response_headers):
  if not status.startswith('2'):
  return True

 It would be called by the middleware just before it's about to
 commit.  If
 the
 commit veto hook return True, it would mean "don't commit".  Tthe
 middleware
 would capture the status and header output and do:

 if transaction.isDoomed() or self.commit_veto(environ, status,
 headers):
  self.abort()

 The commit_veto function would be passed as an argument to the
 repoze.tm
 middleware constructor, so you'd create a TM via:

 txn_managed_app = repoze.tm2.TM(app, commit_veto)
>>> This would be prefect :)
>> OK, I'll try to add it in some form shortly (or you can if you like
>> too, I'd be happy to accept a patch or give commit access).  In the
>> meantime, you might just try to work around the issue with a doom.
> 
> I've attached a patch implementing the commit_veto() hook with a test. I
> had to modify some of the tests to send a dummy start_response callable
> instead of the dummy None since a closure inside __call__ needs to call
> it (like a real app) after grabbing the status and headers but these
> changes shouldn't affect what was being tested, I hope. Commit access
> would be handy in case I missed something, or perhaps you prefer me to
> bug you with a couple more patches before that... :)
> 
> Thanks!
> Alberto
> 

___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Chris McDonough
Chris McDonough wrote:
> Re-added to list...
> 
> Alberto Valverde wrote:
>>> Mark Ramm wrote:
 So, we're finally getting around to handling transactions in
 middleware in tg2, and Alberto and I have been playing with different
 variations on the repoze.tm theme, and ultimately I think it might be
 good if we had a transaction middleware that provided a bit more
 configurability about when it rolls back transactions.
>>> +1
>>>
 Alberto added something which checked the HTTP status code for error
 codes and rolled back when the app indicated that an error had
 occurred (useful when there's middleware that catches and handles
 python exceptions), and I was playing with the idea of setting some
 kind of semi-standard parameter in the environ that signals that
 there's been an error somewhere and the transaction should be rolled
 back.
>>> There is an existing pattern for this if you can get a hold of the
>>> transaction
>>> object itself in app code:  transaction.doom()
>> This is good for the cases where the middleware stacked below repoze.tm
>> knows about the transaction, but worthless otherwise.
> 
> Any app code can doom the current transaction, actually by an import and a 
> couple of function calls:
> 
> import transaction
> transaction.get().doom()

Tres reminded me that this can also be accomplished by the shortcut:

import transaction
transaction.doom()

- C

___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Chris McDonough
Re-added to list...

Alberto Valverde wrote:
>> Mark Ramm wrote:
>>> So, we're finally getting around to handling transactions in
>>> middleware in tg2, and Alberto and I have been playing with different
>>> variations on the repoze.tm theme, and ultimately I think it might be
>>> good if we had a transaction middleware that provided a bit more
>>> configurability about when it rolls back transactions.
>> +1
>>
>>> Alberto added something which checked the HTTP status code for error
>>> codes and rolled back when the app indicated that an error had
>>> occurred (useful when there's middleware that catches and handles
>>> python exceptions), and I was playing with the idea of setting some
>>> kind of semi-standard parameter in the environ that signals that
>>> there's been an error somewhere and the transaction should be rolled
>>> back.
>> There is an existing pattern for this if you can get a hold of the
>> transaction
>> object itself in app code:  transaction.doom()
> 
> This is good for the cases where the middleware stacked below repoze.tm
> knows about the transaction, but worthless otherwise.

Any app code can doom the current transaction, actually by an import and a 
couple of function calls:

import transaction
transaction.get().doom()

"t" is a transaction.Transaction object then representing the current 
transaction.  It is effectively a "thread local" (although it's not a Python 
threading.local, as the transaction package was created before that existed).

>> If that's not convenient, how about a way to define a "commit veto" hook?
>> Then
>> you could do whatever you liked with the environ, status, or response
>> headers to
>> determine that you shouldn't commit. An implementation might be:
>>
>> def commit_veto(environ, status, response_headers):
>>  if not status.startswith('2'):
>>  return True
>>
>> It would be called by the middleware just before it's about to commit.  If
>> the
>> commit veto hook return True, it would mean "don't commit".  Tthe
>> middleware
>> would capture the status and header output and do:
>>
>> if transaction.isDoomed() or self.commit_veto(environ, status, headers):
>>  self.abort()
>>
>> The commit_veto function would be passed as an argument to the repoze.tm
>> middleware constructor, so you'd create a TM via:
>>
>> txn_managed_app = repoze.tm2.TM(app, commit_veto)
> 
> This would be prefect :)

OK, I'll try to add it in some form shortly (or you can if you like too, I'd be 
happy to accept a patch or give commit access).  In the meantime, you might 
just 
try to work around the issue with a doom.

- C

___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Chris McDonough
Mark Ramm wrote:
> So, we're finally getting around to handling transactions in
> middleware in tg2, and Alberto and I have been playing with different
> variations on the repoze.tm theme, and ultimately I think it might be
> good if we had a transaction middleware that provided a bit more
> configurability about when it rolls back transactions.

+1

> Alberto added something which checked the HTTP status code for error
> codes and rolled back when the app indicated that an error had
> occurred (useful when there's middleware that catches and handles
> python exceptions), and I was playing with the idea of setting some
> kind of semi-standard parameter in the environ that signals that
> there's been an error somewhere and the transaction should be rolled
> back.

There is an existing pattern for this if you can get a hold of the transaction 
object itself in app code:  transaction.doom()

If that's not convenient, how about a way to define a "commit veto" hook?  Then 
you could do whatever you liked with the environ, status, or response headers 
to 
determine that you shouldn't commit. An implementation might be:

def commit_veto(environ, status, response_headers):
 if not status.startswith('2'):
 return True

It would be called by the middleware just before it's about to commit.  If the 
commit veto hook return True, it would mean "don't commit".  Tthe middleware 
would capture the status and header output and do:

if transaction.isDoomed() or self.commit_veto(environ, status, headers):
 self.abort()

The commit_veto function would be passed as an argument to the repoze.tm 
middleware constructor, so you'd create a TM via:

txn_managed_app = repoze.tm2.TM(app, commit_veto)

- C

___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev


Re: [Repoze-dev] repoze.tm wishlist

2008-07-14 Thread Tres Seaver
-BEGIN PGP SIGNED MESSAGE-
Hash: SHA1

Mark Ramm wrote:
> So, we're finally getting around to handling transactions in
> middleware in tg2, and Alberto and I have been playing with different
> variations on the repoze.tm theme, and ultimately I think it might be
> good if we had a transaction middleware that provided a bit more
> configurability about when it rolls back transactions.
> 
> Alberto added something which checked the HTTP status code for error
> codes and rolled back when the app indicated that an error had
> occurred (useful when there's middleware that catches and handles
> python exceptions), and I was playing with the idea of setting some
> kind of semi-standard parameter in the environ that signals that
> there's been an error somewhere and the transaction should be rolled
> back.

You can also call 'doom' on the transaction, e.g.:

  import transaction
  transaction.doom()

which will prevent any commit from occurring for the current
transaction, no matter what.

> Of course if we're relying on some kind of "special key" in the
> environ, repoze.tm it couples the application inside to repoze.tm a
> little bit, so I like Alberto's way better.   On the other hand, I
> don't think every application will want the mapping of response-codes
> to rollback, and it's even more likely that some folks will want to be
> able to handle that mapping a bit differently than any default we come
> up with.
> 
> And the benifit of a special key in the environ is that it allows
> users to overide the default behavior for a particular request, which
> provides a nice escape hatch for when things just don't work.
> 
> What do you all think? 

I prefer the library API, myself.  I can imagine wanting the middleware
to do some kind of checking for non-OK response codes, although I don't
really like having the application set it:  raising exceptions is a Good
Thing, compared to making everybody above you have to handle the error
cases inline.


Tres.
- --
===
Tres Seaver  +1 540-429-0999  [EMAIL PROTECTED]
Palladion Software   "Excellence by Design"http://palladion.com
-BEGIN PGP SIGNATURE-
Version: GnuPG v1.4.6 (GNU/Linux)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iD8DBQFIe25y+gerLs4ltQ4RAv/BAJ9uN5NkmJOFeayo/bOtLHJo6fuyzwCggfFG
Kk0ZXn/3xvT6ijjaDxib3Do=
=2sag
-END PGP SIGNATURE-
___
Repoze-dev mailing list
Repoze-dev@lists.repoze.org
http://lists.repoze.org/listinfo/repoze-dev