Creating a multi-tier client/server application

David Bolen db3l.net at gmail.com
Wed Aug 29 22:08:25 CEST 2007


Jeff <jeff.fw at gmail.com> writes:

> reasons, not the least of which is that I've been working almost
> entirely on web apps for the past few years, and I am getting mighty
> sick of it.  A lot of that is due to the language (PHP, which I have
> since grown to hate) I had to use.  I've worked on a site for my self
> in Python (using Pylons, actually--which is excellent) which was
> vastly easier and more fun.  But I'd really like to try something
> different.

To contribute a data point against your original question - I've a similar
(structurally, not functionality) system I completed recently.

Without trying to get too mired in the thick client v. web application
debate, there were a handful of points that decided me in favor of the
thick client:

* Needed to automate QuickTime viewer for video previews and extraction
  of selected frames to serve as thumbnails on web approval page.
* Needed to control transfers to server of multiple very large files
  (hundreds of MBs to GBs at a shot)

But assuming a thick client, in terms of your original question of
components to use, here's what I've got.  My primary networking component
is Twisted.

The pieces are:

Client (OS X Cocoa application):

* PyObjC based.  Twisted for networking, Twisted's PB for the primary
  management channel, with an independent direct network connections for
  bulk file transfers.  (I needed to go Mac native for clean integration of
  QuickTime UI elements including frame extraction to thumbnails)

Server:

* Twisted for networking.  PB and raw connections for clients, web server
  through twisted.web.  Genshi for web templating, with Mochikit (might
  move to JQuery) for client-side JS/AJAX.  Twisted for email transmission
  (email construction using normal Python email package).  Small UI
  front-end module (Cocoa/PyObjC).

The client accesses server-based objects through Twisted PB, which for some
of the server objects also control session change lifetime (transactions).
So at least in my case, having a stateful connection from the client worked
out well, particularly since I needed to coordinate both database changes
as well as filesystem changes through independent file uploads, each of
which can fail independently.
  
Right now a single server application contains all support for client
connections as well as the web application, but I could fracture that (so
the web server was independent for example) if needed.

For the client, I package it using py2app, and put into an normal Mac
installer, and distribute as a dmg.  If it were a Windows client, I'd
probably wrap with py2exe, then Inno Setup.  The server's web server has a
restricted URL that provides access to the DMG.  The client has a Help menu
item taking users to that URL.  Clients are versioned and accepted/rejected
by the server during initial connection - from the server side I can
"retire" old client versions, at which point users get a message at signon
with a button to take them to the download page for the latest DMG.

So right now upgrades are executed manually by the user, and I can support
older clients during any transition period.  I may provide built-in support
for automatically pulling down the new image and executing its installer,
but haven't found it a hardship yet.  I probably won't bother trying to
automate smaller levels of updates.

-- David



More information about the Python-list mailing list