├── tests
├── __init__.py
├── lib
│ ├── __init__.py
│ └── helpers.py
├── test_sanitize_doc.py
├── test_make_class.py
├── test_render_hompage.py
├── test_render_endpoint.py
├── test_model.py
├── test_nested_class.py
├── test_operation.py
├── test_nested_func.py
├── test_resource_lister.py
├── test_extract_swagger_path.py
├── test_swagger_registry.py
├── test_parse_docs.py
├── test_deduce_swagger_type_flat.py
├── test_swagger_endpoint_func.py
├── test_render_page.py
├── test_docs.py
├── test_extract_path_arguments.py
├── test_deduce_swagger_type.py
├── test_merge_parameter_list.py
├── test_get_current_registry.py
├── test_staticfiles.py
├── test_register_once.py
├── test_swagger_endpoint_class.py
├── fixtures_add_model.py
└── test_add_model.py
├── pytest.ini
├── .bandit.rc
├── flask_restful_swagger
├── static
│ ├── .gitignore
│ ├── images
│ │ ├── throbber.gif
│ │ ├── logo_small.png
│ │ ├── wordnik_api.png
│ │ ├── explorer_icons.png
│ │ └── pet_store_api.png
│ ├── lib
│ │ ├── jquery.slideto.min.js
│ │ ├── jquery.wiggle.min.js
│ │ ├── jquery.ba-bbq.min.js
│ │ ├── highlight.7.3.pack.js
│ │ ├── swagger-oauth.js
│ │ ├── shred
│ │ │ └── content.js
│ │ └── underscore-min.js
│ ├── o2c.html
│ ├── css
│ │ ├── highlight.default.css
│ │ └── hightlight.default.css
│ ├── endpoint.html
│ └── index.html
├── __init__.py
└── container_boot.sh
├── .dockerignore
├── MANIFEST.in
├── README
├── assets
├── requirements.txt
└── requirements-dev.txt
├── development
├── bash
│ ├── .bash_customize
│ ├── README.md
│ ├── .bash_profile
│ ├── .bashrc
│ └── .bash_git
├── Dockerfile
└── DEVELOPMENT.md
├── static
├── images
│ ├── throbber.gif
│ ├── logo_small.png
│ ├── wordnik_api.png
│ └── pet_store_api.png
├── resources.json
├── js
│ ├── jquery.slideto.min.js
│ ├── jquery.wiggle.min.js
│ ├── jquery.ba-bbq.min.js
│ ├── highlight.7.3.pack.js
│ ├── shred
│ │ └── content.js
│ └── underscore-min.js
├── docs.html
└── css
│ └── hightlight.default.css
├── development.env
├── container
├── MANIFEST
├── Pipfile
├── scripts
├── releases
│ └── Makefile
├── dev
├── hooks
│ └── pre-commit
├── common
│ ├── wheel.sh
│ ├── upload.sh
│ └── common.sh
└── commander.sh
├── .coveragerc
├── TODO
├── .isort.cfg
├── .flake8
├── CONTRIBUTING.md
├── docker-compose.yml
├── setup.py
├── LICENSE
├── .github
└── workflows
│ ├── docker27.yml
│ └── docker37.yml
├── examples
├── inheritance.py
├── basic.py
└── blueprints.py
├── .gitignore
└── CODE_OF_CONDUCT.md
/tests/__init__.py:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/pytest.ini:
--------------------------------------------------------------------------------
1 | [pytest]
2 |
--------------------------------------------------------------------------------
/tests/lib/__init__.py:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/.bandit.rc:
--------------------------------------------------------------------------------
1 | skips: ['B101']
2 |
--------------------------------------------------------------------------------
/flask_restful_swagger/static/.gitignore:
--------------------------------------------------------------------------------
1 | !lib
2 |
--------------------------------------------------------------------------------
/.dockerignore:
--------------------------------------------------------------------------------
1 | .tox
2 | .pytest_cache
3 | tests/__pycache__
4 | __pycache__
5 | *.pyc
6 |
--------------------------------------------------------------------------------
/MANIFEST.in:
--------------------------------------------------------------------------------
1 | include README*
2 | recursive-include flask_restful_swagger/static *
3 |
--------------------------------------------------------------------------------
/README:
--------------------------------------------------------------------------------
1 | Please see documentation here: https://github.com/rantav/flask-restful-swagger
--------------------------------------------------------------------------------
/flask_restful_swagger/__init__.py:
--------------------------------------------------------------------------------
1 | registry = {"models": {}}
2 |
3 | api_spec_static = ""
4 |
--------------------------------------------------------------------------------
/assets/requirements.txt:
--------------------------------------------------------------------------------
1 | # Application Requirements
2 | Jinja2>=2.10.1,<3.0.0
3 | Flask-RESTful>=0.3.6
4 |
--------------------------------------------------------------------------------
/development/bash/.bash_customize:
--------------------------------------------------------------------------------
1 | # Customize Your Path Here
2 | export PATH="/home/user/.local/bin:${PATH}"
3 |
--------------------------------------------------------------------------------
/static/images/throbber.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/static/images/throbber.gif
--------------------------------------------------------------------------------
/development.env:
--------------------------------------------------------------------------------
1 | PYTHONPATH=/app/flask_restful_swagger/
2 | GIT_HOOKS=1
3 | GIT_HOOKS_PROTECTED_BRANCHES="^(master)"
4 |
--------------------------------------------------------------------------------
/static/images/logo_small.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/static/images/logo_small.png
--------------------------------------------------------------------------------
/static/images/wordnik_api.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/static/images/wordnik_api.png
--------------------------------------------------------------------------------
/static/images/pet_store_api.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/static/images/pet_store_api.png
--------------------------------------------------------------------------------
/container:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | echo "Entering Development Container ..."
4 | docker-compose exec flask_restful_swagger bash
5 |
--------------------------------------------------------------------------------
/MANIFEST:
--------------------------------------------------------------------------------
1 | # file GENERATED by distutils, do NOT edit
2 | setup.py
3 | flask_restful_swagger/__init__.py
4 | flask_restful_swagger/swagger.py
5 |
--------------------------------------------------------------------------------
/flask_restful_swagger/container_boot.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | pushd "flask_restful_swagger" || exit 127
4 | while true; do sleep 1; done
5 |
--------------------------------------------------------------------------------
/development/bash/README.md:
--------------------------------------------------------------------------------
1 | # Bash Environment
2 |
3 | Run the `dev setup` command to re-symlink `.bash_customize` into the container's BASH environment.
4 |
--------------------------------------------------------------------------------
/flask_restful_swagger/static/images/throbber.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/flask_restful_swagger/static/images/throbber.gif
--------------------------------------------------------------------------------
/flask_restful_swagger/static/images/logo_small.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/flask_restful_swagger/static/images/logo_small.png
--------------------------------------------------------------------------------
/flask_restful_swagger/static/images/wordnik_api.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/flask_restful_swagger/static/images/wordnik_api.png
--------------------------------------------------------------------------------
/flask_restful_swagger/static/images/explorer_icons.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/flask_restful_swagger/static/images/explorer_icons.png
--------------------------------------------------------------------------------
/flask_restful_swagger/static/images/pet_store_api.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/rantav/flask-restful-swagger/HEAD/flask_restful_swagger/static/images/pet_store_api.png
--------------------------------------------------------------------------------
/Pipfile:
--------------------------------------------------------------------------------
1 | [[source]]
2 | name = "pypi"
3 | url = "https://pypi.org/simple"
4 | verify_ssl = true
5 |
6 | [dev-packages]
7 |
8 | [packages]
9 |
10 | [requires]
11 | python_version = "3.6"
12 |
--------------------------------------------------------------------------------
/scripts/releases/Makefile:
--------------------------------------------------------------------------------
1 | release:
2 | git tag -a `python setup.py --version` -m "Releasing to https://pypi.python.org/pypi/flask-restful-swagger/"
3 | git push --tags
4 | python setup.py sdist upload
5 |
--------------------------------------------------------------------------------
/.coveragerc:
--------------------------------------------------------------------------------
1 | [run]
2 | branch = True
3 | omit = tests/*
4 | setup.py
5 | source = .
6 |
7 | [report]
8 | precision = 1
9 | show_missing = True
10 | ignore_errors = True
11 | exclude_lines =
12 | no cover
13 |
--------------------------------------------------------------------------------
/static/resources.json:
--------------------------------------------------------------------------------
1 | {
2 | "apiVersion": "0.1",
3 | "swaggerVersion": "1.2",
4 | "apis": [
5 | {
6 | "path": "/../../api/spec.json",
7 | "description": "My TODO service"
8 | }
9 | ]
10 | }
11 |
--------------------------------------------------------------------------------
/development/bash/.bash_profile:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | # Do Not Modify This File, It's Intended To Be Updated From Time to TIme
4 | # INSTEAD: add additional functionality though the .bash_customize file.
5 |
6 | source "${HOME}/.bashrc"
7 |
--------------------------------------------------------------------------------
/TODO:
--------------------------------------------------------------------------------
1 | Syntactic sugar and smartness around dataType. Support the following:
2 | - 'Model'
3 | - Model
4 | - 'List[Model]'
5 | - ['Model']
6 | - [Model]
7 |
8 | Support for HTML pages
9 |
10 | Create a pip package and publish it
11 |
--------------------------------------------------------------------------------
/.isort.cfg:
--------------------------------------------------------------------------------
1 | [settings]
2 | line_length=80
3 | indent=' '
4 | multi_line_output=3
5 | length_sort=0
6 | default_section=FIRSTPARTY
7 | no_lines_before=LOCALFOLDER
8 | sections=FUTURE,STDLIB,THIRDPARTY,FIRSTPARTY,LOCALFOLDER
9 | include_trailing_comma=true
10 |
--------------------------------------------------------------------------------
/.flake8:
--------------------------------------------------------------------------------
1 | [flake8]
2 |
3 | ignore = E203, W503, W504, W605
4 | max-line-length = 79
5 | max-complexity = 12
6 |
7 | exclude =
8 | .git
9 | dist
10 | build
11 | flask_restful_swagger.egg-info
12 | htmlcov
13 | scripts
14 | static
15 |
16 |
--------------------------------------------------------------------------------
/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | # Contribution Guide
2 |
3 | [Code of Conduct](./CODE_OF_CONDUCT.md)
4 |
5 | [Contribution Guide](./development/DEVELOPMENT.md)
6 |
7 | # Contacts
8 |
9 | - @rantav
10 | - @niall-byrne
11 |
12 | __This project is part of the [Cloudify Cosmo project](https://github.com/CloudifySource/)__
13 |
--------------------------------------------------------------------------------
/assets/requirements-dev.txt:
--------------------------------------------------------------------------------
1 | # Development Requirements
2 | bandit>=1.6.2,<1.7.0
3 | bs4>=0.0.1,<0.1.0
4 | commitizen>=0.9.11,<1.17.0
5 | isort>=4.3.21,<4.4.0
6 | flake8>=3.7.9,<3.8.0s
7 | mock>=3.0.5,<3.1.0
8 | pytest>=4.6.9,<5.3.0
9 | pytest-cov>=2.8.1,<2.9.0
10 | safety>=1.8.5,<1.9.0
11 | wheel>=0.34.1,<0.35.0
12 | yapf>=0.28.0,<0.29.0
13 |
--------------------------------------------------------------------------------
/static/js/jquery.slideto.min.js:
--------------------------------------------------------------------------------
1 | (function(b){b.fn.slideto=function(a){a=b.extend({slide_duration:"slow",highlight_duration:3E3,highlight:true,highlight_color:"#FFFF99"},a);return this.each(function(){obj=b(this);b("body").animate({scrollTop:obj.offset().top},a.slide_duration,function(){a.highlight&&b.ui.version&&obj.effect("highlight",{color:a.highlight_color},a.highlight_duration)})})}})(jQuery);
2 |
--------------------------------------------------------------------------------
/flask_restful_swagger/static/lib/jquery.slideto.min.js:
--------------------------------------------------------------------------------
1 | (function(b){b.fn.slideto=function(a){a=b.extend({slide_duration:"slow",highlight_duration:3E3,highlight:true,highlight_color:"#FFFF99"},a);return this.each(function(){obj=b(this);b("body").animate({scrollTop:obj.offset().top},a.slide_duration,function(){a.highlight&&b.ui.version&&obj.effect("highlight",{color:a.highlight_color},a.highlight_duration)})})}})(jQuery);
2 |
--------------------------------------------------------------------------------
/flask_restful_swagger/static/o2c.html:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/docker-compose.yml:
--------------------------------------------------------------------------------
1 | version: "3"
2 |
3 | services:
4 | flask_restful_swagger:
5 | build:
6 | context: .
7 | dockerfile: development/Dockerfile
8 | ports:
9 | - "127.0.0.1:5000:5000"
10 | env_file:
11 | - development.env
12 | volumes:
13 | - ${HOME}/.ssh:/home/user/.ssh
14 | - ${HOME}/.gitconfig:/home/user/.gitconfig
15 | - ${HOME}/.gitconfig_global:/home/user/.gitconfig_global
16 | - ./:/app
17 | command: >
18 | ./flask_restful_swagger/container_boot.sh
19 |
--------------------------------------------------------------------------------
/tests/test_sanitize_doc.py:
--------------------------------------------------------------------------------
1 | import pytest
2 |
3 | from flask_restful_swagger import swagger
4 |
5 |
6 | @pytest.mark.parametrize(
7 | "test_input,expected",
8 | [
9 | ("Hey\n", "Hey
"),
10 | ("\n/n\n/n\n", "
/n
/n
"),
11 | ("No Change", "No Change"),
12 | ],
13 | )
14 | def test_string_sanitize_doc(test_input, expected):
15 | assert swagger._sanitize_doc(test_input) == expected
16 |
17 |
18 | def test_none_sanitize_doc():
19 | assert swagger._sanitize_doc(None) is None
20 |
--------------------------------------------------------------------------------
/tests/test_make_class.py:
--------------------------------------------------------------------------------
1 | from flask_restful_swagger import swagger
2 |
3 |
4 | def test_make_class_with_input_class():
5 | class TestClass:
6 | pass
7 |
8 | assert swagger.make_class(TestClass) == TestClass
9 |
10 |
11 | def test_make_class_with_input_instance():
12 | class TestClass:
13 | pass
14 |
15 | test_class = TestClass()
16 |
17 | assert swagger.make_class(test_class) == TestClass
18 |
19 |
20 | def test_make_class_with_none():
21 | assert isinstance(None, swagger.make_class(None))
22 |
--------------------------------------------------------------------------------
/tests/test_render_hompage.py:
--------------------------------------------------------------------------------
1 | from flask_restful_swagger import swagger
2 |
3 | try:
4 | from unittest.mock import patch
5 | except ImportError:
6 | from mock import patch
7 |
8 |
9 | @patch("flask_restful_swagger.swagger.render_page")
10 | @patch("flask.wrappers.Response")
11 | def test_render_hompage_func(response_obj, mock_render_page):
12 | resource_list_url = "resource_list_url"
13 | swagger.render_homepage(resource_list_url)
14 | mock_render_page.assert_called_once_with(
15 | "index.html", {"resource_list_url": resource_list_url}
16 | )
17 |
--------------------------------------------------------------------------------
/tests/test_render_endpoint.py:
--------------------------------------------------------------------------------
1 | import unittest
2 |
3 | from flask_restful_swagger import swagger
4 |
5 | try:
6 | from unittest.mock import patch
7 | except ImportError:
8 | from mock import patch
9 |
10 |
11 | class Endpoint:
12 | pass
13 |
14 |
15 | class TestRenderEndpoint(unittest.TestCase):
16 | def test_render_endpoint(self):
17 | endpoint = Endpoint()
18 | with patch(
19 | "flask_restful_swagger.swagger.render_page"
20 | ) as mock_render_page:
21 | swagger.render_endpoint(endpoint)
22 | mock_render_page.assert_called_with(
23 | "endpoint.html", endpoint.__dict__
24 | )
25 |
--------------------------------------------------------------------------------
/scripts/dev:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | _script()
4 | {
5 |
6 | shopt -s expand_aliases
7 | _script_commands=$(dev shortlist)
8 |
9 | local cur
10 | COMPREPLY=()
11 | cur="${COMP_WORDS[COMP_CWORD]}"
12 |
13 | while IFS='' read -r line; do COMPREPLY+=("$line"); done < <(compgen -W "${_script_commands}" -- "${cur}")
14 | return 0
15 |
16 | }
17 |
18 | complete -o nospace -F _script dev
19 |
20 | dev_identifier() {
21 | Cyan='\033[36m' # Cyan
22 | BRed='\033[31m' # Red
23 | BGreen='\033[32m' # Green
24 | NC="\033[0m" # Color Reset
25 | echo -en "(${BGreen}flask_restful_swagger${NC})"
26 | }
27 |
28 | alias dev='$(git rev-parse --show-toplevel)/scripts/commander.sh'
29 | PROMPT_COMMAND="dev_identifier; $PROMPT_COMMAND"
30 |
--------------------------------------------------------------------------------
/development/bash/.bashrc:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | # Do Not Modify This File, It's Intended To Be Updated From Time to TIme
4 | # INSTEAD: add additional functionality though the .bash_customize file.
5 |
6 | PS1='${git_branch}\n${debian_chroot:+($debian_chroot)}\[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\w\[\033[00m\]\$ '
7 |
8 | # Terminal Colors
9 | if [[ -x /usr/bin/dircolors ]]; then
10 | test -r ~/.dircolors && eval "$(dircolors -b ~/.dircolors)" || eval "$(dircolors -b)"
11 | alias ls='ls --color=auto'
12 | alias grep='grep --color=auto'
13 | alias fgrep='fgrep --color=auto'
14 | alias egrep='egrep --color=auto'
15 | fi
16 |
17 | set -e
18 | source /app/scripts/dev
19 | source /home/user/.bash_git
20 | source /home/user/.bash_customize
21 | set +e
22 |
--------------------------------------------------------------------------------
/static/js/jquery.wiggle.min.js:
--------------------------------------------------------------------------------
1 | /*
2 | jQuery Wiggle
3 | Author: WonderGroup, Jordan Thomas
4 | URL: http://labs.wondergroup.com/demos/mini-ui/index.html
5 | License: MIT (http://en.wikipedia.org/wiki/MIT_License)
6 | */
7 | jQuery.fn.wiggle=function(o){var d={speed:50,wiggles:3,travel:5,callback:null};var o=jQuery.extend(d,o);return this.each(function(){var cache=this;var wrap=jQuery(this).wrap('
{{description if description != None}}
38 |{{operation.summary if operation.summary != None}}
45 |Implementation notes: {{operation.notes}}
65 | {% endif %} 66 | {% if operation.responseClass %} 67 |Response Class: {{operation.responseClass}}
68 | {% endif %} 69 |