[Zope3-dev] DISCUSS: Correct sequence for PUT

Paul Everitt paul@zope-europe.org
Wed, 19 Feb 2003 10:12:17 +0100


Howdy.  I just started putting PUT support into the stuff I'm doing with 
Moztop.  I used Shane's nice "tcpwatch" application to record the 
request/response interaction, then compared it to a PUT to Apache.

At the end I have cut-and-pasted the request/response for Zope 3 and for 
Apache 2.

Some points and questions:

1) Zope 3 identifies itself as an HTTP/1.1 server.  I didn't realize we 
supported HTTP/1.1.  How much is actually there?

2) I'm not sure Zope 3 is doing the PUT correctly.  I did a PUT of a new 
resource, and RFC 2616 (HTTP/1.1) Section 9.6 says that a status code of 
201 should be returned.  Also, the server should return a Location: 
header with the URI of the newly created resource.

Perhaps I'm reading 9.6 incorrectly?

3) Finally, I gentle plea for a feature.  In Moztop (and in the 
Rotterdam skin), I'd like to support Undo from the client, without 
visiting a page.  That is, I'd like the most recent transaction to be 
undo-able simply by performing a gesture (click on an Undo button, for 
instance).

To avoid sending the user to a page and making them select a transaction 
to undo, I propose that Zope return transaction ids as part of the 
response.  This could be in an HTTP response header.  Or, for things 
like PUT, we could use the response body (which we're not using right now).

Finally, I'd like some advice on how to handle the sequence for creating 
richer objects.  Let's say I want to create a Smart Image without 
filling in an HTML form.  I want to create it using HTTP/DAV verbs.

To make this hard, presume two constraints:

1) You can't create a Smart Image without passing in three parameters to 
the constructor.  Let's say they are author, keyword, and 
publicationname.  Doesn't matter, I'm just being hypothetical.

2) The request body is, obviously, binary.

Using Shane's tcpwatch, I took a look at the sequence for using Windows 
Web Folders to drag-n-drop an image to Apache 2.  It was interesting:

1) Request: HEAD, to see if it already exists. Response: not found.

2) Request: PUT of the resource *without* the body.  Response: 201 
created, Location: the uri.

3) Request: Another HEAD, on the URI returned by (2).  Response: nothing 
terribly meaningful.

4) Request: Another PUT, this time we finally send the binary contents. 
  Response: 204 no content.

5) Request: Another HEAD.  Response: The basic info again.

So for this Smart Image, do I do something like this:

1) HEAD to see if it exists.

2) PUT to create it, sending as the request body some XML for 
construction.  (I could do a PUT and then a PROPPATCH, but after the PUT 
it is alread constructed, so I defeat the constructor.)

3) HEAD, just in case the server thinks the URI is different. :^)

4) PUT to actually send the body.

Geesh, hope our server is fast!  Imagine dragging-and-dropping 100 files 
onto a Zope site.

--Paul

Zope 3 Request-Response
------------------------------
[00:00.000 - client 192.168.1.3:58487 forwarded to 192.168.1.3:8380]
PUT /folder/monkeyboy HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Macintosh; U; PPC Mac OS X Mach-O; en-US; 
rv:1.3b) Gecko/20030210
Accept: 
text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,video/x-mng,image/png,image/jpeg,image/gif;q=0.2,*/*;q=0.1
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate,compress;q=0.9
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Content-Type: text/plain
Content-Length: 3

foo
[00:00.110 - server connected]
HTTP/1.1 200 Ok
Date: Wed, 19 Feb 2003 08:25:55 GMT
Content-Length: 0
X-Powered-By: Zope (www.zope.org), Python (www.python.org)
Server: zope.server.http (HTTP)


Apache 2 Request-Response
------------------------------
[00:00.000 - client 192.168.1.3:58488 forwarded to 192.168.1.2:9000]
PUT /somefile HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Macintosh; U; PPC Mac OS X Mach-O; en-US; 
rv:1.3b) Gecko/20030210
Accept: 
text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,video/x-mng,image/png,image/jpeg,image/gif;q=0.2,*/*;q=0.1
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip,deflate,compress;q=0.9
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive
Content-Type: text/plain
Content-Length: 3
[00:00.050 - server connected]

foo
HTTP/1.1 201 Created
Date: Wed, 19 Feb 2003 08:29:22 GMT
Server: Apache/2.0.40 (Unix) DAV/2
Location: http://localhost:9000/somefile
Content-Length: 251
Keep-Alive: timeout=15, max=100
Connection: Keep-Alive
Content-Type: text/html; charset=ISO-8859-1

<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>201 Created</title>
</head><body>
<h1>Created</h1>
<p>Resource /somefile has been created.</p>
<hr />
<address>Apache/2.0.40 Server at localhost Port 9000</address>
</body></html>