[CalendarServer-changes] [8560] CalendarServer/trunk
source_changes at macosforge.org
source_changes at macosforge.org
Thu Jan 19 11:39:35 PST 2012
Revision: 8560
http://trac.macosforge.org/projects/calendarserver/changeset/8560
Author: sagen at apple.com
Date: 2012-01-19 11:39:34 -0800 (Thu, 19 Jan 2012)
Log Message:
-----------
Support new collabd access API
Modified Paths:
--------------
CalendarServer/trunk/calendarserver/provision/root.py
CalendarServer/trunk/twistedcaldav/directory/test/test_wiki.py
CalendarServer/trunk/twistedcaldav/directory/wiki.py
CalendarServer/trunk/twistedcaldav/stdconfig.py
Added Paths:
-----------
CalendarServer/trunk/calendarserver/platform/darwin/wiki.py
Added: CalendarServer/trunk/calendarserver/platform/darwin/wiki.py
===================================================================
--- CalendarServer/trunk/calendarserver/platform/darwin/wiki.py (rev 0)
+++ CalendarServer/trunk/calendarserver/platform/darwin/wiki.py 2012-01-19 19:39:34 UTC (rev 8560)
@@ -0,0 +1,73 @@
+##
+# Copyright (c) 2012 Apple Inc. All rights reserved.
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+##
+
+from twisted.web.client import HTTPPageGetter, HTTPClientFactory
+from twisted.internet import reactor
+
+def usernameForAuthToken(token, host="localhost", port=4444):
+ """
+ Send a GET request to the wiki collabd service to retrieve the user record
+ name associated with the provided auth token.
+
+ @param token: An auth token, usually passed in via cookie when webcal
+ makes a request.
+ @type token: C{str}
+ @return: deferred returning a record name (C{str}) if successful, or
+ if the auth token is not recognized a twisted.web.error.Error with
+ status FORBIDDEN will errBack.
+ """
+ url = "http://%s:%d/cal/userForSession/%s" % (host, port, token,)
+ return _getPage(url, host, port)
+
+
+def accessForUserToWiki(user, wiki, host="localhost", port=4444):
+ """
+ Send a GET request to the wiki collabd service to retrieve the access level
+ the given user (in GUID form) has to the given wiki (in wiki short-name
+ form).
+
+ @param user: The GUID of the user
+ @type user: C{str}
+ @param wiki: The short name of the wiki
+ @type wiki: C{str}
+ @return: deferred returning a access level (C{str}) if successful, or
+ if the user is not recognized a twisted.web.error.Error with
+ status FORBIDDEN will errBack; an unknown wiki will have a status
+ of NOT_FOUND
+ """
+ url = "http://%s:%s/cal/accessLevelForUserWikiCalendar/%s/%s" % (host, port,
+ user, wiki)
+ return _getPage(url, host, port)
+
+
+def _getPage(url, host, port):
+ """
+ Fetch the body of the given url via HTTP, connecting to the given host
+ and port.
+
+ @param url: The URL to GET
+ @type url: C{str}
+ @param host: The hostname to connect to
+ @type host: C{str}
+ @param port: The port number to connect to
+ @type port: C{int}
+ @return: A deferred; upon 200 success the body of the response is returned,
+ otherwise a twisted.web.error.Error is the result.
+ """
+ factory = HTTPClientFactory(url)
+ factory.protocol = HTTPPageGetter
+ reactor.connectTCP(host, port, factory)
+ return factory.deferred
Modified: CalendarServer/trunk/calendarserver/provision/root.py
===================================================================
--- CalendarServer/trunk/calendarserver/provision/root.py 2012-01-19 15:45:24 UTC (rev 8559)
+++ CalendarServer/trunk/calendarserver/provision/root.py 2012-01-19 19:39:34 UTC (rev 8560)
@@ -30,6 +30,7 @@
from twisted.internet.defer import inlineCallbacks, returnValue
from twisted.python.reflect import namedClass
from twisted.web.xmlrpc import Proxy
+from twisted.web.error import Error as WebError
from twistedcaldav.cache import _CachedResponseResource
from twistedcaldav.cache import MemcacheResponseCache, MemcacheChangeNotifier
@@ -43,6 +44,7 @@
from twistedcaldav.directory.principal import DirectoryPrincipalResource
from twistedcaldav.storebridge import CalendarCollectionResource,\
AddressBookCollectionResource, StoreNotificationCollectionResource
+from calendarserver.platform.darwin.wiki import usernameForAuthToken
log = Logger()
@@ -265,9 +267,25 @@
if token is not None and token != "unauthenticated":
log.debug("Wiki sessionID cookie value: %s" % (token,))
- proxy = Proxy(wikiConfig["URL"])
+
try:
- username = (yield proxy.callRemote(wikiConfig["UserMethod"], token))
+ if wikiConfig.LionCompatibility:
+ proxy = Proxy(wikiConfig["URL"])
+ username = (yield proxy.callRemote(wikiConfig["UserMethod"], token))
+ else:
+ username = (yield usernameForAuthToken(token,
+ host=wikiConfig.CollabHost,
+ port=wikiConfig.CollabPort))
+
+ except WebError, w:
+ username = None
+ # FORBIDDEN status means it's an unknown token
+ if int(w.status) == responsecode.FORBIDDEN:
+ log.debug("Unknown wiki token: %s" % (token,))
+ else:
+ log.error("Failed to look up wiki token %s: %s" %
+ (token, w.message,))
+
except Exception, e:
log.error("Failed to look up wiki token (%s)" % (e,))
username = None
Modified: CalendarServer/trunk/twistedcaldav/directory/test/test_wiki.py
===================================================================
--- CalendarServer/trunk/twistedcaldav/directory/test/test_wiki.py 2012-01-19 15:45:24 UTC (rev 8559)
+++ CalendarServer/trunk/twistedcaldav/directory/test/test_wiki.py 2012-01-19 19:39:34 UTC (rev 8560)
@@ -22,6 +22,8 @@
from twisted.web.xmlrpc import Fault
from twext.web2.http import HTTPError
from twext.web2 import responsecode
+from twistedcaldav.config import config
+from twisted.web.error import Error as WebError
class WikiTestCase(TestCase):
"""
@@ -41,10 +43,11 @@
@inlineCallbacks
- def test_getWikiAccess(self):
+ def test_getWikiAccessLion(self):
"""
XMLRPC Faults result in HTTPErrors
"""
+ self.patch(config.Authentication.Wiki, "LionCompatibility", True)
def successful(self, user, wiki):
return succeed("read")
@@ -74,3 +77,40 @@
self.fail("Incorrect exception")
else:
self.fail("Didn't raise exception")
+
+
+ @inlineCallbacks
+ def test_getWikiAccess(self):
+ """
+ Non-200 GET responses result in HTTPErrors
+ """
+ self.patch(config.Authentication.Wiki, "LionCompatibility", False)
+
+ def successful(user, wiki):
+ return succeed("read")
+
+ def forbidden(user, wiki):
+ raise WebError(403, message="Unknown user")
+
+ def notFound(user, wiki):
+ raise WebError(404, message="Non-existent wiki")
+
+ def other(user, wiki):
+ raise WebError(500, "Error")
+
+ access = (yield getWikiAccess("user", "wiki", method=successful))
+ self.assertEquals(access, "read")
+
+ for (method, code) in (
+ (forbidden, responsecode.FORBIDDEN),
+ (notFound, responsecode.NOT_FOUND),
+ (other, responsecode.SERVICE_UNAVAILABLE),
+ ):
+ try:
+ access = (yield getWikiAccess("user", "wiki", method=method))
+ except HTTPError, e:
+ self.assertEquals(e.response.code, code)
+ except:
+ self.fail("Incorrect exception")
+ else:
+ self.fail("Didn't raise exception")
Modified: CalendarServer/trunk/twistedcaldav/directory/wiki.py
===================================================================
--- CalendarServer/trunk/twistedcaldav/directory/wiki.py 2012-01-19 15:45:24 UTC (rev 8559)
+++ CalendarServer/trunk/twistedcaldav/directory/wiki.py 2012-01-19 19:39:34 UTC (rev 8560)
@@ -37,6 +37,8 @@
from twistedcaldav.directory.directory import (DirectoryService,
DirectoryRecord,
UnknownRecordTypeError)
+from calendarserver.platform.darwin.wiki import accessForUserToWiki
+from twisted.web.error import Error as WebError
log = Logger()
@@ -73,8 +75,6 @@
if self.byShortName.has_key(shortName):
record = self.byShortName[shortName]
- self.log_info("Returning existing wiki record with UID %s" %
- (record.uid,))
return record
record = self._addRecord(shortName)
@@ -84,8 +84,6 @@
if self.byUID.has_key(uid):
record = self.byUID[uid]
- self.log_info("Returning existing wiki record with UID %s" %
- (record.uid,))
return record
if uid.startswith(self.UIDPrefix):
@@ -103,7 +101,6 @@
shortName,
None
)
- self.log_info("Creating wiki record with GUID %s" % (record.guid,))
self.byUID[record.uid] = record
self.byShortName[shortName] = record
return record
@@ -137,16 +134,22 @@
"""
wikiConfig = config.Authentication.Wiki
if method is None:
- method = Proxy(wikiConfig["URL"]).callRemote
+ if wikiConfig.LionCompatibility:
+ method = Proxy(wikiConfig["URL"]).callRemote
+ else:
+ method = accessForUserToWiki
try:
log.debug("Looking up Wiki ACL for: user [%s], wiki [%s]" % (userID,
wikiID))
- access = (yield method(wikiConfig["WikiMethod"],
- userID, wikiID))
+ if wikiConfig.LionCompatibility:
+ access = (yield method(wikiConfig["WikiMethod"],
+ userID, wikiID))
+ else:
+ access = (yield method(userID, wikiID))
- log.debug("Wiki ACL result: user [%s], wiki [%s], access [%s]" % (userID,
- wikiID, access))
+ log.debug("Wiki ACL result: user [%s], wiki [%s], access [%s]" %
+ (userID, wikiID, access))
returnValue(access)
except Fault, fault:
@@ -169,7 +172,28 @@
raise HTTPError(StatusResponse(responsecode.SERVICE_UNAVAILABLE,
fault.faultString))
+ except WebError, w:
+ status = int(w.status)
+ log.debug("Wiki ACL result: user [%s], wiki [%s], status [%s]" %
+ (userID, wikiID, status))
+
+ if status == responsecode.FORBIDDEN: # non-existent user
+ raise HTTPError(StatusResponse(responsecode.FORBIDDEN,
+ "Unknown User"))
+
+ elif status == responsecode.NOT_FOUND: # non-existent wiki
+ raise HTTPError(StatusResponse(responsecode.NOT_FOUND,
+ "Unknown Wiki"))
+
+ else: # Unknown fault returned from wiki server. Log the error and
+ # return 503 Service Unavailable to the client.
+ log.error("Wiki ACL error: user [%s], wiki [%s], status [%s]" %
+ (userID, wikiID, status))
+ raise HTTPError(StatusResponse(responsecode.SERVICE_UNAVAILABLE,
+ w.message))
+
+
@inlineCallbacks
def getWikiACL(resource, request):
"""
@@ -283,5 +307,5 @@
raise
except Exception, e:
- log.error("Wiki ACL RPC failed: %s" % (e,))
- raise HTTPError(StatusResponse(responsecode.SERVICE_UNAVAILABLE, "Wiki ACL RPC failed"))
+ log.error("Wiki ACL lookup failed: %s" % (e,))
+ raise HTTPError(StatusResponse(responsecode.SERVICE_UNAVAILABLE, "Wiki ACL lookup failed"))
Modified: CalendarServer/trunk/twistedcaldav/stdconfig.py
===================================================================
--- CalendarServer/trunk/twistedcaldav/stdconfig.py 2012-01-19 15:45:24 UTC (rev 8559)
+++ CalendarServer/trunk/twistedcaldav/stdconfig.py 2012-01-19 19:39:34 UTC (rev 8560)
@@ -412,6 +412,9 @@
"URL": "http://127.0.0.1:8089/RPC2",
"UserMethod": "userForSession",
"WikiMethod": "accessLevelForUserWikiCalendar",
+ "LionCompatibility": False,
+ "CollabHost": "localhost",
+ "CollabPort": 4444,
},
},
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.macosforge.org/pipermail/calendarserver-changes/attachments/20120119/11bdd781/attachment-0001.html>
More information about the calendarserver-changes
mailing list