Example #1
0
 def preview(self):
     if hasattr(self, '_url'):
         url = self._url + '/preview'
         return self.post(url)
     else:
         url = urljoin(recurly.base_uri(), self.collection_path) + '/preview'
         return self.post(url)
Example #2
0
    def __invoice(self, url):
        # We must null out currency in subscriptions and adjustments
        # TODO we should deprecate and remove default currency support
        def filter_currency(resources):
            for resource in resources:
                resource.attributes = tuple(
                    [a for a in resource.attributes if a != 'currency'])

        try:
            filter_currency(self.adjustments)
        except AttributeError:
            pass
        try:
            filter_currency(self.subscriptions)
        except AttributeError:
            pass

        url = urljoin(recurly.base_uri(), url)
        response = self.http_request(url, 'POST', self)
        if response.status not in (200, 201):
            self.raise_http_error(response)
        response_xml = response.read()
        logging.getLogger('recurly.http.response').debug(response_xml)
        elem = ElementTree.fromstring(response_xml)
        invoice_collection = InvoiceCollection.from_element(elem)
        return invoice_collection
 def preview(self):
     if hasattr(self, '_url'):
         url = self._url + '/preview'
         return self.post(url)
     else:
         url = urljoin(recurly.base_uri(), self.collection_path) + '/preview'
         return self.post(url)
Example #4
0
 def count(cls, **kwargs):
     """Return a count of server side resources given
     filtering arguments in kwargs.
     """
     url = recurly.base_uri() + cls.collection_path
     if kwargs:
         url = '%s?%s' % (url, urlencode_params(kwargs))
     return Page.count_for_url(url)
Example #5
0
    def preview(self):
        """Preview the purchase of this gift card"""

        if hasattr(self, '_url'):
            url = self._url + '/preview'
            return self.post(url)
        else:
            url = urljoin(recurly.base_uri(), self.collection_path) + '/preview'
            return self.post(url)
Example #6
0
 def files(self, date):
     """
     Fetch files for a given date.
     :param date: The date to fetch the export files for
     :return: A list of exported files for that given date or an empty list if not file exists for that date
     """
     url = urljoin(recurly.base_uri() + self.collection_path,
                   '/%s/export_files' % date)
     return ExportDateFile.paginated(url)
Example #7
0
    def invoice(self):
        """
        Will invoice the purchase object and run all validations and transactions.

        Returns:
            InvoiceCollection: The generated collection of invoices
        """
        url = urljoin(recurly.base_uri(), self.collection_path)
        return self.__invoice(self.collection_path)
Example #8
0
    def test_account(self):
        account_code = 'test%s' % self.test_id
        with self.mock_request('account/does-not-exist.xml'):
            self.assertRaises(NotFoundError, Account.get, account_code)

        account = Account(account_code=account_code)
        with self.mock_request('account/created.xml'):
            account.save()
        self.assertEqual(
            account._url,
            urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        with self.mock_request('account/list-active.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) >= 1)
        self.assertEqual(active[0].account_code, account_code)

        with self.mock_request('account/exists.xml'):
            same_account = Account.get(account_code)
        self.assertTrue(isinstance(same_account, Account))
        self.assertTrue(same_account is not account)
        self.assertEqual(same_account.account_code, account_code)
        self.assertTrue(same_account.first_name is None)
        self.assertEqual(
            same_account._url,
            urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        account.username = '******'
        account.email = 'larry.david'
        account.first_name = u'L\xe4rry'
        account.last_name = 'David'
        account.company_name = 'Home Box Office'
        account.accept_language = 'en-US'
        with self.mock_request('account/update-bad-email.xml'):
            try:
                account.save()
            except ValidationError, exc:
                self.assertTrue(isinstance(exc.errors, collections.Mapping))
                self.assertTrue('account.email' in exc.errors)
                suberror = exc.errors['account.email']
                self.assertEqual(suberror.symbol, 'invalid_email')
                self.assertTrue(suberror.message)
                self.assertEqual(suberror.message, str(suberror))
            else:
Example #9
0
    def preview(self):
        """
        Will create a preview invoice for the purchase. It runs all the
        validations but not the transactions.

        Returns:
            InvoiceCollection: The preview of collection of invoices
        """
        url = urljoin(recurly.base_uri(), self.collection_path + '/preview')
        return self.__invoice(url)
Example #10
0
    def get(cls, uuid):
        """Return a `Resource` instance of this class identified by
        the given code or UUID.

        Only `Resource` classes with specified `member_path` attributes
        can be directly requested with this method.

        """
        url = urljoin(recurly.base_uri(), cls.member_path % (uuid,))
        resp, elem = cls.element_for_url(url)
        return cls.from_element(elem)
    def get(cls, uuid):
        """Return a `Resource` instance of this class identified by
        the given code or UUID.

        Only `Resource` classes with specified `member_path` attributes
        can be directly requested with this method.

        """
        url = urljoin(recurly.base_uri(), cls.member_path % (uuid, ))
        resp, elem = cls.element_for_url(url)
        return cls.from_element(elem)
Example #12
0
    def redeem(self, account_code):
        """Redeem this gift card on the specified account code"""

        redemption_path = '%s/redeem' % (self.redemption_code)

        if hasattr(self, '_url'):
            url = urljoin(self._url, redemption_path)
        else:
            url = urljoin(recurly.base_uri(), self.collection_path) + '/' + redemption_path

        recipient_account = _RecipientAccount(account_code=account_code)
        return self.post(url, recipient_account)
    def test_account(self):
        account_code = 'test%s' % self.test_id
        with self.mock_request('account/does-not-exist.xml'):
            self.assertRaises(NotFoundError, Account.get, account_code)

        account = Account(account_code=account_code)
        with self.mock_request('account/created.xml'):
            account.save()
        self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        with self.mock_request('account/list-active.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) >= 1)
        self.assertEqual(active[0].account_code, account_code)

        with self.mock_request('account/exists.xml'):
            same_account = Account.get(account_code)
        self.assertTrue(isinstance(same_account, Account))
        self.assertTrue(same_account is not account)
        self.assertEqual(same_account.account_code, account_code)
        self.assertTrue(same_account.first_name is None)
        self.assertEqual(same_account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        account.username = '******'
        account.email = 'larry.david'
        account.first_name = u'L\xe4rry'
        account.last_name = 'David'
        account.company_name = 'Home Box Office'
        account.accept_language = 'en-US'
        with self.mock_request('account/update-bad-email.xml'):
            try:
                account.save()
            except ValidationError, exc:
                self.assertTrue(isinstance(exc.errors, collections.Mapping))
                self.assertTrue('account.email' in exc.errors)
                suberror = exc.errors['account.email']
                self.assertEqual(suberror.symbol, 'invalid_email')
                self.assertTrue(suberror.message)
                self.assertEqual(suberror.message, str(suberror))
            else:
Example #14
0
    def authorize(self):
        """
        Will generate an authorized invoice for the purchase. Runs validations
        but does not run any transactions. This endpoint will create a
        pending purchase that can be activated at a later time once payment
        has been completed on an external source (e.g. Adyen's Hosted
        Payment Pages).

        Returns:
            InvoiceCollection: The authorized collection of invoices
        """
        url = recurly.base_uri() + self.collection_path + '/authorize'
        return self.__invoice(url)
Example #15
0
    def all(cls, **kwargs):
        """Return a `Page` of instances of this `Resource` class from
        its general collection endpoint.

        Only `Resource` classes with specified `collection_path`
        endpoints can be requested with this method. Any provided
        keyword arguments are passed to the API endpoint as query
        parameters.

        """
        url = urljoin(recurly.base_uri(), cls.collection_path)
        if kwargs:
            url = '%s?%s' % (url, urlencode(kwargs))
        return Page.page_for_url(url)
Example #16
0
    def get(cls, uuid):
        """Return a `Resource` instance of this class identified by
        the given code or UUID.

        Only `Resource` classes with specified `member_path` attributes
        can be directly requested with this method.

        """
        if not uuid:
            raise ValueError("get must have a value passed as an argument")
        uuid = quote(str(uuid))
        url = recurly.base_uri() + (cls.member_path % (uuid, ))
        _resp, elem = cls.element_for_url(url)
        return cls.from_element(elem)
    def all(cls, **kwargs):
        """Return a `Page` of instances of this `Resource` class from
        its general collection endpoint.

        Only `Resource` classes with specified `collection_path`
        endpoints can be requested with this method. Any provided
        keyword arguments are passed to the API endpoint as query
        parameters.

        """
        url = urljoin(recurly.base_uri(), cls.collection_path)
        if kwargs:
            url = '%s?%s' % (url, urlencode(kwargs))
        return Page.page_for_url(url)
Example #18
0
 def _create(self):
     url = urljoin(recurly.base_uri(), self.collection_path)
     return self.post(url)
    def test_account(self):
        account_code = "test%s" % self.test_id
        with self.mock_request("account/does-not-exist.xml"):
            self.assertRaises(NotFoundError, Account.get, account_code)

        account = Account(account_code=account_code)
        account.vat_number = "444444-UK"
        with self.mock_request("account/created.xml"):
            account.save()
        self.assertEqual(account._url, urljoin(recurly.base_uri(), "accounts/%s" % account_code))
        self.assertEqual(account.vat_number, "444444-UK")
        self.assertEqual(account.vat_location_enabled, True)

        with self.mock_request("account/list-active.xml"):
            active = Account.all_active()
        self.assertTrue(len(active) >= 1)
        self.assertEqual(active[0].account_code, account_code)

        with self.mock_request("account/exists.xml"):
            same_account = Account.get(account_code)
        self.assertTrue(isinstance(same_account, Account))
        self.assertTrue(same_account is not account)
        self.assertEqual(same_account.account_code, account_code)
        self.assertTrue(same_account.first_name is None)
        self.assertTrue(same_account.entity_use_code == "I")
        self.assertEqual(same_account._url, urljoin(recurly.base_uri(), "accounts/%s" % account_code))

        account.username = "******"
        account.email = "larry.david"
        account.first_name = six.u("L\xe4rry")
        account.last_name = "David"
        account.company_name = "Home Box Office"
        account.accept_language = "en-US"
        with self.mock_request("account/update-bad-email.xml"):
            try:
                account.save()
            except ValidationError as exc:
                self.assertTrue(isinstance(exc.errors, collections.Mapping))
                self.assertTrue("account.email" in exc.errors)
                suberror = exc.errors["account.email"]
                self.assertEqual(suberror.symbol, "invalid_email")
                self.assertTrue(suberror.message)
                self.assertEqual(suberror.message, suberror.message)
            else:
                self.fail("Updating account with invalid email address did not raise a ValidationError")

        account.email = "*****@*****.**"
        with self.mock_request("account/updated.xml"):
            account.save()

        with self.mock_request("account/deleted.xml"):
            account.delete()

        with self.mock_request("account/list-closed.xml"):
            closed = Account.all_closed()
        self.assertTrue(len(closed) >= 1)
        self.assertEqual(closed[0].account_code, account_code)

        with self.mock_request("account/list-active-when-closed.xml"):
            active = Account.all_active()
        self.assertTrue(len(active) < 1 or active[0].account_code != account_code)

        # Make sure we can reopen a closed account.
        with self.mock_request("account/reopened.xml"):
            account.reopen()
        try:
            with self.mock_request("account/list-active.xml"):
                active = Account.all_active()
            self.assertTrue(len(active) >= 1)
            self.assertEqual(active[0].account_code, account_code)
        finally:
            with self.mock_request("account/deleted.xml"):
                account.delete()

        # Make sure numeric account codes work.
        if self.test_id == "mock":
            numeric_test_id = 58
        else:
            numeric_test_id = int(self.test_id)

        account = Account(account_code=numeric_test_id)
        with self.mock_request("account/numeric-created.xml"):
            account.save()
        try:
            self.assertEqual(account._url, urljoin(recurly.base_uri(), "accounts/%d" % numeric_test_id))
        finally:
            with self.mock_request("account/numeric-deleted.xml"):
                account.delete()

        """Create an account with an account level address"""
        account = Account(account_code=account_code)
        account.address.address1 = "123 Main St"
        account.address.city = "San Francisco"
        account.address.zip = "94105"
        account.address.state = "CA"
        account.address.country = "US"
        account.address.phone = "8015559876"
        with self.mock_request("account/created-with-address.xml"):
            account.save()
        self.assertEqual(account.address.address1, "123 Main St")
        self.assertEqual(account.address.city, "San Francisco")
        self.assertEqual(account.address.zip, "94105")
        self.assertEqual(account.address.state, "CA")
        self.assertEqual(account.address.country, "US")
        self.assertEqual(account.address.phone, "8015559876")

        """Get taxed account"""
        with self.mock_request("account/show-taxed.xml"):
            account = Account.get(account_code)
            self.assertTrue(account.tax_exempt)
    def test_account(self):
        account_code = 'test%s' % self.test_id
        with self.mock_request('account/does-not-exist.xml'):
            self.assertRaises(NotFoundError, Account.get, account_code)

        account = Account(account_code=account_code)
        account.vat_number = '444444-UK'
        with self.mock_request('account/created.xml'):
            account.save()
        self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))
        self.assertEqual(account.vat_number, '444444-UK')

        with self.mock_request('account/list-active.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) >= 1)
        self.assertEqual(active[0].account_code, account_code)

        with self.mock_request('account/exists.xml'):
            same_account = Account.get(account_code)
        self.assertTrue(isinstance(same_account, Account))
        self.assertTrue(same_account is not account)
        self.assertEqual(same_account.account_code, account_code)
        self.assertTrue(same_account.first_name is None)
        self.assertTrue(same_account.entity_use_code == 'I')
        self.assertEqual(same_account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        account.username = '******'
        account.email = 'larry.david'
        account.first_name = six.u('L\xe4rry')
        account.last_name = 'David'
        account.company_name = 'Home Box Office'
        account.accept_language = 'en-US'
        with self.mock_request('account/update-bad-email.xml'):
            try:
                account.save()
            except ValidationError as exc:
                self.assertTrue(isinstance(exc.errors, collections.Mapping))
                self.assertTrue('account.email' in exc.errors)
                suberror = exc.errors['account.email']
                self.assertEqual(suberror.symbol, 'invalid_email')
                self.assertTrue(suberror.message)
                self.assertEqual(suberror.message, suberror.message)
            else:
                self.fail("Updating account with invalid email address did not raise a ValidationError")

        account.email = '*****@*****.**'
        with self.mock_request('account/updated.xml'):
            account.save()

        with self.mock_request('account/deleted.xml'):
            account.delete()

        with self.mock_request('account/list-closed.xml'):
            closed = Account.all_closed()
        self.assertTrue(len(closed) >= 1)
        self.assertEqual(closed[0].account_code, account_code)

        with self.mock_request('account/list-active-when-closed.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) < 1 or active[0].account_code != account_code)

        # Make sure we can reopen a closed account.
        with self.mock_request('account/reopened.xml'):
            account.reopen()
        try:
            with self.mock_request('account/list-active.xml'):
                active = Account.all_active()
            self.assertTrue(len(active) >= 1)
            self.assertEqual(active[0].account_code, account_code)
        finally:
            with self.mock_request('account/deleted.xml'):
                account.delete()

        # Make sure numeric account codes work.
        if self.test_id == 'mock':
            numeric_test_id = 58
        else:
            numeric_test_id = int(self.test_id)

        account = Account(account_code=numeric_test_id)
        with self.mock_request('account/numeric-created.xml'):
            account.save()
        try:
            self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%d' % numeric_test_id))
        finally:
            with self.mock_request('account/numeric-deleted.xml'):
                account.delete()

        """Create an account with an account level address"""
        account = Account(account_code=account_code)
        account.address.address1 = '123 Main St'
        account.address.city = 'San Francisco'
        account.address.zip = '94105'
        account.address.state = 'CA'
        account.address.country = 'US'
        account.address.phone = '8015559876'
        with self.mock_request('account/created-with-address.xml'):
            account.save()
        self.assertEqual(account.address.address1, '123 Main St')
        self.assertEqual(account.address.city, 'San Francisco')
        self.assertEqual(account.address.zip, '94105')
        self.assertEqual(account.address.state, 'CA')
        self.assertEqual(account.address.country, 'US')
        self.assertEqual(account.address.phone, '8015559876')

        """Get taxed account"""
        with self.mock_request('account/show-taxed.xml'):
            account = Account.get(account_code)
            self.assertTrue(account.tax_exempt)
Example #21
0
 def billing_info_uris(self, obj):
     uri_out = {}
     uri_out['account_uri'] = recurly.base_uri() + AccountsEndpoint.base_uri + '/' + obj['account']
     uri_out['object_uri'] = uri_out['account_uri'] + '/billing_info'
     return uri_out
Example #22
0
    def test_account(self):
        account_code = 'test%s' % self.test_id
        with self.mock_request('account/does-not-exist.xml'):
            self.assertRaises(NotFoundError, Account.get, account_code)

        account = Account(account_code=account_code)
        account.vat_number = '444444-UK'
        with self.mock_request('account/created.xml'):
            account.save()
        self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))
        self.assertEqual(account.vat_number, '444444-UK')

        with self.mock_request('account/list-active.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) >= 1)
        self.assertEqual(active[0].account_code, account_code)

        with self.mock_request('account/exists.xml'):
            same_account = Account.get(account_code)
        self.assertTrue(isinstance(same_account, Account))
        self.assertTrue(same_account is not account)
        self.assertEqual(same_account.account_code, account_code)
        self.assertTrue(same_account.first_name is None)
        self.assertEqual(same_account._url, urljoin(recurly.base_uri(), 'accounts/%s' % account_code))

        account.username = '******'
        account.email = 'larry.david'
        account.first_name = six.u('L\xe4rry')
        account.last_name = 'David'
        account.company_name = 'Home Box Office'
        account.accept_language = 'en-US'
        with self.mock_request('account/update-bad-email.xml'):
            try:
                account.save()
            except ValidationError as exc:
                self.assertTrue(isinstance(exc.errors, collections.Mapping))
                self.assertTrue('account.email' in exc.errors)
                suberror = exc.errors['account.email']
                self.assertEqual(suberror.symbol, 'invalid_email')
                self.assertTrue(suberror.message)
                self.assertEqual(suberror.message, suberror.message)
            else:
                self.fail("Updating account with invalid email address did not raise a ValidationError")

        account.email = '*****@*****.**'
        with self.mock_request('account/updated.xml'):
            account.save()

        with self.mock_request('account/deleted.xml'):
            account.delete()

        with self.mock_request('account/list-closed.xml'):
            closed = Account.all_closed()
        self.assertTrue(len(closed) >= 1)
        self.assertEqual(closed[0].account_code, account_code)

        with self.mock_request('account/list-active-when-closed.xml'):
            active = Account.all_active()
        self.assertTrue(len(active) < 1 or active[0].account_code != account_code)

        # Make sure we can reopen a closed account.
        with self.mock_request('account/reopened.xml'):
            account.reopen()
        try:
            with self.mock_request('account/list-active.xml'):
                active = Account.all_active()
            self.assertTrue(len(active) >= 1)
            self.assertEqual(active[0].account_code, account_code)
        finally:
            with self.mock_request('account/deleted.xml'):
                account.delete()

        # Make sure numeric account codes work.
        if self.test_id == 'mock':
            numeric_test_id = 58
        else:
            numeric_test_id = int(self.test_id)

        account = Account(account_code=numeric_test_id)
        with self.mock_request('account/numeric-created.xml'):
            account.save()
        try:
            self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%d' % numeric_test_id))
        finally:
            with self.mock_request('account/numeric-deleted.xml'):
                account.delete()

        """Create an account with an account level address"""
        account = Account(account_code=account_code)
        account.address.address1 = '123 Main St'
        account.address.city = 'San Francisco'
        account.address.zip = '94105'
        account.address.state = 'CA'
        account.address.country = 'US'
        account.address.phone = '8015559876'
        with self.mock_request('account/created-with-address.xml'):
            account.save()
        self.assertEqual(account.address.address1, '123 Main St')
        self.assertEqual(account.address.city, 'San Francisco')
        self.assertEqual(account.address.zip, '94105')
        self.assertEqual(account.address.state, 'CA')
        self.assertEqual(account.address.country, 'US')
        self.assertEqual(account.address.phone, '8015559876')
Example #23
0
 def get_object_uri(self, obj):
     """Returns the URI to access the given object resource
     """
     cls = self.__class__
     return recurly.base_uri() + cls.base_uri + '/' + obj[cls.pk_attr]
Example #24
0
 def _create(self):
     url = recurly.base_uri() + self.collection_path
     return self.post(url)
Example #25
0
    def _register(self):
        """Walks the endpoints to register all its URIs to HTTPretty so that
        they can mock recurly requests.
        """
        from .endpoints import endpoints
        for endpoint in endpoints:
            # register list views
            list_uri = recurly.base_uri() + endpoint.base_uri

            def list_callback(request, uri, headers, endpoint=endpoint):
                xml, item_count = endpoint.list()
                headers['X-Records'] = item_count
                return 200, headers, xml
            HTTPretty.register_uri(HTTPretty.GET, list_uri, body=_callback(self)(list_callback), content_type="application/xml")

            def create_callback(request, uri, headers, endpoint=endpoint):
                return 200, headers, endpoint.create(deserialize(request.body)[1])
            HTTPretty.register_uri(HTTPretty.POST, list_uri, body=_callback(self)(create_callback), content_type="application/xml")

            # register details views
            detail_uri = recurly.base_uri() + endpoint.base_uri + r'/([^/ ]+)'
            detail_uri_re = re.compile(detail_uri + r'$')

            def retrieve_callback(request, uri, headers, endpoint=endpoint, detail_uri_re=detail_uri_re):
                pk = detail_uri_re.match(uri).group(1)
                return 200, headers, endpoint.retrieve(pk)
            HTTPretty.register_uri(HTTPretty.GET, detail_uri_re, body=_callback(self)(retrieve_callback), content_type="application/xml")

            def update_callback(request, uri, headers, endpoint=endpoint, detail_uri_re=detail_uri_re):
                pk = detail_uri_re.match(uri).group(1)
                return 200, headers, endpoint.update(pk, deserialize(request.body)[1])
            HTTPretty.register_uri(HTTPretty.PUT, detail_uri_re, body=_callback(self)(update_callback), content_type="application/xml")

            def delete_callback(request, uri, headers, endpoint=endpoint, detail_uri_re=detail_uri_re):
                parsed_url = urlparse(uri)
                pk = detail_uri_re.match('{0}://{1}{2}'.format(parsed_url.scheme, parsed_url.netloc, parsed_url.path)).group(1)
                endpoint.delete(pk, **parse_qs(parsed_url.query))
                return 204, headers, ''
            HTTPretty.register_uri(HTTPretty.DELETE, detail_uri_re, body=_callback(self)(delete_callback))

            # register extra views
            for method in filter(lambda method: callable(method) and getattr(method, 'is_route', False), (getattr(endpoint, m) for m in dir(endpoint))):
                uri = detail_uri + '/' + method.uri
                uri_re = re.compile(uri)

                def extra_route_callback(request, uri, headers, method=method, uri_re=uri_re):
                    pk = uri_re.match(uri).group(1)
                    if method.method == 'DELETE':
                        status = 204
                    else:
                        status = 200
                    if request.method in ['POST', 'PUT']:
                        post_data = request.querystring.copy()
                        if request.body:
                            post_data.update(deserialize(request.body)[1])
                        result = method(pk, post_data)
                    elif method.is_list:
                        result = method(pk, filters=request.querystring)
                        headers['X-Records'] = result[1]
                        result = result[0]
                    else:
                        result = method(pk)
                    return status, headers, result
                if method.method == 'DELETE':
                    HTTPretty.register_uri(HTTPretty.DELETE, uri_re, body=_callback(self)(extra_route_callback))
                else:
                    HTTPretty.register_uri(method.method, uri_re, body=_callback(self)(extra_route_callback), content_type="application/xml")
Example #26
0
 def get_object_uri(self, obj):
     """Returns the URI to access the given object resource
     """
     cls = self.__class__
     return recurly.base_uri() + cls.base_uri + '/' + obj[cls.pk_attr]
def fetch(token):
    url = urljoin(recurly.base_uri(), 'recurly_js/result/%s' % token)
    resp, elem = recurly.Resource.element_for_url(url)
    cls = recurly.Resource.value_for_element(elem)
    return cls.from_element(elem)
 def _create(self):
     url = urljoin(recurly.base_uri(), self.collection_path)
     return self.post(url)
Example #29
0
    def _register(self):
        """Walks the endpoints to register all its URIs to HTTPretty so that
        they can mock recurly requests.
        """
        from .endpoints import endpoints
        for endpoint in endpoints:
            # register list views
            list_uri = recurly.base_uri() + endpoint.base_uri
            list_uri_re = re.compile(list_uri + r'$')

            def list_callback(request, uri, headers, endpoint=endpoint):
                xml, item_count = endpoint.list()
                headers['X-Records'] = item_count
                return 200, headers, xml

            HTTPretty.register_uri(HTTPretty.GET,
                                   list_uri_re,
                                   body=_callback(self)(list_callback),
                                   content_type="application/xml")

            def create_callback(request, uri, headers, endpoint=endpoint):
                return 200, headers, endpoint.create(
                    deserialize(request.body)[1])

            HTTPretty.register_uri(HTTPretty.POST,
                                   list_uri_re,
                                   body=_callback(self)(create_callback),
                                   content_type="application/xml")

            # register details views
            detail_uri = recurly.base_uri() + endpoint.base_uri + r'/([^/ ]+)'
            detail_uri_re = re.compile(detail_uri + r'$')

            def retrieve_callback(request,
                                  uri,
                                  headers,
                                  endpoint=endpoint,
                                  detail_uri_re=detail_uri_re):
                raw_pk = detail_uri_re.match(uri).group(1)
                pk = unquote(raw_pk)
                return 200, headers, endpoint.retrieve(pk)

            HTTPretty.register_uri(HTTPretty.GET,
                                   detail_uri_re,
                                   body=_callback(self)(retrieve_callback),
                                   content_type="application/xml")

            def update_callback(request,
                                uri,
                                headers,
                                endpoint=endpoint,
                                detail_uri_re=detail_uri_re):
                raw_pk = detail_uri_re.match(uri).group(1)
                pk = unquote(raw_pk)
                return 200, headers, endpoint.update(
                    pk,
                    deserialize(request.body)[1])

            HTTPretty.register_uri(HTTPretty.PUT,
                                   detail_uri_re,
                                   body=_callback(self)(update_callback),
                                   content_type="application/xml")

            def delete_callback(request,
                                uri,
                                headers,
                                endpoint=endpoint,
                                detail_uri_re=detail_uri_re):
                parsed_url = urlparse(uri)
                url_domain_part = '{0}://{1}{2}'.format(
                    parsed_url.scheme, parsed_url.netloc, parsed_url.path)
                raw_pk = detail_uri_re.match(url_domain_part).group(1)
                pk = unquote(raw_pk)
                endpoint.delete(pk, **parse_qs(parsed_url.query))
                return 204, headers, ''

            HTTPretty.register_uri(HTTPretty.DELETE,
                                   detail_uri_re,
                                   body=_callback(self)(delete_callback))

            # register extra views
            extra_views = filter(
                lambda method: callable(method) and getattr(
                    method, 'is_route', False),
                (getattr(endpoint, m) for m in dir(endpoint)))
            for method in extra_views:
                uri = detail_uri + '/' + method.uri
                uri_re = re.compile(uri)

                def extra_route_callback(request,
                                         uri,
                                         headers,
                                         method=method,
                                         uri_re=uri_re):
                    uri_args = uri_re.match(uri).groups()
                    uri_args = list(uri_args)
                    uri_args[0] = unquote(uri_args[0])
                    if method.method == 'DELETE':
                        status = 204
                    else:
                        status = 200
                    if request.method in ['POST', 'PUT']:
                        post_data = request.querystring.copy()
                        if request.body:
                            post_data.update(deserialize(request.body)[1])
                        uri_args.append(post_data)
                        result = method(*uri_args)
                    elif method.is_list:
                        result = method(*uri_args, filters=request.querystring)
                        headers['X-Records'] = result[1]
                        result = result[0]
                    else:
                        result = method(*uri_args)
                    return status, headers, result

                if method.method == 'DELETE':
                    HTTPretty.register_uri(
                        HTTPretty.DELETE,
                        uri_re,
                        body=_callback(self)(extra_route_callback))
                else:
                    HTTPretty.register_uri(
                        method.method,
                        uri_re,
                        body=_callback(self)(extra_route_callback),
                        content_type="application/xml")
Example #30
0
 def billing_info_uris(self, obj):
     uri_out = {}
     uri_out['account_uri'] = recurly.base_uri() + AccountsEndpoint.base_uri + '/' + obj['account']
     uri_out['object_uri'] = uri_out['account_uri'] + '/billing_info'
     return uri_out
Example #31
0
def fetch(token):
    url = urljoin(recurly.base_uri(), 'recurly_js/result/%s' % token)
    resp, elem = recurly.Resource.element_for_url(url)
    cls = recurly.Resource.value_for_element(elem)
    return cls.from_element(elem)
            self.assertEqual(active[0].account_code, account_code)
        finally:
            with self.mock_request('account/deleted.xml'):
                account.delete()

        # Make sure numeric account codes work.
        if self.test_id == 'mock':
            numeric_test_id = 58
        else:
            numeric_test_id = int(self.test_id)

        account = Account(account_code=numeric_test_id)
        with self.mock_request('account/numeric-created.xml'):
            account.save()
        try:
            self.assertEqual(account._url, urljoin(recurly.base_uri(), 'accounts/%d' % numeric_test_id))
        finally:
            with self.mock_request('account/numeric-deleted.xml'):
                account.delete()

    def test_add_on(self):
        plan_code = 'plan%s' % self.test_id
        add_on_code = 'addon%s' % self.test_id

        plan = Plan(
            plan_code=plan_code,
            name='Mock Plan',
            setup_fee_in_cents=Money(0),
            unit_amount_in_cents=Money(1000),
        )
        with self.mock_request('add-on/plan-created.xml'):
Example #33
0
            with self.mock_request('account/deleted.xml'):
                account.delete()

        # Make sure numeric account codes work.
        if self.test_id == 'mock':
            numeric_test_id = 58
        else:
            numeric_test_id = int(self.test_id)

        account = Account(account_code=numeric_test_id)
        with self.mock_request('account/numeric-created.xml'):
            account.save()
        try:
            self.assertEqual(
                account._url,
                urljoin(recurly.base_uri(), 'accounts/%d' % numeric_test_id))
        finally:
            with self.mock_request('account/numeric-deleted.xml'):
                account.delete()

    def test_add_on(self):
        plan_code = 'plan%s' % self.test_id
        add_on_code = 'addon%s' % self.test_id

        plan = Plan(
            plan_code=plan_code,
            name='Mock Plan',
            setup_fee_in_cents=Money(0),
            unit_amount_in_cents=Money(1000),
        )
        with self.mock_request('add-on/plan-created.xml'):