[CalendarServer-changes] [65] CalendarServer/branches/users/cdaboo/acl-merge

source_changes at macosforge.org source_changes at macosforge.org
Fri Aug 25 10:50:15 PDT 2006


Revision: 65
Author:   cdaboo at apple.com
Date:     2006-08-25 10:50:13 -0700 (Fri, 25 Aug 2006)

Log Message:
-----------
Fix for MKCALENDAR/MKCOL. Mostly switching over to use of deferreds.

Modified Paths:
--------------
    CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcalendar.py
    CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcol.py
    CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/static.py

Added Paths:
-----------
    CalendarServer/branches/users/cdaboo/acl-merge/patches/Twisted/twisted.web2.dav.method.mkcol.patch

Added: CalendarServer/branches/users/cdaboo/acl-merge/patches/Twisted/twisted.web2.dav.method.mkcol.patch
===================================================================
--- CalendarServer/branches/users/cdaboo/acl-merge/patches/Twisted/twisted.web2.dav.method.mkcol.patch	                        (rev 0)
+++ CalendarServer/branches/users/cdaboo/acl-merge/patches/Twisted/twisted.web2.dav.method.mkcol.patch	2006-08-25 17:50:13 UTC (rev 65)
@@ -0,0 +1,19 @@
+Index: twisted/web2/dav/method/mkcol.py
+===================================================================
+--- twisted/web2/dav/method/mkcol.py	(revision 17951)
++++ twisted/web2/dav/method/mkcol.py	(working copy)
+@@ -62,14 +62,6 @@
+             "Parent resource is not a collection."
+         ))
+ 
+-    if not self.fp.parent().isdir():
+-        log.err("Attempt to create collection with no parent directory: %s"
+-                % (self.fp.path,))
+-        raise HTTPError(StatusResponse(
+-            responsecode.INTERNAL_SERVER_ERROR,
+-            "The requested resource is not backed by a parent directory."
+-        ))
+-
+     #
+     # Read request body
+     #

Modified: CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcalendar.py
===================================================================
--- CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcalendar.py	2006-08-25 16:26:35 UTC (rev 64)
+++ CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcalendar.py	2006-08-25 17:50:13 UTC (rev 65)
@@ -15,6 +15,10 @@
 #
 # DRI: Wilfredo Sanchez, wsanchez at apple.com
 ##
+from twisted.internet.defer import succeed
+from twisted.internet.defer import waitForDeferred
+from twisted.web2.dav.util import parentForURL
+from twisted.internet.defer import deferredGenerator
 
 """
 CalDAV MKCALENDAR method.
@@ -43,89 +47,86 @@
     Respond to a MKCALENDAR request.
     (CalDAV-access-09, section 5.3.1)
     """
-    self.fp.restat(False)
 
+    #
+    # Check authentication and access controls
+    #
+    parent = waitForDeferred(request.locateResource(parentForURL(request.uri)))
+    yield parent
+    parent = parent.getResult()
+
+    x = waitForDeferred(parent.securityCheck(request, (davxml.Bind(),)))
+    yield x
+    x.getResult()
+
     if self.exists():
-        return ErrorResponse(
+        log.err("Attempt to create collection where file exists: %s"
+                % (self.fp.path,))
+        raise HTTPError(ErrorResponse(
             responsecode.FORBIDDEN,
-            (davxml.dav_namespace, "resource-must-be-null")
+            (davxml.dav_namespace, "resource-must-be-null"))
         )
 
-    if not os.path.isdir(self.fp.dirname()):
-        return ErrorResponse(
+    if not parent.isCollection():
+        log.err("Attempt to create collection with non-collection parent: %s"
+                % (self.fp.path,))
+        raise HTTPError(ErrorResponse(
             responsecode.CONFLICT,
-            (caldavxml.caldav_namespace, "calendar-collection-location-ok")
+            (caldavxml.caldav_namespace, "calendar-collection-location-ok"))
         )
 
     #
-    # Check authentication and access controls
-    #
-    parent = self.locateParent(request, request.uri)
-    parent.securityCheck(request, (davxml.Bind(),))
-
-    #
     # Read request body
     #
-    d = davXMLFromStream(request.stream)
+    try:
+        doc = waitForDeferred(davXMLFromStream(request.stream))
+        yield doc
+        doc = doc.getResult()
 
-    def gotError(f):
-        log.err("Error while handling MKCALENDAR: %s" % (f,))
+        result = waitForDeferred(self.createCalendar(request))
+        yield result
+        result = result.getResult()
+    except ValueError, e:
+        log.err("Error while handling MKCALENDAR: %s" % (e,))
+        raise HTTPError(StatusResponse(responsecode.BAD_REQUEST, str(e)))
 
-        # Clean up
-        if self.fp.exists(): self.fp.remove()
+    if doc is not None:
+        makecalendar = doc.root_element
+        if not isinstance(makecalendar, caldavxml.MakeCalendar):
+            # Clean up
+            if self.fp.exists(): self.fp.remove()
 
-        if f.check(ValueError):
-            return StatusResponse(responsecode.BAD_REQUEST, str(f))
-        elif f.check(HTTPError):
-            return f.value.response
-        else:
-            return f
+            error = ("Non-%s element in MKCALENDAR request body: %s"
+                     % (caldavxml.MakeCalendar.name, makecalendar))
+            log.err(error)
+            raise HTTPError(StatusResponse(responsecode.UNSUPPORTED_MEDIA_TYPE, error))
 
-    def gotXML(doc):
-        # FIXME: if we get any errors, we need to delete the calendar
-
-        d = maybeDeferred(self.createCalendar, request)
-
-        if doc:
-            makecalendar = doc.root_element
-            if not isinstance(makecalendar, caldavxml.MakeCalendar):
-                error = ("Non-%s element in MKCALENDAR request body: %s"
-                         % (caldavxml.MakeCalendar.name, makecalendar))
-                log.err(error)
-                raise HTTPError(StatusResponse(responsecode.UNSUPPORTED_MEDIA_TYPE, error))
-
-            def finish(response):
-                errors = PropertyStatusResponseQueue("PROPPATCH", request.uri, responsecode.NO_CONTENT)
-                got_an_error = False
-
-                if makecalendar.children:
-                    # mkcalendar -> set -> prop -> property*
-                    for property in makecalendar.children[0].children[0].children:
-                        try:
-                            if property.qname() == (caldavxml.caldav_namespace, "supported-calendar-component-set"):
-                                self.writeDeadProperty(property)
-                            else:
-                                self.writeProperty(property, request)
-                        except:
-                            errors.add(Failure(), property)
-                            got_an_error = True
-                        else:
-                            errors.add(responsecode.OK, property)
-
-                if got_an_error:
-                    errors.error()
-                    raise HTTPError(MultiStatusResponse([errors.response()]))
+        errors = PropertyStatusResponseQueue("PROPPATCH", request.uri, responsecode.NO_CONTENT)
+        got_an_error = False
+    
+        if makecalendar.children:
+            # mkcalendar -> set -> prop -> property*
+            for property in makecalendar.children[0].children[0].children:
+                try:
+                    if property.qname() == (caldavxml.caldav_namespace, "supported-calendar-component-set"):
+                        self.writeDeadProperty(property)
+                    else:
+                        p = waitForDeferred(self.writeProperty(property, request))
+                        yield p
+                        p.getResult()
+                except:
+                    errors.add(Failure(), property)
+                    got_an_error = True
                 else:
-                    response = IResponse(response)
-                    response.headers.setHeader("cache-control", { "no-cache": None })
-                    return response
+                    errors.add(responsecode.OK, property)
+    
+        if got_an_error:
+            # Clean up
+            if self.fp.exists(): self.fp.remove()
 
-            d.addCallback(finish)
-            d.addErrback(gotError)
+            errors.error()
+            raise HTTPError(MultiStatusResponse([errors.response()]))
 
-        return d
+    yield responsecode.CREATED
 
-    d.addCallback(gotXML)
-    d.addErrback(gotError)
-
-    return d
+http_MKCALENDAR = deferredGenerator(http_MKCALENDAR)

Modified: CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcol.py
===================================================================
--- CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcol.py	2006-08-25 16:26:35 UTC (rev 64)
+++ CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/method/mkcol.py	2006-08-25 17:50:13 UTC (rev 65)
@@ -24,8 +24,9 @@
 
 __all__ = ["http_MKCOL"]
 
+from twisted.internet.defer import deferredGenerator, waitForDeferred
 from twisted.web2 import responsecode
-from twisted.web2.http import StatusResponse
+from twisted.web2.http import HTTPError, StatusResponse
 
 from twistedcaldav.resource import isPseudoCalendarCollectionResource
 
@@ -33,11 +34,15 @@
     #
     # Don't allow DAV collections in a calendar collection for now
     #
-    parent = self._checkParents(request, isPseudoCalendarCollectionResource)
+    parent = waitForDeferred(self._checkParents(request, isPseudoCalendarCollectionResource))
+    yield parent
+    parent = parent.getResult()
     if parent is not None:
-        return StatusResponse(
+        raise HTTPError(StatusResponse(
             responsecode.FORBIDDEN,
-            "Cannot create collection within special collection %s" % (parent,)
+            "Cannot create collection within special collection %s" % (parent,))
         )
 
-    return super(CalDAVFile, self).http_MKCOL(request)
+    yield super(CalDAVFile, self).http_MKCOL(request)
+
+http_MKCOL = deferredGenerator(http_MKCOL)
\ No newline at end of file

Modified: CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/static.py
===================================================================
--- CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/static.py	2006-08-25 16:26:35 UTC (rev 64)
+++ CalendarServer/branches/users/cdaboo/acl-merge/twistedcaldav/static.py	2006-08-25 17:50:13 UTC (rev 65)
@@ -37,9 +37,7 @@
 import errno
 from urlparse import urlsplit
 
-from twisted.internet.defer import fail
-from twisted.internet.defer import succeed
-from twisted.internet.defer import waitForDeferred
+from twisted.internet.defer import deferredGenerator, fail, succeed, waitForDeferred
 from twisted.python import log
 from twisted.python.failure import Failure
 from twisted.python.filepath import FilePath
@@ -140,27 +138,31 @@
 
         if self.fp.exists():
             log.err("Attempt to create collection where file exists: %s" % (self.fp.path,))
-            return responsecode.NOT_ALLOWED
+            return fail(responsecode.NOT_ALLOWED)
 
         if not os.path.isdir(os.path.dirname(self.fp.path)):
             log.err("Attempt to create collection with no parent: %s" % (self.fp.path,))
-            return StatusResponse(responsecode.CONFLICT, "No parent collection")
+            return succeed(StatusResponse(responsecode.CONFLICT, "No parent collection"))
 
         #
         # Verify that no parent collection is a calendar also
         #
         log.msg("Creating calendar collection %s" % (self,))
 
+        def _defer(parent):
+            if parent is not None:
+                log.err("Cannot create a calendar collection within a calendar collection %s" % (parent,))
+                return ErrorResponse(
+                    responsecode.FORBIDDEN,
+                    (caldavxml.caldav_namespace, "calendar-collection-location-ok")
+                )
+    
+            return self.createCalendarCollection()
+            
         parent = self._checkParents(request, isPseudoCalendarCollectionResource)
-        if parent is not None:
-            log.err("Cannot create a calendar collection within a calendar collection %s" % (parent,))
-            return ErrorResponse(
-                responsecode.FORBIDDEN,
-                (caldavxml.caldav_namespace, "calendar-collection-location-ok")
-            )
+        parent.addCallback(_defer)
+        return parent
 
-        return self.createCalendarCollection()
-
     def createCalendarCollection(self):
         #
         # Create the collection once we know it is safe to do so
@@ -395,14 +397,18 @@
             parent_uri = parentForURL(parent_uri)
             if not parent_uri: break
 
-            parent = self.locateSiblingResource(request, parent_uri)
+            parent = waitForDeferred(request.locateResource(parent_uri))
+            yield parent
+            parent = parent.getResult()
 
-            log.msg("Testing parent: %s" % (parent,))
+            if test(parent):
+                yield parent
+                return
 
-            if test(parent): return parent
+        yield None
+    
+    _checkParents = deferredGenerator(_checkParents)
 
-        return None
-
 class ScheduleInboxFile (ScheduleInboxResource, CalDAVFile):
     """
     L{CalDAVFile} calendar inbox collection resource.

-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.macosforge.org/pipermail/calendarserver-changes/attachments/20060825/53f85da9/attachment.html


More information about the calendarserver-changes mailing list