Test simple ReST conversion to JSON
Added initial tests to cover simple httpdomain conversion to JSON.
This commit is contained in:
parent
bfd623cc0a
commit
b95d3176d7
|
@ -18,9 +18,14 @@
|
|||
"""
|
||||
|
||||
"""
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import logging
|
||||
|
||||
from docutils import writers, nodes
|
||||
import docutils.core
|
||||
import docutils.utils
|
||||
from docutils import frontend
|
||||
from docutils.parsers.rst import directives
|
||||
from docutils.parsers.rst import Directive
|
||||
|
||||
|
@ -110,6 +115,12 @@ class JSONTranslator(nodes.GenericNodeVisitor):
|
|||
"""Default node depart method."""
|
||||
self.node_stack.pop()
|
||||
|
||||
def visit_system_message(self, node):
|
||||
pass
|
||||
|
||||
def depart_system_message(self, node):
|
||||
pass
|
||||
|
||||
def visit_Text(self, node):
|
||||
self.text += node.astext()
|
||||
|
||||
|
@ -123,6 +134,12 @@ class JSONTranslator(nodes.GenericNodeVisitor):
|
|||
def depart_literal(self, node):
|
||||
pass
|
||||
|
||||
def visit_literal_block(self, node):
|
||||
self.text += '```\n'
|
||||
|
||||
def depart_literal_block(self, node):
|
||||
self.text += '\n```\n'
|
||||
|
||||
def visit_bullet_list(self, node):
|
||||
self.bullet_stack.append('*')
|
||||
|
||||
|
@ -466,7 +483,7 @@ class Resource(Directive):
|
|||
|
||||
method = None
|
||||
|
||||
required_arguments = 0
|
||||
required_arguments = 1
|
||||
optional_arguments = 0
|
||||
has_content = True
|
||||
final_argument_whitespace = True
|
||||
|
@ -547,12 +564,16 @@ class Resource(Directive):
|
|||
self.state.nested_parse(self.content, self.content_offset, node)
|
||||
fields = self.transform_fields()
|
||||
|
||||
# This is the first line of the definition.
|
||||
url = self.arguments[0]
|
||||
node.insert(0, resource_url(url, url))
|
||||
|
||||
if not node.children:
|
||||
return [node]
|
||||
|
||||
if node[0].tagname == 'system_message':
|
||||
logger.error(node[0].astext())
|
||||
node.remove(node[0])
|
||||
# This is the first line of the definition.
|
||||
url = node[0].astext()
|
||||
node[0].replace_self(resource_url(url, url))
|
||||
|
||||
# Method
|
||||
node.insert(1, resource_method(self.method, self.method))
|
||||
|
@ -663,3 +684,16 @@ class SwaggerTag(Directive):
|
|||
|
||||
|
||||
directives.register_directive('swagger:tag', SwaggerTag)
|
||||
|
||||
|
||||
class error_writer(object):
|
||||
|
||||
def write(self, line):
|
||||
logger.warning(line.strip())
|
||||
|
||||
|
||||
def publish_string(string):
|
||||
settings_overrides = {'warning_stream': error_writer()}
|
||||
return docutils.core.publish_string(
|
||||
string, writer=JSONWriter(),
|
||||
settings_overrides=settings_overrides)
|
||||
|
|
|
@ -9,6 +9,7 @@ app = {
|
|||
'root': 'fairy_slipper.controllers.root.RootController',
|
||||
'modules': ['fairy_slipper'],
|
||||
'static_root': '%(confdir)s/../../public',
|
||||
'api_doc': '%(confdir)s/../../api_doc',
|
||||
'template_path': '%(confdir)s/../templates',
|
||||
'debug': True,
|
||||
'errors': {
|
||||
|
|
|
@ -27,7 +27,7 @@ Tests for `fairy_slipper` module.
|
|||
from fairy_slipper.tests import base
|
||||
|
||||
|
||||
class TestFairy_slipper(base.TestCase):
|
||||
class TestFairySlipper(base.TestCase):
|
||||
|
||||
def test_something(self):
|
||||
pass
|
||||
|
|
|
@ -29,11 +29,7 @@ class TestRootController(FunctionalTest):
|
|||
|
||||
def test_search(self):
|
||||
response = self.app.post('/', params={'q': 'RestController'})
|
||||
assert response.status_int == 302
|
||||
assert response.headers['Location'] == (
|
||||
'http://pecan.readthedocs.org/en/latest/search.html'
|
||||
'?q=RestController'
|
||||
)
|
||||
assert response.status_int == 200
|
||||
|
||||
def test_get_not_found(self):
|
||||
response = self.app.get('/a/bogus/url', expect_errors=True)
|
||||
|
|
|
@ -0,0 +1,263 @@
|
|||
# Copyright (c) 2015 Russell Sim <russell.sim@gmail.com>
|
||||
#
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
# implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from unittest import TestCase
|
||||
import docutils.core
|
||||
|
||||
from fairy_slipper import rest
|
||||
from fairy_slipper.rest import JSONWriter
|
||||
|
||||
|
||||
def minimal_method_json(consumes=[],
|
||||
description='',
|
||||
method='get',
|
||||
parameters=[],
|
||||
produces=[],
|
||||
responses={},
|
||||
summary='',
|
||||
tags=[],
|
||||
title=''):
|
||||
return dict(consumes=consumes,
|
||||
description=description,
|
||||
method=method,
|
||||
parameters=parameters,
|
||||
produces=produces,
|
||||
responses=responses,
|
||||
summary=summary,
|
||||
tags=tags,
|
||||
title=title)
|
||||
|
||||
|
||||
class TestReSTMethod(TestCase):
|
||||
|
||||
def test_no_path(self):
|
||||
rst = """
|
||||
.. http:get::
|
||||
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths': {}, 'tags': []}
|
||||
|
||||
def test_path_with_body(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
body
|
||||
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path': [
|
||||
minimal_method_json(description='body\n\n')]},
|
||||
'tags': []}
|
||||
|
||||
def test_minimal(self):
|
||||
rst = """
|
||||
.. http:%s:: /path
|
||||
|
||||
"""
|
||||
for method in ['get', 'post', 'put', 'patch',
|
||||
'options', 'head', 'delete', 'copy']:
|
||||
json = docutils.core.publish_string(
|
||||
rst % method, writer=JSONWriter())
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path': [
|
||||
minimal_method_json(method=method)]},
|
||||
'tags': []}
|
||||
|
||||
def test_body_literal(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
literal block::
|
||||
|
||||
banana
|
||||
1
|
||||
2
|
||||
3
|
||||
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(description='''literal block:
|
||||
|
||||
```
|
||||
banana
|
||||
1
|
||||
2
|
||||
3
|
||||
```
|
||||
''')]},
|
||||
'tags': []}
|
||||
|
||||
def test_synopsis(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
:synopsis: Some description of the operation
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
summary='Some description of the operation')]},
|
||||
'tags': []}
|
||||
|
||||
def test_title(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
:title: Path Thing
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(title='Path Thing')]},
|
||||
'tags': []}
|
||||
|
||||
def test_method_tags(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:tag: cool-tag
|
||||
:tag: cool-tag1
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
tags=['cool-tag', 'cool-tag1'])]},
|
||||
'tags': []}
|
||||
|
||||
def test_produces(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:produces: application/json
|
||||
:produces: text/plain
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
produces=['application/json',
|
||||
'text/plain'])]},
|
||||
'tags': []}
|
||||
|
||||
def test_accepts(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:accepts: application/json
|
||||
:accepts: text/plain
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
consumes=['application/json',
|
||||
'text/plain'])]},
|
||||
'tags': []}
|
||||
|
||||
def test_parameter(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:parameter thing: A parameter something.
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
parameters=[{
|
||||
'description': u'A parameter something.',
|
||||
'in': 'path',
|
||||
'name': u'thing',
|
||||
'required': True,
|
||||
'type': 'string'}])]},
|
||||
'tags': []}
|
||||
|
||||
def test_response_example(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:responseexample 200: example.json
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
responses={'200':
|
||||
{'description': '',
|
||||
'examples':
|
||||
{'application/json':
|
||||
{'$ref':
|
||||
'example.json'}}}})]},
|
||||
'tags': []}
|
||||
|
||||
def test_statuscode(self):
|
||||
rst = """
|
||||
.. http:get:: /path
|
||||
|
||||
:statuscode 200: Success! Yeah!
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
|
||||
assert json == {'paths':
|
||||
{'/path':
|
||||
[minimal_method_json(
|
||||
responses={'200':
|
||||
{'description': 'Success! Yeah!'}})]},
|
||||
'tags': []}
|
||||
|
||||
|
||||
class TestReSTTag(TestCase):
|
||||
|
||||
def test_synopsis(self):
|
||||
rst = """
|
||||
.. swagger:tag:: my-tag
|
||||
:synopsis: Interesting things!
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
assert json == {'paths': {},
|
||||
'tags': [{'name': 'my-tag',
|
||||
'description': '',
|
||||
'summary': 'Interesting things!'}]}
|
||||
|
||||
def test_description(self):
|
||||
rst = """
|
||||
.. swagger:tag:: my-tag
|
||||
|
||||
body
|
||||
"""
|
||||
json = rest.publish_string(rst)
|
||||
assert json == {'paths': {},
|
||||
'tags': [{'name': 'my-tag',
|
||||
'description': 'body\n\n',
|
||||
'summary': ''}]}
|
|
@ -13,3 +13,4 @@ oslotest>=1.2.0 # Apache-2.0
|
|||
testrepository>=0.0.18
|
||||
testscenarios>=0.4
|
||||
testtools>=0.9.36,!=1.2.0
|
||||
pytest
|
||||
|
|
Loading…
Reference in New Issue