Commit 9fdea465 authored by Jacek Furmankiewicz's avatar Jacek Furmankiewicz

automatic parsing of incoming JSON and XML

parent cd0e0bc8
Using step definitions from: '../steps'
@content_types
Feature: Content types
CorePost should be able to
correctly parse/generate
JSON/XML/YAML based on content types
@json
Scenario Outline: Parse incoming JSON data
Given 'home_resource' is running
When as user 'None:None' I <method> 'http://127.0.0.1:8080/post/json' with JSON
"""
{"test":"test2"}
"""
Then I expect HTTP code <code>
And I expect JSON content
"""
{"test":"test2"}
"""
Examples:
| method | code |
| POST | 201 |
| PUT | 200 |
@xml
Scenario Outline: Parse incoming XML data
Given 'home_resource' is running
When as user 'None:None' I <method> 'http://127.0.0.1:8080/post/xml' with XML
"""
<root><test>TEST</test><test2>Yo</test2></root>
"""
Then I expect HTTP code <code>
# ElementTree object
And I expect content contains '<Element 'root' at'
Examples:
| method | code |
| POST | 201 |
| PUT | 200 |
\ No newline at end of file
...@@ -6,6 +6,7 @@ Server tests ...@@ -6,6 +6,7 @@ Server tests
from corepost.web import CorePost, route from corepost.web import CorePost, route
from corepost.enums import Http from corepost.enums import Http
from twisted.internet import defer from twisted.internet import defer
import json
class HomeApp(CorePost): class HomeApp(CorePost):
...@@ -39,6 +40,14 @@ class HomeApp(CorePost): ...@@ -39,6 +40,14 @@ class HomeApp(CorePost):
@route("/delete",Http.DELETE) @route("/delete",Http.DELETE)
def test_delete(self,request,**kwargs): def test_delete(self,request,**kwargs):
return "%s" % kwargs return "%s" % kwargs
@route("/post/json",(Http.POST,Http.PUT))
def test_json(self,request,**kwargs):
return "%s" % json.dumps(request.json)
@route("/post/xml",(Http.POST,Http.PUT))
def test_xml(self,request,**kwargs):
return "%s" % request.xml
def run_app_home(): def run_app_home():
app = HomeApp() app = HomeApp()
......
...@@ -13,6 +13,8 @@ from corepost.test.arguments import run_app_arguments ...@@ -13,6 +13,8 @@ from corepost.test.arguments import run_app_arguments
apps = {'home_resource' : run_app_home,'multi_resource':run_app_multi,'arguments':run_app_arguments} apps = {'home_resource' : run_app_home,'multi_resource':run_app_multi,'arguments':run_app_arguments}
NULL = 'None'
def as_dict(parameters): def as_dict(parameters):
dict_val = {} dict_val = {}
for pair in parameters.split('&') : for pair in parameters.split('&') :
...@@ -74,6 +76,11 @@ def when_as_user_i_send_post_put_xml_json_to_url(payload,user,password,method,ur ...@@ -74,6 +76,11 @@ def when_as_user_i_send_post_put_xml_json_to_url(payload,user,password,method,ur
scc.http_headers['Content-type'] = 'application/json' if request_type == "JSON" else 'text/xml' scc.http_headers['Content-type'] = 'application/json' if request_type == "JSON" else 'text/xml'
scc.response, scc.content = h.request(url, method, payload, headers = scc.http_headers) scc.response, scc.content = h.request(url, method, payload, headers = scc.http_headers)
@When("I prepare HTTP header '(.*)' = '(.*)'")
def when_i_define_http_header_with_value(header,value):
if header != NULL:
scc.http_headers[header] = value
################################## ##################################
# THEN # THEN
################################## ##################################
...@@ -95,4 +102,11 @@ def then_check_http_header_matches(header,regex): ...@@ -95,4 +102,11 @@ def then_check_http_header_matches(header,regex):
assert_true(re.search(regex,scc.response[header.lower()], re.X | re.I) != None, assert_true(re.search(regex,scc.response[header.lower()], re.X | re.I) != None,
"the regex %s does not match the response\n%s" % (regex, scc.response[header.lower()])) "the regex %s does not match the response\n%s" % (regex, scc.response[header.lower()]))
@Then("^I expect JSON content\s*$")
def then_i_expect_json(content):
expected_json = json.loads(content)
expected_json_sorted = json.dumps(expected_json,sort_keys=True,indent=4)
received_json = json.loads(scc.content)
received_json_sorted = json.dumps(received_json,sort_keys=True,indent=4)
assert_equals(expected_json_sorted,received_json_sorted,"Expected JSON\n%s\n*** actual ****\n%s" % (expected_json_sorted,received_json_sorted))
...@@ -197,7 +197,8 @@ class CorePost(Resource): ...@@ -197,7 +197,8 @@ class CorePost(Resource):
# handler for weird Twisted logic where PUT does not get form params # handler for weird Twisted logic where PUT does not get form params
# see: http://twistedmatrix.com/pipermail/twisted-web/2007-March/003338.html # see: http://twistedmatrix.com/pipermail/twisted-web/2007-March/003338.html
requestargs = request.args requestargs = request.args
if request.method == Http.PUT: if request.method == Http.PUT and HttpHeader.CONTENT_TYPE in request.received_headers.keys() \
and request.received_headers[HttpHeader.CONTENT_TYPE] == MediaType.APPLICATION_FORM_URLENCODED:
requestargs = parse_qs(request.content.read(), 1) requestargs = parse_qs(request.content.read(), 1)
#merge form args #merge form args
...@@ -242,14 +243,12 @@ class CorePost(Resource): ...@@ -242,14 +243,12 @@ class CorePost(Resource):
def __parseRequestData(self,request): def __parseRequestData(self,request):
'''Automatically parses JSON,XML,YAML if present''' '''Automatically parses JSON,XML,YAML if present'''
if HttpHeader.CONTENT_TYPE in request.headers.keys(): if HttpHeader.CONTENT_TYPE in request.received_headers.keys():
type = request.headers["content-type"] type = request.received_headers["content-type"]
if type == MediaType.APPLICATION_JSON: if type == MediaType.APPLICATION_JSON:
request.json = json.loads(request.content.read()) request.json = json.loads(request.content.read())
pass
elif type in (MediaType.APPLICATION_XML,MediaType.TEXT_XML): elif type in (MediaType.APPLICATION_XML,MediaType.TEXT_XML):
request.xml = ElementTree.XML(request.content.read()) request.xml = ElementTree.XML(request.content.read())
pass
elif type == MediaType.TEXT_YAML: elif type == MediaType.TEXT_YAML:
#TODO: parse YAML #TODO: parse YAML
pass pass
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment