def tests_get_subscription(self):
        """Test retrieving subscriptions information.
        """
        manager_root = ISubscriptionManager(self.root)
        manager_root.subscribability = SUBSCRIBABLE
        manager_root.subscribe("*****@*****.**")
        manager_folder = ISubscriptionManager(self.root.folder)
        manager_folder.subscribe("*****@*****.**")

        manager = ISubscriptionManager(self.root.folder.index)
        manager.subscribability = SUBSCRIBABLE
        manager.subscribe("*****@*****.**")

        self.assertEqual(manager.get_subscription("*****@*****.**"), None)
        subscription = manager.get_subscription("*****@*****.**")
        self.assertTrue(verifyObject(ISubscription, subscription))
        self.assertEqual(subscription.email, "*****@*****.**")
        self.assertEqual(subscription.content, self.root)
        self.assertEqual(len(manager.get_subscriptions()), 3)

        manager_root.subscribability = NOT_SUBSCRIBABLE

        self.assertEqual(manager.get_subscription("*****@*****.**"), None)
        subscription = manager.get_subscription("*****@*****.**")
        self.assertTrue(verifyObject(ISubscription, subscription))
        self.assertEqual(subscription.email, "*****@*****.**")
        self.assertEqual(subscription.content, self.root.folder.index)
        self.assertEqual(len(manager.get_subscriptions()), 1)
    def test_subscription_failures(self):
        """Test cases where you can't request subscription to a content.
        """
        service = getUtility(ISubscriptionService)
        service.enable_subscriptions()

        # first use something not subscribable at all
        self.assertRaises(
            errors.NotSubscribableError,
            service.request_subscription,
            self.root.file, "*****@*****.**")

        # even if all parameters are correct, content has to have its
        # subscribability set
        self.assertRaises(
            errors.NotSubscribableError,
            service.request_subscription,
            self.root.document, "*****@*****.**")

        # Set subscribability, invalid emailaddress though
        manager = ISubscriptionManager(self.root.document)
        manager.subscribability = SUBSCRIBABLE
        self.assertRaises(
            errors.InvalidEmailaddressError,
            service.request_subscription,
            self.root.document, "lekker zalm")

        # emailaddress already subscribed
        manager.subscribe("*****@*****.**")
        self.assertRaises(
            errors.AlreadySubscribedError,
            service.request_subscription,
            self.root.document, "*****@*****.**")
    def test_is_subscribed(self):
        """is_subscribed returns True if you are subscribed on of the
        parents.
        """
        manager_root = ISubscriptionManager(self.root)
        manager_root.subscribability = SUBSCRIBABLE
        manager_root.subscribe("*****@*****.**")
        self.assertEqual(manager_root.is_subscribed("*****@*****.**"), True)
        self.assertEqual(manager_root.is_subscribed("*****@*****.**"), False)

        manager = ISubscriptionManager(self.root.folder)
        self.assertEqual(manager.is_subscribed("*****@*****.**"), True)
        self.assertEqual(manager.is_subscribed("*****@*****.**"), False)

        # If you turn off subscription off at the folder level, you
        # are no longer subscribed
        manager.subscribability = NOT_SUBSCRIBABLE
        self.assertEqual(manager.is_subscribed("*****@*****.**"), False)

        # That didn't changed anything on the parent
        self.assertEqual(manager_root.is_subscribed("*****@*****.**"), True)
    def test_subscribability(self):
        """Test the subscribability setting.
        """
        manager = ISubscriptionManager(self.root.document)
        self.assertEqual(manager.is_subscribable(), False)
        self.assertEqual(manager.subscribability, ACQUIRE_SUBSCRIBABILITY)

        # You can enable or disable that setting
        manager.subscribability = SUBSCRIBABLE
        self.assertEqual(manager.is_subscribable(), True)
        self.assertEqual(manager.subscribability, SUBSCRIBABLE)

        manager.subscribability = NOT_SUBSCRIBABLE
        self.assertEqual(manager.is_subscribable(), False)
        self.assertEqual(manager.subscribability, NOT_SUBSCRIBABLE)

        # You can set the setting on the parent root
        manager_root = ISubscriptionManager(self.root)
        self.assertEqual(manager_root.is_subscribable(), False)
        self.assertEqual(manager_root.subscribability, NOT_SUBSCRIBABLE)

        # You can change the setting. Not to acquired.
        manager_root.subscribability = SUBSCRIBABLE
        self.assertEqual(manager_root.is_subscribable(), True)
        self.assertEqual(manager_root.subscribability, SUBSCRIBABLE)

        self.assertRaises(AssertionError, setattr, manager_root, "subscribability", ACQUIRE_SUBSCRIBABILITY)
        self.assertEqual(manager_root.is_subscribable(), True)
        self.assertEqual(manager_root.subscribability, SUBSCRIBABLE)

        # The setting was disabled on the document, it is still is.
        # However if we set it to acquired it will be enabled (since root is)
        self.assertEqual(manager.is_subscribable(), False)
        self.assertEqual(manager.subscribability, NOT_SUBSCRIBABLE)

        manager.subscribability = ACQUIRE_SUBSCRIBABILITY
        self.assertEqual(manager.is_subscribable(), True)
        self.assertEqual(manager.subscribability, ACQUIRE_SUBSCRIBABILITY)
    def test_subscribe_unsubscribe(self):
        manager = ISubscriptionManager(self.root.document)
        manager.subscribability = SUBSCRIBABLE
        self.assertEqual(manager.locally_subscribed_emails, set([]))
        self.assertEqual(manager.is_subscribed("*****@*****.**"), False)

        # we can subscribe some emails
        manager.subscribe("*****@*****.**")
        manager.subscribe("*****@*****.**")
        manager.subscribe("*****@*****.**")
        self.assertEqual(manager.locally_subscribed_emails, set(["*****@*****.**", "*****@*****.**"]))
        self.assertEqual(manager.is_subscribed("*****@*****.**"), True)

        # and unscribe others
        manager.unsubscribe("*****@*****.**")
        manager.unsubscribe("*****@*****.**")
        self.assertEqual(manager.locally_subscribed_emails, set(["*****@*****.**"]))
        self.assertEqual(manager.is_subscribed("*****@*****.**"), False)
    def test_subscribe(self):
        """Test request_subscription sends a mail, and we can get
        subscribed with it.
        """
        browser = self.layer.get_browser()

        manager = ISubscriptionManager(self.root.document)
        manager.subscribability = SUBSCRIBABLE
        self.assertEqual(manager.is_subscribed('*****@*****.**'), False)
        self.assertEqual(self.root.service_mailhost.messages, [])

        service = getUtility(ISubscriptionService)
        service.enable_subscriptions()
        service.request_subscription(self.root.document, "*****@*****.**")

        message = self.root.service_mailhost.read_last_message()
        self.assertNotEqual(message, None)
        self.assertEqual(message.content_type, 'text/plain')
        self.assertEqual(message.charset, 'utf-8')
        self.assertEqual(message.mto, ['*****@*****.**'])
        self.assertEqual(
            message.mfrom,
            'Subscription Service <*****@*****.**>')
        self.assertEqual(
            message.subject,
            'Subscription confirmation to "document"')
        self.assertEqual(len(message.urls), 2)

        # XXX it is a bit hardcoded on the template, the confirmation
        # is the second like in the mail.
        confirmation_url = message.urls[-1]
        self.assertEqual(browser.open(confirmation_url), 200)
        self.assertEqual(
            browser.location,
            '/root/document/subscriptions.html/@@confirm_subscription')
        self.assertEqual(
            browser.html.xpath('//p[@class="subscription-result"]/text()'),
            ['You have been successfully subscribed. '
             'You will now receive email notifications.'])

        # Torvald is now subscribed
        self.assertEqual(manager.is_subscribed('*****@*****.**'), True)
    def test_publication_notification(self):
        """We verify that if a document is publish, and the
        notification are enabled, a mail is sent to the susbcribed people.
        """
        service = getUtility(ISubscriptionService)
        service.enable_subscriptions()
        service._from = '*****@*****.**'

        manager = ISubscriptionManager(self.root)
        manager.subscribability = SUBSCRIBABLE
        manager.subscribe('*****@*****.**')
        self.assertEqual(len(self.root.service_mailhost.messages), 0)

        IPublicationWorkflow(self.root.document).publish()

        # We have two notification, one for the document, one for the ghost
        self.assertEqual(len(self.root.service_mailhost.messages), 2)
        message = self.root.service_mailhost.messages[0]
        self.assertEqual(message.content_type, 'text/plain')
        self.assertEqual(message.charset, 'utf-8')
        self.assertEqual(message.mto, ['*****@*****.**'])
        self.assertEqual(message.mfrom, '*****@*****.**')
        self.assertEqual(message.subject, 'Change notification for "Document"')

        message = self.root.service_mailhost.messages[1]
        self.assertEqual(message.content_type, 'text/plain')
        self.assertEqual(message.charset, 'utf-8')
        self.assertEqual(message.mto, ['*****@*****.**'])
        self.assertEqual(message.mfrom, '*****@*****.**')
        self.assertEqual(message.subject, 'Change notification for "ghost"')

        self.root.service_mailhost.reset()
        self.assertEqual(len(self.root.service_mailhost.messages), 0)

        # We now disable the subscription. And publish a new version.
        service.disable_subscriptions()
        self.root.document.create_copy()
        IPublicationWorkflow(self.root.document).publish()

        # No notification have been sent
        self.assertEqual(len(self.root.service_mailhost.messages), 0)
    def test_service(self):
        """Test service settings.
        """
        service = getUtility(ISubscriptionService)
        self.assertTrue(verifyObject(ISubscriptionService, service))
        self.assertEqual(self.root.service_subscriptions, service)

        # By default subscription are off, but you can change it
        self.assertEqual(service.are_subscriptions_enabled(), False)

        service.enable_subscriptions()
        self.assertEqual(service.are_subscriptions_enabled(), True)

        # You can now if at one given context they are enabled
        self.assertEqual(service.are_subscriptions_enabled(self.root), False)
        manager = ISubscriptionManager(self.root)
        manager.subscribability = SUBSCRIBABLE
        self.assertEqual(service.are_subscriptions_enabled(self.root), True)

        # And we disable them globaly now
        service.disable_subscriptions()
        self.assertEqual(service.are_subscriptions_enabled(), False)
        self.assertEqual(service.are_subscriptions_enabled(self.root), False)