Open jpbufe3 opened 9 years ago
Hi !
Until now, I tried to stick to the upstream flask-restful which doesn't support this.
flask-restplus provides a workaround with the model
kwarg for the @api.doc
decorator:
from flask import Flask
from flask.ext.restplus import Api, Resource, fields
from nltk.tokenize import word_tokenize
import os, nltk
app = Flask(__name__)
api = Api(app, version='1.0', title='NLP Tools API',
description='A set of easy to use NLP tools powered by NLTK.',
)
ns = api.namespace('nlptools/api/v1', description='NLP operations')
parser = api.parser()
parser.add_argument('text', type=str, required=True, help='The text to be processed', location='json')
@ns.route('/tokenize')
@api.doc(responses={400: 'Invalid request'})
class Tokenizer(Resource):
@api.doc(parser=parser, description='Tokenizes the input text into a list of strings.')
@api.doc(model=[str])
def post(self):
args = parser.parse_args()
return word_tokenize(args['text'])
if __name__ == '__main__':
app.run(host=os.getenv('VCAP_APP_HOST', '127.0.0.1'), port=int(os.getenv('VCAP_APP_PORT', '5000')), debug=True)
It should do the job. Just let me know if I can close the issue.
Thanks for the response.
I added in the change, and it fixed the method so that the REST call ran properly!
127.0.0.1 - - [08/May/2015 17:43:00] "POST /nlptools/api/v1/tokenize HTTP/1.1" 200 -
However, the swagger doc generation now fails.
127.0.0.1 - - [08/May/2015 17:32:21] "GET /swagger.json HTTP/1.1" 500 -
Traceback (most recent call last):
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1836, in __call__
return self.wsgi_app(environ, start_response)
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1820, in wsgi_app
response = self.make_response(self.handle_exception(e))
File "/usr/local/lib/python3.4/site-packages/flask_restful/__init__.py", line 265, in error_router
return original_handler(e)
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1403, in handle_exception
reraise(exc_type, exc_value, tb)
File "/usr/local/lib/python3.4/site-packages/flask/_compat.py", line 32, in reraise
raise value.with_traceback(tb)
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1817, in wsgi_app
response = self.full_dispatch_request()
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1477, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/usr/local/lib/python3.4/site-packages/flask_restful/__init__.py", line 265, in error_router
return original_handler(e)
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1381, in handle_user_exception
reraise(exc_type, exc_value, tb)
File "/usr/local/lib/python3.4/site-packages/flask/_compat.py", line 32, in reraise
raise value.with_traceback(tb)
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1475, in full_dispatch_request
rv = self.dispatch_request()
File "/usr/local/lib/python3.4/site-packages/flask/app.py", line 1461, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "/usr/local/lib/python3.4/site-packages/flask_restful/__init__.py", line 450, in wrapper
return self.make_response(data, code, headers=headers)
File "/usr/local/lib/python3.4/site-packages/flask_restful/__init__.py", line 474, in make_response
resp = self.representations[mediatype](data, *args, **kwargs)
File "/usr/local/lib/python3.4/site-packages/flask_restful/representations/json.py", line 24, in output_json
dumped = dumps(data, **local_settings)
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/__init__.py", line 237, in dumps
**kw).encode(obj)
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 194, in encode
chunks = list(chunks)
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 422, in _iterencode
yield from _iterencode_dict(o, _current_indent_level)
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 396, in _iterencode_dict
yield from chunks
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 396, in _iterencode_dict
yield from chunks
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 396, in _iterencode_dict
yield from chunks
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 396, in _iterencode_dict
yield from chunks
File "/usr/local/Cellar/python3/3.4.3/Frameworks/Python.framework/Versions/3.4/lib/python3.4/json/encoder.py", line 345, in _iterencode_dict
items = sorted(dct.items(), key=lambda kv: kv[0])
TypeError: unorderable types: str() < int()
Any thoughts?
I have a very simple method that is generating a list of strings and returning it. Currently the only way that the swagger docs will show the response type is if the method has @api.marshal_with() or @api.marshal_list_with(). However, neither of these methods seem to work appropriately with simple objects. Below is an example:
Running this with a REST client with a json body of {"text":"this is a test sentence to tokenize."} returns the following error:
I have also tried
return json.dumps(word_tokenize(args['text']))
and@api.marshal_with(fields.List(fields.String))
with the same result in all four cases. Is there an alternative way to represent the response object? Is there a way to appropriate marshal basic fields?Thanks.