diff --git a/tests/test_cornice.py b/tests/test_cornice.py
new file mode 100644
index 0000000..19c93f1
--- /dev/null
+++ b/tests/test_cornice.py
@@ -0,0 +1,79 @@
+import unittest
+import json
+
+import webtest
+
+from cornice import Service
+from pyramid.config import Configurator
+
+from wsme.types import text, Base
+from wsmeext.cornice import signature
+
+
+class User(Base):
+ id = int
+ name = text
+
+users = Service(name='users', path='/users')
+
+
+@users.get()
+@signature([User])
+def users_get():
+ return [User(id=1, name='first')]
+
+
+@users.post()
+@signature(User, body=User)
+def users_create(data):
+ data.id = 2
+ return data
+
+
+def make_app():
+ config = Configurator()
+ config.include("cornice")
+ config.include("wsmeext.cornice")
+ config.scan("test_cornice")
+ return config.make_wsgi_app()
+
+
+class WSMECorniceTestCase(unittest.TestCase):
+ def setUp(self):
+ self.app = webtest.TestApp(make_app())
+
+ def test_get_json_list(self):
+ resp = self.app.get('/users')
+ self.assertEquals(
+ resp.body,
+ '[{"id": 1, "name": "first"}]'
+ )
+
+ def test_get_xml_list(self):
+ resp = self.app.get('/users', headers={"Accept": "text/xml"})
+ self.assertEquals(
+ resp.body,
+ '- 1first
'
+ )
+
+ def test_post_json_data(self):
+ data = json.dumps({"name": "new"})
+ resp = self.app.post(
+ '/users', data,
+ headers={"Content-Type": "application/json"}
+ )
+ self.assertEquals(
+ resp.body,
+ '{"id": 2, "name": "new"}'
+ )
+
+ def test_post_xml_data(self):
+ data = 'new'
+ resp = self.app.post(
+ '/users', data,
+ headers={"Content-Type": "text/xml"}
+ )
+ self.assertEquals(
+ resp.body,
+ '2new'
+ )
diff --git a/tox-tmpl.ini b/tox-tmpl.ini
index c348e73..4a8627e 100644
--- a/tox-tmpl.ini
+++ b/tox-tmpl.ini
@@ -1,6 +1,6 @@
# content of: tox.ini , put in same dir as setup.py
[tox]
-envlist = py27,py27-nolxml,py32,py32-nolxml,pypy,py25-simplejson,sphinxext,tg11,tg15,pecan,flask,coverage
+envlist = py27,py27-nolxml,py32,py32-nolxml,pypy,py25-simplejson,sphinxext,tg11,tg15,pecan,flask,cornice,coverage
[common]
testtools=
@@ -187,7 +187,18 @@ deps=
commands=
{envbindir}/nosetests tests/test_flask.py --with-xunit --xunit-file nosetests-{envname}.xml --verbose --with-coverage --cover-package wsme {posargs}
{envbindir}/coverage xml -o coverage-{envname}.xml wsme/*.py wsmeext/flask.py
-
+
+[testenv:cornice]
+basepython=python2.7
+deps=
+ d2to1
+ nose
+ webtest
+ coverage
+ cornice
+commands=
+ {envbindir}/nosetests tests/test_cornice.py --with-xunit --xunit-file nosetests-{envname}.xml --verbose --with-coverage --cover-package wsmeext {posargs}
+ {envbindir}/coverage xml -o coverage-{envname}.xml wsme/*.py wsmeext/cornice.py
[testenv:coverage]
basepython=python
diff --git a/tox.ini b/tox.ini
index fe9b46e..6c5b99b 100644
--- a/tox.ini
+++ b/tox.ini
@@ -1,5 +1,5 @@
[tox]
-envlist = py27,py27-nolxml,py32,py32-nolxml,pypy,py25-simplejson,sphinxext,tg11,tg15,pecan,flask,coverage
+envlist = py27,py27-nolxml,py32,py32-nolxml,pypy,py25-simplejson,sphinxext,tg11,tg15,pecan,flask,cornice,coverage
[common]
testtools =
@@ -105,6 +105,18 @@ commands =
{envbindir}/nosetests tests/test_flask.py --with-xunit --xunit-file nosetests-{envname}.xml --verbose --with-coverage --cover-package wsme {posargs}
{envbindir}/coverage xml -o coverage-{envname}.xml wsme/*.py wsmeext/flask.py
+[testenv:cornice]
+basepython = python2.7
+deps =
+ d2to1
+ nose
+ webtest
+ coverage
+ cornice
+commands =
+ {envbindir}/nosetests tests/test_cornice.py --with-xunit --xunit-file nosetests-{envname}.xml --verbose --with-coverage --cover-package wsmeext {posargs}
+ {envbindir}/coverage xml -o coverage-{envname}.xml wsme/*.py wsmeext/cornice.py
+
[testenv:coverage]
basepython = python
deps =
diff --git a/wsme/rest/xml.py b/wsme/rest/xml.py
index 2d1b585..01ffaed 100644
--- a/wsme/rest/xml.py
+++ b/wsme/rest/xml.py
@@ -61,7 +61,7 @@ def toxml(datatype, key, value):
else:
if wsme.types.isusertype(datatype):
return toxml(datatype.basetype,
- key, datatype.tobasetype(value))
+ key, datatype.tobasetype(value))
elif wsme.types.iscomplex(datatype):
for attrdef in datatype._wsme_attributes:
attrvalue = getattr(value, attrdef.key)
@@ -95,8 +95,7 @@ def fromxml(datatype, element):
if element.get('nil', False):
return None
if wsme.types.isusertype(datatype):
- return datatype.frombasetype(
- fromxml(datatype.basetype, element))
+ return datatype.frombasetype(fromxml(datatype.basetype, element))
if wsme.types.iscomplex(datatype):
obj = datatype()
for attrdef in datatype._wsme_attributes:
@@ -243,7 +242,7 @@ def parse(s, datatypes, bodyarg):
tree = et.fromstring(s)
if bodyarg:
name = list(datatypes.keys())[0]
- return fromxml(datatypes[name], tree)
+ return {name: fromxml(datatypes[name], tree)}
else:
kw = {}
extra_args = []
diff --git a/wsmeext/cornice.py b/wsmeext/cornice.py
index 16e4efd..e03ed5e 100644
--- a/wsmeext/cornice.py
+++ b/wsmeext/cornice.py
@@ -15,17 +15,13 @@ And use it::
return Message(text='Hello %s' % who)
"""
from __future__ import absolute_import
-import json
-
-import xml.etree.ElementTree as et
import wsme
-import wsme.protocols
-from wsme.protocols import restjson
-from wsme.protocols import restxml
+from wsme.rest import json as restjson
+from wsme.rest import xml as restxml
import functools
-from wsme.protocols.commons import (
+from wsme.rest.args import (
args_from_params, args_from_body, combine_args
)
@@ -37,11 +33,7 @@ class WSMEJsonRenderer(object):
def __call__(self, data, context):
response = context['request'].response
response.content_type = 'application/json'
- data = restjson.tojson(
- data['datatype'],
- data['result']
- )
- return json.dumps(data)
+ return restjson.encode_result(data['result'], data['datatype'])
class WSMEXmlRenderer(object):
@@ -51,34 +43,40 @@ class WSMEXmlRenderer(object):
def __call__(self, data, context):
response = context['request'].response
response.content_type = 'text/xml'
- data = restxml.toxml(
- data['datatype'],
- 'result',
- data['result']
- )
- return et.tostring(data)
+ return restxml.encode_result(data['result'], data['datatype'])
+
+
+def get_outputformat(request):
+ df = None
+ if 'Accept' in request.headers:
+ if 'application/json' in request.headers['Accept']:
+ df = 'json'
+ elif 'text/xml' in request.headers['Accept']:
+ df = 'xml'
+ if df is None and 'Content-Type' in request.headers:
+ if 'application/json' in request.headers['Content-Type']:
+ df = 'json'
+ elif 'text/xml' in request.headers['Content-Type']:
+ df = 'xml'
+ return df if df else 'json'
def signature(*args, **kwargs):
- sig = wsme.sig(*args, **kwargs)
+ sig = wsme.signature(*args, **kwargs)
def decorate(f):
sig(f)
funcdef = wsme.api.FunctionDefinition.get(f)
+ funcdef.resolve_types(wsme.types.registry)
@functools.wraps(f)
def callfunction(request):
args, kwargs = combine_args(
funcdef,
- args_from_params(funcdef, request.params),
- args_from_body(funcdef, request.body, request.content_type)
+ (args_from_params(funcdef, request.params),
+ args_from_body(funcdef, request.body, request.content_type))
)
- if 'application/json' in request.headers['Accept']:
- request.override_renderer = 'wsmejson'
- elif 'text/xml' in request.headers['Accept']:
- request.override_renderer = 'wsmexml'
- else:
- request.override_renderer = 'wsmejson'
+ request.override_renderer = 'wsme' + get_outputformat(request)
return {
'datatype': funcdef.return_type,
'result': f(*args, **kwargs)