Index: main/waeup.sirp/trunk/src/waeup/sirp/hostels/browser.py
===================================================================
--- main/waeup.sirp/trunk/src/waeup/sirp/hostels/browser.py	(revision 7030)
+++ main/waeup.sirp/trunk/src/waeup/sirp/hostels/browser.py	(revision 7042)
@@ -260,12 +260,33 @@
             message = ', '.join(switched)
             self.flash('Successfully switched beds: %s' % message)
-            write_log_message(self, 'switched: % s' % message)
-            self.redirect(self.url(self.context, '@@manage')+'#tab-2')
-        return
-
-    # Needed for removing students from beds
-    #@grok.action('Release selected beds')
-    #def releaseBeds(self, **data):
-    #    #self.flash('%d released' % released)
-    #    self.redirect(self.url(self.context, '@@manage')+'#tab-2')
-    #    return
+            write_log_message(self, 'switched: %s' % message)
+            self.redirect(self.url(self.context, '@@manage')+'#tab-2')
+        return
+
+    @grok.action('Release selected beds')
+    def releaseBeds(self, **data):
+        form = self.request.form
+        if form.has_key('val_id'):
+            child_id = form['val_id']
+        else:
+            self.flash('No item selected.')
+            self.redirect(self.url(self.context, '@@manage')+'#tab-2')
+            return
+        if not isinstance(child_id, list):
+            child_id = [child_id]
+        released = []
+        for bed_id in child_id:
+            try:
+                message = self.context[bed_id].releaseBed()
+                released.append('%s (%s)' % (bed_id,message))
+            except:
+                self.flash('Could not release %s: %s: %s' % (
+                        id, sys.exc_info()[0], sys.exc_info()[1]))
+                self.redirect(self.url(self.context, '@@manage')+'#tab-2')
+                return
+        if len(released):
+            message = ', '.join(released)
+            self.flash('Successfully released beds: %s' % message)
+            write_log_message(self, 'released: %s' % message)
+            self.redirect(self.url(self.context, '@@manage')+'#tab-2')
+        return
Index: main/waeup.sirp/trunk/src/waeup/sirp/hostels/hostel.py
===================================================================
--- main/waeup.sirp/trunk/src/waeup/sirp/hostels/hostel.py	(revision 7030)
+++ main/waeup.sirp/trunk/src/waeup/sirp/hostels/hostel.py	(revision 7042)
@@ -177,4 +177,24 @@
         return message
 
+    def releaseBed(self):
+        if self.owner == NOT_OCCUPIED:
+            return u'not occupied'
+        else:
+            old_owner = self.owner
+            self.owner = NOT_OCCUPIED
+            notify(grok.ObjectModifiedEvent(self))
+            accommodation_session = grok.getSite()[
+                'configuration'].accommodation_session
+            try:
+            #import pdb; pdb.set_trace()
+                bedticket = grok.getSite()['students'][old_owner][
+                              'accommodation'][str(accommodation_session)]
+            except KeyError:
+                return '%s without bed ticket' % old_owner
+            bedticket.bed = None
+            timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
+            bedticket.bed_coordinates = u'-- booking cancelled on %s --' % timestamp
+            return old_owner
+
     def loggerInfo(self, ob_class, comment=None):
         target = self.__name__
@@ -188,5 +208,8 @@
     of the bed is cleared (set to NOT_OCCUPIED).
     """
-    allocated_bed = bedticket.bed
-    allocated_bed.owner = NOT_OCCUPIED
-    notify(grok.ObjectModifiedEvent(allocated_bed))
+    if bedticket.bed:
+        allocated_bed = bedticket.bed
+        allocated_bed.owner = NOT_OCCUPIED
+        notify(grok.ObjectModifiedEvent(allocated_bed))
+    else:
+        pass
Index: main/waeup.sirp/trunk/src/waeup/sirp/students/browser.py
===================================================================
--- main/waeup.sirp/trunk/src/waeup/sirp/students/browser.py	(revision 7030)
+++ main/waeup.sirp/trunk/src/waeup/sirp/students/browser.py	(revision 7042)
@@ -1381,7 +1381,11 @@
             owner=(student.student_id,student.student_id))
         # Rlease old bed
-        allocated_bed = self.context.bed
-        allocated_bed.owner = NOT_OCCUPIED
-        notify(grok.ObjectModifiedEvent(allocated_bed))
+        try:
+            allocated_bed = self.context.bed
+            allocated_bed.owner = NOT_OCCUPIED
+            notify(grok.ObjectModifiedEvent(allocated_bed))
+        except AttributeError:
+            # Cannot happen but anyway...
+            pass
         # Alocate new bed
         self.context.bed_type = acc_details['bt']
