From 7d42f18de373063fa1ed9e3cee7d20251b91a0df Mon Sep 17 00:00:00 2001 From: Jeremy Cline Date: Mar 16 2017 14:22:19 +0000 Subject: [PATCH 1/2] Start a Sphinx docs project This just adds a Sphinx project skeleton and sets up the ReStructuredText files for autogenerated documentation. Signed-off-by: Jeremy Cline --- diff --git a/.gitignore b/.gitignore index d7cbf6c..2f50910 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,4 @@ conf/settings.py /env*/ test_env .cache +docs/_build diff --git a/README.md b/README.md index 7e65ba4..0f1c4e9 100644 --- a/README.md +++ b/README.md @@ -40,3 +40,11 @@ To test against all supported versions of Python, you can use tox:: $ sudo dnf install python3-tox $ tox + +## Building the docs + +You can view the docs locally with:: + + $ cd docs + $ make html + $ firefox _build/html/index.html diff --git a/docs/Makefile b/docs/Makefile new file mode 100644 index 0000000..e57b761 --- /dev/null +++ b/docs/Makefile @@ -0,0 +1,20 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line. +SPHINXOPTS = +SPHINXBUILD = sphinx-build +SPHINXPROJ = WaiverDB +SOURCEDIR = . +BUILDDIR = _build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) \ No newline at end of file diff --git a/docs/api.rst b/docs/api.rst new file mode 100644 index 0000000..7e9eb45 --- /dev/null +++ b/docs/api.rst @@ -0,0 +1,15 @@ +============= +WaiverDB APIs +============= + +WavierDB offers a HTTP REST API. + + +.. _rest-api: + +REST API +======== + +.. autoflask:: waiverdb.app:create_app() + :undoc-static: + :order: path diff --git a/docs/conf.py b/docs/conf.py new file mode 100644 index 0000000..caf66ba --- /dev/null +++ b/docs/conf.py @@ -0,0 +1,191 @@ +# -*- coding: utf-8 -*- +# +# WaiverDB documentation build configuration file, created by +# sphinx-quickstart on Wed Mar 15 17:21:27 2017. +# +# This file is execfile()d with the current directory set to its +# containing dir. +# +# Note that not all possible configuration values are present in this +# autogenerated file. +# +# All configuration values have a default; values that are commented out +# serve to show the default. + +# If extensions (or modules to document with autodoc) are in another directory, +# add these directories to sys.path here. If the directory is relative to the +# documentation root, use os.path.abspath to make it absolute, like shown here. +# +import os +import sys + +# This will cause the Flask application to be created with development configs +os.environ['DEV'] = 'true' + +sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), '../'))) + + +# -- General configuration ------------------------------------------------ + +# If your documentation needs a minimal Sphinx version, state it here. +# +needs_sphinx = '1.3' + +# Add any Sphinx extension module names here, as strings. They can be +# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom +# ones. +extensions = [ + 'sphinx.ext.autodoc', + 'sphinx.ext.doctest', + 'sphinx.ext.intersphinx', + 'sphinx.ext.napoleon', + 'sphinx.ext.viewcode', + 'sphinxcontrib.autohttp.flask', +] + +# Add any paths that contain templates here, relative to this directory. +templates_path = ['_templates'] + +# The suffix(es) of source filenames. +# You can specify multiple suffix as a list of string: +# +# source_suffix = ['.rst', '.md'] +source_suffix = '.rst' + +# The master toctree document. +master_doc = 'index' + +# General information about the project. +project = u'WaiverDB' +copyright = u'2017, Red Hat, Inc. and others' +author = u'Red Hat, Inc. and others' + +# The version info for the project you're documenting, acts as replacement for +# |version| and |release|, also used in various other places throughout the +# built documents. +# +# The short X.Y version. +version = u'1.0' +# The full version, including alpha/beta/rc tags. +release = u'1.0.0' + +# The language for content autogenerated by Sphinx. Refer to documentation +# for a list of supported languages. +# +# This is also used if you do content translation via gettext catalogs. +# Usually you set "language" from the command line for these cases. +language = None + +# List of patterns, relative to source directory, that match files and +# directories to ignore when looking for source files. +# This patterns also effect to html_static_path and html_extra_path +exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store'] + +# The name of the Pygments (syntax highlighting) style to use. +pygments_style = 'sphinx' + +# If true, `todo` and `todoList` produce output, else they produce nothing. +todo_include_todos = False + + +# -- Options for HTML output ---------------------------------------------- + +# The theme to use for HTML and HTML Help pages. See the documentation for +# a list of builtin themes. +# +html_theme = 'alabaster' + +# Theme options are theme-specific and customize the look and feel of a theme +# further. For a list of options available for each theme, see the +# documentation. +# +# html_theme_options = {} + +# Add any paths that contain custom static files (such as style sheets) here, +# relative to this directory. They are copied after the builtin static files, +# so a file named "default.css" will overwrite the builtin "default.css". +html_static_path = ['_static'] + + +# -- Options for HTMLHelp output ------------------------------------------ + +# Output file base name for HTML help builder. +htmlhelp_basename = 'WaiverDBdoc' + + +# -- Options for LaTeX output --------------------------------------------- + +latex_elements = { + # The paper size ('letterpaper' or 'a4paper'). + # + # 'papersize': 'letterpaper', + + # The font size ('10pt', '11pt' or '12pt'). + # + # 'pointsize': '10pt', + + # Additional stuff for the LaTeX preamble. + # + # 'preamble': '', + + # Latex figure (float) alignment + # + # 'figure_align': 'htbp', +} + +# Grouping the document tree into LaTeX files. List of tuples +# (source start file, target name, title, +# author, documentclass [howto, manual, or own class]). +latex_documents = [ + (master_doc, 'WaiverDB.tex', u'WaiverDB Documentation', + u'Red Hat, Inc. and others', 'manual'), +] + + +# -- Options for manual page output --------------------------------------- + +# One entry per manual page. List of tuples +# (source start file, name, description, authors, manual section). +man_pages = [ + (master_doc, 'waiverdb', u'WaiverDB Documentation', + [author], 1) +] + + +# -- Options for Texinfo output ------------------------------------------- + +# Grouping the document tree into Texinfo files. List of tuples +# (source start file, target name, title, author, +# dir menu entry, description, category) +texinfo_documents = [ + (master_doc, 'WaiverDB', u'WaiverDB Documentation', + author, 'WaiverDB', 'One line description of project.', + 'Miscellaneous'), +] + + + +# -- Options for Epub output ---------------------------------------------- + +# Bibliographic Dublin Core info. +epub_title = project +epub_author = author +epub_publisher = author +epub_copyright = copyright + +# The unique identifier of the text. This can be a ISBN number +# or the project homepage. +# +# epub_identifier = '' + +# A unique identification for the text. +# +# epub_uid = '' + +# A list of files that should not be packed into the epub file. +epub_exclude_files = ['search.html'] + + + +# Example configuration for intersphinx: refer to the Python standard library. +intersphinx_mapping = {'https://docs.python.org/': None} diff --git a/docs/developer-guide.rst b/docs/developer-guide.rst new file mode 100644 index 0000000..6a91d19 --- /dev/null +++ b/docs/developer-guide.rst @@ -0,0 +1,48 @@ +================= +Development Guide +================= + +Quick development setup +======================= + +Set up a python virtualenv:: + + $ sudo dnf install python-virtualenv + $ virtualenv env_waiverdb + $ source env_resultsdb/bin/activate + $ pip install -r requirements.txt + +Install the project:: + + $ python setup.py develop + +Run the server:: + + $ DEV=true python runapp.py + +The server is now running at on `localhost port 5004`_. Consult the +:ref:`rest-api` for available API calls. All data is stored inside +``/var/tmp/waiverdb_db.sqlite``. + + +Adjusting configuration +======================= + +You can configure this app by copying ``conf/settings.py.example`` into +``conf/setting.py`` and adjusting values as you see fit. It overrides default +values in ``waiverdb/config.py``. + + +Running test suite +================== + +You can run this test suite with the following command:: + + $ py.test tests/ + +To test against all supported versions of Python, you can use tox:: + + $ sudo dnf install python3-tox + $ tox + +.. _localhost port 5004: http://localhost:5004 diff --git a/docs/index.rst b/docs/index.rst new file mode 100644 index 0000000..d10dd1a --- /dev/null +++ b/docs/index.rst @@ -0,0 +1,23 @@ +======== +WaiverDB +======== +WaiverDB is a companion service to `ResultsDB`_, for recording waivers against +test results. + +.. toctree:: + :maxdepth: 2 + :caption: Contents: + + developer-guide + api + + + +Indices and tables +================== + +* :ref:`genindex` +* :ref:`modindex` +* :ref:`search` + +.. _ResultsDB: https://pagure.io/taskotron/resultsdb diff --git a/requirements.txt b/requirements.txt index 0682ff2..33e8f36 100644 --- a/requirements.txt +++ b/requirements.txt @@ -9,3 +9,7 @@ kerberos >= 1.1.1 pytest >= 2.4.2 mock + +# Documentation requirements +sphinx +sphinxcontrib-httpdomain diff --git a/tox.ini b/tox.ini index 93c0243..d57b02a 100644 --- a/tox.ini +++ b/tox.ini @@ -1,5 +1,5 @@ [tox] -envlist = lint,py27,py34,py35,py36 +envlist = lint,py27,py34,py35,py36,docs # If the user is missing an interpreter, don't fail skip_missing_interpreters = True @@ -12,6 +12,18 @@ commands = find -name *.pyc -delete py.test tests/ +[testenv:docs] +changedir = docs +deps = + -rrequirements.txt +whitelist_externals = + mkdir + rm +commands= + mkdir -p _static + rm -rf _build/ + sphinx-build -W -b html -d {envtmpdir}/doctrees . _build/html + [testenv:lint] deps = flake8 > 3.0 From 8868e8155756a282a577db17ed9cf0e23973b5bc Mon Sep 17 00:00:00 2001 From: Jeremy Cline Date: Mar 17 2017 13:32:16 +0000 Subject: [PATCH 2/2] Add documentation for all the HTTP endpoints in the API Signed-off-by: Jeremy Cline --- diff --git a/waiverdb/api_v1.py b/waiverdb/api_v1.py index 09927ff..93528ad 100644 --- a/waiverdb/api_v1.py +++ b/waiverdb/api_v1.py @@ -47,6 +47,51 @@ RP['get_waivers'].add_argument('limit', default=10, type=int, location='args') class WaiversResource(Resource): @jsonp def get(self): + """ + Get waiver records. + + **Sample request**: + + .. sourcecode:: http + + GET /api/v1.0/waivers/ HTTP/1.1 + Host: localhost:5004 + User-Agent: curl/7.51.0 + Accept: application/json + + **Sample response**: + + .. sourcecode:: http + + HTTP/1.1 200 OK + Content-Type: application/json + Content-Length: 184 + Server: Werkzeug/0.12.1 Python/2.7.13 + Date: Thu, 16 Mar 2017 13:53:14 GMT + + { + "data": [], + "first": "http://localhost:5004/api/v1.0/waivers/?page=1", + "last": "http://localhost:5004/api/v1.0/waivers/?page=0", + "next": null, + "prev": null + } + + + :query int page: The page to get. + :query int limit: Limit the number of items returned. + :query int result_id: Filter the waivers by result ID. + :query string product_version: Filter the waivers by product version. + :query string username: Filter the waivers by username. + :query string since: A ISO 8601 formatted datetime (e.g. 2017-03-16T13:40:05+00:00) + to filter results by. Optionally provide a second ISO 8601 datetime separated + by a comma to retrieve a range (e.g. 2017-03-16T13:40:05+00:00, + 2017-03-16T13:40:15+00:00) + :query boolean include_obsolete: If true, obsolete waivers will be included. + :statuscode 200: If the query was valid and no problems were encountered. + Note that the response may still contain 0 waivers. + :statuscode 400: The request was malformed and could not be processed. + """ args = RP['get_waivers'].parse_args() query = Waiver.query.order_by(Waiver.timestamp.desc()) if args['result_id']: @@ -72,6 +117,57 @@ class WaiversResource(Resource): @jsonp @marshal_with(waiver_fields) def post(self): + """ + Create a new waiver. + + **Sample request**: + + .. sourcecode:: http + + POST /api/v1.0/waivers/ HTTP/1.1 + Host: localhost:5004 + Accept-Encoding: gzip, deflate + Accept: application/json + Connection: keep-alive + User-Agent: HTTPie/0.9.4 + Content-Type: application/json + Content-Length: 91 + + { + "result_id": "1", + "waived": "false", + "product_version": "Parrot", + "comment": "It's dead!" + } + + + + **Sample response**: + + .. sourcecode:: http + + HTTP/1.0 201 CREATED + Content-Length: 228 + Content-Type: application/json + Date: Thu, 16 Mar 2017 17:42:04 GMT + Server: Werkzeug/0.12.1 Python/2.7.13 + + { + "comment": "It's dead!", + "id": 15, + "product_version": "Parrot", + "result_id": "1", + "timestamp": "2017-03-16T17:42:04.209638", + "username": "http://jcline.id.fedoraproject.org/", + "waived": "false" + } + + :json int result_id: The result ID for the waiver. + :json boolean waived: Whether or not the result is waived. + :json string product_version: The product version string. + :json string comment: A comment explaining the waiver. + :statuscode 201: The waiver was successfully created. + """ user, headers = waiverdb.auth.get_user(request) args = RP['create_waiver'].parse_args() waiver = Waiver(args['result_id'], user, args['product_version'], args['waived'], @@ -85,6 +181,14 @@ class WaiverResource(Resource): @jsonp @marshal_with(waiver_fields) def get(self, waiver_id): + """ + Get a single waiver by waiver ID. + + :param int waiver_id: The waiver's database ID. + + :statuscode 200: The waiver was found and returned. + :statuscode 404: No waiver exists with that ID. + """ try: return Waiver.query.get_or_404(waiver_id) except: