diff --git a/setup.py b/setup.py index 2cf45c4f..7cc8f867 100644 --- a/setup.py +++ b/setup.py @@ -95,6 +95,7 @@ requires = [ 'rattail[db,bouncer]', # 0.5.0 'six', # 1.10.0 'sa-filters', # 1.2.0 + 'simplejson', # 3.18.3 'transaction', # 1.2.0 'waitress', # 0.8.1 'WebHelpers2', # 2.0 diff --git a/tailbone/api/batch/core.py b/tailbone/api/batch/core.py index a1c06ee6..f239aaaf 100644 --- a/tailbone/api/batch/core.py +++ b/tailbone/api/batch/core.py @@ -348,13 +348,12 @@ class APIBatchRowView(APIBatchMixin, APIMasterView): route_prefix = cls.get_route_prefix() permission_prefix = cls.get_permission_prefix() collection_url_prefix = cls.get_collection_url_prefix() - object_url_prefix = cls.get_object_url_prefix() if cls.supports_quick_entry: # quick entry - config.add_route('{}.quick_entry'.format(route_prefix), '{}/quick-entry'.format(collection_url_prefix), - request_method=('OPTIONS', 'POST')) - config.add_view(cls, attr='quick_entry', route_name='{}.quick_entry'.format(route_prefix), - permission='{}.edit'.format(permission_prefix), - renderer='json') + quick_entry = Service(name='{}.quick_entry'.format(route_prefix), + path='{}/quick-entry'.format(collection_url_prefix)) + quick_entry.add_view('POST', 'quick_entry', klass=cls, + permission='{}.edit'.format(permission_prefix)) + config.add_cornice_service(quick_entry) diff --git a/tailbone/api/batch/receiving.py b/tailbone/api/batch/receiving.py index 339fc43f..53d5f98a 100644 --- a/tailbone/api/batch/receiving.py +++ b/tailbone/api/batch/receiving.py @@ -31,6 +31,7 @@ import humanize from rattail.db import model from rattail.util import pretty_quantity +from cornice import Service from deform import widget as dfwidget from tailbone import forms @@ -143,26 +144,26 @@ class ReceivingBatchViews(APIBatchView): collection_url_prefix = cls.get_collection_url_prefix() object_url_prefix = cls.get_object_url_prefix() - # auto-receive - config.add_route('{}.auto_receive'.format(route_prefix), - '{}/{{uuid}}/auto-receive'.format(object_url_prefix)) - config.add_view(cls, attr='auto_receive', - route_name='{}.auto_receive'.format(route_prefix), - permission='{}.auto_receive'.format(permission_prefix), - renderer='json') + # auto_receive + auto_receive = Service(name='{}.auto_receive'.format(route_prefix), + path='{}/{{uuid}}/auto-receive'.format(object_url_prefix)) + auto_receive.add_view('GET', 'auto_receive', klass=cls, + permission='{}.auto_receive'.format(permission_prefix)) + config.add_cornice_service(auto_receive) - # mark receiving complete - config.add_route('{}.mark_receiving_complete'.format(route_prefix), '{}/{{uuid}}/mark-receiving-complete'.format(object_url_prefix)) - config.add_view(cls, attr='mark_receiving_complete', route_name='{}.mark_receiving_complete'.format(route_prefix), - permission='{}.edit'.format(permission_prefix), - renderer='json') + # mark_receiving_complete + mark_receiving_complete = Service(name='{}.mark_receiving_complete'.format(route_prefix), + path='{}/{{uuid}}/mark-receiving-complete'.format(object_url_prefix)) + mark_receiving_complete.add_view('POST', 'mark_receiving_complete', klass=cls, + permission='{}.edit'.format(permission_prefix)) + config.add_cornice_service(mark_receiving_complete) # eligible purchases - config.add_route('{}.eligible_purchases'.format(route_prefix), '{}/eligible-purchases'.format(collection_url_prefix), - request_method='GET') - config.add_view(cls, attr='eligible_purchases', route_name='{}.eligible_purchases'.format(route_prefix), - permission='{}.create'.format(permission_prefix), - renderer='json') + eligible_purchases = Service(name='{}.eligible_purchases'.format(route_prefix), + path='{}/eligible-purchases'.format(collection_url_prefix)) + eligible_purchases.add_view('GET', 'eligible_purchases', klass=cls, + permission='{}.create'.format(permission_prefix)) + config.add_cornice_service(eligible_purchases) class ReceivingBatchRowViews(APIBatchRowView): @@ -437,11 +438,11 @@ class ReceivingBatchRowViews(APIBatchRowView): object_url_prefix = cls.get_object_url_prefix() # receive (row) - config.add_route('{}.receive'.format(route_prefix), '{}/{{uuid}}/receive'.format(object_url_prefix), - request_method=('OPTIONS', 'POST')) - config.add_view(cls, attr='receive', route_name='{}.receive'.format(route_prefix), - permission='{}.edit_row'.format(permission_prefix), - renderer='json') + receive = Service(name='{}.receive'.format(route_prefix), + path='{}/{{uuid}}/receive'.format(object_url_prefix)) + receive.add_view('POST', 'receive', klass=cls, + permission='{}.edit_row'.format(permission_prefix)) + config.add_cornice_service(receive) def defaults(config, **kwargs): diff --git a/tailbone/webapi.py b/tailbone/webapi.py index 10c3460b..b623bd70 100644 --- a/tailbone/webapi.py +++ b/tailbone/webapi.py @@ -2,7 +2,7 @@ ################################################################################ # # Rattail -- Retail Software Framework -# Copyright © 2010-2021 Lance Edgar +# Copyright © 2010-2023 Lance Edgar # # This file is part of Rattail. # @@ -24,8 +24,9 @@ Tailbone Web API """ -from __future__ import unicode_literals, absolute_import +import simplejson +from cornice.renderer import CorniceRenderer from pyramid.config import Configurator from pyramid.authentication import SessionAuthenticationPolicy @@ -61,6 +62,12 @@ def make_pyramid_config(settings): pyramid_config.include('pyramid_tm') pyramid_config.include('cornice') + # use simplejson to serialize cornice view context; cf. + # https://cornice.readthedocs.io/en/latest/upgrading.html#x-to-5-x + # https://docs.pylonsproject.org/projects/pyramid/en/latest/narr/renderers.html + json_renderer = CorniceRenderer(serializer=simplejson.dumps) + pyramid_config.add_renderer('cornicejson', json_renderer) + # bring in the pyramid_retry logic, if available # TODO: pretty soon we can require this package, hopefully.. try: