[Zope-dev] Customizing zope w/proxy

Michel Pelletier michel@digicool.com
Wed, 29 Mar 2000 17:47:16 -0800


"Robert W. Bill" wrote:
> 
> Hello all,
> 
> I was looking for hints concerning customizing zope.  I want to use zope
> as a proxy server (ie squid) only I need the access control structure and
> other features in zope. 

Then it's not going to be a very fast proxy, unless you get fancy.

> With apache this is done by the module system- a
> very well defined framework for the customization of apache.  However,
> after looking through Zope I am having tremendous difficulty figuring out
> how to do this. 

It's not a task Zope was designed for.  Keep in mind it's also not a job
Apache was designed for and Apache isn't all that hot of a proxy server
compared to others like Squid.  Apache is not all that great because it
is based on a fork() model.  Zope would not be all that great the way
you want to do it because the Zope application is based on threads.  The
best way to proxy is the way Squid does it, asychronously.  Zope *does*
have an asychronous 'socket kernel' that runs in one thread and is very
much like Squid.

> I'm working on it within apache as well, but wanted a
> comparison with a zope implimentation.  A few hints to get me started
> would be great! 

There's three ways to go about this:

  1) Create a component of Zope that accepts HTTP proxy connections
(would probably require modification to ZServer's http server) and
forwards them up to an application thread, like all http requests.  This
request would then be groked in whatever way you want to grok it by your
code, and then your code would either serve a cached page or make an
external http request to an outside server to satisfy the request, and
turn it back around to the client.

Pros:  Uhm... fairly straightforward.

Cons:  Slow.

  2) Add caching behavior directly to ZServer.  Because the cache exists
in the same thread of execution as the server, this is very fast.  A
ZServer cache like this would be the pythonic equivalent to squid, which
is based on asychronous sockets just like ZServer.  This would be very
cool.

Pros:  Fast.  High-Load, Scalable, Fast, cool.

Cons:  Kinda tricky.  Not very configurable from the application
(Zope).  You don't want to ask the application to do things for you,
because this involves communicating somehow with another thread, which
is a slow proposition.  Also, programming in asyncore and asychat is
really simple, _once_ you grok the concept.  I suggest reading up alot
on the various theories of select() and poll() and understanding the
asychronous model.

  3) There is probably a hybrid solution that will do what you want.  If
you created both the ZServer cache and the component, then you can
probably get the beneifts of both worlds.  Your ZServer cache could get
its 'routing' information from an object that it only reads.  Up in the
application, you have your component that has write access to this
object.  Keep in mind that this object is in another thread and that
other threads also running your component may try to read the common
object at the same time.  There are no pros or cons for this one, this
is pure Nirvana.  I would try comming up with 2 first, then tackle this.

-Michel