예제 #1
0
    def put(self, resource_id):
        """Return the JSON representation of a new resource created or updated
        through an HTTP PUT call.
        If resource_id is not provided, it is assumed the primary key field is
        included and a totally new resource is created. Otherwise, the existing
        resource referred to by *resource_id* is updated with the provided JSON
        data. This method is idempotent.
        :returns: ``HTTP 201`` if a new resource is created
        :returns: ``HTTP 200`` if a resource is updated
        :returns: ``HTTP 400`` if the request is malformed or missing data
        """
        resource = self.__model__.query.get(resource_id)
        if resource:
            error_message = is_valid_method(self.__model__, resource)
            if error_message:
                raise BadRequestException(error_message)
            resource.update(request.json)
            db.session().merge(resource)
            db.session().commit()
            return jsonify(resource)

        resource = self.__model__(**request.json)  # pylint: disable=not-callable
        error_message = is_valid_method(self.__model__, resource)
        if error_message:
            raise BadRequestException(error_message)
        db.session().add(resource)
        db.session().commit()
        return self._created_response(resource)
예제 #2
0
    def get(self, resource_id=None):
        """Return an HTTP response object resulting from an HTTP GET call.
        If *resource_id* is provided, return just the single resource.
        Otherwise, return the full collection.
        :param resource_id: The value of the resource's primary key
        """
        if request.path.endswith('meta'):
            return self._meta()

        if resource_id is None:
            error_message = is_valid_method(self.__model__)
            if error_message:
                raise BadRequestException(error_message)

            if 'export' in request.args:
                return self._export(self._all_resources())

            return flask.jsonify(
                {self.__json_collection_name__: self._all_resources()})
        else:
            resource = self._resource(resource_id)
            error_message = is_valid_method(self.__model__, resource)
            if error_message:
                raise BadRequestException(error_message)
            return jsonify(resource)
예제 #3
0
 def decorated(instance, *args, **kwargs):
     """The decorator function."""
     data = request.get_json(force=True, silent=True)
     if not data:
         raise BadRequestException('No data received from request')
     for key in data:
         if key not in (instance.__model__.required() +
                        instance.__model__.optional()):
             raise BadRequestException('Unknown field [{}]'.format(key))
     missing = set(instance.__model__.required()) - set(data)
     if missing:
         message = 'The following required fields are missing: ' + ', '.join(
             missing)
         raise BadRequestException(message)
     return func(instance, *args, **kwargs)
예제 #4
0
 def patch(self, resource_id):
     """Return an HTTP response object resulting from an HTTP PATCH call.
     :returns: ``HTTP 200`` if the resource already exists
     :returns: ``HTTP 400`` if the request is malformed
     :returns: ``HTTP 404`` if the resource is not found
     :param resource_id: The value of the resource's primary key
     """
     resource = self._resource(resource_id)
     error_message = is_valid_method(self.__model__, resource)
     if error_message:
         raise BadRequestException(error_message)
     if not request.json:
         raise BadRequestException('No JSON data received')
     resource.update(request.json)
     db.session().merge(resource)
     db.session().commit()
     return jsonify(resource)
예제 #5
0
 def delete(self, resource_id):
     """Return an HTTP response object resulting from a HTTP DELETE call.
     :param resource_id: The value of the resource's primary key
     """
     resource = self._resource(resource_id)
     error_message = is_valid_method(self.__model__, resource)
     if error_message:
         raise BadRequestException(error_message)
     db.session().delete(resource)
     db.session().commit()
     return self._no_content_response()
예제 #6
0
    def post(self):
        """Return the JSON representation of a new resource created through
        an HTTP POST call.
        :returns: ``HTTP 201`` if a resource is properly created
        :returns: ``HTTP 204`` if the resource already exists
        :returns: ``HTTP 400`` if the request is malformed or missing data
        """
        resource = self.__model__.query.filter_by(**request.json).first()
        if resource:
            error_message = is_valid_method(self.__model__, resource)
            if error_message:
                raise BadRequestException(error_message)
            return self._no_content_response()

        resource = self.__model__(**request.json)  # pylint: disable=not-callable
        error_message = is_valid_method(self.__model__, resource)
        if error_message:
            raise BadRequestException(error_message)
        db.session().add(resource)
        db.session().commit()
        return self._created_response(resource)
예제 #7
0
 def _all_resources(self):
     """Return the complete collection of resources as a list of
     dictionaries.
     :rtype: :class:`app_autorest.model.Model`
     """
     queryset = self.__model__.query
     args = {
         k: v
         for (k, v) in request.args.items() if k not in ('page', 'export')
     }
     if args:
         filters = []
         order = []
         limit = None
         for key, value in args.items():
             if value.startswith('%'):
                 filters.append(
                     getattr(self.__model__, key).like(str(value),
                                                       escape='/'))
             elif key == 'sort':
                 direction = desc if value.startswith('-') else asc
                 order.append(
                     direction(getattr(self.__model__, value.lstrip('-'))))
             elif key == 'limit':
                 limit = value
             elif hasattr(self.__model__, key):
                 filters.append(getattr(self.__model__, key) == value)
             else:
                 raise BadRequestException('Invalid field [{}]'.format(key))
             queryset = queryset.filter(*filters).order_by(
                 *order).limit(limit)
     if 'page' in request.args:
         resources = queryset.paginate(int(request.args['page'])).items
     else:
         resources = queryset.all()
     return [r.to_dict() for r in resources]