summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorThomas Bruederli <bruederli@kolabsys.com>2014-02-20 06:09:15 -0500
committerThomas Bruederli <bruederli@kolabsys.com>2014-02-20 06:09:15 -0500
commitc1153b7c7214af35d7057f93592bb08d7de63f88 (patch)
tree10dc6d50371c74273e2ddf2a843d847849c8d070
parent4d460abbc06e0cc54f0a0b285708102829b618cc (diff)
downloadpykolab-c1153b7c7214af35d7057f93592bb08d7de63f88.tar.gz
Add the resource's common name when delegating; allow customized subject and text for iTip replies
-rw-r--r--pykolab/xml/event.py27
-rw-r--r--tests/functional/test_wallace/test_005_resource_invitation.py25
-rw-r--r--wallace/module_resources.py10
3 files changed, 36 insertions, 26 deletions
diff --git a/pykolab/xml/event.py b/pykolab/xml/event.py
index 4f3ca0a..2dea819 100644
--- a/pykolab/xml/event.py
+++ b/pykolab/xml/event.py
@@ -153,25 +153,28 @@ class Event(object):
elif hasattr(cal, 'as_string'):
return cal.as_string()
- def delegate(self, delegators, delegatees):
+ def delegate(self, delegators, delegatees, names=None):
if not isinstance(delegators, list):
delegators = [delegators]
if not isinstance(delegatees, list):
delegatees = [delegatees]
+ if not isinstance(names, list):
+ names = [names]
+
_delegators = []
for delegator in delegators:
_delegators.append(self.get_attendee(delegator))
_delegatees = []
- for delegatee in delegatees:
+ for i,delegatee in enumerate(delegatees):
try:
_delegatees.append(self.get_attendee(delegatee))
except:
# TODO: An iTip needs to be sent out to the new attendee
- self.add_attendee(delegatee)
+ self.add_attendee(delegatee, names[i] if i < len(names) else None)
_delegatees.append(self.get_attendee(delegatee))
for delegator in _delegators:
@@ -916,7 +919,7 @@ class Event(object):
return msg
- def to_message_itip(self, from_address, method="REQUEST", participant_status="ACCEPTED"):
+ def to_message_itip(self, from_address, method="REQUEST", participant_status="ACCEPTED", subject=None, message_text=None):
from email.MIMEMultipart import MIMEMultipart
from email.MIMEBase import MIMEBase
from email.MIMEText import MIMEText
@@ -979,19 +982,19 @@ class Event(object):
msg['Date'] = formatdate(localtime=True)
- # TODO: Should allow for localization
- text = utils.multiline_message("""
- This is a response to one of your event requests.
- """)
+ if subject is None:
+ subject = _("Reservation Request for %s was %s") % (self.get_summary(), participant_status)
- msg.attach( MIMEText(text) )
+ msg["Subject"] = subject
+
+ if message_text is None:
+ message_text = _("""This is an automated response to one of your event requests.""")
+
+ msg.attach(MIMEText(utils.multiline_message(message_text)))
part = MIMEBase('text', 'calendar', charset='UTF-8', method=method)
del part['MIME-Version'] # mime parts don't need this
- # TODO: Should allow for localization
- msg["Subject"] = "Meeting Request %s" % (participant_status)
-
part.set_payload(self.as_string_itip(method=method))
part.add_header('Content-Disposition', 'attachment; filename="event.ics"')
diff --git a/tests/functional/test_wallace/test_005_resource_invitation.py b/tests/functional/test_wallace/test_005_resource_invitation.py
index 780ca0f..8d6803d 100644
--- a/tests/functional/test_wallace/test_005_resource_invitation.py
+++ b/tests/functional/test_wallace/test_005_resource_invitation.py
@@ -52,7 +52,7 @@ DTEND;TZID=Europe/London:%s
SUMMARY:test
DESCRIPTION:test
ORGANIZER;CN="Doe, John":mailto:john.doe@example.org
-ATTENDEE;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP=TRUE:mailto:%s
+ATTENDEE;ROLE=REQ-PARTICIPANT;CUTYPE=RESOURCE;PARTSTAT=NEEDS-ACTION;RSVP=TRUE:mailto:%s
TRANSP:OPAQUE
END:VEVENT
END:VCALENDAR
@@ -94,7 +94,7 @@ SEQUENCE:2
SUMMARY:test
DESCRIPTION:test
ORGANIZER;CN="Doe, John":mailto:john.doe@example.org
-ATTENDEE;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP=TRUE:mailto:%s
+ATTENDEE;ROLE=REQ-PARTICIPANT;CUTYPE=RESOURCE;PARTSTAT=NEEDS-ACTION;RSVP=TRUE:mailto:%s
TRANSP:OPAQUE
END:VEVENT
END:VCALENDAR
@@ -305,7 +305,7 @@ class TestResourceInvitation(unittest.TestCase):
def test_002_invite_resource(self):
uid = self.send_itip_invitation(self.audi['mail'], datetime.datetime(2014,7,13, 10,0,0))
- response = self.check_message_received("Meeting Request ACCEPTED", self.audi['mail'])
+ response = self.check_message_received("Reservation Request for test was ACCEPTED", self.audi['mail'])
self.assertIsInstance(response, email.message.Message)
event = self.check_resource_calendar_event(self.audi['kolabtargetfolder'], uid)
@@ -316,7 +316,7 @@ class TestResourceInvitation(unittest.TestCase):
def test_003_invite_resource_conflict(self):
uid = self.send_itip_invitation(self.audi['mail'], datetime.datetime(2014,7,13, 12,0,0))
- response = self.check_message_received("Meeting Request DECLINED", self.audi['mail'])
+ response = self.check_message_received("Reservation Request for test was DECLINED", self.audi['mail'])
self.assertIsInstance(response, email.message.Message)
self.assertEqual(self.check_resource_calendar_event(self.audi['kolabtargetfolder'], uid), None)
@@ -328,29 +328,30 @@ class TestResourceInvitation(unittest.TestCase):
uid = self.send_itip_invitation(self.cars['mail'], datetime.datetime(2014,7,13, 12,0,0))
# one of the collection members accepted the reservation
- accept = self.check_message_received("Meeting Request ACCEPTED")
+ accept = self.check_message_received("Reservation Request for test was ACCEPTED")
self.assertIsInstance(accept, email.message.Message)
- self.assertIn(accept['from'], [ self.passat['mail'], self.boxter['mail'] ])
+
+ delegatee = self.passat if accept['from'].find(self.passat['mail']) >= 0 else self.boxter
+ self.assertIn(delegatee['mail'], accept['from'])
# check booking in the delegatee's resource calendar
- delegatee = self.passat if accept['from'] == self.passat['mail'] else self.boxter
self.assertIsInstance(self.check_resource_calendar_event(delegatee['kolabtargetfolder'], uid), pykolab.xml.Event)
- # resource collection respons with a DELEGATED message
- response = self.check_message_received("Meeting Request DELEGATED", self.cars['mail'])
+ # resource collection responds with a DELEGATED message
+ response = self.check_message_received("Reservation Request for test was DELEGATED", self.cars['mail'])
self.assertIsInstance(response, email.message.Message)
def test_005_rescheduling_reservation(self):
uid = self.send_itip_invitation(self.audi['mail'], datetime.datetime(2014,5,1, 10,0,0))
- response = self.check_message_received("Meeting Request ACCEPTED", self.audi['mail'])
+ response = self.check_message_received("Reservation Request for test was ACCEPTED", self.audi['mail'])
self.assertIsInstance(response, email.message.Message)
self.purge_mailbox(self.john['mailbox'])
self.send_itip_update(self.audi['mail'], uid, datetime.datetime(2014,5,1, 12,0,0)) # conflict with myself
- response = self.check_message_received("Meeting Request ACCEPTED", self.audi['mail'])
+ response = self.check_message_received("Reservation Request for test was ACCEPTED", self.audi['mail'])
self.assertIsInstance(response, email.message.Message)
event = self.check_resource_calendar_event(self.audi['kolabtargetfolder'], uid)
@@ -371,5 +372,5 @@ class TestResourceInvitation(unittest.TestCase):
# make new reservation to the now free'd slot
self.send_itip_invitation(self.boxter['mail'], datetime.datetime(2014,5,1, 9,0,0))
- response = self.check_message_received("Meeting Request ACCEPTED", self.boxter['mail'])
+ response = self.check_message_received("Reservation Request for test was ACCEPTED", self.boxter['mail'])
self.assertIsInstance(response, email.message.Message)
diff --git a/wallace/module_resources.py b/wallace/module_resources.py
index dfd419a..b718ac4 100644
--- a/wallace/module_resources.py
+++ b/wallace/module_resources.py
@@ -358,7 +358,7 @@ def execute(*args, **kw):
# - delegator: the original resource collection
# - delegatee: the target resource
#
- itip_event['xml'].delegate(original_resource['mail'], _target_resource['mail'])
+ itip_event['xml'].delegate(original_resource['mail'], _target_resource['mail'], _target_resource['cn'])
accept_reservation_request(itip_event, _target_resource, original_resource)
done = True
@@ -822,6 +822,7 @@ def send_response(from_address, itip_events):
for itip_event in itip_events:
attendee = itip_event['xml'].get_attendee_by_email(from_address)
participant_status = itip_event['xml'].get_ical_attendee_participant_status(attendee)
+ message_text = None
if participant_status == "DELEGATED":
# Extra actions to take
@@ -834,9 +835,14 @@ def send_response(from_address, itip_events):
# restore list of attendees after to_message_itip()
itip_event['xml']._attendees = [ delegator, delegatee ]
itip_event['xml'].event.setAttendees(itip_event['xml']._attendees)
+
participant_status = "DELEGATED"
+ message_text = _("""
+ Your reservation request was delegated to "%s"
+ which is available for the requested time.
+ """) % (delegatee.get_name())
- message = itip_event['xml'].to_message_itip(from_address, method="REPLY", participant_status=participant_status)
+ message = itip_event['xml'].to_message_itip(from_address, method="REPLY", participant_status=participant_status, message_text=message_text)
smtp.sendmail(message['From'], message['To'], message.as_string())
smtp.quit()