<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[12986] CalendarServer/branches/users/sagen/move2who-4</title>
</head>
<body>
<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; }
#msg dl a { font-weight: bold}
#msg dl a:link { color:#fc3; }
#msg dl a:active { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.calendarserver.org//changeset/12986">12986</a></dd>
<dt>Author</dt> <dd>sagen@apple.com</dd>
<dt>Date</dt> <dd>2014-03-21 11:47:20 -0700 (Fri, 21 Mar 2014)</dd>
</dl>
<h3>Log Message</h3>
<pre>The test for calendarserver_manage_principals works now</pre>
<h3>Modified Paths</h3>
<ul>
<li><a href="#CalendarServerbranchesuserssagenmove2who4calendarservertoolsprincipalspy">CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/principals.py</a></li>
<li><a href="#CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalscaldavdplist">CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/caldavd.plist</a></li>
<li><a href="#CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalsresourceslocationsxml">CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/resources-locations.xml</a></li>
<li><a href="#CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalsusersgroupsxml">CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/users-groups.xml</a></li>
<li><a href="#CalendarServerbranchesuserssagenmove2who4calendarservertoolstesttest_principalspy">CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/test_principals.py</a></li>
<li><a href="#CalendarServerbranchesuserssagenmove2who4twistedcaldavdirectorytestaccountsxml">CalendarServer/branches/users/sagen/move2who-4/twistedcaldav/directory/test/accounts.xml</a></li>
</ul>
</div>
<div id="patch">
<h3>Diff</h3>
<a id="CalendarServerbranchesuserssagenmove2who4calendarservertoolsprincipalspy"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/principals.py (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/principals.py        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/principals.py        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -32,7 +32,9 @@
</span><span class="cx"> from twisted.internet import reactor
</span><span class="cx"> from twisted.internet.defer import inlineCallbacks, returnValue, succeed
</span><span class="cx"> from twistedcaldav.config import config
</span><del>-from txdav.who.delegates import addDelegate, removeDelegate
</del><ins>+from txdav.who.delegates import (
+ addDelegate, removeDelegate, RecordType as DelegateRecordType
+)
</ins><span class="cx"> from txdav.who.idirectory import AutoScheduleMode
</span><span class="cx">
</span><span class="cx">
</span><span class="lines">@@ -84,7 +86,7 @@
</span><span class="cx"> print(" --get-auto-schedule-mode: read auto-schedule mode")
</span><span class="cx"> print(" --set-auto-accept-group=principal: set auto-accept-group")
</span><span class="cx"> print(" --get-auto-accept-group: read auto-accept-group")
</span><del>- print(" --add {locations|resources|addresses} 'full name' [record name] [GUID]: add a principal")
</del><ins>+ print(" --add {locations|resources|addresses} full-name record-name UID: add a principal")
</ins><span class="cx"> print(" --remove: remove a principal")
</span><span class="cx"> print(" --set-geo=url: set the geo: url for an address (e.g. geo:37.331741,-122.030333)")
</span><span class="cx"> print(" --get-geo: get the geo: url for an address")
</span><span class="lines">@@ -358,7 +360,7 @@
</span><span class="cx"> def runListPrincipalTypes(service, store):
</span><span class="cx"> directory = store.directoryService()
</span><span class="cx"> for recordType in directory.recordTypes():
</span><del>- print(directory.recordTypeToOldString(recordType))
</del><ins>+ print(directory.recordTypeToOldName(recordType))
</ins><span class="cx"> return succeed(None)
</span><span class="cx">
</span><span class="cx">
</span><span class="lines">@@ -446,6 +448,20 @@
</span><span class="cx"> def runAddPrincipal(service, store, addType, uid, shortNames, fullNames):
</span><span class="cx"> directory = store.directoryService()
</span><span class="cx"> recordType = directory.oldNameToRecordType(addType)
</span><ins>+
+ # See if that UID is in use
+ record = yield directory.recordWithUID(uid)
+ if record is not None:
+ print("UID already in use: {uid}".format(uid=uid))
+ returnValue(None)
+
+ # See if the shortnames are in use
+ for shortName in shortNames:
+ record = yield directory.recordWithShortName(recordType, shortName)
+ if record is not None:
+ print("Record name already in use: {name}".format(name=shortName))
+ returnValue(None)
+
</ins><span class="cx"> fields = {
</span><span class="cx"> directory.fieldName.recordType: recordType,
</span><span class="cx"> directory.fieldName.uid: uid,
</span><span class="lines">@@ -454,6 +470,7 @@
</span><span class="cx"> }
</span><span class="cx"> record = DirectoryRecord(directory, fields)
</span><span class="cx"> yield record.service.updateRecords([record], create=True)
</span><ins>+ print("Added '{name}'".format(name=fullNames[0]))
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx">
</span><span class="lines">@@ -531,7 +548,7 @@
</span><span class="cx">
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><del>-def _addRemoveProxy(fn, store, record, proxyType, *proxyIDs):
</del><ins>+def _addRemoveProxy(msg, fn, store, record, proxyType, *proxyIDs):
</ins><span class="cx"> directory = store.directoryService()
</span><span class="cx"> readWrite = (proxyType == "write")
</span><span class="cx"> for proxyID in proxyIDs:
</span><span class="lines">@@ -542,80 +559,83 @@
</span><span class="cx"> txn = store.newTransaction()
</span><span class="cx"> yield fn(txn, record, proxyRecord, readWrite)
</span><span class="cx"> yield txn.commit()
</span><ins>+ print(
+ "{msg} {proxy} as a {proxyType} proxy for {record}".format(
+ msg=msg, proxy=prettyRecord(proxyRecord),
+ proxyType=proxyType, record=prettyRecord(record)
+ )
+ )
</ins><span class="cx">
</span><span class="cx">
</span><ins>+@inlineCallbacks
</ins><span class="cx"> def action_addProxy(store, record, proxyType, *proxyIDs):
</span><del>- return _addRemoveProxy(addDelegate, store, record, proxyType, *proxyIDs)
</del><ins>+ yield _addRemoveProxy("Added", addDelegate, store, record, proxyType, *proxyIDs)
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><span class="cx"> def action_removeProxy(store, record, *proxyIDs):
</span><span class="cx"> # Write
</span><del>- yield _addRemoveProxy(removeDelegate, store, record, "write", *proxyIDs)
</del><ins>+ yield _addRemoveProxy("Removed", removeDelegate, store, record, "write", *proxyIDs)
</ins><span class="cx"> # Read
</span><del>- yield _addRemoveProxy(removeDelegate, store, record, "read", *proxyIDs)
</del><ins>+ yield _addRemoveProxy("Removed", removeDelegate, store, record, "read", *proxyIDs)
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx">
</span><del>-# @inlineCallbacks
-# def setProxies(store, principal, readProxyPrincipals, writeProxyPrincipals, directory=None):
-# """
-# Set read/write proxies en masse for a principal
-# @param principal: DirectoryPrincipalResource
-# @param readProxyPrincipals: a list of principal IDs (see principalForPrincipalID)
-# @param writeProxyPrincipals: a list of principal IDs (see principalForPrincipalID)
-# """
</del><ins>+@inlineCallbacks
+def setProxies(record, readProxyRecords, writeProxyRecords):
+ """
+ Set read/write proxies en masse for a record
+ @param record: L{IDirectoryRecord}
+ @param readProxyRecords: a list of records
+ @param writeProxyRecords: a list of records
+ """
</ins><span class="cx">
</span><del>-# proxyTypes = [
-# ("read", readProxyPrincipals),
-# ("write", writeProxyPrincipals),
-# ]
-# for proxyType, proxyIDs in proxyTypes:
-# if proxyIDs is None:
-# continue
-# subPrincipal = proxySubprincipal(principal, proxyType)
-# if subPrincipal is None:
-# raise ProxyError("Unable to edit %s proxies for %s\n" % (proxyType,
-# prettyPrincipal(principal)))
-# memberURLs = []
-# for proxyID in proxyIDs:
-# proxyPrincipal = yield principalForPrincipalID(proxyID, directory=directory)
-# proxyURL = proxyPrincipal.url()
-# memberURLs.append(davxml.HRef(proxyURL))
-# membersProperty = davxml.GroupMemberSet(*memberURLs)
-# yield subPrincipal.writeProperty(membersProperty, None)
-# if store is not None:
-# # Schedule work the PeerConnectionPool will pick up as overdue
-# yield schedulePolledGroupCachingUpdate(store)
</del><ins>+ proxyTypes = [
+ (DelegateRecordType.readDelegateGroup, readProxyRecords),
+ (DelegateRecordType.writeDelegateGroup, writeProxyRecords),
+ ]
+ for recordType, proxyRecords in proxyTypes:
+ if proxyRecords is None:
+ continue
+ proxyGroup = yield record.service.recordWithShortName(
+ recordType, record.uid
+ )
+ yield proxyGroup.setMembers(proxyRecords)
</ins><span class="cx">
</span><ins>+ # if store is not None:
+ # # Schedule work the PeerConnectionPool will pick up as overdue
+ # yield schedulePolledGroupCachingUpdate(store)
</ins><span class="cx">
</span><span class="cx">
</span><del>-# @inlineCallbacks
-# def getProxies(principal, directory=None):
-# """
-# Returns a tuple containing the GUIDs for read proxies and write proxies
-# of the given principal
-# """
</del><span class="cx">
</span><del>-# proxies = {
-# "read": [],
-# "write": [],
-# }
-# for proxyType in proxies.iterkeys():
-# subPrincipal = proxySubprincipal(principal, proxyType)
-# if subPrincipal is not None:
-# membersProperty = (yield subPrincipal.readProperty(davxml.GroupMemberSet, None))
-# if membersProperty.children:
-# for member in membersProperty.children:
-# proxyPrincipal = yield principalForPrincipalID(str(member), directory=directory)
-# proxies[proxyType].append(proxyPrincipal.record.guid)
</del><ins>+@inlineCallbacks
+def getProxies(record):
+ """
+ Returns a tuple containing the records for read proxies and write proxies
+ of the given record
+ """
</ins><span class="cx">
</span><del>-# returnValue((proxies['read'], proxies['write']))
</del><ins>+ allProxies = {
+ DelegateRecordType.readDelegateGroup: [],
+ DelegateRecordType.writeDelegateGroup: [],
+ }
+ for recordType in allProxies.iterkeys():
+ proxyGroup = yield record.service.recordWithShortName(
+ recordType, record.uid
+ )
+ allProxies[recordType] = yield proxyGroup.members()
</ins><span class="cx">
</span><ins>+ returnValue(
+ (
+ allProxies[DelegateRecordType.readDelegateGroup],
+ allProxies[DelegateRecordType.writeDelegateGroup]
+ )
+ )
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx">
</span><span class="cx">
</span><ins>+
</ins><span class="cx"> def action_getAutoScheduleMode(store, record):
</span><span class="cx"> print(
</span><span class="cx"> "Auto-schedule mode for {record} is {mode}".format(
</span><span class="lines">@@ -782,6 +802,13 @@
</span><span class="cx"> this fancier later.
</span><span class="cx"> """
</span><span class="cx">
</span><ins>+ if len(args) != 3:
+ print(
+ "When adding a principal, you must provide full-name, record-name, "
+ "and UID"
+ )
+ sys.exit(64)
+
</ins><span class="cx"> fullName = args[0].decode("utf-8")
</span><span class="cx"> shortName = args[1].decode("utf-8")
</span><span class="cx"> uid = args[2].decode("utf-8")
</span></span></pre></div>
<a id="CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalscaldavdplist"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/caldavd.plist (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/caldavd.plist        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/caldavd.plist        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -139,7 +139,7 @@
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.xmlfile.XMLDirectoryService</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>xmlFile</key>
</span><span class="lines">@@ -159,7 +159,7 @@
</span><span class="cx"> <true/>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.xmlfile.XMLDirectoryService</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>xmlFile</key>
</span><span class="lines">@@ -168,17 +168,18 @@
</span><span class="cx"> <array>
</span><span class="cx"> <string>resources</string>
</span><span class="cx"> <string>locations</string>
</span><ins>+ <string>addresses</string>
</ins><span class="cx"> </array>
</span><span class="cx"> </dict>
</span><span class="cx"> </dict>
</span><del>-
</del><ins>+
</ins><span class="cx"> <!-- Open Directory Service (Mac OS X) -->
</span><span class="cx"> <!--
</span><span class="cx"> <key>DirectoryService</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.appleopendirectory.OpenDirectoryService</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>node</key>
</span><span class="lines">@@ -202,7 +203,7 @@
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.augment.AugmentXMLDB</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>xmlFiles</key>
</span><span class="lines">@@ -211,14 +212,14 @@
</span><span class="cx"> </array>
</span><span class="cx"> </dict>
</span><span class="cx"> </dict>
</span><del>-
</del><ins>+
</ins><span class="cx"> <!-- Sqlite Augment Service -->
</span><span class="cx"> <!--
</span><span class="cx"> <key>AugmentService</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.augment.AugmentSqliteDB</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>dbpath</key>
</span><span class="lines">@@ -233,7 +234,7 @@
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.augment.AugmentPostgreSQLDB</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>host</key>
</span><span class="lines">@@ -249,7 +250,7 @@
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.calendaruserproxy.ProxySqliteDB</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>dbpath</key>
</span><span class="lines">@@ -263,7 +264,7 @@
</span><span class="cx"> <dict>
</span><span class="cx"> <key>type</key>
</span><span class="cx"> <string>twistedcaldav.directory.calendaruserproxy.ProxyPostgreSQLDB</string>
</span><del>-
</del><ins>+
</ins><span class="cx"> <key>params</key>
</span><span class="cx"> <dict>
</span><span class="cx"> <key>host</key>
</span><span class="lines">@@ -692,7 +693,7 @@
</span><span class="cx"> <!-- Support for Content-Encoding compression options as specified in RFC2616 Section 3.5 -->
</span><span class="cx"> <key>ResponseCompression</key>
</span><span class="cx"> <false/>
</span><del>-
</del><ins>+
</ins><span class="cx"> <!-- The retry-after value (in seconds) to return with a 503 error. -->
</span><span class="cx"> <key>HTTPRetryAfter</key>
</span><span class="cx"> <integer>180</integer>
</span></span></pre></div>
<a id="CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalsresourceslocationsxml"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/resources-locations.xml (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/resources-locations.xml        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/resources-locations.xml        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -18,7 +18,110 @@
</span><span class="cx">
</span><span class="cx"> <!DOCTYPE accounts SYSTEM "accounts.dtd">
</span><span class="cx">
</span><del>-<accounts realm="Test Realm">
</del><ins>+<directory realm="Test Realm">
+ <record type="location">
+ <short-name>location01</short-name>
+ <uid>location01</uid>
+ <full-name>Room 01</full-name>
+ </record>
+ <record type="location">
+ <short-name>location02</short-name>
+ <uid>location02</uid>
+ <full-name>Room 02</full-name>
+ </record>
+ <record type="location">
+ <short-name>location03</short-name>
+ <uid>location03</uid>
+ <full-name>Room 03</full-name>
+ </record>
+ <record type="location">
+ <short-name>location04</short-name>
+ <uid>location04</uid>
+ <full-name>Room 04</full-name>
+ </record>
+ <record type="location">
+ <short-name>location05</short-name>
+ <uid>location05</uid>
+ <full-name>Room 05</full-name>
+ </record>
+ <record type="location">
+ <short-name>location06</short-name>
+ <uid>location06</uid>
+ <full-name>Room 06</full-name>
+ </record>
+ <record type="location">
+ <short-name>location07</short-name>
+ <uid>location07</uid>
+ <full-name>Room 07</full-name>
+ </record>
+ <record type="location">
+ <short-name>location08</short-name>
+ <uid>location08</uid>
+ <full-name>Room 08</full-name>
+ </record>
+ <record type="location">
+ <short-name>location09</short-name>
+ <uid>location09</uid>
+ <full-name>Room 09</full-name>
+ </record>
+ <record type="location">
+ <short-name>location10</short-name>
+ <uid>location10</uid>
+ <full-name>Room 10</full-name>
+ </record>
+
+ <record type="resource">
+ <short-name>resource01</short-name>
+ <uid>resource01</uid>
+ <full-name>Resource 01</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource02</short-name>
+ <uid>resource02</uid>
+ <full-name>Resource 02</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource03</short-name>
+ <uid>resource03</uid>
+ <full-name>Resource 03</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource04</short-name>
+ <uid>resource04</uid>
+ <full-name>Resource 04</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource05</short-name>
+ <uid>resource05</uid>
+ <full-name>Resource 05</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource06</short-name>
+ <uid>resource06</uid>
+ <full-name>Resource 06</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource07</short-name>
+ <uid>resource07</uid>
+ <full-name>Resource 07</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource08</short-name>
+ <uid>resource08</uid>
+ <full-name>Resource 08</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource09</short-name>
+ <uid>resource09</uid>
+ <full-name>Resource 09</full-name>
+ </record>
+ <record type="resource">
+ <short-name>resource10</short-name>
+ <uid>resource10</uid>
+ <full-name>Resource 10</full-name>
+ </record>
+
+ <!--
</ins><span class="cx"> <location repeat="10">
</span><span class="cx"> <uid>location%02d</uid>
</span><span class="cx"> <guid>location%02d</guid>
</span><span class="lines">@@ -31,4 +134,5 @@
</span><span class="cx"> <password>resource%02d</password>
</span><span class="cx"> <name>Resource %02d</name>
</span><span class="cx"> </resource>
</span><del>-</accounts>
</del><ins>+-->
+</directory>
</ins></span></pre></div>
<a id="CalendarServerbranchesuserssagenmove2who4calendarservertoolstestprincipalsusersgroupsxml"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/users-groups.xml (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/users-groups.xml        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/principals/users-groups.xml        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -18,7 +18,95 @@
</span><span class="cx">
</span><span class="cx"> <!DOCTYPE accounts SYSTEM "accounts.dtd">
</span><span class="cx">
</span><del>-<accounts realm="Test Realm">
</del><ins>+<directory realm="Test Realm">
+ <record type="user">
+ <short-name>user01</short-name>
+ <uid>user01</uid>
+ <password>user01</password>
+ <full-name>User 01</full-name>
+ <email>user01@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user02</short-name>
+ <uid>user02</uid>
+ <password>user02</password>
+ <full-name>User 02</full-name>
+ <email>user02@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user03</short-name>
+ <uid>user03</uid>
+ <password>user03</password>
+ <full-name>User 03</full-name>
+ <email>user03@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user04</short-name>
+ <uid>user04</uid>
+ <password>user04</password>
+ <full-name>User 04</full-name>
+ <email>user04@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user05</short-name>
+ <uid>user05</uid>
+ <password>user05</password>
+ <full-name>User 05</full-name>
+ <email>user05@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user06</short-name>
+ <uid>user06</uid>
+ <password>user06</password>
+ <full-name>User 06</full-name>
+ <email>user06@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user07</short-name>
+ <uid>user07</uid>
+ <password>user07</password>
+ <full-name>User 07</full-name>
+ <email>user07@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user08</short-name>
+ <uid>user08</uid>
+ <password>user08</password>
+ <full-name>User 08</full-name>
+ <email>user08@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user09</short-name>
+ <uid>user09</uid>
+ <password>user09</password>
+ <full-name>User 09</full-name>
+ <email>user09@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user10</short-name>
+ <uid>user10</uid>
+ <password>user10</password>
+ <full-name>User 10</full-name>
+ <email>user10@example.com</email>
+ </record>
+
+ <record type="group">
+ <uid>e5a6142c-4189-4e9e-90b0-9cd0268b314b</uid>
+ <short-name>testgroup1</short-name>
+ <full-name>Group 01</full-name>
+ <member-uid type="users">user01</member-uid>
+ <member-uid type="users">user02</member-uid>
+ </record>
+ <!--
</ins><span class="cx"> <user repeat="10">
</span><span class="cx"> <uid>user%02d</uid>
</span><span class="cx"> <guid>user%02d</guid>
</span><span class="lines">@@ -37,4 +125,5 @@
</span><span class="cx"> <member type="users">user02</member>
</span><span class="cx"> </members>
</span><span class="cx"> </group>
</span><del>-</accounts>
</del><ins>+ -->
+</directory>
</ins></span></pre></div>
<a id="CalendarServerbranchesuserssagenmove2who4calendarservertoolstesttest_principalspy"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/test_principals.py (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/test_principals.py        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/calendarserver/tools/test/test_principals.py        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -19,18 +19,15 @@
</span><span class="cx">
</span><span class="cx"> from calendarserver.tools.principals import (
</span><span class="cx"> parseCreationArgs, matchStrings,
</span><del>- updateRecord, principalForPrincipalID, getProxies, setProxies
</del><ins>+ recordForPrincipalID, getProxies, setProxies
</ins><span class="cx"> )
</span><span class="cx"> from twext.python.filepath import CachingFilePath as FilePath
</span><span class="cx"> from twisted.internet import reactor
</span><span class="cx"> from twisted.internet.defer import inlineCallbacks, Deferred, returnValue
</span><span class="cx"> from twistedcaldav.config import config
</span><del>-from twistedcaldav.directory import calendaruserproxy
-from twistedcaldav.directory.directory import DirectoryError
</del><span class="cx"> from twistedcaldav.test.util import (
</span><del>- TestCase, CapturingProcessProtocol, ErrorOutput
</del><ins>+ TestCase, StoreTestCase, CapturingProcessProtocol, ErrorOutput
</ins><span class="cx"> )
</span><del>-from txdav.who.util import directoryFromConfig
</del><span class="cx">
</span><span class="cx">
</span><span class="cx">
</span><span class="lines">@@ -39,8 +36,8 @@
</span><span class="cx"> def setUp(self):
</span><span class="cx"> super(ManagePrincipalsTestCase, self).setUp()
</span><span class="cx">
</span><del>- # Since this test operates on proxy db, we need to assign the service:
- calendaruserproxy.ProxyDBService = calendaruserproxy.ProxySqliteDB(os.path.abspath(self.mktemp()))
</del><ins>+ # # Since this test operates on proxy db, we need to assign the service:
+ # calendaruserproxy.ProxyDBService = calendaruserproxy.ProxySqliteDB(os.path.abspath(self.mktemp()))
</ins><span class="cx">
</span><span class="cx"> testRoot = os.path.join(os.path.dirname(__file__), "principals")
</span><span class="cx"> templateName = os.path.join(testRoot, "caldavd.plist")
</span><span class="lines">@@ -50,11 +47,11 @@
</span><span class="cx">
</span><span class="cx"> databaseRoot = os.path.abspath("_spawned_scripts_db" + str(os.getpid()))
</span><span class="cx"> newConfig = template % {
</span><del>- "ServerRoot" : os.path.abspath(config.ServerRoot),
- "DataRoot" : os.path.abspath(config.DataRoot),
- "DatabaseRoot" : databaseRoot,
- "DocumentRoot" : os.path.abspath(config.DocumentRoot),
- "LogRoot" : os.path.abspath(config.LogRoot),
</del><ins>+ "ServerRoot": os.path.abspath(config.ServerRoot),
+ "DataRoot": os.path.abspath(config.DataRoot),
+ "DatabaseRoot": databaseRoot,
+ "DocumentRoot": os.path.abspath(config.DocumentRoot),
+ "LogRoot": os.path.abspath(config.LogRoot),
</ins><span class="cx"> }
</span><span class="cx"> configFilePath = FilePath(os.path.join(config.ConfigRoot, "caldavd.plist"))
</span><span class="cx"> configFilePath.setContent(newConfig)
</span><span class="lines">@@ -62,18 +59,33 @@
</span><span class="cx"> self.configFileName = configFilePath.path
</span><span class="cx"> config.load(self.configFileName)
</span><span class="cx">
</span><del>- origUsersFile = FilePath(os.path.join(os.path.dirname(__file__),
- "principals", "users-groups.xml"))
</del><ins>+ origUsersFile = FilePath(
+ os.path.join(
+ os.path.dirname(__file__),
+ "principals",
+ "users-groups.xml"
+ )
+ )
</ins><span class="cx"> copyUsersFile = FilePath(os.path.join(config.DataRoot, "accounts.xml"))
</span><span class="cx"> origUsersFile.copyTo(copyUsersFile)
</span><span class="cx">
</span><del>- origResourcesFile = FilePath(os.path.join(os.path.dirname(__file__),
- "principals", "resources-locations.xml"))
</del><ins>+ origResourcesFile = FilePath(
+ os.path.join(
+ os.path.dirname(__file__),
+ "principals",
+ "resources-locations.xml"
+ )
+ )
</ins><span class="cx"> copyResourcesFile = FilePath(os.path.join(config.DataRoot, "resources.xml"))
</span><span class="cx"> origResourcesFile.copyTo(copyResourcesFile)
</span><span class="cx">
</span><del>- origAugmentFile = FilePath(os.path.join(os.path.dirname(__file__),
- "principals", "augments.xml"))
</del><ins>+ origAugmentFile = FilePath(
+ os.path.join(
+ os.path.dirname(__file__),
+ "principals",
+ "augments.xml"
+ )
+ )
</ins><span class="cx"> copyAugmentFile = FilePath(os.path.join(config.DataRoot, "augments.xml"))
</span><span class="cx"> origAugmentFile.copyTo(copyAugmentFile)
</span><span class="cx">
</span><span class="lines">@@ -116,6 +128,7 @@
</span><span class="cx"> self.assertTrue("users" in results)
</span><span class="cx"> self.assertTrue("locations" in results)
</span><span class="cx"> self.assertTrue("resources" in results)
</span><ins>+ self.assertTrue("addresses" in results)
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><span class="lines">@@ -135,28 +148,36 @@
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><span class="cx"> def test_addRemove(self):
</span><del>- results = yield self.runCommand("--add", "resources", "New Resource",
- "newresource", "edaa6ae6-011b-4d89-ace3-6b688cdd91d9")
</del><ins>+ results = yield self.runCommand(
+ "--add", "resources",
+ "New Resource", "newresource", "newresourceuid"
+ )
</ins><span class="cx"> self.assertTrue("Added 'New Resource'" in results)
</span><span class="cx">
</span><del>- results = yield self.runCommand("--get-auto-schedule",
- "resources:newresource")
- self.assertTrue(results.startswith('Auto-schedule for "New Resource" (resources:newresource) is true'))
</del><ins>+ results = yield self.runCommand(
+ "--get-auto-schedule-mode",
+ "resources:newresource"
+ )
+ self.assertTrue(
+ results.startswith(
+ 'Auto-schedule mode for "New Resource" newresourceuid (resource) newresource is Default'
+ )
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--get-auto-schedule-mode",
- "resources:newresource")
- self.assertTrue(results.startswith('Auto-schedule mode for "New Resource" (resources:newresource) is default'))
-
</del><span class="cx"> results = yield self.runCommand("--list-principals=resources")
</span><span class="cx"> self.assertTrue("newresource" in results)
</span><span class="cx">
</span><del>- results = yield self.runCommand("--add", "resources", "New Resource",
- "newresource1", "edaa6ae6-011b-4d89-ace3-6b688cdd91d9")
- self.assertTrue("Duplicate guid" in results)
</del><ins>+ results = yield self.runCommand(
+ "--add", "resources", "New Resource",
+ "newresource1", "newresourceuid"
+ )
+ self.assertTrue("UID already in use: newresourceuid" in results)
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--add", "resources", "New Resource",
- "newresource", "fdaa6ae6-011b-4d89-ace3-6b688cdd91d9")
- self.assertTrue("Duplicate shortName" in results)
</del><ins>+ results = yield self.runCommand(
+ "--add", "resources", "New Resource",
+ "newresource", "uniqueuid"
+ )
+ self.assertTrue("Record name already in use" in results)
</ins><span class="cx">
</span><span class="cx"> results = yield self.runCommand("--remove", "resources:newresource")
</span><span class="cx"> self.assertTrue("Removed 'New Resource'" in results)
</span><span class="lines">@@ -167,29 +188,13 @@
</span><span class="cx">
</span><span class="cx"> def test_parseCreationArgs(self):
</span><span class="cx">
</span><del>- self.assertEquals(("full name", None, None),
- parseCreationArgs(("full name",)))
-
- self.assertEquals(("full name", "short name", None),
- parseCreationArgs(("full name", "short name")))
-
- guid = "02C3DE93-E655-4856-47B76B8BB1A7BDCE"
-
- self.assertEquals(("full name", "short name", guid),
- parseCreationArgs(("full name", "short name", guid)))
-
- self.assertEquals(("full name", "short name", guid),
- parseCreationArgs(("full name", guid, "short name")))
-
- self.assertEquals(("full name", None, guid),
- parseCreationArgs(("full name", guid)))
-
- self.assertRaises(
- ValueError,
- parseCreationArgs, ("full name", "non guid", "non guid")
</del><ins>+ self.assertEquals(
+ ("full name", "short name", "uid"),
+ parseCreationArgs(("full name", "short name", "uid"))
</ins><span class="cx"> )
</span><span class="cx">
</span><span class="cx">
</span><ins>+
</ins><span class="cx"> def test_matchStrings(self):
</span><span class="cx"> self.assertEquals("abc", matchStrings("a", ("abc", "def")))
</span><span class="cx"> self.assertEquals("def", matchStrings("de", ("abc", "def")))
</span><span class="lines">@@ -201,161 +206,126 @@
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><span class="cx"> def test_modifyWriteProxies(self):
</span><del>- results = yield self.runCommand("--add-write-proxy=users:user01",
- "locations:location01")
- self.assertTrue(results.startswith('Added "Test User 01" (users:user01) as a write proxy for "Room 01" (locations:location01)'))
</del><ins>+ results = yield self.runCommand(
+ "--add-write-proxy=users:user01", "locations:location01"
+ )
+ self.assertTrue(
+ results.startswith('Added "User 01" user01 (user) user01 as a write proxy for "Room 01" location01 (location) location01')
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--list-write-proxies",
- "locations:location01")
- self.assertTrue("Test User 01" in results)
</del><ins>+ results = yield self.runCommand(
+ "--list-write-proxies", "locations:location01"
+ )
+ self.assertTrue("User 01" in results)
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--remove-proxy=users:user01",
- "locations:location01")
</del><ins>+ results = yield self.runCommand(
+ "--remove-proxy=users:user01", "locations:location01"
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--list-write-proxies",
- "locations:location01")
- self.assertTrue('No write proxies for "Room 01" (locations:location01)' in results)
</del><ins>+ results = yield self.runCommand(
+ "--list-write-proxies", "locations:location01"
+ )
+ self.assertTrue(
+ 'No write proxies for "Room 01" location01 (location) location01' in results
+ )
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><span class="cx"> def test_modifyReadProxies(self):
</span><del>- results = yield self.runCommand("--add-read-proxy=users:user01",
- "locations:location01")
- self.assertTrue(results.startswith('Added "Test User 01" (users:user01) as a read proxy for "Room 01" (locations:location01)'))
</del><ins>+ results = yield self.runCommand(
+ "--add-read-proxy=users:user01", "locations:location01"
+ )
+ self.assertTrue(
+ results.startswith('Added "User 01" user01 (user) user01 as a read proxy for "Room 01" location01 (location) location01')
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--list-read-proxies",
- "locations:location01")
- self.assertTrue("Test User 01" in results)
</del><ins>+ results = yield self.runCommand(
+ "--list-read-proxies", "locations:location01"
+ )
+ self.assertTrue("User 01" in results)
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--remove-proxy=users:user01",
- "locations:location01")
</del><ins>+ results = yield self.runCommand(
+ "--remove-proxy=users:user01", "locations:location01"
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--list-read-proxies",
- "locations:location01")
- self.assertTrue('No read proxies for "Room 01" (locations:location01)' in results)
</del><ins>+ results = yield self.runCommand(
+ "--list-read-proxies", "locations:location01"
+ )
+ self.assertTrue(
+ 'No read proxies for "Room 01" location01 (location) location01' in results
+ )
</ins><span class="cx">
</span><span class="cx">
</span><span class="cx"> @inlineCallbacks
</span><del>- def test_autoSchedule(self):
- results = yield self.runCommand("--get-auto-schedule",
- "locations:location01")
- self.assertTrue(results.startswith('Auto-schedule for "Room 01" (locations:location01) is false'))
-
- results = yield self.runCommand("--set-auto-schedule=true",
- "locations:location01")
- self.assertTrue(results.startswith('Setting auto-schedule to true for "Room 01" (locations:location01)'))
-
- results = yield self.runCommand("--get-auto-schedule",
- "locations:location01")
- self.assertTrue(results.startswith('Auto-schedule for "Room 01" (locations:location01) is true'))
-
- results = yield self.runCommand("--set-auto-schedule=true",
- "users:user01")
- self.assertTrue(results.startswith('Enabling auto-schedule for (users)user01 is not allowed.'))
-
-
- @inlineCallbacks
</del><span class="cx"> def test_autoScheduleMode(self):
</span><del>- results = yield self.runCommand("--get-auto-schedule-mode",
- "locations:location01")
- self.assertTrue(results.startswith('Auto-schedule mode for "Room 01" (locations:location01) is default'))
</del><ins>+ results = yield self.runCommand(
+ "--get-auto-schedule-mode", "locations:location01"
+ )
+ self.assertTrue(
+ results.startswith('Auto-schedule mode for "Room 01" location01 (location) location01 is Default')
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--set-auto-schedule-mode=accept-if-free",
- "locations:location01")
- self.assertTrue(results.startswith('Setting auto-schedule mode to accept-if-free for "Room 01" (locations:location01)'))
</del><ins>+ results = yield self.runCommand(
+ "--set-auto-schedule-mode=accept-if-free", "locations:location01"
+ )
+ self.assertTrue(
+ results.startswith('Setting auto-schedule-mode to accept if free for "Room 01" location01 (location) location01')
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--get-auto-schedule-mode",
- "locations:location01")
- self.assertTrue(results.startswith('Auto-schedule mode for "Room 01" (locations:location01) is accept-if-free'))
</del><ins>+ results = yield self.runCommand(
+ "--get-auto-schedule-mode",
+ "locations:location01"
+ )
+ self.assertTrue(
+ results.startswith('Auto-schedule mode for "Room 01" location01 (location) location01 is accept if free')
+ )
</ins><span class="cx">
</span><del>- results = yield self.runCommand("--set-auto-schedule-mode=decline-if-busy",
- "users:user01")
- self.assertTrue(results.startswith('Setting auto-schedule mode for (users)user01 is not allowed.'))
</del><ins>+ results = yield self.runCommand(
+ "--set-auto-schedule-mode=decline-if-busy", "users:user01"
+ )
+ self.assertTrue(results.startswith('Setting auto-schedule-mode for "User 01" user01 (user) user01 is not allowed.'))
</ins><span class="cx">
</span><span class="cx"> try:
</span><del>- results = yield self.runCommand("--set-auto-schedule-mode=bogus",
- "users:user01")
</del><ins>+ results = yield self.runCommand(
+ "--set-auto-schedule-mode=bogus",
+ "users:user01"
+ )
</ins><span class="cx"> except ErrorOutput:
</span><span class="cx"> pass
</span><span class="cx"> else:
</span><span class="cx"> self.fail("Expected command failure")
</span><span class="cx">
</span><span class="cx">
</span><del>- @inlineCallbacks
- def test_updateRecord(self):
- directory = directoryFromConfig(config)
- guid = "EEE28807-A8C5-46C8-A558-A08281C558A7"
</del><span class="cx">
</span><del>- (yield updateRecord(True, directory, "locations",
- guid=guid, fullName="Test Location", shortNames=["testlocation", ],)
- )
- try:
- (yield updateRecord(True, directory, "locations",
- guid=guid, fullName="Test Location", shortNames=["testlocation", ],)
- )
- except DirectoryError:
- # We're expecting an error for trying to create a record with
- # an existing GUID
- pass
- else:
- raise self.failureException("Duplicate guid expected")
</del><ins>+class SetProxiesTestCase(StoreTestCase):
</ins><span class="cx">
</span><del>- record = directory.recordWithGUID(guid)
- self.assertTrue(record is not None)
- self.assertEquals(record.fullName, "Test Location")
- self.assertTrue(record.autoSchedule)
-
- (yield updateRecord(False, directory, "locations",
- guid=guid, fullName="Changed", shortNames=["testlocation", ],)
- )
- record = directory.recordWithGUID(guid)
- self.assertTrue(record is not None)
- self.assertEquals(record.fullName, "Changed")
-
- directory.destroyRecord("locations", guid=guid)
- record = directory.recordWithGUID(guid)
- self.assertTrue(record is None)
-
- # Create a user, change autoSchedule
- guid = "F0DE73A8-39D4-4830-8D32-1FA03ABA3470"
- (yield updateRecord(True, directory, "users",
- guid=guid, fullName="Test User", shortNames=["testuser", ],
- autoSchedule=True)
- )
- record = directory.recordWithGUID(guid)
- self.assertTrue(record is not None)
- self.assertEquals(record.fullName, "Test User")
- self.assertTrue(record.autoSchedule)
-
- (yield updateRecord(False, directory, "users",
- guid=guid, fullName="Test User", shortNames=["testuser", ],
- autoSchedule=False)
- )
- record = directory.recordWithGUID(guid)
- self.assertTrue(record is not None)
- self.assertEquals(record.fullName, "Test User")
- self.assertFalse(record.autoSchedule)
-
-
</del><span class="cx"> @inlineCallbacks
</span><span class="cx"> def test_setProxies(self):
</span><span class="cx"> """
</span><span class="cx"> Read and Write proxies can be set en masse
</span><span class="cx"> """
</span><del>- directory = directoryFromConfig(config)
</del><ins>+ directory = self.directory
+ record = yield recordForPrincipalID(directory, "users:user01")
</ins><span class="cx">
</span><del>- principal = principalForPrincipalID("users:user01", directory=directory)
- readProxies, writeProxies = (yield getProxies(principal, directory=directory))
- self.assertEquals(readProxies, []) # initially empty
- self.assertEquals(writeProxies, []) # initially empty
</del><ins>+ readProxies, writeProxies = yield getProxies(record)
+ self.assertEquals(readProxies, []) # initially empty
+ self.assertEquals(writeProxies, []) # initially empty
</ins><span class="cx">
</span><del>- (yield setProxies(None, principal, ["users:user03", "users:user04"], ["users:user05"], directory=directory))
- readProxies, writeProxies = (yield getProxies(principal, directory=directory))
- self.assertEquals(set(readProxies), set(["user03", "user04"]))
- self.assertEquals(set(writeProxies), set(["user05"]))
</del><ins>+ readProxies = [
+ (yield recordForPrincipalID(directory, "users:user03")),
+ (yield recordForPrincipalID(directory, "users:user04")),
+ ]
+ writeProxies = [
+ (yield recordForPrincipalID(directory, "users:user05")),
+ ]
+ yield setProxies(record, readProxies, writeProxies)
</ins><span class="cx">
</span><ins>+ readProxies, writeProxies = yield getProxies(record)
+ self.assertEquals(set([r.uid for r in readProxies]), set(["user03", "user04"]))
+ self.assertEquals(set([r.uid for r in writeProxies]), set(["user05"]))
+
</ins><span class="cx"> # Using None for a proxy list indicates a no-op
</span><del>- (yield setProxies(None, principal, [], None, directory=directory))
- readProxies, writeProxies = (yield getProxies(principal, directory=directory))
- self.assertEquals(readProxies, []) # now empty
- self.assertEquals(set(writeProxies), set(["user05"])) # unchanged
</del><ins>+ yield setProxies(record, [], None)
+ readProxies, writeProxies = yield getProxies(record)
+ self.assertEquals(readProxies, []) # now empty
+ self.assertEquals(set([r.uid for r in writeProxies]), set(["user05"])) # unchanged
</ins></span></pre></div>
<a id="CalendarServerbranchesuserssagenmove2who4twistedcaldavdirectorytestaccountsxml"></a>
<div class="modfile"><h4>Modified: CalendarServer/branches/users/sagen/move2who-4/twistedcaldav/directory/test/accounts.xml (12985 => 12986)</h4>
<pre class="diff"><span>
<span class="info">--- CalendarServer/branches/users/sagen/move2who-4/twistedcaldav/directory/test/accounts.xml        2014-03-21 02:05:52 UTC (rev 12985)
+++ CalendarServer/branches/users/sagen/move2who-4/twistedcaldav/directory/test/accounts.xml        2014-03-21 18:47:20 UTC (rev 12986)
</span><span class="lines">@@ -170,6 +170,23 @@
</span><span class="cx"> <email>user04@example.com</email>
</span><span class="cx"> </record>
</span><span class="cx">
</span><ins>+ <record type="user">
+ <short-name>user05</short-name>
+ <uid>user05</uid>
+ <password>user05</password>
+ <full-name>User 05</full-name>
+ <email>user05@example.com</email>
+ </record>
+
+ <record type="user">
+ <short-name>user06</short-name>
+ <uid>user06</uid>
+ <password>user06</password>
+ <full-name>User 06</full-name>
+ <email>user06@example.com</email>
+ </record>
+
+
</ins><span class="cx"> <!-- Repeat is not (yet?) supported in twext.who.xml
</span><span class="cx"> <user repeat="100">
</span><span class="cx"> <short-name>user%02d</short-name>
</span></span></pre>
</div>
</div>
</body>
</html>