diff --git a/.github/workflows/docker-publish.yml b/.github/workflows/docker-publish.yml index de3346a..37cebf4 100644 --- a/.github/workflows/docker-publish.yml +++ b/.github/workflows/docker-publish.yml @@ -7,6 +7,8 @@ on: - main paths-ignore: - '**.md' + - 'docs' + - 'docsrc' pull_request: # run tests only for pull requests to `main` @@ -14,6 +16,8 @@ on: - main paths-ignore: - '**.md' + - 'docs' + - 'docsrc' env: # Docker image diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 98e0dfd..a7f4359 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -22,7 +22,27 @@ When you're done, submit a pull request and for one of the maintainers to check ### Tests -Package-level unit tests are written in pytest and we ask that you run them via [tox][1] in a [poetry][2] virtual environment. To run all package-level unit tests, which require [tox][1] and [poetry][2] installed and in your `$PATH`, issue: `tox`. Tox will pass positional arguments to pytest, e.g. `tox -- --pdb -xk 'test_can_send_message'` +#### GitHub Actions + +GitHub Actions CI will automatically run package tests on pull requests and pushes to `main` branch. Therefore, the recommended method of testing is to simply create a new pull request. + +#### Testing Locally + +Package-level unit tests are written in pytest and we ask that you run them via [tox][1] in a [poetry][2] virtual environment if running locally. To run all package-level unit tests, which require [tox][1] and [poetry][2] installed and in your `$PATH`, issue: `tox`. Tox will pass positional arguments to pytest, e.g. `tox -- --pdb -xk 'test_can_send_message'` + +Note that some tests require a valid [Loggly customer token](https://documentation.solarwinds.com/en/success_center/loggly/content/admin/customer-token-authentication-token.html) set in the environment. The token is already included in the GitHub Secrets for this repository, so these tests will run on Actions CI. To run these tests locally, specify the environment variable when calling `tox`: + +```bash +_TEST_LOGGLY_CUSTOMER_TOKEN='f5cc76a7-XXXX-XXXX-XXXX-3864b42c1215' tox +``` + +If you do not have a valid customer token, simply skip these tests by skipping the tests marked as `loggly_auth`: + +```bash +tox -- -k 'not loggly_auth' +``` + +#### Docker Tests This repository also maintains a [base Docker image](./Dockerfile) for Tapis Actors. To run unit tests and check CLI usage in the Docker environment, issue: @@ -34,7 +54,9 @@ make pytest-docker make test-cli-docker ``` -To run all tests mentioned above, issue `make tests`. +Note that poetry and Docker are required to run build the image using make. In addition, the user must have a [valid Tapis/Agave credentials cache](https://tapis-cli.readthedocs.io/en/latest/usage/apim.html) at `$HOME/.agave`, since it is used for pytests marked `tapis_auth` and [mounted in the container](https://github.com/TACC-Cloud/python-reactors/blob/97d071416c586d0333a49f5b949580d7f74ff37c/Makefile#L45-L45). + +To run all tests mentioned thus far, issue `make tests`. ### Documentation diff --git a/Makefile b/Makefile index e96d977..11e28e5 100644 --- a/Makefile +++ b/Makefile @@ -2,7 +2,7 @@ PYTHON ?= python3 PREF_SHELL ?= bash GITREF=$(shell git rev-parse --short HEAD) GITREF_FULL=$(shell git rev-parse HEAD) -PYTEST_OPTS ?= -s -vvv +PYTEST_OPTS ?= -k 'not loggly_auth' PYTEST_DIR ?= tests DOT_ENV ?= ./.env @@ -21,9 +21,13 @@ IMAGE_DOCKER ?= $(IMAGE_ORG)/$(IMAGE_NAME):$(IMAGE_TAG) #################################### # Build Docker image #################################### -.PHONY: image +.PHONY: image build -image: Dockerfile +build: + rm -rf dist + poetry build + +image: Dockerfile build docker build -t $(IMAGE_DOCKER) -f $< . #################################### @@ -31,19 +35,19 @@ image: Dockerfile #################################### .PHONY: pytest-docker test-cli-docker tests shell clean -tests: test-cli-docker pytest-docker pytest-native +tests: pytest-native test-cli-docker pytest-docker pytest-native tox: - tox -- + tox -- $(PYTEST_OPTS) $(PYTEST_DIR) pytest-docker: clean image docker run --rm -t \ -v ${HOME}/.agave:/root/.agave \ -v ${PWD}/tests/data/abacoschemas:/schemas:ro \ -v ${PWD}/tests/data/message.jsonschema:/message.jsonschema:ro \ - -v ${PWD}/$(PYTEST_DIR):/tmp/$(PKG)-$(VERSION)/$(PYTEST_DIR) \ + -v ${PWD}/$(PYTEST_DIR):/mnt/ephemeral-01/$(PYTEST_DIR) \ $(IMAGE_DOCKER) \ - bash -c "(python3 -m pip install -q pytest && python3 -m pytest $(PYTEST_OPTS) /tmp/$(PKG)-$(VERSION)/$(PYTEST_DIR))" + bash -c "(python3 -m pip install -q pytest polling2 && python3 -m pytest $(PYTEST_OPTS) /mnt/ephemeral-01/$(PYTEST_DIR))" test-cli-docker: clean image docker run --rm -t \ @@ -68,3 +72,6 @@ clean: docs: cd docsrc && make html + +livehtml: + cd docsrc && make livehtml diff --git a/docs/.buildinfo b/docs/.buildinfo index 78a79ba..8ce2d44 100644 --- a/docs/.buildinfo +++ b/docs/.buildinfo @@ -1,4 +1,4 @@ # Sphinx build info version 1 # This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done. -config: 69e3b12298528aa9ff69b6802fed3003 +config: fb289cb2d8dadc13e7de412f7312a5d2 tags: 645f666f9bcd5a90fca523b33c5a78b7 diff --git a/docs/_sources/api-ref/reactors.aliases.agavedb.rst.txt b/docs/_sources/api-ref/reactors.aliases.agavedb.rst.txt deleted file mode 100644 index 71f303d..0000000 --- a/docs/_sources/api-ref/reactors.aliases.agavedb.rst.txt +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb package -================================ - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb.tests - -Submodules ----------- - -reactors.aliases.agavedb.keyval module --------------------------------------- - -.. automodule:: reactors.aliases.agavedb.keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.uniqueid module ----------------------------------------- - -.. automodule:: reactors.aliases.agavedb.uniqueid - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb - :members: - :undoc-members: - :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt b/docs/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt deleted file mode 100644 index 6bf5367..0000000 --- a/docs/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb.tests package -====================================== - -Submodules ----------- - -reactors.aliases.agavedb.tests.agavefixtures module ---------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.agavefixtures - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.test\_keyval module --------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.test_keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.testdata module ----------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.testdata - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb.tests - :members: - :undoc-members: - :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.aliases.rst.txt b/docs/_sources/api-ref/reactors.aliases.rst.txt deleted file mode 100644 index db80925..0000000 --- a/docs/_sources/api-ref/reactors.aliases.rst.txt +++ /dev/null @@ -1,29 +0,0 @@ -reactors.aliases package -======================== - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb - -Submodules ----------- - -reactors.aliases.store module ------------------------------ - -.. automodule:: reactors.aliases.store - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases - :members: - :undoc-members: - :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.cli.rst.txt b/docs/_sources/api-ref/reactors.cli.rst.txt new file mode 100644 index 0000000..b669b8c --- /dev/null +++ b/docs/_sources/api-ref/reactors.cli.rst.txt @@ -0,0 +1,29 @@ +reactors.cli package +==================== + +Submodules +---------- + +reactors.cli.run module +----------------------- + +.. automodule:: reactors.cli.run + :members: + :undoc-members: + :show-inheritance: + +reactors.cli.usage module +------------------------- + +.. automodule:: reactors.cli.usage + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.cli + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.logtypes.rst.txt b/docs/_sources/api-ref/reactors.logtypes.rst.txt index e9aaf9f..d00a94f 100644 --- a/docs/_sources/api-ref/reactors.logtypes.rst.txt +++ b/docs/_sources/api-ref/reactors.logtypes.rst.txt @@ -4,18 +4,26 @@ reactors.logtypes package Submodules ---------- -reactors.logtypes.logstash module ---------------------------------- +reactors.logtypes.loggly module +------------------------------- -.. automodule:: reactors.logtypes.logstash +.. automodule:: reactors.logtypes.loggly :members: :undoc-members: :show-inheritance: -reactors.logtypes.logstash\_asyncio module ------------------------------------------- +reactors.logtypes.loggly\_futures\_session module +------------------------------------------------- -.. automodule:: reactors.logtypes.logstash_asyncio +.. automodule:: reactors.logtypes.loggly_futures_session + :members: + :undoc-members: + :show-inheritance: + +reactors.logtypes.logstash module +--------------------------------- + +.. automodule:: reactors.logtypes.logstash :members: :undoc-members: :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.rst.txt b/docs/_sources/api-ref/reactors.rst.txt index aba558d..f5c0b2e 100644 --- a/docs/_sources/api-ref/reactors.rst.txt +++ b/docs/_sources/api-ref/reactors.rst.txt @@ -8,48 +8,18 @@ Subpackages :maxdepth: 4 reactors.agaveutils - reactors.aliases + reactors.cli reactors.logtypes + reactors.runtime + reactors.validation Submodules ---------- -reactors.jsonmessages module ----------------------------- +reactors.config module +---------------------- -.. automodule:: reactors.jsonmessages - :members: - :undoc-members: - :show-inheritance: - -reactors.process module ------------------------ - -.. automodule:: reactors.process - :members: - :undoc-members: - :show-inheritance: - -reactors.runtime module ------------------------ - -.. automodule:: reactors.runtime - :members: - :undoc-members: - :show-inheritance: - -reactors.storage module ------------------------ - -.. automodule:: reactors.storage - :members: - :undoc-members: - :show-inheritance: - -reactors.uniqueid module ------------------------- - -.. automodule:: reactors.uniqueid +.. automodule:: reactors.config :members: :undoc-members: :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.runtime.rst.txt b/docs/_sources/api-ref/reactors.runtime.rst.txt new file mode 100644 index 0000000..853efa1 --- /dev/null +++ b/docs/_sources/api-ref/reactors.runtime.rst.txt @@ -0,0 +1,69 @@ +reactors.runtime package +======================== + +Submodules +---------- + +reactors.runtime.abaco module +----------------------------- + +.. automodule:: reactors.runtime.abaco + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.base module +---------------------------- + +.. automodule:: reactors.runtime.base + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.messaging module +--------------------------------- + +.. automodule:: reactors.runtime.messaging + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.reactor module +------------------------------- + +.. automodule:: reactors.runtime.reactor + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.sessions module +-------------------------------- + +.. automodule:: reactors.runtime.sessions + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.validating module +---------------------------------- + +.. automodule:: reactors.runtime.validating + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.webhooks module +-------------------------------- + +.. automodule:: reactors.runtime.webhooks + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.runtime + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/_sources/api-ref/reactors.validation.rst.txt b/docs/_sources/api-ref/reactors.validation.rst.txt new file mode 100644 index 0000000..0225729 --- /dev/null +++ b/docs/_sources/api-ref/reactors.validation.rst.txt @@ -0,0 +1,45 @@ +reactors.validation package +=========================== + +Submodules +---------- + +reactors.validation.binary module +--------------------------------- + +.. automodule:: reactors.validation.binary + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.context module +---------------------------------- + +.. automodule:: reactors.validation.context + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.jsondoc module +---------------------------------- + +.. automodule:: reactors.validation.jsondoc + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.message module +---------------------------------- + +.. automodule:: reactors.validation.message + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.validation + :members: + :undoc-members: + :show-inheritance: diff --git a/docs/_static/basic.css b/docs/_static/basic.css index 24bc73e..912859b 100644 --- a/docs/_static/basic.css +++ b/docs/_static/basic.css @@ -4,7 +4,7 @@ * * Sphinx stylesheet -- basic theme. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ @@ -130,7 +130,7 @@ ul.search li a { font-weight: bold; } -ul.search li div.context { +ul.search li p.context { color: #888; margin: 2px 0 0 30px; text-align: left; @@ -277,25 +277,25 @@ p.rubric { font-weight: bold; } -img.align-left, .figure.align-left, object.align-left { +img.align-left, figure.align-left, .figure.align-left, object.align-left { clear: left; float: left; margin-right: 1em; } -img.align-right, .figure.align-right, object.align-right { +img.align-right, figure.align-right, .figure.align-right, object.align-right { clear: right; float: right; margin-left: 1em; } -img.align-center, .figure.align-center, object.align-center { +img.align-center, figure.align-center, .figure.align-center, object.align-center { display: block; margin-left: auto; margin-right: auto; } -img.align-default, .figure.align-default { +img.align-default, figure.align-default, .figure.align-default { display: block; margin-left: auto; margin-right: auto; @@ -319,7 +319,8 @@ img.align-default, .figure.align-default { /* -- sidebars -------------------------------------------------------------- */ -div.sidebar { +div.sidebar, +aside.sidebar { margin: 0 0 0.5em 1em; border: 1px solid #ddb; padding: 7px; @@ -377,12 +378,14 @@ div.body p.centered { /* -- content of sidebars/topics/admonitions -------------------------------- */ div.sidebar > :last-child, +aside.sidebar > :last-child, div.topic > :last-child, div.admonition > :last-child { margin-bottom: 0; } div.sidebar::after, +aside.sidebar::after, div.topic::after, div.admonition::after, blockquote::after { @@ -455,20 +458,22 @@ td > :last-child { /* -- figures --------------------------------------------------------------- */ -div.figure { +div.figure, figure { margin: 0.5em; padding: 0.5em; } -div.figure p.caption { +div.figure p.caption, figcaption { padding: 0.3em; } -div.figure p.caption span.caption-number { +div.figure p.caption span.caption-number, +figcaption span.caption-number { font-style: italic; } -div.figure p.caption span.caption-text { +div.figure p.caption span.caption-text, +figcaption span.caption-text { } /* -- field list styles ----------------------------------------------------- */ @@ -503,6 +508,63 @@ table.hlist td { vertical-align: top; } +/* -- object description styles --------------------------------------------- */ + +.sig { + font-family: 'Consolas', 'Menlo', 'DejaVu Sans Mono', 'Bitstream Vera Sans Mono', monospace; +} + +.sig-name, code.descname { + background-color: transparent; + font-weight: bold; +} + +.sig-name { + font-size: 1.1em; +} + +code.descname { + font-size: 1.2em; +} + +.sig-prename, code.descclassname { + background-color: transparent; +} + +.optional { + font-size: 1.3em; +} + +.sig-paren { + font-size: larger; +} + +.sig-param.n { + font-style: italic; +} + +/* C++ specific styling */ + +.sig-inline.c-texpr, +.sig-inline.cpp-texpr { + font-family: unset; +} + +.sig.c .k, .sig.c .kt, +.sig.cpp .k, .sig.cpp .kt { + color: #0033B3; +} + +.sig.c .m, +.sig.cpp .m { + color: #1750EB; +} + +.sig.c .s, .sig.c .sc, +.sig.cpp .s, .sig.cpp .sc { + color: #067D17; +} + /* -- other body styles ----------------------------------------------------- */ @@ -629,14 +691,6 @@ dl.glossary dt { font-size: 1.1em; } -.optional { - font-size: 1.3em; -} - -.sig-paren { - font-size: larger; -} - .versionmodified { font-style: italic; } @@ -764,8 +818,13 @@ div.code-block-caption code { } table.highlighttable td.linenos, -div.doctest > div.highlight span.gp { /* gp: Generic.Prompt */ - user-select: none; +span.linenos, +div.highlight span.gp { /* gp: Generic.Prompt */ + user-select: none; + -webkit-user-select: text; /* Safari fallback only */ + -webkit-user-select: none; /* Chrome/Safari */ + -moz-user-select: none; /* Firefox */ + -ms-user-select: none; /* IE10+ */ } div.code-block-caption span.caption-number { @@ -780,16 +839,6 @@ div.literal-block-wrapper { margin: 1em 0; } -code.descname { - background-color: transparent; - font-weight: bold; - font-size: 1.2em; -} - -code.descclassname { - background-color: transparent; -} - code.xref, a code { background-color: transparent; font-weight: bold; diff --git a/docs/_static/classic.css b/docs/_static/classic.css deleted file mode 100644 index cceb67a..0000000 --- a/docs/_static/classic.css +++ /dev/null @@ -1,266 +0,0 @@ -/* - * classic.css_t - * ~~~~~~~~~~~~~ - * - * Sphinx stylesheet -- classic theme. - * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ - -@import url("basic.css"); - -/* -- page layout ----------------------------------------------------------- */ - -html { - /* CSS hack for macOS's scrollbar (see #1125) */ - background-color: #FFFFFF; -} - -body { - font-family: sans-serif; - font-size: 100%; - background-color: #11303d; - color: #000; - margin: 0; - padding: 0; -} - -div.document { - background-color: #1c4e63; -} - -div.documentwrapper { - float: left; - width: 100%; -} - -div.bodywrapper { - margin: 0 0 0 230px; -} - -div.body { - background-color: #ffffff; - color: #000000; - padding: 0 20px 30px 20px; -} - -div.footer { - color: #ffffff; - width: 100%; - padding: 9px 0 9px 0; - text-align: center; - font-size: 75%; -} - -div.footer a { - color: #ffffff; - text-decoration: underline; -} - -div.related { - background-color: #133f52; - line-height: 30px; - color: #ffffff; -} - -div.related a { - color: #ffffff; -} - -div.sphinxsidebar { -} - -div.sphinxsidebar h3 { - font-family: 'Trebuchet MS', sans-serif; - color: #ffffff; - font-size: 1.4em; - font-weight: normal; - margin: 0; - padding: 0; -} - -div.sphinxsidebar h3 a { - color: #ffffff; -} - -div.sphinxsidebar h4 { - font-family: 'Trebuchet MS', sans-serif; - color: #ffffff; - font-size: 1.3em; - font-weight: normal; - margin: 5px 0 0 0; - padding: 0; -} - -div.sphinxsidebar p { - color: #ffffff; -} - -div.sphinxsidebar p.topless { - margin: 5px 10px 10px 10px; -} - -div.sphinxsidebar ul { - margin: 10px; - padding: 0; - color: #ffffff; -} - -div.sphinxsidebar a { - color: #98dbcc; -} - -div.sphinxsidebar input { - border: 1px solid #98dbcc; - font-family: sans-serif; - font-size: 1em; -} - - - -/* -- hyperlink styles ------------------------------------------------------ */ - -a { - color: #355f7c; - text-decoration: none; -} - -a:visited { - color: #355f7c; - text-decoration: none; -} - -a:hover { - text-decoration: underline; -} - - - -/* -- body styles ----------------------------------------------------------- */ - -div.body h1, -div.body h2, -div.body h3, -div.body h4, -div.body h5, -div.body h6 { - font-family: 'Trebuchet MS', sans-serif; - background-color: #f2f2f2; - font-weight: normal; - color: #20435c; - border-bottom: 1px solid #ccc; - margin: 20px -20px 10px -20px; - padding: 3px 0 3px 10px; -} - -div.body h1 { margin-top: 0; font-size: 200%; } -div.body h2 { font-size: 160%; } -div.body h3 { font-size: 140%; } -div.body h4 { font-size: 120%; } -div.body h5 { font-size: 110%; } -div.body h6 { font-size: 100%; } - -a.headerlink { - color: #c60f0f; - font-size: 0.8em; - padding: 0 4px 0 4px; - text-decoration: none; -} - -a.headerlink:hover { - background-color: #c60f0f; - color: white; -} - -div.body p, div.body dd, div.body li, div.body blockquote { - text-align: justify; - line-height: 130%; -} - -div.admonition p.admonition-title + p { - display: inline; -} - -div.admonition p { - margin-bottom: 5px; -} - -div.admonition pre { - margin-bottom: 5px; -} - -div.admonition ul, div.admonition ol { - margin-bottom: 5px; -} - -div.note { - background-color: #eee; - border: 1px solid #ccc; -} - -div.seealso { - background-color: #ffc; - border: 1px solid #ff6; -} - -div.topic { - background-color: #eee; -} - -div.warning { - background-color: #ffe4e4; - border: 1px solid #f66; -} - -p.admonition-title { - display: inline; -} - -p.admonition-title:after { - content: ":"; -} - -pre { - padding: 5px; - background-color: unset; - color: unset; - line-height: 120%; - border: 1px solid #ac9; - border-left: none; - border-right: none; -} - -code { - background-color: #ecf0f3; - padding: 0 1px 0 1px; - font-size: 0.95em; -} - -th, dl.field-list > dt { - background-color: #ede; -} - -.warning code { - background: #efc2c2; -} - -.note code { - background: #d6d6d6; -} - -.viewcode-back { - font-family: sans-serif; -} - -div.viewcode-block:target { - background-color: #f4debf; - border-top: 1px solid #ac9; - border-bottom: 1px solid #ac9; -} - -div.code-block-caption { - color: #efefef; - background-color: #1c4e63; -} \ No newline at end of file diff --git a/docs/_static/css/badge_only.css b/docs/_static/css/badge_only.css new file mode 100644 index 0000000..e380325 --- /dev/null +++ b/docs/_static/css/badge_only.css @@ -0,0 +1 @@ +.fa:before{-webkit-font-smoothing:antialiased}.clearfix{*zoom:1}.clearfix:after,.clearfix:before{display:table;content:""}.clearfix:after{clear:both}@font-face{font-family:FontAwesome;font-style:normal;font-weight:400;src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713?#iefix) format("embedded-opentype"),url(fonts/fontawesome-webfont.woff2?af7ae505a9eed503f8b8e6982036873e) format("woff2"),url(fonts/fontawesome-webfont.woff?fee66e712a8a08eef5805a46892932ad) format("woff"),url(fonts/fontawesome-webfont.ttf?b06871f281fee6b241d60582ae9369b9) format("truetype"),url(fonts/fontawesome-webfont.svg?912ec66d7572ff821749319396470bde#FontAwesome) format("svg")}.fa:before{font-family:FontAwesome;font-style:normal;font-weight:400;line-height:1}.fa:before,a .fa{text-decoration:inherit}.fa:before,a .fa,li .fa{display:inline-block}li .fa-large:before{width:1.875em}ul.fas{list-style-type:none;margin-left:2em;text-indent:-.8em}ul.fas li .fa{width:.8em}ul.fas li .fa-large:before{vertical-align:baseline}.fa-book:before,.icon-book:before{content:"\f02d"}.fa-caret-down:before,.icon-caret-down:before{content:"\f0d7"}.fa-caret-up:before,.icon-caret-up:before{content:"\f0d8"}.fa-caret-left:before,.icon-caret-left:before{content:"\f0d9"}.fa-caret-right:before,.icon-caret-right:before{content:"\f0da"}.rst-versions{position:fixed;bottom:0;left:0;width:300px;color:#fcfcfc;background:#1f1d1d;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;z-index:400}.rst-versions a{color:#2980b9;text-decoration:none}.rst-versions .rst-badge-small{display:none}.rst-versions .rst-current-version{padding:12px;background-color:#272525;display:block;text-align:right;font-size:90%;cursor:pointer;color:#27ae60}.rst-versions .rst-current-version:after{clear:both;content:"";display:block}.rst-versions .rst-current-version .fa{color:#fcfcfc}.rst-versions .rst-current-version .fa-book,.rst-versions .rst-current-version .icon-book{float:left}.rst-versions .rst-current-version.rst-out-of-date{background-color:#e74c3c;color:#fff}.rst-versions .rst-current-version.rst-active-old-version{background-color:#f1c40f;color:#000}.rst-versions.shift-up{height:auto;max-height:100%;overflow-y:scroll}.rst-versions.shift-up .rst-other-versions{display:block}.rst-versions .rst-other-versions{font-size:90%;padding:12px;color:grey;display:none}.rst-versions .rst-other-versions hr{display:block;height:1px;border:0;margin:20px 0;padding:0;border-top:1px solid #413d3d}.rst-versions .rst-other-versions dd{display:inline-block;margin:0}.rst-versions .rst-other-versions dd a{display:inline-block;padding:6px;color:#fcfcfc}.rst-versions.rst-badge{width:auto;bottom:20px;right:20px;left:auto;border:none;max-width:300px;max-height:90%}.rst-versions.rst-badge .fa-book,.rst-versions.rst-badge .icon-book{float:none;line-height:30px}.rst-versions.rst-badge.shift-up .rst-current-version{text-align:right}.rst-versions.rst-badge.shift-up .rst-current-version .fa-book,.rst-versions.rst-badge.shift-up .rst-current-version .icon-book{float:left}.rst-versions.rst-badge>.rst-current-version{width:auto;height:30px;line-height:30px;padding:0 6px;display:block;text-align:center}@media screen and (max-width:768px){.rst-versions{width:85%;display:none}.rst-versions.shift{display:block}} \ No newline at end of file diff --git a/docs/_static/css/fonts/Roboto-Slab-Bold.woff b/docs/_static/css/fonts/Roboto-Slab-Bold.woff new file mode 100644 index 0000000..6cb6000 Binary files /dev/null and b/docs/_static/css/fonts/Roboto-Slab-Bold.woff differ diff --git a/docs/_static/css/fonts/Roboto-Slab-Bold.woff2 b/docs/_static/css/fonts/Roboto-Slab-Bold.woff2 new file mode 100644 index 0000000..7059e23 Binary files /dev/null and b/docs/_static/css/fonts/Roboto-Slab-Bold.woff2 differ diff --git a/docs/_static/css/fonts/Roboto-Slab-Regular.woff b/docs/_static/css/fonts/Roboto-Slab-Regular.woff new file mode 100644 index 0000000..f815f63 Binary files /dev/null and b/docs/_static/css/fonts/Roboto-Slab-Regular.woff differ diff --git a/docs/_static/css/fonts/Roboto-Slab-Regular.woff2 b/docs/_static/css/fonts/Roboto-Slab-Regular.woff2 new file mode 100644 index 0000000..f2c76e5 Binary files /dev/null and b/docs/_static/css/fonts/Roboto-Slab-Regular.woff2 differ diff --git a/docs/_static/css/fonts/fontawesome-webfont.eot b/docs/_static/css/fonts/fontawesome-webfont.eot new file mode 100644 index 0000000..e9f60ca Binary files /dev/null and b/docs/_static/css/fonts/fontawesome-webfont.eot differ diff --git a/docs/_static/css/fonts/fontawesome-webfont.svg b/docs/_static/css/fonts/fontawesome-webfont.svg new file mode 100644 index 0000000..855c845 --- /dev/null +++ b/docs/_static/css/fonts/fontawesome-webfont.svg @@ -0,0 +1,2671 @@ + + + + +Created by FontForge 20120731 at Mon Oct 24 17:37:40 2016 + By ,,, +Copyright Dave Gandy 2016. All rights reserved. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/_static/css/fonts/fontawesome-webfont.ttf b/docs/_static/css/fonts/fontawesome-webfont.ttf new file mode 100644 index 0000000..35acda2 Binary files /dev/null and b/docs/_static/css/fonts/fontawesome-webfont.ttf differ diff --git a/docs/_static/css/fonts/fontawesome-webfont.woff b/docs/_static/css/fonts/fontawesome-webfont.woff new file mode 100644 index 0000000..400014a Binary files /dev/null and b/docs/_static/css/fonts/fontawesome-webfont.woff differ diff --git a/docs/_static/css/fonts/fontawesome-webfont.woff2 b/docs/_static/css/fonts/fontawesome-webfont.woff2 new file mode 100644 index 0000000..4d13fc6 Binary files /dev/null and b/docs/_static/css/fonts/fontawesome-webfont.woff2 differ diff --git a/docs/_static/css/fonts/lato-bold-italic.woff b/docs/_static/css/fonts/lato-bold-italic.woff new file mode 100644 index 0000000..88ad05b Binary files /dev/null and b/docs/_static/css/fonts/lato-bold-italic.woff differ diff --git a/docs/_static/css/fonts/lato-bold-italic.woff2 b/docs/_static/css/fonts/lato-bold-italic.woff2 new file mode 100644 index 0000000..c4e3d80 Binary files /dev/null and b/docs/_static/css/fonts/lato-bold-italic.woff2 differ diff --git a/docs/_static/css/fonts/lato-bold.woff b/docs/_static/css/fonts/lato-bold.woff new file mode 100644 index 0000000..c6dff51 Binary files /dev/null and b/docs/_static/css/fonts/lato-bold.woff differ diff --git a/docs/_static/css/fonts/lato-bold.woff2 b/docs/_static/css/fonts/lato-bold.woff2 new file mode 100644 index 0000000..bb19504 Binary files /dev/null and b/docs/_static/css/fonts/lato-bold.woff2 differ diff --git a/docs/_static/css/fonts/lato-normal-italic.woff b/docs/_static/css/fonts/lato-normal-italic.woff new file mode 100644 index 0000000..76114bc Binary files /dev/null and b/docs/_static/css/fonts/lato-normal-italic.woff differ diff --git a/docs/_static/css/fonts/lato-normal-italic.woff2 b/docs/_static/css/fonts/lato-normal-italic.woff2 new file mode 100644 index 0000000..3404f37 Binary files /dev/null and b/docs/_static/css/fonts/lato-normal-italic.woff2 differ diff --git a/docs/_static/css/fonts/lato-normal.woff b/docs/_static/css/fonts/lato-normal.woff new file mode 100644 index 0000000..ae1307f Binary files /dev/null and b/docs/_static/css/fonts/lato-normal.woff differ diff --git a/docs/_static/css/fonts/lato-normal.woff2 b/docs/_static/css/fonts/lato-normal.woff2 new file mode 100644 index 0000000..3bf9843 Binary files /dev/null and b/docs/_static/css/fonts/lato-normal.woff2 differ diff --git a/docs/_static/css/theme.css b/docs/_static/css/theme.css new file mode 100644 index 0000000..0d9ae7e --- /dev/null +++ b/docs/_static/css/theme.css @@ -0,0 +1,4 @@ +html{box-sizing:border-box}*,:after,:before{box-sizing:inherit}article,aside,details,figcaption,figure,footer,header,hgroup,nav,section{display:block}audio,canvas,video{display:inline-block;*display:inline;*zoom:1}[hidden],audio:not([controls]){display:none}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:100%;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:700}blockquote{margin:0}dfn{font-style:italic}ins{background:#ff9;text-decoration:none}ins,mark{color:#000}mark{background:#ff0;font-style:italic;font-weight:700}.rst-content code,.rst-content tt,code,kbd,pre,samp{font-family:monospace,serif;_font-family:courier new,monospace;font-size:1em}pre{white-space:pre}q{quotes:none}q:after,q:before{content:"";content:none}small{font-size:85%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sup{top:-.5em}sub{bottom:-.25em}dl,ol,ul{margin:0;padding:0;list-style:none;list-style-image:none}li{list-style:none}dd{margin:0}img{border:0;-ms-interpolation-mode:bicubic;vertical-align:middle;max-width:100%}svg:not(:root){overflow:hidden}figure,form{margin:0}label{cursor:pointer}button,input,select,textarea{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle}button,input{line-height:normal}button,input[type=button],input[type=reset],input[type=submit]{cursor:pointer;-webkit-appearance:button;*overflow:visible}button[disabled],input[disabled]{cursor:default}input[type=search]{-webkit-appearance:textfield;-moz-box-sizing:content-box;-webkit-box-sizing:content-box;box-sizing:content-box}textarea{resize:vertical}table{border-collapse:collapse;border-spacing:0}td{vertical-align:top}.chromeframe{margin:.2em 0;background:#ccc;color:#000;padding:.2em 0}.ir{display:block;border:0;text-indent:-999em;overflow:hidden;background-color:transparent;background-repeat:no-repeat;text-align:left;direction:ltr;*line-height:0}.ir br{display:none}.hidden{display:none!important;visibility:hidden}.visuallyhidden{border:0;clip:rect(0 0 0 0);height:1px;margin:-1px;overflow:hidden;padding:0;position:absolute;width:1px}.visuallyhidden.focusable:active,.visuallyhidden.focusable:focus{clip:auto;height:auto;margin:0;overflow:visible;position:static;width:auto}.invisible{visibility:hidden}.relative{position:relative}big,small{font-size:100%}@media print{body,html,section{background:none!important}*{box-shadow:none!important;text-shadow:none!important;filter:none!important;-ms-filter:none!important}a,a:visited{text-decoration:underline}.ir a:after,a[href^="#"]:after,a[href^="javascript:"]:after{content:""}blockquote,pre{page-break-inside:avoid}thead{display:table-header-group}img,tr{page-break-inside:avoid}img{max-width:100%!important}@page{margin:.5cm}.rst-content .toctree-wrapper>p.caption,h2,h3,p{orphans:3;widows:3}.rst-content .toctree-wrapper>p.caption,h2,h3{page-break-after:avoid}}.btn,.fa:before,.icon:before,.rst-content .admonition,.rst-content .admonition-title:before,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .code-block-caption .headerlink:before,.rst-content .danger,.rst-content .eqno .headerlink:before,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning,.rst-content code.download span:first-child:before,.rst-content dl dt .headerlink:before,.rst-content h1 .headerlink:before,.rst-content h2 .headerlink:before,.rst-content h3 .headerlink:before,.rst-content h4 .headerlink:before,.rst-content h5 .headerlink:before,.rst-content h6 .headerlink:before,.rst-content p.caption .headerlink:before,.rst-content p .headerlink:before,.rst-content table>caption .headerlink:before,.rst-content tt.download span:first-child:before,.wy-alert,.wy-dropdown .caret:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before,.wy-menu-vertical li.current>a,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a,.wy-menu-vertical li.on a button.toctree-expand:before,.wy-menu-vertical li button.toctree-expand:before,.wy-nav-top a,.wy-side-nav-search .wy-dropdown>a,.wy-side-nav-search>a,input[type=color],input[type=date],input[type=datetime-local],input[type=datetime],input[type=email],input[type=month],input[type=number],input[type=password],input[type=search],input[type=tel],input[type=text],input[type=time],input[type=url],input[type=week],select,textarea{-webkit-font-smoothing:antialiased}.clearfix{*zoom:1}.clearfix:after,.clearfix:before{display:table;content:""}.clearfix:after{clear:both}/*! + * Font Awesome 4.7.0 by @davegandy - http://fontawesome.io - @fontawesome + * License - http://fontawesome.io/license (Font: SIL OFL 1.1, CSS: MIT License) + */@font-face{font-family:FontAwesome;src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713);src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713?#iefix&v=4.7.0) format("embedded-opentype"),url(fonts/fontawesome-webfont.woff2?af7ae505a9eed503f8b8e6982036873e) format("woff2"),url(fonts/fontawesome-webfont.woff?fee66e712a8a08eef5805a46892932ad) format("woff"),url(fonts/fontawesome-webfont.ttf?b06871f281fee6b241d60582ae9369b9) format("truetype"),url(fonts/fontawesome-webfont.svg?912ec66d7572ff821749319396470bde#fontawesomeregular) format("svg");font-weight:400;font-style:normal}.fa,.icon,.rst-content .admonition-title,.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content code.download span:first-child,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink,.rst-content tt.download span:first-child,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li button.toctree-expand{display:inline-block;font:normal normal normal 14px/1 FontAwesome;font-size:inherit;text-rendering:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.fa-lg{font-size:1.33333em;line-height:.75em;vertical-align:-15%}.fa-2x{font-size:2em}.fa-3x{font-size:3em}.fa-4x{font-size:4em}.fa-5x{font-size:5em}.fa-fw{width:1.28571em;text-align:center}.fa-ul{padding-left:0;margin-left:2.14286em;list-style-type:none}.fa-ul>li{position:relative}.fa-li{position:absolute;left:-2.14286em;width:2.14286em;top:.14286em;text-align:center}.fa-li.fa-lg{left:-1.85714em}.fa-border{padding:.2em .25em .15em;border:.08em solid #eee;border-radius:.1em}.fa-pull-left{float:left}.fa-pull-right{float:right}.fa-pull-left.icon,.fa.fa-pull-left,.rst-content .code-block-caption .fa-pull-left.headerlink,.rst-content .eqno .fa-pull-left.headerlink,.rst-content .fa-pull-left.admonition-title,.rst-content code.download span.fa-pull-left:first-child,.rst-content dl dt .fa-pull-left.headerlink,.rst-content h1 .fa-pull-left.headerlink,.rst-content h2 .fa-pull-left.headerlink,.rst-content h3 .fa-pull-left.headerlink,.rst-content h4 .fa-pull-left.headerlink,.rst-content h5 .fa-pull-left.headerlink,.rst-content h6 .fa-pull-left.headerlink,.rst-content p .fa-pull-left.headerlink,.rst-content table>caption .fa-pull-left.headerlink,.rst-content tt.download span.fa-pull-left:first-child,.wy-menu-vertical li.current>a button.fa-pull-left.toctree-expand,.wy-menu-vertical li.on a button.fa-pull-left.toctree-expand,.wy-menu-vertical li button.fa-pull-left.toctree-expand{margin-right:.3em}.fa-pull-right.icon,.fa.fa-pull-right,.rst-content .code-block-caption .fa-pull-right.headerlink,.rst-content .eqno .fa-pull-right.headerlink,.rst-content .fa-pull-right.admonition-title,.rst-content code.download span.fa-pull-right:first-child,.rst-content dl dt .fa-pull-right.headerlink,.rst-content h1 .fa-pull-right.headerlink,.rst-content h2 .fa-pull-right.headerlink,.rst-content h3 .fa-pull-right.headerlink,.rst-content h4 .fa-pull-right.headerlink,.rst-content h5 .fa-pull-right.headerlink,.rst-content h6 .fa-pull-right.headerlink,.rst-content p .fa-pull-right.headerlink,.rst-content table>caption .fa-pull-right.headerlink,.rst-content tt.download span.fa-pull-right:first-child,.wy-menu-vertical li.current>a button.fa-pull-right.toctree-expand,.wy-menu-vertical li.on a button.fa-pull-right.toctree-expand,.wy-menu-vertical li button.fa-pull-right.toctree-expand{margin-left:.3em}.pull-right{float:right}.pull-left{float:left}.fa.pull-left,.pull-left.icon,.rst-content .code-block-caption .pull-left.headerlink,.rst-content .eqno .pull-left.headerlink,.rst-content .pull-left.admonition-title,.rst-content code.download span.pull-left:first-child,.rst-content dl dt .pull-left.headerlink,.rst-content h1 .pull-left.headerlink,.rst-content h2 .pull-left.headerlink,.rst-content h3 .pull-left.headerlink,.rst-content h4 .pull-left.headerlink,.rst-content h5 .pull-left.headerlink,.rst-content h6 .pull-left.headerlink,.rst-content p .pull-left.headerlink,.rst-content table>caption .pull-left.headerlink,.rst-content tt.download span.pull-left:first-child,.wy-menu-vertical li.current>a button.pull-left.toctree-expand,.wy-menu-vertical li.on a button.pull-left.toctree-expand,.wy-menu-vertical li button.pull-left.toctree-expand{margin-right:.3em}.fa.pull-right,.pull-right.icon,.rst-content .code-block-caption .pull-right.headerlink,.rst-content .eqno .pull-right.headerlink,.rst-content .pull-right.admonition-title,.rst-content code.download span.pull-right:first-child,.rst-content dl dt .pull-right.headerlink,.rst-content h1 .pull-right.headerlink,.rst-content h2 .pull-right.headerlink,.rst-content h3 .pull-right.headerlink,.rst-content h4 .pull-right.headerlink,.rst-content h5 .pull-right.headerlink,.rst-content h6 .pull-right.headerlink,.rst-content p .pull-right.headerlink,.rst-content table>caption .pull-right.headerlink,.rst-content tt.download span.pull-right:first-child,.wy-menu-vertical li.current>a button.pull-right.toctree-expand,.wy-menu-vertical li.on a button.pull-right.toctree-expand,.wy-menu-vertical li button.pull-right.toctree-expand{margin-left:.3em}.fa-spin{-webkit-animation:fa-spin 2s linear infinite;animation:fa-spin 2s linear infinite}.fa-pulse{-webkit-animation:fa-spin 1s steps(8) infinite;animation:fa-spin 1s steps(8) infinite}@-webkit-keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}to{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}@keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}to{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}.fa-rotate-90{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=1)";-webkit-transform:rotate(90deg);-ms-transform:rotate(90deg);transform:rotate(90deg)}.fa-rotate-180{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2)";-webkit-transform:rotate(180deg);-ms-transform:rotate(180deg);transform:rotate(180deg)}.fa-rotate-270{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=3)";-webkit-transform:rotate(270deg);-ms-transform:rotate(270deg);transform:rotate(270deg)}.fa-flip-horizontal{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)";-webkit-transform:scaleX(-1);-ms-transform:scaleX(-1);transform:scaleX(-1)}.fa-flip-vertical{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)";-webkit-transform:scaleY(-1);-ms-transform:scaleY(-1);transform:scaleY(-1)}:root .fa-flip-horizontal,:root .fa-flip-vertical,:root .fa-rotate-90,:root .fa-rotate-180,:root .fa-rotate-270{filter:none}.fa-stack{position:relative;display:inline-block;width:2em;height:2em;line-height:2em;vertical-align:middle}.fa-stack-1x,.fa-stack-2x{position:absolute;left:0;width:100%;text-align:center}.fa-stack-1x{line-height:inherit}.fa-stack-2x{font-size:2em}.fa-inverse{color:#fff}.fa-glass:before{content:""}.fa-music:before{content:""}.fa-search:before,.icon-search:before{content:""}.fa-envelope-o:before{content:""}.fa-heart:before{content:""}.fa-star:before{content:""}.fa-star-o:before{content:""}.fa-user:before{content:""}.fa-film:before{content:""}.fa-th-large:before{content:""}.fa-th:before{content:""}.fa-th-list:before{content:""}.fa-check:before{content:""}.fa-close:before,.fa-remove:before,.fa-times:before{content:""}.fa-search-plus:before{content:""}.fa-search-minus:before{content:""}.fa-power-off:before{content:""}.fa-signal:before{content:""}.fa-cog:before,.fa-gear:before{content:""}.fa-trash-o:before{content:""}.fa-home:before,.icon-home:before{content:""}.fa-file-o:before{content:""}.fa-clock-o:before{content:""}.fa-road:before{content:""}.fa-download:before,.rst-content code.download span:first-child:before,.rst-content tt.download span:first-child:before{content:""}.fa-arrow-circle-o-down:before{content:""}.fa-arrow-circle-o-up:before{content:""}.fa-inbox:before{content:""}.fa-play-circle-o:before{content:""}.fa-repeat:before,.fa-rotate-right:before{content:""}.fa-refresh:before{content:""}.fa-list-alt:before{content:""}.fa-lock:before{content:""}.fa-flag:before{content:""}.fa-headphones:before{content:""}.fa-volume-off:before{content:""}.fa-volume-down:before{content:""}.fa-volume-up:before{content:""}.fa-qrcode:before{content:""}.fa-barcode:before{content:""}.fa-tag:before{content:""}.fa-tags:before{content:""}.fa-book:before,.icon-book:before{content:""}.fa-bookmark:before{content:""}.fa-print:before{content:""}.fa-camera:before{content:""}.fa-font:before{content:""}.fa-bold:before{content:""}.fa-italic:before{content:""}.fa-text-height:before{content:""}.fa-text-width:before{content:""}.fa-align-left:before{content:""}.fa-align-center:before{content:""}.fa-align-right:before{content:""}.fa-align-justify:before{content:""}.fa-list:before{content:""}.fa-dedent:before,.fa-outdent:before{content:""}.fa-indent:before{content:""}.fa-video-camera:before{content:""}.fa-image:before,.fa-photo:before,.fa-picture-o:before{content:""}.fa-pencil:before{content:""}.fa-map-marker:before{content:""}.fa-adjust:before{content:""}.fa-tint:before{content:""}.fa-edit:before,.fa-pencil-square-o:before{content:""}.fa-share-square-o:before{content:""}.fa-check-square-o:before{content:""}.fa-arrows:before{content:""}.fa-step-backward:before{content:""}.fa-fast-backward:before{content:""}.fa-backward:before{content:""}.fa-play:before{content:""}.fa-pause:before{content:""}.fa-stop:before{content:""}.fa-forward:before{content:""}.fa-fast-forward:before{content:""}.fa-step-forward:before{content:""}.fa-eject:before{content:""}.fa-chevron-left:before{content:""}.fa-chevron-right:before{content:""}.fa-plus-circle:before{content:""}.fa-minus-circle:before{content:""}.fa-times-circle:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before{content:""}.fa-check-circle:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before{content:""}.fa-question-circle:before{content:""}.fa-info-circle:before{content:""}.fa-crosshairs:before{content:""}.fa-times-circle-o:before{content:""}.fa-check-circle-o:before{content:""}.fa-ban:before{content:""}.fa-arrow-left:before{content:""}.fa-arrow-right:before{content:""}.fa-arrow-up:before{content:""}.fa-arrow-down:before{content:""}.fa-mail-forward:before,.fa-share:before{content:""}.fa-expand:before{content:""}.fa-compress:before{content:""}.fa-plus:before{content:""}.fa-minus:before{content:""}.fa-asterisk:before{content:""}.fa-exclamation-circle:before,.rst-content .admonition-title:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before{content:""}.fa-gift:before{content:""}.fa-leaf:before{content:""}.fa-fire:before,.icon-fire:before{content:""}.fa-eye:before{content:""}.fa-eye-slash:before{content:""}.fa-exclamation-triangle:before,.fa-warning:before{content:""}.fa-plane:before{content:""}.fa-calendar:before{content:""}.fa-random:before{content:""}.fa-comment:before{content:""}.fa-magnet:before{content:""}.fa-chevron-up:before{content:""}.fa-chevron-down:before{content:""}.fa-retweet:before{content:""}.fa-shopping-cart:before{content:""}.fa-folder:before{content:""}.fa-folder-open:before{content:""}.fa-arrows-v:before{content:""}.fa-arrows-h:before{content:""}.fa-bar-chart-o:before,.fa-bar-chart:before{content:""}.fa-twitter-square:before{content:""}.fa-facebook-square:before{content:""}.fa-camera-retro:before{content:""}.fa-key:before{content:""}.fa-cogs:before,.fa-gears:before{content:""}.fa-comments:before{content:""}.fa-thumbs-o-up:before{content:""}.fa-thumbs-o-down:before{content:""}.fa-star-half:before{content:""}.fa-heart-o:before{content:""}.fa-sign-out:before{content:""}.fa-linkedin-square:before{content:""}.fa-thumb-tack:before{content:""}.fa-external-link:before{content:""}.fa-sign-in:before{content:""}.fa-trophy:before{content:""}.fa-github-square:before{content:""}.fa-upload:before{content:""}.fa-lemon-o:before{content:""}.fa-phone:before{content:""}.fa-square-o:before{content:""}.fa-bookmark-o:before{content:""}.fa-phone-square:before{content:""}.fa-twitter:before{content:""}.fa-facebook-f:before,.fa-facebook:before{content:""}.fa-github:before,.icon-github:before{content:""}.fa-unlock:before{content:""}.fa-credit-card:before{content:""}.fa-feed:before,.fa-rss:before{content:""}.fa-hdd-o:before{content:""}.fa-bullhorn:before{content:""}.fa-bell:before{content:""}.fa-certificate:before{content:""}.fa-hand-o-right:before{content:""}.fa-hand-o-left:before{content:""}.fa-hand-o-up:before{content:""}.fa-hand-o-down:before{content:""}.fa-arrow-circle-left:before,.icon-circle-arrow-left:before{content:""}.fa-arrow-circle-right:before,.icon-circle-arrow-right:before{content:""}.fa-arrow-circle-up:before{content:""}.fa-arrow-circle-down:before{content:""}.fa-globe:before{content:""}.fa-wrench:before{content:""}.fa-tasks:before{content:""}.fa-filter:before{content:""}.fa-briefcase:before{content:""}.fa-arrows-alt:before{content:""}.fa-group:before,.fa-users:before{content:""}.fa-chain:before,.fa-link:before,.icon-link:before{content:""}.fa-cloud:before{content:""}.fa-flask:before{content:""}.fa-cut:before,.fa-scissors:before{content:""}.fa-copy:before,.fa-files-o:before{content:""}.fa-paperclip:before{content:""}.fa-floppy-o:before,.fa-save:before{content:""}.fa-square:before{content:""}.fa-bars:before,.fa-navicon:before,.fa-reorder:before{content:""}.fa-list-ul:before{content:""}.fa-list-ol:before{content:""}.fa-strikethrough:before{content:""}.fa-underline:before{content:""}.fa-table:before{content:""}.fa-magic:before{content:""}.fa-truck:before{content:""}.fa-pinterest:before{content:""}.fa-pinterest-square:before{content:""}.fa-google-plus-square:before{content:""}.fa-google-plus:before{content:""}.fa-money:before{content:""}.fa-caret-down:before,.icon-caret-down:before,.wy-dropdown .caret:before{content:""}.fa-caret-up:before{content:""}.fa-caret-left:before{content:""}.fa-caret-right:before{content:""}.fa-columns:before{content:""}.fa-sort:before,.fa-unsorted:before{content:""}.fa-sort-desc:before,.fa-sort-down:before{content:""}.fa-sort-asc:before,.fa-sort-up:before{content:""}.fa-envelope:before{content:""}.fa-linkedin:before{content:""}.fa-rotate-left:before,.fa-undo:before{content:""}.fa-gavel:before,.fa-legal:before{content:""}.fa-dashboard:before,.fa-tachometer:before{content:""}.fa-comment-o:before{content:""}.fa-comments-o:before{content:""}.fa-bolt:before,.fa-flash:before{content:""}.fa-sitemap:before{content:""}.fa-umbrella:before{content:""}.fa-clipboard:before,.fa-paste:before{content:""}.fa-lightbulb-o:before{content:""}.fa-exchange:before{content:""}.fa-cloud-download:before{content:""}.fa-cloud-upload:before{content:""}.fa-user-md:before{content:""}.fa-stethoscope:before{content:""}.fa-suitcase:before{content:""}.fa-bell-o:before{content:""}.fa-coffee:before{content:""}.fa-cutlery:before{content:""}.fa-file-text-o:before{content:""}.fa-building-o:before{content:""}.fa-hospital-o:before{content:""}.fa-ambulance:before{content:""}.fa-medkit:before{content:""}.fa-fighter-jet:before{content:""}.fa-beer:before{content:""}.fa-h-square:before{content:""}.fa-plus-square:before{content:""}.fa-angle-double-left:before{content:""}.fa-angle-double-right:before{content:""}.fa-angle-double-up:before{content:""}.fa-angle-double-down:before{content:""}.fa-angle-left:before{content:""}.fa-angle-right:before{content:""}.fa-angle-up:before{content:""}.fa-angle-down:before{content:""}.fa-desktop:before{content:""}.fa-laptop:before{content:""}.fa-tablet:before{content:""}.fa-mobile-phone:before,.fa-mobile:before{content:""}.fa-circle-o:before{content:""}.fa-quote-left:before{content:""}.fa-quote-right:before{content:""}.fa-spinner:before{content:""}.fa-circle:before{content:""}.fa-mail-reply:before,.fa-reply:before{content:""}.fa-github-alt:before{content:""}.fa-folder-o:before{content:""}.fa-folder-open-o:before{content:""}.fa-smile-o:before{content:""}.fa-frown-o:before{content:""}.fa-meh-o:before{content:""}.fa-gamepad:before{content:""}.fa-keyboard-o:before{content:""}.fa-flag-o:before{content:""}.fa-flag-checkered:before{content:""}.fa-terminal:before{content:""}.fa-code:before{content:""}.fa-mail-reply-all:before,.fa-reply-all:before{content:""}.fa-star-half-empty:before,.fa-star-half-full:before,.fa-star-half-o:before{content:""}.fa-location-arrow:before{content:""}.fa-crop:before{content:""}.fa-code-fork:before{content:""}.fa-chain-broken:before,.fa-unlink:before{content:""}.fa-question:before{content:""}.fa-info:before{content:""}.fa-exclamation:before{content:""}.fa-superscript:before{content:""}.fa-subscript:before{content:""}.fa-eraser:before{content:""}.fa-puzzle-piece:before{content:""}.fa-microphone:before{content:""}.fa-microphone-slash:before{content:""}.fa-shield:before{content:""}.fa-calendar-o:before{content:""}.fa-fire-extinguisher:before{content:""}.fa-rocket:before{content:""}.fa-maxcdn:before{content:""}.fa-chevron-circle-left:before{content:""}.fa-chevron-circle-right:before{content:""}.fa-chevron-circle-up:before{content:""}.fa-chevron-circle-down:before{content:""}.fa-html5:before{content:""}.fa-css3:before{content:""}.fa-anchor:before{content:""}.fa-unlock-alt:before{content:""}.fa-bullseye:before{content:""}.fa-ellipsis-h:before{content:""}.fa-ellipsis-v:before{content:""}.fa-rss-square:before{content:""}.fa-play-circle:before{content:""}.fa-ticket:before{content:""}.fa-minus-square:before{content:""}.fa-minus-square-o:before,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a button.toctree-expand:before{content:""}.fa-level-up:before{content:""}.fa-level-down:before{content:""}.fa-check-square:before{content:""}.fa-pencil-square:before{content:""}.fa-external-link-square:before{content:""}.fa-share-square:before{content:""}.fa-compass:before{content:""}.fa-caret-square-o-down:before,.fa-toggle-down:before{content:""}.fa-caret-square-o-up:before,.fa-toggle-up:before{content:""}.fa-caret-square-o-right:before,.fa-toggle-right:before{content:""}.fa-eur:before,.fa-euro:before{content:""}.fa-gbp:before{content:""}.fa-dollar:before,.fa-usd:before{content:""}.fa-inr:before,.fa-rupee:before{content:""}.fa-cny:before,.fa-jpy:before,.fa-rmb:before,.fa-yen:before{content:""}.fa-rouble:before,.fa-rub:before,.fa-ruble:before{content:""}.fa-krw:before,.fa-won:before{content:""}.fa-bitcoin:before,.fa-btc:before{content:""}.fa-file:before{content:""}.fa-file-text:before{content:""}.fa-sort-alpha-asc:before{content:""}.fa-sort-alpha-desc:before{content:""}.fa-sort-amount-asc:before{content:""}.fa-sort-amount-desc:before{content:""}.fa-sort-numeric-asc:before{content:""}.fa-sort-numeric-desc:before{content:""}.fa-thumbs-up:before{content:""}.fa-thumbs-down:before{content:""}.fa-youtube-square:before{content:""}.fa-youtube:before{content:""}.fa-xing:before{content:""}.fa-xing-square:before{content:""}.fa-youtube-play:before{content:""}.fa-dropbox:before{content:""}.fa-stack-overflow:before{content:""}.fa-instagram:before{content:""}.fa-flickr:before{content:""}.fa-adn:before{content:""}.fa-bitbucket:before,.icon-bitbucket:before{content:""}.fa-bitbucket-square:before{content:""}.fa-tumblr:before{content:""}.fa-tumblr-square:before{content:""}.fa-long-arrow-down:before{content:""}.fa-long-arrow-up:before{content:""}.fa-long-arrow-left:before{content:""}.fa-long-arrow-right:before{content:""}.fa-apple:before{content:""}.fa-windows:before{content:""}.fa-android:before{content:""}.fa-linux:before{content:""}.fa-dribbble:before{content:""}.fa-skype:before{content:""}.fa-foursquare:before{content:""}.fa-trello:before{content:""}.fa-female:before{content:""}.fa-male:before{content:""}.fa-gittip:before,.fa-gratipay:before{content:""}.fa-sun-o:before{content:""}.fa-moon-o:before{content:""}.fa-archive:before{content:""}.fa-bug:before{content:""}.fa-vk:before{content:""}.fa-weibo:before{content:""}.fa-renren:before{content:""}.fa-pagelines:before{content:""}.fa-stack-exchange:before{content:""}.fa-arrow-circle-o-right:before{content:""}.fa-arrow-circle-o-left:before{content:""}.fa-caret-square-o-left:before,.fa-toggle-left:before{content:""}.fa-dot-circle-o:before{content:""}.fa-wheelchair:before{content:""}.fa-vimeo-square:before{content:""}.fa-try:before,.fa-turkish-lira:before{content:""}.fa-plus-square-o:before,.wy-menu-vertical li button.toctree-expand:before{content:""}.fa-space-shuttle:before{content:""}.fa-slack:before{content:""}.fa-envelope-square:before{content:""}.fa-wordpress:before{content:""}.fa-openid:before{content:""}.fa-bank:before,.fa-institution:before,.fa-university:before{content:""}.fa-graduation-cap:before,.fa-mortar-board:before{content:""}.fa-yahoo:before{content:""}.fa-google:before{content:""}.fa-reddit:before{content:""}.fa-reddit-square:before{content:""}.fa-stumbleupon-circle:before{content:""}.fa-stumbleupon:before{content:""}.fa-delicious:before{content:""}.fa-digg:before{content:""}.fa-pied-piper-pp:before{content:""}.fa-pied-piper-alt:before{content:""}.fa-drupal:before{content:""}.fa-joomla:before{content:""}.fa-language:before{content:""}.fa-fax:before{content:""}.fa-building:before{content:""}.fa-child:before{content:""}.fa-paw:before{content:""}.fa-spoon:before{content:""}.fa-cube:before{content:""}.fa-cubes:before{content:""}.fa-behance:before{content:""}.fa-behance-square:before{content:""}.fa-steam:before{content:""}.fa-steam-square:before{content:""}.fa-recycle:before{content:""}.fa-automobile:before,.fa-car:before{content:""}.fa-cab:before,.fa-taxi:before{content:""}.fa-tree:before{content:""}.fa-spotify:before{content:""}.fa-deviantart:before{content:""}.fa-soundcloud:before{content:""}.fa-database:before{content:""}.fa-file-pdf-o:before{content:""}.fa-file-word-o:before{content:""}.fa-file-excel-o:before{content:""}.fa-file-powerpoint-o:before{content:""}.fa-file-image-o:before,.fa-file-photo-o:before,.fa-file-picture-o:before{content:""}.fa-file-archive-o:before,.fa-file-zip-o:before{content:""}.fa-file-audio-o:before,.fa-file-sound-o:before{content:""}.fa-file-movie-o:before,.fa-file-video-o:before{content:""}.fa-file-code-o:before{content:""}.fa-vine:before{content:""}.fa-codepen:before{content:""}.fa-jsfiddle:before{content:""}.fa-life-bouy:before,.fa-life-buoy:before,.fa-life-ring:before,.fa-life-saver:before,.fa-support:before{content:""}.fa-circle-o-notch:before{content:""}.fa-ra:before,.fa-rebel:before,.fa-resistance:before{content:""}.fa-empire:before,.fa-ge:before{content:""}.fa-git-square:before{content:""}.fa-git:before{content:""}.fa-hacker-news:before,.fa-y-combinator-square:before,.fa-yc-square:before{content:""}.fa-tencent-weibo:before{content:""}.fa-qq:before{content:""}.fa-wechat:before,.fa-weixin:before{content:""}.fa-paper-plane:before,.fa-send:before{content:""}.fa-paper-plane-o:before,.fa-send-o:before{content:""}.fa-history:before{content:""}.fa-circle-thin:before{content:""}.fa-header:before{content:""}.fa-paragraph:before{content:""}.fa-sliders:before{content:""}.fa-share-alt:before{content:""}.fa-share-alt-square:before{content:""}.fa-bomb:before{content:""}.fa-futbol-o:before,.fa-soccer-ball-o:before{content:""}.fa-tty:before{content:""}.fa-binoculars:before{content:""}.fa-plug:before{content:""}.fa-slideshare:before{content:""}.fa-twitch:before{content:""}.fa-yelp:before{content:""}.fa-newspaper-o:before{content:""}.fa-wifi:before{content:""}.fa-calculator:before{content:""}.fa-paypal:before{content:""}.fa-google-wallet:before{content:""}.fa-cc-visa:before{content:""}.fa-cc-mastercard:before{content:""}.fa-cc-discover:before{content:""}.fa-cc-amex:before{content:""}.fa-cc-paypal:before{content:""}.fa-cc-stripe:before{content:""}.fa-bell-slash:before{content:""}.fa-bell-slash-o:before{content:""}.fa-trash:before{content:""}.fa-copyright:before{content:""}.fa-at:before{content:""}.fa-eyedropper:before{content:""}.fa-paint-brush:before{content:""}.fa-birthday-cake:before{content:""}.fa-area-chart:before{content:""}.fa-pie-chart:before{content:""}.fa-line-chart:before{content:""}.fa-lastfm:before{content:""}.fa-lastfm-square:before{content:""}.fa-toggle-off:before{content:""}.fa-toggle-on:before{content:""}.fa-bicycle:before{content:""}.fa-bus:before{content:""}.fa-ioxhost:before{content:""}.fa-angellist:before{content:""}.fa-cc:before{content:""}.fa-ils:before,.fa-shekel:before,.fa-sheqel:before{content:""}.fa-meanpath:before{content:""}.fa-buysellads:before{content:""}.fa-connectdevelop:before{content:""}.fa-dashcube:before{content:""}.fa-forumbee:before{content:""}.fa-leanpub:before{content:""}.fa-sellsy:before{content:""}.fa-shirtsinbulk:before{content:""}.fa-simplybuilt:before{content:""}.fa-skyatlas:before{content:""}.fa-cart-plus:before{content:""}.fa-cart-arrow-down:before{content:""}.fa-diamond:before{content:""}.fa-ship:before{content:""}.fa-user-secret:before{content:""}.fa-motorcycle:before{content:""}.fa-street-view:before{content:""}.fa-heartbeat:before{content:""}.fa-venus:before{content:""}.fa-mars:before{content:""}.fa-mercury:before{content:""}.fa-intersex:before,.fa-transgender:before{content:""}.fa-transgender-alt:before{content:""}.fa-venus-double:before{content:""}.fa-mars-double:before{content:""}.fa-venus-mars:before{content:""}.fa-mars-stroke:before{content:""}.fa-mars-stroke-v:before{content:""}.fa-mars-stroke-h:before{content:""}.fa-neuter:before{content:""}.fa-genderless:before{content:""}.fa-facebook-official:before{content:""}.fa-pinterest-p:before{content:""}.fa-whatsapp:before{content:""}.fa-server:before{content:""}.fa-user-plus:before{content:""}.fa-user-times:before{content:""}.fa-bed:before,.fa-hotel:before{content:""}.fa-viacoin:before{content:""}.fa-train:before{content:""}.fa-subway:before{content:""}.fa-medium:before{content:""}.fa-y-combinator:before,.fa-yc:before{content:""}.fa-optin-monster:before{content:""}.fa-opencart:before{content:""}.fa-expeditedssl:before{content:""}.fa-battery-4:before,.fa-battery-full:before,.fa-battery:before{content:""}.fa-battery-3:before,.fa-battery-three-quarters:before{content:""}.fa-battery-2:before,.fa-battery-half:before{content:""}.fa-battery-1:before,.fa-battery-quarter:before{content:""}.fa-battery-0:before,.fa-battery-empty:before{content:""}.fa-mouse-pointer:before{content:""}.fa-i-cursor:before{content:""}.fa-object-group:before{content:""}.fa-object-ungroup:before{content:""}.fa-sticky-note:before{content:""}.fa-sticky-note-o:before{content:""}.fa-cc-jcb:before{content:""}.fa-cc-diners-club:before{content:""}.fa-clone:before{content:""}.fa-balance-scale:before{content:""}.fa-hourglass-o:before{content:""}.fa-hourglass-1:before,.fa-hourglass-start:before{content:""}.fa-hourglass-2:before,.fa-hourglass-half:before{content:""}.fa-hourglass-3:before,.fa-hourglass-end:before{content:""}.fa-hourglass:before{content:""}.fa-hand-grab-o:before,.fa-hand-rock-o:before{content:""}.fa-hand-paper-o:before,.fa-hand-stop-o:before{content:""}.fa-hand-scissors-o:before{content:""}.fa-hand-lizard-o:before{content:""}.fa-hand-spock-o:before{content:""}.fa-hand-pointer-o:before{content:""}.fa-hand-peace-o:before{content:""}.fa-trademark:before{content:""}.fa-registered:before{content:""}.fa-creative-commons:before{content:""}.fa-gg:before{content:""}.fa-gg-circle:before{content:""}.fa-tripadvisor:before{content:""}.fa-odnoklassniki:before{content:""}.fa-odnoklassniki-square:before{content:""}.fa-get-pocket:before{content:""}.fa-wikipedia-w:before{content:""}.fa-safari:before{content:""}.fa-chrome:before{content:""}.fa-firefox:before{content:""}.fa-opera:before{content:""}.fa-internet-explorer:before{content:""}.fa-television:before,.fa-tv:before{content:""}.fa-contao:before{content:""}.fa-500px:before{content:""}.fa-amazon:before{content:""}.fa-calendar-plus-o:before{content:""}.fa-calendar-minus-o:before{content:""}.fa-calendar-times-o:before{content:""}.fa-calendar-check-o:before{content:""}.fa-industry:before{content:""}.fa-map-pin:before{content:""}.fa-map-signs:before{content:""}.fa-map-o:before{content:""}.fa-map:before{content:""}.fa-commenting:before{content:""}.fa-commenting-o:before{content:""}.fa-houzz:before{content:""}.fa-vimeo:before{content:""}.fa-black-tie:before{content:""}.fa-fonticons:before{content:""}.fa-reddit-alien:before{content:""}.fa-edge:before{content:""}.fa-credit-card-alt:before{content:""}.fa-codiepie:before{content:""}.fa-modx:before{content:""}.fa-fort-awesome:before{content:""}.fa-usb:before{content:""}.fa-product-hunt:before{content:""}.fa-mixcloud:before{content:""}.fa-scribd:before{content:""}.fa-pause-circle:before{content:""}.fa-pause-circle-o:before{content:""}.fa-stop-circle:before{content:""}.fa-stop-circle-o:before{content:""}.fa-shopping-bag:before{content:""}.fa-shopping-basket:before{content:""}.fa-hashtag:before{content:""}.fa-bluetooth:before{content:""}.fa-bluetooth-b:before{content:""}.fa-percent:before{content:""}.fa-gitlab:before,.icon-gitlab:before{content:""}.fa-wpbeginner:before{content:""}.fa-wpforms:before{content:""}.fa-envira:before{content:""}.fa-universal-access:before{content:""}.fa-wheelchair-alt:before{content:""}.fa-question-circle-o:before{content:""}.fa-blind:before{content:""}.fa-audio-description:before{content:""}.fa-volume-control-phone:before{content:""}.fa-braille:before{content:""}.fa-assistive-listening-systems:before{content:""}.fa-american-sign-language-interpreting:before,.fa-asl-interpreting:before{content:""}.fa-deaf:before,.fa-deafness:before,.fa-hard-of-hearing:before{content:""}.fa-glide:before{content:""}.fa-glide-g:before{content:""}.fa-sign-language:before,.fa-signing:before{content:""}.fa-low-vision:before{content:""}.fa-viadeo:before{content:""}.fa-viadeo-square:before{content:""}.fa-snapchat:before{content:""}.fa-snapchat-ghost:before{content:""}.fa-snapchat-square:before{content:""}.fa-pied-piper:before{content:""}.fa-first-order:before{content:""}.fa-yoast:before{content:""}.fa-themeisle:before{content:""}.fa-google-plus-circle:before,.fa-google-plus-official:before{content:""}.fa-fa:before,.fa-font-awesome:before{content:""}.fa-handshake-o:before{content:""}.fa-envelope-open:before{content:""}.fa-envelope-open-o:before{content:""}.fa-linode:before{content:""}.fa-address-book:before{content:""}.fa-address-book-o:before{content:""}.fa-address-card:before,.fa-vcard:before{content:""}.fa-address-card-o:before,.fa-vcard-o:before{content:""}.fa-user-circle:before{content:""}.fa-user-circle-o:before{content:""}.fa-user-o:before{content:""}.fa-id-badge:before{content:""}.fa-drivers-license:before,.fa-id-card:before{content:""}.fa-drivers-license-o:before,.fa-id-card-o:before{content:""}.fa-quora:before{content:""}.fa-free-code-camp:before{content:""}.fa-telegram:before{content:""}.fa-thermometer-4:before,.fa-thermometer-full:before,.fa-thermometer:before{content:""}.fa-thermometer-3:before,.fa-thermometer-three-quarters:before{content:""}.fa-thermometer-2:before,.fa-thermometer-half:before{content:""}.fa-thermometer-1:before,.fa-thermometer-quarter:before{content:""}.fa-thermometer-0:before,.fa-thermometer-empty:before{content:""}.fa-shower:before{content:""}.fa-bath:before,.fa-bathtub:before,.fa-s15:before{content:""}.fa-podcast:before{content:""}.fa-window-maximize:before{content:""}.fa-window-minimize:before{content:""}.fa-window-restore:before{content:""}.fa-times-rectangle:before,.fa-window-close:before{content:""}.fa-times-rectangle-o:before,.fa-window-close-o:before{content:""}.fa-bandcamp:before{content:""}.fa-grav:before{content:""}.fa-etsy:before{content:""}.fa-imdb:before{content:""}.fa-ravelry:before{content:""}.fa-eercast:before{content:""}.fa-microchip:before{content:""}.fa-snowflake-o:before{content:""}.fa-superpowers:before{content:""}.fa-wpexplorer:before{content:""}.fa-meetup:before{content:""}.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}.fa,.icon,.rst-content .admonition-title,.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content code.download span:first-child,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink,.rst-content tt.download span:first-child,.wy-dropdown .caret,.wy-inline-validate.wy-inline-validate-danger .wy-input-context,.wy-inline-validate.wy-inline-validate-info .wy-input-context,.wy-inline-validate.wy-inline-validate-success .wy-input-context,.wy-inline-validate.wy-inline-validate-warning .wy-input-context,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li button.toctree-expand{font-family:inherit}.fa:before,.icon:before,.rst-content .admonition-title:before,.rst-content .code-block-caption .headerlink:before,.rst-content .eqno .headerlink:before,.rst-content code.download span:first-child:before,.rst-content dl dt .headerlink:before,.rst-content h1 .headerlink:before,.rst-content h2 .headerlink:before,.rst-content h3 .headerlink:before,.rst-content h4 .headerlink:before,.rst-content h5 .headerlink:before,.rst-content h6 .headerlink:before,.rst-content p.caption .headerlink:before,.rst-content p .headerlink:before,.rst-content table>caption .headerlink:before,.rst-content tt.download span:first-child:before,.wy-dropdown .caret:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a button.toctree-expand:before,.wy-menu-vertical li button.toctree-expand:before{font-family:FontAwesome;display:inline-block;font-style:normal;font-weight:400;line-height:1;text-decoration:inherit}.rst-content .code-block-caption a .headerlink,.rst-content .eqno a .headerlink,.rst-content a .admonition-title,.rst-content code.download a span:first-child,.rst-content dl dt a .headerlink,.rst-content h1 a .headerlink,.rst-content h2 a .headerlink,.rst-content h3 a .headerlink,.rst-content h4 a .headerlink,.rst-content h5 a .headerlink,.rst-content h6 a .headerlink,.rst-content p.caption a .headerlink,.rst-content p a .headerlink,.rst-content table>caption a .headerlink,.rst-content tt.download a span:first-child,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li a button.toctree-expand,a .fa,a .icon,a .rst-content .admonition-title,a .rst-content .code-block-caption .headerlink,a .rst-content .eqno .headerlink,a .rst-content code.download span:first-child,a .rst-content dl dt .headerlink,a .rst-content h1 .headerlink,a .rst-content h2 .headerlink,a .rst-content h3 .headerlink,a .rst-content h4 .headerlink,a .rst-content h5 .headerlink,a .rst-content h6 .headerlink,a .rst-content p.caption .headerlink,a .rst-content p .headerlink,a .rst-content table>caption .headerlink,a .rst-content tt.download span:first-child,a .wy-menu-vertical li button.toctree-expand{display:inline-block;text-decoration:inherit}.btn .fa,.btn .icon,.btn .rst-content .admonition-title,.btn .rst-content .code-block-caption .headerlink,.btn .rst-content .eqno .headerlink,.btn .rst-content code.download span:first-child,.btn .rst-content dl dt .headerlink,.btn .rst-content h1 .headerlink,.btn .rst-content h2 .headerlink,.btn .rst-content h3 .headerlink,.btn .rst-content h4 .headerlink,.btn .rst-content h5 .headerlink,.btn .rst-content h6 .headerlink,.btn .rst-content p .headerlink,.btn .rst-content table>caption .headerlink,.btn .rst-content tt.download span:first-child,.btn .wy-menu-vertical li.current>a button.toctree-expand,.btn .wy-menu-vertical li.on a button.toctree-expand,.btn .wy-menu-vertical li button.toctree-expand,.nav .fa,.nav .icon,.nav .rst-content .admonition-title,.nav .rst-content .code-block-caption .headerlink,.nav .rst-content .eqno .headerlink,.nav .rst-content code.download span:first-child,.nav .rst-content dl dt .headerlink,.nav .rst-content h1 .headerlink,.nav .rst-content h2 .headerlink,.nav .rst-content h3 .headerlink,.nav .rst-content h4 .headerlink,.nav .rst-content h5 .headerlink,.nav .rst-content h6 .headerlink,.nav .rst-content p .headerlink,.nav .rst-content table>caption .headerlink,.nav .rst-content tt.download span:first-child,.nav .wy-menu-vertical li.current>a button.toctree-expand,.nav .wy-menu-vertical li.on a button.toctree-expand,.nav .wy-menu-vertical li button.toctree-expand,.rst-content .btn .admonition-title,.rst-content .code-block-caption .btn .headerlink,.rst-content .code-block-caption .nav .headerlink,.rst-content .eqno .btn .headerlink,.rst-content .eqno .nav .headerlink,.rst-content .nav .admonition-title,.rst-content code.download .btn span:first-child,.rst-content code.download .nav span:first-child,.rst-content dl dt .btn .headerlink,.rst-content dl dt .nav .headerlink,.rst-content h1 .btn .headerlink,.rst-content h1 .nav .headerlink,.rst-content h2 .btn .headerlink,.rst-content h2 .nav .headerlink,.rst-content h3 .btn .headerlink,.rst-content h3 .nav .headerlink,.rst-content h4 .btn .headerlink,.rst-content h4 .nav .headerlink,.rst-content h5 .btn .headerlink,.rst-content h5 .nav .headerlink,.rst-content h6 .btn .headerlink,.rst-content h6 .nav .headerlink,.rst-content p .btn .headerlink,.rst-content p .nav .headerlink,.rst-content table>caption .btn .headerlink,.rst-content table>caption .nav .headerlink,.rst-content tt.download .btn span:first-child,.rst-content tt.download .nav span:first-child,.wy-menu-vertical li .btn button.toctree-expand,.wy-menu-vertical li.current>a .btn button.toctree-expand,.wy-menu-vertical li.current>a .nav button.toctree-expand,.wy-menu-vertical li .nav button.toctree-expand,.wy-menu-vertical li.on a .btn button.toctree-expand,.wy-menu-vertical li.on a .nav button.toctree-expand{display:inline}.btn .fa-large.icon,.btn .fa.fa-large,.btn .rst-content .code-block-caption .fa-large.headerlink,.btn .rst-content .eqno .fa-large.headerlink,.btn .rst-content .fa-large.admonition-title,.btn .rst-content code.download span.fa-large:first-child,.btn .rst-content dl dt .fa-large.headerlink,.btn .rst-content h1 .fa-large.headerlink,.btn .rst-content h2 .fa-large.headerlink,.btn .rst-content h3 .fa-large.headerlink,.btn .rst-content h4 .fa-large.headerlink,.btn .rst-content h5 .fa-large.headerlink,.btn .rst-content h6 .fa-large.headerlink,.btn .rst-content p .fa-large.headerlink,.btn .rst-content table>caption .fa-large.headerlink,.btn .rst-content tt.download span.fa-large:first-child,.btn .wy-menu-vertical li button.fa-large.toctree-expand,.nav .fa-large.icon,.nav .fa.fa-large,.nav .rst-content .code-block-caption .fa-large.headerlink,.nav .rst-content .eqno .fa-large.headerlink,.nav .rst-content .fa-large.admonition-title,.nav .rst-content code.download span.fa-large:first-child,.nav .rst-content dl dt .fa-large.headerlink,.nav .rst-content h1 .fa-large.headerlink,.nav .rst-content h2 .fa-large.headerlink,.nav .rst-content h3 .fa-large.headerlink,.nav .rst-content h4 .fa-large.headerlink,.nav .rst-content h5 .fa-large.headerlink,.nav .rst-content h6 .fa-large.headerlink,.nav .rst-content p .fa-large.headerlink,.nav .rst-content table>caption .fa-large.headerlink,.nav .rst-content tt.download span.fa-large:first-child,.nav .wy-menu-vertical li button.fa-large.toctree-expand,.rst-content .btn .fa-large.admonition-title,.rst-content .code-block-caption .btn .fa-large.headerlink,.rst-content .code-block-caption .nav .fa-large.headerlink,.rst-content .eqno .btn .fa-large.headerlink,.rst-content .eqno .nav .fa-large.headerlink,.rst-content .nav .fa-large.admonition-title,.rst-content code.download .btn span.fa-large:first-child,.rst-content code.download .nav span.fa-large:first-child,.rst-content dl dt .btn .fa-large.headerlink,.rst-content dl dt .nav .fa-large.headerlink,.rst-content h1 .btn .fa-large.headerlink,.rst-content h1 .nav .fa-large.headerlink,.rst-content h2 .btn .fa-large.headerlink,.rst-content h2 .nav .fa-large.headerlink,.rst-content h3 .btn .fa-large.headerlink,.rst-content h3 .nav .fa-large.headerlink,.rst-content h4 .btn .fa-large.headerlink,.rst-content h4 .nav .fa-large.headerlink,.rst-content h5 .btn .fa-large.headerlink,.rst-content h5 .nav .fa-large.headerlink,.rst-content h6 .btn .fa-large.headerlink,.rst-content h6 .nav .fa-large.headerlink,.rst-content p .btn .fa-large.headerlink,.rst-content p .nav .fa-large.headerlink,.rst-content table>caption .btn .fa-large.headerlink,.rst-content table>caption .nav .fa-large.headerlink,.rst-content tt.download .btn span.fa-large:first-child,.rst-content tt.download .nav span.fa-large:first-child,.wy-menu-vertical li .btn button.fa-large.toctree-expand,.wy-menu-vertical li .nav button.fa-large.toctree-expand{line-height:.9em}.btn .fa-spin.icon,.btn .fa.fa-spin,.btn .rst-content .code-block-caption .fa-spin.headerlink,.btn .rst-content .eqno .fa-spin.headerlink,.btn .rst-content .fa-spin.admonition-title,.btn .rst-content code.download span.fa-spin:first-child,.btn .rst-content dl dt .fa-spin.headerlink,.btn .rst-content h1 .fa-spin.headerlink,.btn .rst-content h2 .fa-spin.headerlink,.btn .rst-content h3 .fa-spin.headerlink,.btn .rst-content h4 .fa-spin.headerlink,.btn .rst-content h5 .fa-spin.headerlink,.btn .rst-content h6 .fa-spin.headerlink,.btn .rst-content p .fa-spin.headerlink,.btn .rst-content table>caption .fa-spin.headerlink,.btn .rst-content tt.download span.fa-spin:first-child,.btn .wy-menu-vertical li button.fa-spin.toctree-expand,.nav .fa-spin.icon,.nav .fa.fa-spin,.nav .rst-content .code-block-caption .fa-spin.headerlink,.nav .rst-content .eqno .fa-spin.headerlink,.nav .rst-content .fa-spin.admonition-title,.nav .rst-content code.download span.fa-spin:first-child,.nav .rst-content dl dt .fa-spin.headerlink,.nav .rst-content h1 .fa-spin.headerlink,.nav .rst-content h2 .fa-spin.headerlink,.nav .rst-content h3 .fa-spin.headerlink,.nav .rst-content h4 .fa-spin.headerlink,.nav .rst-content h5 .fa-spin.headerlink,.nav .rst-content h6 .fa-spin.headerlink,.nav .rst-content p .fa-spin.headerlink,.nav .rst-content table>caption .fa-spin.headerlink,.nav .rst-content tt.download span.fa-spin:first-child,.nav .wy-menu-vertical li button.fa-spin.toctree-expand,.rst-content .btn .fa-spin.admonition-title,.rst-content .code-block-caption .btn .fa-spin.headerlink,.rst-content .code-block-caption .nav .fa-spin.headerlink,.rst-content .eqno .btn .fa-spin.headerlink,.rst-content .eqno .nav .fa-spin.headerlink,.rst-content .nav .fa-spin.admonition-title,.rst-content code.download .btn span.fa-spin:first-child,.rst-content code.download .nav span.fa-spin:first-child,.rst-content dl dt .btn .fa-spin.headerlink,.rst-content dl dt .nav .fa-spin.headerlink,.rst-content h1 .btn .fa-spin.headerlink,.rst-content h1 .nav .fa-spin.headerlink,.rst-content h2 .btn .fa-spin.headerlink,.rst-content h2 .nav .fa-spin.headerlink,.rst-content h3 .btn .fa-spin.headerlink,.rst-content h3 .nav .fa-spin.headerlink,.rst-content h4 .btn .fa-spin.headerlink,.rst-content h4 .nav .fa-spin.headerlink,.rst-content h5 .btn .fa-spin.headerlink,.rst-content h5 .nav .fa-spin.headerlink,.rst-content h6 .btn .fa-spin.headerlink,.rst-content h6 .nav .fa-spin.headerlink,.rst-content p .btn .fa-spin.headerlink,.rst-content p .nav .fa-spin.headerlink,.rst-content table>caption .btn .fa-spin.headerlink,.rst-content table>caption .nav .fa-spin.headerlink,.rst-content tt.download .btn span.fa-spin:first-child,.rst-content tt.download .nav span.fa-spin:first-child,.wy-menu-vertical li .btn button.fa-spin.toctree-expand,.wy-menu-vertical li .nav button.fa-spin.toctree-expand{display:inline-block}.btn.fa:before,.btn.icon:before,.rst-content .btn.admonition-title:before,.rst-content .code-block-caption .btn.headerlink:before,.rst-content .eqno .btn.headerlink:before,.rst-content code.download span.btn:first-child:before,.rst-content dl dt .btn.headerlink:before,.rst-content h1 .btn.headerlink:before,.rst-content h2 .btn.headerlink:before,.rst-content h3 .btn.headerlink:before,.rst-content h4 .btn.headerlink:before,.rst-content h5 .btn.headerlink:before,.rst-content h6 .btn.headerlink:before,.rst-content p .btn.headerlink:before,.rst-content table>caption .btn.headerlink:before,.rst-content tt.download span.btn:first-child:before,.wy-menu-vertical li button.btn.toctree-expand:before{opacity:.5;-webkit-transition:opacity .05s ease-in;-moz-transition:opacity .05s ease-in;transition:opacity .05s ease-in}.btn.fa:hover:before,.btn.icon:hover:before,.rst-content .btn.admonition-title:hover:before,.rst-content .code-block-caption .btn.headerlink:hover:before,.rst-content .eqno .btn.headerlink:hover:before,.rst-content code.download span.btn:first-child:hover:before,.rst-content dl dt .btn.headerlink:hover:before,.rst-content h1 .btn.headerlink:hover:before,.rst-content h2 .btn.headerlink:hover:before,.rst-content h3 .btn.headerlink:hover:before,.rst-content h4 .btn.headerlink:hover:before,.rst-content h5 .btn.headerlink:hover:before,.rst-content h6 .btn.headerlink:hover:before,.rst-content p .btn.headerlink:hover:before,.rst-content table>caption .btn.headerlink:hover:before,.rst-content tt.download span.btn:first-child:hover:before,.wy-menu-vertical li button.btn.toctree-expand:hover:before{opacity:1}.btn-mini .fa:before,.btn-mini .icon:before,.btn-mini .rst-content .admonition-title:before,.btn-mini .rst-content .code-block-caption .headerlink:before,.btn-mini .rst-content .eqno .headerlink:before,.btn-mini .rst-content code.download span:first-child:before,.btn-mini .rst-content dl dt .headerlink:before,.btn-mini .rst-content h1 .headerlink:before,.btn-mini .rst-content h2 .headerlink:before,.btn-mini .rst-content h3 .headerlink:before,.btn-mini .rst-content h4 .headerlink:before,.btn-mini .rst-content h5 .headerlink:before,.btn-mini .rst-content h6 .headerlink:before,.btn-mini .rst-content p .headerlink:before,.btn-mini .rst-content table>caption .headerlink:before,.btn-mini .rst-content tt.download span:first-child:before,.btn-mini .wy-menu-vertical li button.toctree-expand:before,.rst-content .btn-mini .admonition-title:before,.rst-content .code-block-caption .btn-mini .headerlink:before,.rst-content .eqno .btn-mini .headerlink:before,.rst-content code.download .btn-mini span:first-child:before,.rst-content dl dt .btn-mini .headerlink:before,.rst-content h1 .btn-mini .headerlink:before,.rst-content h2 .btn-mini .headerlink:before,.rst-content h3 .btn-mini .headerlink:before,.rst-content h4 .btn-mini .headerlink:before,.rst-content h5 .btn-mini .headerlink:before,.rst-content h6 .btn-mini .headerlink:before,.rst-content p .btn-mini .headerlink:before,.rst-content table>caption .btn-mini .headerlink:before,.rst-content tt.download .btn-mini span:first-child:before,.wy-menu-vertical li .btn-mini button.toctree-expand:before{font-size:14px;vertical-align:-15%}.rst-content .admonition,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .danger,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning,.wy-alert{padding:12px;line-height:24px;margin-bottom:24px;background:#e7f2fa}.rst-content .admonition-title,.wy-alert-title{font-weight:700;display:block;color:#fff;background:#6ab0de;padding:6px 12px;margin:-12px -12px 12px}.rst-content .danger,.rst-content .error,.rst-content .wy-alert-danger.admonition,.rst-content .wy-alert-danger.admonition-todo,.rst-content .wy-alert-danger.attention,.rst-content .wy-alert-danger.caution,.rst-content .wy-alert-danger.hint,.rst-content .wy-alert-danger.important,.rst-content .wy-alert-danger.note,.rst-content .wy-alert-danger.seealso,.rst-content .wy-alert-danger.tip,.rst-content .wy-alert-danger.warning,.wy-alert.wy-alert-danger{background:#fdf3f2}.rst-content .danger .admonition-title,.rst-content .danger .wy-alert-title,.rst-content .error .admonition-title,.rst-content .error .wy-alert-title,.rst-content .wy-alert-danger.admonition-todo .admonition-title,.rst-content .wy-alert-danger.admonition-todo .wy-alert-title,.rst-content .wy-alert-danger.admonition .admonition-title,.rst-content .wy-alert-danger.admonition .wy-alert-title,.rst-content .wy-alert-danger.attention .admonition-title,.rst-content .wy-alert-danger.attention .wy-alert-title,.rst-content .wy-alert-danger.caution .admonition-title,.rst-content .wy-alert-danger.caution .wy-alert-title,.rst-content .wy-alert-danger.hint .admonition-title,.rst-content .wy-alert-danger.hint .wy-alert-title,.rst-content .wy-alert-danger.important .admonition-title,.rst-content .wy-alert-danger.important .wy-alert-title,.rst-content .wy-alert-danger.note .admonition-title,.rst-content .wy-alert-danger.note .wy-alert-title,.rst-content .wy-alert-danger.seealso .admonition-title,.rst-content .wy-alert-danger.seealso .wy-alert-title,.rst-content .wy-alert-danger.tip .admonition-title,.rst-content .wy-alert-danger.tip .wy-alert-title,.rst-content .wy-alert-danger.warning .admonition-title,.rst-content .wy-alert-danger.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-danger .admonition-title,.wy-alert.wy-alert-danger .rst-content .admonition-title,.wy-alert.wy-alert-danger .wy-alert-title{background:#f29f97}.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .warning,.rst-content .wy-alert-warning.admonition,.rst-content .wy-alert-warning.danger,.rst-content .wy-alert-warning.error,.rst-content .wy-alert-warning.hint,.rst-content .wy-alert-warning.important,.rst-content .wy-alert-warning.note,.rst-content .wy-alert-warning.seealso,.rst-content .wy-alert-warning.tip,.wy-alert.wy-alert-warning{background:#ffedcc}.rst-content .admonition-todo .admonition-title,.rst-content .admonition-todo .wy-alert-title,.rst-content .attention .admonition-title,.rst-content .attention .wy-alert-title,.rst-content .caution .admonition-title,.rst-content .caution .wy-alert-title,.rst-content .warning .admonition-title,.rst-content .warning .wy-alert-title,.rst-content .wy-alert-warning.admonition .admonition-title,.rst-content .wy-alert-warning.admonition .wy-alert-title,.rst-content .wy-alert-warning.danger .admonition-title,.rst-content .wy-alert-warning.danger .wy-alert-title,.rst-content .wy-alert-warning.error .admonition-title,.rst-content .wy-alert-warning.error .wy-alert-title,.rst-content .wy-alert-warning.hint .admonition-title,.rst-content .wy-alert-warning.hint .wy-alert-title,.rst-content .wy-alert-warning.important .admonition-title,.rst-content .wy-alert-warning.important .wy-alert-title,.rst-content .wy-alert-warning.note .admonition-title,.rst-content .wy-alert-warning.note .wy-alert-title,.rst-content .wy-alert-warning.seealso .admonition-title,.rst-content .wy-alert-warning.seealso .wy-alert-title,.rst-content .wy-alert-warning.tip .admonition-title,.rst-content .wy-alert-warning.tip .wy-alert-title,.rst-content .wy-alert.wy-alert-warning .admonition-title,.wy-alert.wy-alert-warning .rst-content .admonition-title,.wy-alert.wy-alert-warning .wy-alert-title{background:#f0b37e}.rst-content .note,.rst-content .seealso,.rst-content .wy-alert-info.admonition,.rst-content .wy-alert-info.admonition-todo,.rst-content .wy-alert-info.attention,.rst-content .wy-alert-info.caution,.rst-content .wy-alert-info.danger,.rst-content .wy-alert-info.error,.rst-content .wy-alert-info.hint,.rst-content .wy-alert-info.important,.rst-content .wy-alert-info.tip,.rst-content .wy-alert-info.warning,.wy-alert.wy-alert-info{background:#e7f2fa}.rst-content .note .admonition-title,.rst-content .note .wy-alert-title,.rst-content .seealso .admonition-title,.rst-content .seealso .wy-alert-title,.rst-content .wy-alert-info.admonition-todo .admonition-title,.rst-content .wy-alert-info.admonition-todo .wy-alert-title,.rst-content .wy-alert-info.admonition .admonition-title,.rst-content .wy-alert-info.admonition .wy-alert-title,.rst-content .wy-alert-info.attention .admonition-title,.rst-content .wy-alert-info.attention .wy-alert-title,.rst-content .wy-alert-info.caution .admonition-title,.rst-content .wy-alert-info.caution .wy-alert-title,.rst-content .wy-alert-info.danger .admonition-title,.rst-content .wy-alert-info.danger .wy-alert-title,.rst-content .wy-alert-info.error .admonition-title,.rst-content .wy-alert-info.error .wy-alert-title,.rst-content .wy-alert-info.hint .admonition-title,.rst-content .wy-alert-info.hint .wy-alert-title,.rst-content .wy-alert-info.important .admonition-title,.rst-content .wy-alert-info.important .wy-alert-title,.rst-content .wy-alert-info.tip .admonition-title,.rst-content .wy-alert-info.tip .wy-alert-title,.rst-content .wy-alert-info.warning .admonition-title,.rst-content .wy-alert-info.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-info .admonition-title,.wy-alert.wy-alert-info .rst-content .admonition-title,.wy-alert.wy-alert-info .wy-alert-title{background:#6ab0de}.rst-content .hint,.rst-content .important,.rst-content .tip,.rst-content .wy-alert-success.admonition,.rst-content .wy-alert-success.admonition-todo,.rst-content .wy-alert-success.attention,.rst-content .wy-alert-success.caution,.rst-content .wy-alert-success.danger,.rst-content .wy-alert-success.error,.rst-content .wy-alert-success.note,.rst-content .wy-alert-success.seealso,.rst-content .wy-alert-success.warning,.wy-alert.wy-alert-success{background:#dbfaf4}.rst-content .hint .admonition-title,.rst-content .hint .wy-alert-title,.rst-content .important .admonition-title,.rst-content .important .wy-alert-title,.rst-content .tip .admonition-title,.rst-content .tip .wy-alert-title,.rst-content .wy-alert-success.admonition-todo .admonition-title,.rst-content .wy-alert-success.admonition-todo .wy-alert-title,.rst-content .wy-alert-success.admonition .admonition-title,.rst-content .wy-alert-success.admonition .wy-alert-title,.rst-content .wy-alert-success.attention .admonition-title,.rst-content .wy-alert-success.attention .wy-alert-title,.rst-content .wy-alert-success.caution .admonition-title,.rst-content .wy-alert-success.caution .wy-alert-title,.rst-content .wy-alert-success.danger .admonition-title,.rst-content .wy-alert-success.danger .wy-alert-title,.rst-content .wy-alert-success.error .admonition-title,.rst-content .wy-alert-success.error .wy-alert-title,.rst-content .wy-alert-success.note .admonition-title,.rst-content .wy-alert-success.note .wy-alert-title,.rst-content .wy-alert-success.seealso .admonition-title,.rst-content .wy-alert-success.seealso .wy-alert-title,.rst-content .wy-alert-success.warning .admonition-title,.rst-content .wy-alert-success.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-success .admonition-title,.wy-alert.wy-alert-success .rst-content .admonition-title,.wy-alert.wy-alert-success .wy-alert-title{background:#1abc9c}.rst-content .wy-alert-neutral.admonition,.rst-content .wy-alert-neutral.admonition-todo,.rst-content .wy-alert-neutral.attention,.rst-content .wy-alert-neutral.caution,.rst-content .wy-alert-neutral.danger,.rst-content .wy-alert-neutral.error,.rst-content .wy-alert-neutral.hint,.rst-content .wy-alert-neutral.important,.rst-content .wy-alert-neutral.note,.rst-content .wy-alert-neutral.seealso,.rst-content .wy-alert-neutral.tip,.rst-content .wy-alert-neutral.warning,.wy-alert.wy-alert-neutral{background:#f3f6f6}.rst-content .wy-alert-neutral.admonition-todo .admonition-title,.rst-content .wy-alert-neutral.admonition-todo .wy-alert-title,.rst-content .wy-alert-neutral.admonition .admonition-title,.rst-content .wy-alert-neutral.admonition .wy-alert-title,.rst-content .wy-alert-neutral.attention .admonition-title,.rst-content .wy-alert-neutral.attention .wy-alert-title,.rst-content .wy-alert-neutral.caution .admonition-title,.rst-content .wy-alert-neutral.caution .wy-alert-title,.rst-content .wy-alert-neutral.danger .admonition-title,.rst-content .wy-alert-neutral.danger .wy-alert-title,.rst-content .wy-alert-neutral.error .admonition-title,.rst-content .wy-alert-neutral.error .wy-alert-title,.rst-content .wy-alert-neutral.hint .admonition-title,.rst-content .wy-alert-neutral.hint .wy-alert-title,.rst-content .wy-alert-neutral.important .admonition-title,.rst-content .wy-alert-neutral.important .wy-alert-title,.rst-content .wy-alert-neutral.note .admonition-title,.rst-content .wy-alert-neutral.note .wy-alert-title,.rst-content .wy-alert-neutral.seealso .admonition-title,.rst-content .wy-alert-neutral.seealso .wy-alert-title,.rst-content .wy-alert-neutral.tip .admonition-title,.rst-content .wy-alert-neutral.tip .wy-alert-title,.rst-content .wy-alert-neutral.warning .admonition-title,.rst-content .wy-alert-neutral.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-neutral .admonition-title,.wy-alert.wy-alert-neutral .rst-content .admonition-title,.wy-alert.wy-alert-neutral .wy-alert-title{color:#404040;background:#e1e4e5}.rst-content .wy-alert-neutral.admonition-todo a,.rst-content .wy-alert-neutral.admonition a,.rst-content .wy-alert-neutral.attention a,.rst-content .wy-alert-neutral.caution a,.rst-content .wy-alert-neutral.danger a,.rst-content .wy-alert-neutral.error a,.rst-content .wy-alert-neutral.hint a,.rst-content .wy-alert-neutral.important a,.rst-content .wy-alert-neutral.note a,.rst-content .wy-alert-neutral.seealso a,.rst-content .wy-alert-neutral.tip a,.rst-content .wy-alert-neutral.warning a,.wy-alert.wy-alert-neutral a{color:#2980b9}.rst-content .admonition-todo p:last-child,.rst-content .admonition p:last-child,.rst-content .attention p:last-child,.rst-content .caution p:last-child,.rst-content .danger p:last-child,.rst-content .error p:last-child,.rst-content .hint p:last-child,.rst-content .important p:last-child,.rst-content .note p:last-child,.rst-content .seealso p:last-child,.rst-content .tip p:last-child,.rst-content .warning p:last-child,.wy-alert p:last-child{margin-bottom:0}.wy-tray-container{position:fixed;bottom:0;left:0;z-index:600}.wy-tray-container li{display:block;width:300px;background:transparent;color:#fff;text-align:center;box-shadow:0 5px 5px 0 rgba(0,0,0,.1);padding:0 24px;min-width:20%;opacity:0;height:0;line-height:56px;overflow:hidden;-webkit-transition:all .3s ease-in;-moz-transition:all .3s ease-in;transition:all .3s ease-in}.wy-tray-container li.wy-tray-item-success{background:#27ae60}.wy-tray-container li.wy-tray-item-info{background:#2980b9}.wy-tray-container li.wy-tray-item-warning{background:#e67e22}.wy-tray-container li.wy-tray-item-danger{background:#e74c3c}.wy-tray-container li.on{opacity:1;height:56px}@media screen and (max-width:768px){.wy-tray-container{bottom:auto;top:0;width:100%}.wy-tray-container li{width:100%}}button{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle;cursor:pointer;line-height:normal;-webkit-appearance:button;*overflow:visible}button::-moz-focus-inner,input::-moz-focus-inner{border:0;padding:0}button[disabled]{cursor:default}.btn{display:inline-block;border-radius:2px;line-height:normal;white-space:nowrap;text-align:center;cursor:pointer;font-size:100%;padding:6px 12px 8px;color:#fff;border:1px solid rgba(0,0,0,.1);background-color:#27ae60;text-decoration:none;font-weight:400;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;box-shadow:inset 0 1px 2px -1px hsla(0,0%,100%,.5),inset 0 -2px 0 0 rgba(0,0,0,.1);outline-none:false;vertical-align:middle;*display:inline;zoom:1;-webkit-user-drag:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;-webkit-transition:all .1s linear;-moz-transition:all .1s linear;transition:all .1s linear}.btn-hover{background:#2e8ece;color:#fff}.btn:hover{background:#2cc36b;color:#fff}.btn:focus{background:#2cc36b;outline:0}.btn:active{box-shadow:inset 0 -1px 0 0 rgba(0,0,0,.05),inset 0 2px 0 0 rgba(0,0,0,.1);padding:8px 12px 6px}.btn:visited{color:#fff}.btn-disabled,.btn-disabled:active,.btn-disabled:focus,.btn-disabled:hover,.btn:disabled{background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);filter:alpha(opacity=40);opacity:.4;cursor:not-allowed;box-shadow:none}.btn::-moz-focus-inner{padding:0;border:0}.btn-small{font-size:80%}.btn-info{background-color:#2980b9!important}.btn-info:hover{background-color:#2e8ece!important}.btn-neutral{background-color:#f3f6f6!important;color:#404040!important}.btn-neutral:hover{background-color:#e5ebeb!important;color:#404040}.btn-neutral:visited{color:#404040!important}.btn-success{background-color:#27ae60!important}.btn-success:hover{background-color:#295!important}.btn-danger{background-color:#e74c3c!important}.btn-danger:hover{background-color:#ea6153!important}.btn-warning{background-color:#e67e22!important}.btn-warning:hover{background-color:#e98b39!important}.btn-invert{background-color:#222}.btn-invert:hover{background-color:#2f2f2f!important}.btn-link{background-color:transparent!important;color:#2980b9;box-shadow:none;border-color:transparent!important}.btn-link:active,.btn-link:hover{background-color:transparent!important;color:#409ad5!important;box-shadow:none}.btn-link:visited{color:#9b59b6}.wy-btn-group .btn,.wy-control .btn{vertical-align:middle}.wy-btn-group{margin-bottom:24px;*zoom:1}.wy-btn-group:after,.wy-btn-group:before{display:table;content:""}.wy-btn-group:after{clear:both}.wy-dropdown{position:relative;display:inline-block}.wy-dropdown-active .wy-dropdown-menu{display:block}.wy-dropdown-menu{position:absolute;left:0;display:none;float:left;top:100%;min-width:100%;background:#fcfcfc;z-index:100;border:1px solid #cfd7dd;box-shadow:0 2px 2px 0 rgba(0,0,0,.1);padding:12px}.wy-dropdown-menu>dd>a{display:block;clear:both;color:#404040;white-space:nowrap;font-size:90%;padding:0 12px;cursor:pointer}.wy-dropdown-menu>dd>a:hover{background:#2980b9;color:#fff}.wy-dropdown-menu>dd.divider{border-top:1px solid #cfd7dd;margin:6px 0}.wy-dropdown-menu>dd.search{padding-bottom:12px}.wy-dropdown-menu>dd.search input[type=search]{width:100%}.wy-dropdown-menu>dd.call-to-action{background:#e3e3e3;text-transform:uppercase;font-weight:500;font-size:80%}.wy-dropdown-menu>dd.call-to-action:hover{background:#e3e3e3}.wy-dropdown-menu>dd.call-to-action .btn{color:#fff}.wy-dropdown.wy-dropdown-up .wy-dropdown-menu{bottom:100%;top:auto;left:auto;right:0}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu{background:#fcfcfc;margin-top:2px}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu a{padding:6px 12px}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu a:hover{background:#2980b9;color:#fff}.wy-dropdown.wy-dropdown-left .wy-dropdown-menu{right:0;left:auto;text-align:right}.wy-dropdown-arrow:before{content:" ";border-bottom:5px solid #f5f5f5;border-left:5px solid transparent;border-right:5px solid transparent;position:absolute;display:block;top:-4px;left:50%;margin-left:-3px}.wy-dropdown-arrow.wy-dropdown-arrow-left:before{left:11px}.wy-form-stacked select{display:block}.wy-form-aligned .wy-help-inline,.wy-form-aligned input,.wy-form-aligned label,.wy-form-aligned select,.wy-form-aligned textarea{display:inline-block;*display:inline;*zoom:1;vertical-align:middle}.wy-form-aligned .wy-control-group>label{display:inline-block;vertical-align:middle;width:10em;margin:6px 12px 0 0;float:left}.wy-form-aligned .wy-control{float:left}.wy-form-aligned .wy-control label{display:block}.wy-form-aligned .wy-control select{margin-top:6px}fieldset{margin:0}fieldset,legend{border:0;padding:0}legend{width:100%;white-space:normal;margin-bottom:24px;font-size:150%;*margin-left:-7px}label,legend{display:block}label{margin:0 0 .3125em;color:#333;font-size:90%}input,select,textarea{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle}.wy-control-group{margin-bottom:24px;max-width:1200px;margin-left:auto;margin-right:auto;*zoom:1}.wy-control-group:after,.wy-control-group:before{display:table;content:""}.wy-control-group:after{clear:both}.wy-control-group.wy-control-group-required>label:after{content:" *";color:#e74c3c}.wy-control-group .wy-form-full,.wy-control-group .wy-form-halves,.wy-control-group .wy-form-thirds{padding-bottom:12px}.wy-control-group .wy-form-full input[type=color],.wy-control-group .wy-form-full input[type=date],.wy-control-group .wy-form-full input[type=datetime-local],.wy-control-group .wy-form-full input[type=datetime],.wy-control-group .wy-form-full input[type=email],.wy-control-group .wy-form-full input[type=month],.wy-control-group .wy-form-full input[type=number],.wy-control-group .wy-form-full input[type=password],.wy-control-group .wy-form-full input[type=search],.wy-control-group .wy-form-full input[type=tel],.wy-control-group .wy-form-full input[type=text],.wy-control-group .wy-form-full input[type=time],.wy-control-group .wy-form-full input[type=url],.wy-control-group .wy-form-full input[type=week],.wy-control-group .wy-form-full select,.wy-control-group .wy-form-halves input[type=color],.wy-control-group .wy-form-halves input[type=date],.wy-control-group .wy-form-halves input[type=datetime-local],.wy-control-group .wy-form-halves input[type=datetime],.wy-control-group .wy-form-halves input[type=email],.wy-control-group .wy-form-halves input[type=month],.wy-control-group .wy-form-halves input[type=number],.wy-control-group .wy-form-halves input[type=password],.wy-control-group .wy-form-halves input[type=search],.wy-control-group .wy-form-halves input[type=tel],.wy-control-group .wy-form-halves input[type=text],.wy-control-group .wy-form-halves input[type=time],.wy-control-group .wy-form-halves input[type=url],.wy-control-group .wy-form-halves input[type=week],.wy-control-group .wy-form-halves select,.wy-control-group .wy-form-thirds input[type=color],.wy-control-group .wy-form-thirds input[type=date],.wy-control-group .wy-form-thirds input[type=datetime-local],.wy-control-group .wy-form-thirds input[type=datetime],.wy-control-group .wy-form-thirds input[type=email],.wy-control-group .wy-form-thirds input[type=month],.wy-control-group .wy-form-thirds input[type=number],.wy-control-group .wy-form-thirds input[type=password],.wy-control-group .wy-form-thirds input[type=search],.wy-control-group .wy-form-thirds input[type=tel],.wy-control-group .wy-form-thirds input[type=text],.wy-control-group .wy-form-thirds input[type=time],.wy-control-group .wy-form-thirds input[type=url],.wy-control-group .wy-form-thirds input[type=week],.wy-control-group .wy-form-thirds select{width:100%}.wy-control-group .wy-form-full{float:left;display:block;width:100%;margin-right:0}.wy-control-group .wy-form-full:last-child{margin-right:0}.wy-control-group .wy-form-halves{float:left;display:block;margin-right:2.35765%;width:48.82117%}.wy-control-group .wy-form-halves:last-child,.wy-control-group .wy-form-halves:nth-of-type(2n){margin-right:0}.wy-control-group .wy-form-halves:nth-of-type(odd){clear:left}.wy-control-group .wy-form-thirds{float:left;display:block;margin-right:2.35765%;width:31.76157%}.wy-control-group .wy-form-thirds:last-child,.wy-control-group .wy-form-thirds:nth-of-type(3n){margin-right:0}.wy-control-group .wy-form-thirds:nth-of-type(3n+1){clear:left}.wy-control-group.wy-control-group-no-input .wy-control,.wy-control-no-input{margin:6px 0 0;font-size:90%}.wy-control-no-input{display:inline-block}.wy-control-group.fluid-input input[type=color],.wy-control-group.fluid-input input[type=date],.wy-control-group.fluid-input input[type=datetime-local],.wy-control-group.fluid-input input[type=datetime],.wy-control-group.fluid-input input[type=email],.wy-control-group.fluid-input input[type=month],.wy-control-group.fluid-input input[type=number],.wy-control-group.fluid-input input[type=password],.wy-control-group.fluid-input input[type=search],.wy-control-group.fluid-input input[type=tel],.wy-control-group.fluid-input input[type=text],.wy-control-group.fluid-input input[type=time],.wy-control-group.fluid-input input[type=url],.wy-control-group.fluid-input input[type=week]{width:100%}.wy-form-message-inline{padding-left:.3em;color:#666;font-size:90%}.wy-form-message{display:block;color:#999;font-size:70%;margin-top:.3125em;font-style:italic}.wy-form-message p{font-size:inherit;font-style:italic;margin-bottom:6px}.wy-form-message p:last-child{margin-bottom:0}input{line-height:normal}input[type=button],input[type=reset],input[type=submit]{-webkit-appearance:button;cursor:pointer;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;*overflow:visible}input[type=color],input[type=date],input[type=datetime-local],input[type=datetime],input[type=email],input[type=month],input[type=number],input[type=password],input[type=search],input[type=tel],input[type=text],input[type=time],input[type=url],input[type=week]{-webkit-appearance:none;padding:6px;display:inline-block;border:1px solid #ccc;font-size:80%;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;box-shadow:inset 0 1px 3px #ddd;border-radius:0;-webkit-transition:border .3s linear;-moz-transition:border .3s linear;transition:border .3s linear}input[type=datetime-local]{padding:.34375em .625em}input[disabled]{cursor:default}input[type=checkbox],input[type=radio]{padding:0;margin-right:.3125em;*height:13px;*width:13px}input[type=checkbox],input[type=radio],input[type=search]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type=search]::-webkit-search-cancel-button,input[type=search]::-webkit-search-decoration{-webkit-appearance:none}input[type=color]:focus,input[type=date]:focus,input[type=datetime-local]:focus,input[type=datetime]:focus,input[type=email]:focus,input[type=month]:focus,input[type=number]:focus,input[type=password]:focus,input[type=search]:focus,input[type=tel]:focus,input[type=text]:focus,input[type=time]:focus,input[type=url]:focus,input[type=week]:focus{outline:0;outline:thin dotted\9;border-color:#333}input.no-focus:focus{border-color:#ccc!important}input[type=checkbox]:focus,input[type=file]:focus,input[type=radio]:focus{outline:thin dotted #333;outline:1px auto #129fea}input[type=color][disabled],input[type=date][disabled],input[type=datetime-local][disabled],input[type=datetime][disabled],input[type=email][disabled],input[type=month][disabled],input[type=number][disabled],input[type=password][disabled],input[type=search][disabled],input[type=tel][disabled],input[type=text][disabled],input[type=time][disabled],input[type=url][disabled],input[type=week][disabled]{cursor:not-allowed;background-color:#fafafa}input:focus:invalid,select:focus:invalid,textarea:focus:invalid{color:#e74c3c;border:1px solid #e74c3c}input:focus:invalid:focus,select:focus:invalid:focus,textarea:focus:invalid:focus{border-color:#e74c3c}input[type=checkbox]:focus:invalid:focus,input[type=file]:focus:invalid:focus,input[type=radio]:focus:invalid:focus{outline-color:#e74c3c}input.wy-input-large{padding:12px;font-size:100%}textarea{overflow:auto;vertical-align:top;width:100%;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif}select,textarea{padding:.5em .625em;display:inline-block;border:1px solid #ccc;font-size:80%;box-shadow:inset 0 1px 3px #ddd;-webkit-transition:border .3s linear;-moz-transition:border .3s linear;transition:border .3s linear}select{border:1px solid #ccc;background-color:#fff}select[multiple]{height:auto}select:focus,textarea:focus{outline:0}input[readonly],select[disabled],select[readonly],textarea[disabled],textarea[readonly]{cursor:not-allowed;background-color:#fafafa}input[type=checkbox][disabled],input[type=radio][disabled]{cursor:not-allowed}.wy-checkbox,.wy-radio{margin:6px 0;color:#404040;display:block}.wy-checkbox input,.wy-radio input{vertical-align:baseline}.wy-form-message-inline{display:inline-block;*display:inline;*zoom:1;vertical-align:middle}.wy-input-prefix,.wy-input-suffix{white-space:nowrap;padding:6px}.wy-input-prefix .wy-input-context,.wy-input-suffix .wy-input-context{line-height:27px;padding:0 8px;display:inline-block;font-size:80%;background-color:#f3f6f6;border:1px solid #ccc;color:#999}.wy-input-suffix .wy-input-context{border-left:0}.wy-input-prefix .wy-input-context{border-right:0}.wy-switch{position:relative;display:block;height:24px;margin-top:12px;cursor:pointer}.wy-switch:before{left:0;top:0;width:36px;height:12px;background:#ccc}.wy-switch:after,.wy-switch:before{position:absolute;content:"";display:block;border-radius:4px;-webkit-transition:all .2s ease-in-out;-moz-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.wy-switch:after{width:18px;height:18px;background:#999;left:-3px;top:-3px}.wy-switch span{position:absolute;left:48px;display:block;font-size:12px;color:#ccc;line-height:1}.wy-switch.active:before{background:#1e8449}.wy-switch.active:after{left:24px;background:#27ae60}.wy-switch.disabled{cursor:not-allowed;opacity:.8}.wy-control-group.wy-control-group-error .wy-form-message,.wy-control-group.wy-control-group-error>label{color:#e74c3c}.wy-control-group.wy-control-group-error input[type=color],.wy-control-group.wy-control-group-error input[type=date],.wy-control-group.wy-control-group-error input[type=datetime-local],.wy-control-group.wy-control-group-error input[type=datetime],.wy-control-group.wy-control-group-error input[type=email],.wy-control-group.wy-control-group-error input[type=month],.wy-control-group.wy-control-group-error input[type=number],.wy-control-group.wy-control-group-error input[type=password],.wy-control-group.wy-control-group-error input[type=search],.wy-control-group.wy-control-group-error input[type=tel],.wy-control-group.wy-control-group-error input[type=text],.wy-control-group.wy-control-group-error input[type=time],.wy-control-group.wy-control-group-error input[type=url],.wy-control-group.wy-control-group-error input[type=week],.wy-control-group.wy-control-group-error textarea{border:1px solid #e74c3c}.wy-inline-validate{white-space:nowrap}.wy-inline-validate .wy-input-context{padding:.5em .625em;display:inline-block;font-size:80%}.wy-inline-validate.wy-inline-validate-success .wy-input-context{color:#27ae60}.wy-inline-validate.wy-inline-validate-danger .wy-input-context{color:#e74c3c}.wy-inline-validate.wy-inline-validate-warning .wy-input-context{color:#e67e22}.wy-inline-validate.wy-inline-validate-info .wy-input-context{color:#2980b9}.rotate-90{-webkit-transform:rotate(90deg);-moz-transform:rotate(90deg);-ms-transform:rotate(90deg);-o-transform:rotate(90deg);transform:rotate(90deg)}.rotate-180{-webkit-transform:rotate(180deg);-moz-transform:rotate(180deg);-ms-transform:rotate(180deg);-o-transform:rotate(180deg);transform:rotate(180deg)}.rotate-270{-webkit-transform:rotate(270deg);-moz-transform:rotate(270deg);-ms-transform:rotate(270deg);-o-transform:rotate(270deg);transform:rotate(270deg)}.mirror{-webkit-transform:scaleX(-1);-moz-transform:scaleX(-1);-ms-transform:scaleX(-1);-o-transform:scaleX(-1);transform:scaleX(-1)}.mirror.rotate-90{-webkit-transform:scaleX(-1) rotate(90deg);-moz-transform:scaleX(-1) rotate(90deg);-ms-transform:scaleX(-1) rotate(90deg);-o-transform:scaleX(-1) rotate(90deg);transform:scaleX(-1) rotate(90deg)}.mirror.rotate-180{-webkit-transform:scaleX(-1) rotate(180deg);-moz-transform:scaleX(-1) rotate(180deg);-ms-transform:scaleX(-1) rotate(180deg);-o-transform:scaleX(-1) rotate(180deg);transform:scaleX(-1) rotate(180deg)}.mirror.rotate-270{-webkit-transform:scaleX(-1) rotate(270deg);-moz-transform:scaleX(-1) rotate(270deg);-ms-transform:scaleX(-1) rotate(270deg);-o-transform:scaleX(-1) rotate(270deg);transform:scaleX(-1) rotate(270deg)}@media only screen and (max-width:480px){.wy-form button[type=submit]{margin:.7em 0 0}.wy-form input[type=color],.wy-form input[type=date],.wy-form input[type=datetime-local],.wy-form input[type=datetime],.wy-form input[type=email],.wy-form input[type=month],.wy-form input[type=number],.wy-form input[type=password],.wy-form input[type=search],.wy-form input[type=tel],.wy-form input[type=text],.wy-form input[type=time],.wy-form input[type=url],.wy-form input[type=week],.wy-form label{margin-bottom:.3em;display:block}.wy-form input[type=color],.wy-form input[type=date],.wy-form input[type=datetime-local],.wy-form input[type=datetime],.wy-form input[type=email],.wy-form input[type=month],.wy-form input[type=number],.wy-form input[type=password],.wy-form input[type=search],.wy-form input[type=tel],.wy-form input[type=time],.wy-form input[type=url],.wy-form input[type=week]{margin-bottom:0}.wy-form-aligned .wy-control-group label{margin-bottom:.3em;text-align:left;display:block;width:100%}.wy-form-aligned .wy-control{margin:1.5em 0 0}.wy-form-message,.wy-form-message-inline,.wy-form .wy-help-inline{display:block;font-size:80%;padding:6px 0}}@media screen and (max-width:768px){.tablet-hide{display:none}}@media screen and (max-width:480px){.mobile-hide{display:none}}.float-left{float:left}.float-right{float:right}.full-width{width:100%}.rst-content table.docutils,.rst-content table.field-list,.wy-table{border-collapse:collapse;border-spacing:0;empty-cells:show;margin-bottom:24px}.rst-content table.docutils caption,.rst-content table.field-list caption,.wy-table caption{color:#000;font:italic 85%/1 arial,sans-serif;padding:1em 0;text-align:center}.rst-content table.docutils td,.rst-content table.docutils th,.rst-content table.field-list td,.rst-content table.field-list th,.wy-table td,.wy-table th{font-size:90%;margin:0;overflow:visible;padding:8px 16px}.rst-content table.docutils td:first-child,.rst-content table.docutils th:first-child,.rst-content table.field-list td:first-child,.rst-content table.field-list th:first-child,.wy-table td:first-child,.wy-table th:first-child{border-left-width:0}.rst-content table.docutils thead,.rst-content table.field-list thead,.wy-table thead{color:#000;text-align:left;vertical-align:bottom;white-space:nowrap}.rst-content table.docutils thead th,.rst-content table.field-list thead th,.wy-table thead th{font-weight:700;border-bottom:2px solid #e1e4e5}.rst-content table.docutils td,.rst-content table.field-list td,.wy-table td{background-color:transparent;vertical-align:middle}.rst-content table.docutils td p,.rst-content table.field-list td p,.wy-table td p{line-height:18px}.rst-content table.docutils td p:last-child,.rst-content table.field-list td p:last-child,.wy-table td p:last-child{margin-bottom:0}.rst-content table.docutils .wy-table-cell-min,.rst-content table.field-list .wy-table-cell-min,.wy-table .wy-table-cell-min{width:1%;padding-right:0}.rst-content table.docutils .wy-table-cell-min input[type=checkbox],.rst-content table.field-list .wy-table-cell-min input[type=checkbox],.wy-table .wy-table-cell-min input[type=checkbox]{margin:0}.wy-table-secondary{color:grey;font-size:90%}.wy-table-tertiary{color:grey;font-size:80%}.rst-content table.docutils:not(.field-list) tr:nth-child(2n-1) td,.wy-table-backed,.wy-table-odd td,.wy-table-striped tr:nth-child(2n-1) td{background-color:#f3f6f6}.rst-content table.docutils,.wy-table-bordered-all{border:1px solid #e1e4e5}.rst-content table.docutils td,.wy-table-bordered-all td{border-bottom:1px solid #e1e4e5;border-left:1px solid #e1e4e5}.rst-content table.docutils tbody>tr:last-child td,.wy-table-bordered-all tbody>tr:last-child td{border-bottom-width:0}.wy-table-bordered{border:1px solid #e1e4e5}.wy-table-bordered-rows td{border-bottom:1px solid #e1e4e5}.wy-table-bordered-rows tbody>tr:last-child td{border-bottom-width:0}.wy-table-horizontal td,.wy-table-horizontal th{border-width:0 0 1px;border-bottom:1px solid #e1e4e5}.wy-table-horizontal tbody>tr:last-child td{border-bottom-width:0}.wy-table-responsive{margin-bottom:24px;max-width:100%;overflow:auto}.wy-table-responsive table{margin-bottom:0!important}.wy-table-responsive table td,.wy-table-responsive table th{white-space:nowrap}a{color:#2980b9;text-decoration:none;cursor:pointer}a:hover{color:#3091d1}a:visited{color:#9b59b6}html{height:100%}body,html{overflow-x:hidden}body{font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;font-weight:400;color:#404040;min-height:100%;background:#edf0f2}.wy-text-left{text-align:left}.wy-text-center{text-align:center}.wy-text-right{text-align:right}.wy-text-large{font-size:120%}.wy-text-normal{font-size:100%}.wy-text-small,small{font-size:80%}.wy-text-strike{text-decoration:line-through}.wy-text-warning{color:#e67e22!important}a.wy-text-warning:hover{color:#eb9950!important}.wy-text-info{color:#2980b9!important}a.wy-text-info:hover{color:#409ad5!important}.wy-text-success{color:#27ae60!important}a.wy-text-success:hover{color:#36d278!important}.wy-text-danger{color:#e74c3c!important}a.wy-text-danger:hover{color:#ed7669!important}.wy-text-neutral{color:#404040!important}a.wy-text-neutral:hover{color:#595959!important}.rst-content .toctree-wrapper>p.caption,h1,h2,h3,h4,h5,h6,legend{margin-top:0;font-weight:700;font-family:Roboto Slab,ff-tisa-web-pro,Georgia,Arial,sans-serif}p{line-height:24px;font-size:16px;margin:0 0 24px}h1{font-size:175%}.rst-content .toctree-wrapper>p.caption,h2{font-size:150%}h3{font-size:125%}h4{font-size:115%}h5{font-size:110%}h6{font-size:100%}hr{display:block;height:1px;border:0;border-top:1px solid #e1e4e5;margin:24px 0;padding:0}.rst-content code,.rst-content tt,code{white-space:nowrap;max-width:100%;background:#fff;border:1px solid #e1e4e5;font-size:75%;padding:0 5px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;color:#e74c3c;overflow-x:auto}.rst-content tt.code-large,code.code-large{font-size:90%}.rst-content .section ul,.rst-content .toctree-wrapper ul,.rst-content section ul,.wy-plain-list-disc,article ul{list-style:disc;line-height:24px;margin-bottom:24px}.rst-content .section ul li,.rst-content .toctree-wrapper ul li,.rst-content section ul li,.wy-plain-list-disc li,article ul li{list-style:disc;margin-left:24px}.rst-content .section ul li p:last-child,.rst-content .section ul li ul,.rst-content .toctree-wrapper ul li p:last-child,.rst-content .toctree-wrapper ul li ul,.rst-content section ul li p:last-child,.rst-content section ul li ul,.wy-plain-list-disc li p:last-child,.wy-plain-list-disc li ul,article ul li p:last-child,article ul li ul{margin-bottom:0}.rst-content .section ul li li,.rst-content .toctree-wrapper ul li li,.rst-content section ul li li,.wy-plain-list-disc li li,article ul li li{list-style:circle}.rst-content .section ul li li li,.rst-content .toctree-wrapper ul li li li,.rst-content section ul li li li,.wy-plain-list-disc li li li,article ul li li li{list-style:square}.rst-content .section ul li ol li,.rst-content .toctree-wrapper ul li ol li,.rst-content section ul li ol li,.wy-plain-list-disc li ol li,article ul li ol li{list-style:decimal}.rst-content .section ol,.rst-content .section ol.arabic,.rst-content .toctree-wrapper ol,.rst-content .toctree-wrapper ol.arabic,.rst-content section ol,.rst-content section ol.arabic,.wy-plain-list-decimal,article ol{list-style:decimal;line-height:24px;margin-bottom:24px}.rst-content .section ol.arabic li,.rst-content .section ol li,.rst-content .toctree-wrapper ol.arabic li,.rst-content .toctree-wrapper ol li,.rst-content section ol.arabic li,.rst-content section ol li,.wy-plain-list-decimal li,article ol li{list-style:decimal;margin-left:24px}.rst-content .section ol.arabic li ul,.rst-content .section ol li p:last-child,.rst-content .section ol li ul,.rst-content .toctree-wrapper ol.arabic li ul,.rst-content .toctree-wrapper ol li p:last-child,.rst-content .toctree-wrapper ol li ul,.rst-content section ol.arabic li ul,.rst-content section ol li p:last-child,.rst-content section ol li ul,.wy-plain-list-decimal li p:last-child,.wy-plain-list-decimal li ul,article ol li p:last-child,article ol li ul{margin-bottom:0}.rst-content .section ol.arabic li ul li,.rst-content .section ol li ul li,.rst-content .toctree-wrapper ol.arabic li ul li,.rst-content .toctree-wrapper ol li ul li,.rst-content section ol.arabic li ul li,.rst-content section ol li ul li,.wy-plain-list-decimal li ul li,article ol li ul li{list-style:disc}.wy-breadcrumbs{*zoom:1}.wy-breadcrumbs:after,.wy-breadcrumbs:before{display:table;content:""}.wy-breadcrumbs:after{clear:both}.wy-breadcrumbs li{display:inline-block}.wy-breadcrumbs li.wy-breadcrumbs-aside{float:right}.wy-breadcrumbs li a{display:inline-block;padding:5px}.wy-breadcrumbs li a:first-child{padding-left:0}.rst-content .wy-breadcrumbs li tt,.wy-breadcrumbs li .rst-content tt,.wy-breadcrumbs li code{padding:5px;border:none;background:none}.rst-content .wy-breadcrumbs li tt.literal,.wy-breadcrumbs li .rst-content tt.literal,.wy-breadcrumbs li code.literal{color:#404040}.wy-breadcrumbs-extra{margin-bottom:0;color:#b3b3b3;font-size:80%;display:inline-block}@media screen and (max-width:480px){.wy-breadcrumbs-extra,.wy-breadcrumbs li.wy-breadcrumbs-aside{display:none}}@media print{.wy-breadcrumbs li.wy-breadcrumbs-aside{display:none}}html{font-size:16px}.wy-affix{position:fixed;top:1.618em}.wy-menu a:hover{text-decoration:none}.wy-menu-horiz{*zoom:1}.wy-menu-horiz:after,.wy-menu-horiz:before{display:table;content:""}.wy-menu-horiz:after{clear:both}.wy-menu-horiz li,.wy-menu-horiz ul{display:inline-block}.wy-menu-horiz li:hover{background:hsla(0,0%,100%,.1)}.wy-menu-horiz li.divide-left{border-left:1px solid #404040}.wy-menu-horiz li.divide-right{border-right:1px solid #404040}.wy-menu-horiz a{height:32px;display:inline-block;line-height:32px;padding:0 16px}.wy-menu-vertical{width:300px}.wy-menu-vertical header,.wy-menu-vertical p.caption{color:#55a5d9;height:32px;line-height:32px;padding:0 1.618em;margin:12px 0 0;display:block;font-weight:700;text-transform:uppercase;font-size:85%;white-space:nowrap}.wy-menu-vertical ul{margin-bottom:0}.wy-menu-vertical li.divide-top{border-top:1px solid #404040}.wy-menu-vertical li.divide-bottom{border-bottom:1px solid #404040}.wy-menu-vertical li.current{background:#e3e3e3}.wy-menu-vertical li.current a{color:grey;border-right:1px solid #c9c9c9;padding:.4045em 2.427em}.wy-menu-vertical li.current a:hover{background:#d6d6d6}.rst-content .wy-menu-vertical li tt,.wy-menu-vertical li .rst-content tt,.wy-menu-vertical li code{border:none;background:inherit;color:inherit;padding-left:0;padding-right:0}.wy-menu-vertical li button.toctree-expand{display:block;float:left;margin-left:-1.2em;line-height:18px;color:#4d4d4d;border:none;background:none;padding:0}.wy-menu-vertical li.current>a,.wy-menu-vertical li.on a{color:#404040;font-weight:700;position:relative;background:#fcfcfc;border:none;padding:.4045em 1.618em}.wy-menu-vertical li.current>a:hover,.wy-menu-vertical li.on a:hover{background:#fcfcfc}.wy-menu-vertical li.current>a:hover button.toctree-expand,.wy-menu-vertical li.on a:hover button.toctree-expand{color:grey}.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand{display:block;line-height:18px;color:#333}.wy-menu-vertical li.toctree-l1.current>a{border-bottom:1px solid #c9c9c9;border-top:1px solid #c9c9c9}.wy-menu-vertical .toctree-l1.current .toctree-l2>ul,.wy-menu-vertical .toctree-l2.current .toctree-l3>ul,.wy-menu-vertical .toctree-l3.current .toctree-l4>ul,.wy-menu-vertical .toctree-l4.current .toctree-l5>ul,.wy-menu-vertical .toctree-l5.current .toctree-l6>ul,.wy-menu-vertical .toctree-l6.current .toctree-l7>ul,.wy-menu-vertical .toctree-l7.current .toctree-l8>ul,.wy-menu-vertical .toctree-l8.current .toctree-l9>ul,.wy-menu-vertical .toctree-l9.current .toctree-l10>ul,.wy-menu-vertical .toctree-l10.current .toctree-l11>ul{display:none}.wy-menu-vertical .toctree-l1.current .current.toctree-l2>ul,.wy-menu-vertical .toctree-l2.current .current.toctree-l3>ul,.wy-menu-vertical .toctree-l3.current .current.toctree-l4>ul,.wy-menu-vertical .toctree-l4.current .current.toctree-l5>ul,.wy-menu-vertical .toctree-l5.current .current.toctree-l6>ul,.wy-menu-vertical .toctree-l6.current .current.toctree-l7>ul,.wy-menu-vertical .toctree-l7.current .current.toctree-l8>ul,.wy-menu-vertical .toctree-l8.current .current.toctree-l9>ul,.wy-menu-vertical .toctree-l9.current .current.toctree-l10>ul,.wy-menu-vertical .toctree-l10.current .current.toctree-l11>ul{display:block}.wy-menu-vertical li.toctree-l3,.wy-menu-vertical li.toctree-l4{font-size:.9em}.wy-menu-vertical li.toctree-l2 a,.wy-menu-vertical li.toctree-l3 a,.wy-menu-vertical li.toctree-l4 a,.wy-menu-vertical li.toctree-l5 a,.wy-menu-vertical li.toctree-l6 a,.wy-menu-vertical li.toctree-l7 a,.wy-menu-vertical li.toctree-l8 a,.wy-menu-vertical li.toctree-l9 a,.wy-menu-vertical li.toctree-l10 a{color:#404040}.wy-menu-vertical li.toctree-l2 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l3 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l4 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l5 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l6 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l7 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l8 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l9 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l10 a:hover button.toctree-expand{color:grey}.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a,.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a,.wy-menu-vertical li.toctree-l4.current li.toctree-l5>a,.wy-menu-vertical li.toctree-l5.current li.toctree-l6>a,.wy-menu-vertical li.toctree-l6.current li.toctree-l7>a,.wy-menu-vertical li.toctree-l7.current li.toctree-l8>a,.wy-menu-vertical li.toctree-l8.current li.toctree-l9>a,.wy-menu-vertical li.toctree-l9.current li.toctree-l10>a,.wy-menu-vertical li.toctree-l10.current li.toctree-l11>a{display:block}.wy-menu-vertical li.toctree-l2.current>a{padding:.4045em 2.427em}.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a{padding:.4045em 1.618em .4045em 4.045em}.wy-menu-vertical li.toctree-l3.current>a{padding:.4045em 4.045em}.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a{padding:.4045em 1.618em .4045em 5.663em}.wy-menu-vertical li.toctree-l4.current>a{padding:.4045em 5.663em}.wy-menu-vertical li.toctree-l4.current li.toctree-l5>a{padding:.4045em 1.618em .4045em 7.281em}.wy-menu-vertical li.toctree-l5.current>a{padding:.4045em 7.281em}.wy-menu-vertical li.toctree-l5.current li.toctree-l6>a{padding:.4045em 1.618em .4045em 8.899em}.wy-menu-vertical li.toctree-l6.current>a{padding:.4045em 8.899em}.wy-menu-vertical li.toctree-l6.current li.toctree-l7>a{padding:.4045em 1.618em .4045em 10.517em}.wy-menu-vertical li.toctree-l7.current>a{padding:.4045em 10.517em}.wy-menu-vertical li.toctree-l7.current li.toctree-l8>a{padding:.4045em 1.618em .4045em 12.135em}.wy-menu-vertical li.toctree-l8.current>a{padding:.4045em 12.135em}.wy-menu-vertical li.toctree-l8.current li.toctree-l9>a{padding:.4045em 1.618em .4045em 13.753em}.wy-menu-vertical li.toctree-l9.current>a{padding:.4045em 13.753em}.wy-menu-vertical li.toctree-l9.current li.toctree-l10>a{padding:.4045em 1.618em .4045em 15.371em}.wy-menu-vertical li.toctree-l10.current>a{padding:.4045em 15.371em}.wy-menu-vertical li.toctree-l10.current li.toctree-l11>a{padding:.4045em 1.618em .4045em 16.989em}.wy-menu-vertical li.toctree-l2.current>a,.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a{background:#c9c9c9}.wy-menu-vertical li.toctree-l2 button.toctree-expand{color:#a3a3a3}.wy-menu-vertical li.toctree-l3.current>a,.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a{background:#bdbdbd}.wy-menu-vertical li.toctree-l3 button.toctree-expand{color:#969696}.wy-menu-vertical li.current ul{display:block}.wy-menu-vertical li ul{margin-bottom:0;display:none}.wy-menu-vertical li ul li a{margin-bottom:0;color:#d9d9d9;font-weight:400}.wy-menu-vertical a{line-height:18px;padding:.4045em 1.618em;display:block;position:relative;font-size:90%;color:#d9d9d9}.wy-menu-vertical a:hover{background-color:#4e4a4a;cursor:pointer}.wy-menu-vertical a:hover button.toctree-expand{color:#d9d9d9}.wy-menu-vertical a:active{background-color:#2980b9;cursor:pointer;color:#fff}.wy-menu-vertical a:active button.toctree-expand{color:#fff}.wy-side-nav-search{display:block;width:300px;padding:.809em;margin-bottom:.809em;z-index:200;background-color:#2980b9;text-align:center;color:#fcfcfc}.wy-side-nav-search input[type=text]{width:100%;border-radius:50px;padding:6px 12px;border-color:#2472a4}.wy-side-nav-search img{display:block;margin:auto auto .809em;height:45px;width:45px;background-color:#2980b9;padding:5px;border-radius:100%}.wy-side-nav-search .wy-dropdown>a,.wy-side-nav-search>a{color:#fcfcfc;font-size:100%;font-weight:700;display:inline-block;padding:4px 6px;margin-bottom:.809em;max-width:100%}.wy-side-nav-search .wy-dropdown>a:hover,.wy-side-nav-search>a:hover{background:hsla(0,0%,100%,.1)}.wy-side-nav-search .wy-dropdown>a img.logo,.wy-side-nav-search>a img.logo{display:block;margin:0 auto;height:auto;width:auto;border-radius:0;max-width:100%;background:transparent}.wy-side-nav-search .wy-dropdown>a.icon img.logo,.wy-side-nav-search>a.icon img.logo{margin-top:.85em}.wy-side-nav-search>div.version{margin-top:-.4045em;margin-bottom:.809em;font-weight:400;color:hsla(0,0%,100%,.3)}.wy-nav .wy-menu-vertical header{color:#2980b9}.wy-nav .wy-menu-vertical a{color:#b3b3b3}.wy-nav .wy-menu-vertical a:hover{background-color:#2980b9;color:#fff}[data-menu-wrap]{-webkit-transition:all .2s ease-in;-moz-transition:all .2s ease-in;transition:all .2s ease-in;position:absolute;opacity:1;width:100%;opacity:0}[data-menu-wrap].move-center{left:0;right:auto;opacity:1}[data-menu-wrap].move-left{right:auto;left:-100%;opacity:0}[data-menu-wrap].move-right{right:-100%;left:auto;opacity:0}.wy-body-for-nav{background:#fcfcfc}.wy-grid-for-nav{position:absolute;width:100%;height:100%}.wy-nav-side{position:fixed;top:0;bottom:0;left:0;padding-bottom:2em;width:300px;overflow-x:hidden;overflow-y:hidden;min-height:100%;color:#9b9b9b;background:#343131;z-index:200}.wy-side-scroll{width:320px;position:relative;overflow-x:hidden;overflow-y:scroll;height:100%}.wy-nav-top{display:none;background:#2980b9;color:#fff;padding:.4045em .809em;position:relative;line-height:50px;text-align:center;font-size:100%;*zoom:1}.wy-nav-top:after,.wy-nav-top:before{display:table;content:""}.wy-nav-top:after{clear:both}.wy-nav-top a{color:#fff;font-weight:700}.wy-nav-top img{margin-right:12px;height:45px;width:45px;background-color:#2980b9;padding:5px;border-radius:100%}.wy-nav-top i{font-size:30px;float:left;cursor:pointer;padding-top:inherit}.wy-nav-content-wrap{margin-left:300px;background:#fcfcfc;min-height:100%}.wy-nav-content{padding:1.618em 3.236em;height:100%;max-width:800px;margin:auto}.wy-body-mask{position:fixed;width:100%;height:100%;background:rgba(0,0,0,.2);display:none;z-index:499}.wy-body-mask.on{display:block}footer{color:grey}footer p{margin-bottom:12px}.rst-content footer span.commit tt,footer span.commit .rst-content tt,footer span.commit code{padding:0;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;font-size:1em;background:none;border:none;color:grey}.rst-footer-buttons{*zoom:1}.rst-footer-buttons:after,.rst-footer-buttons:before{width:100%;display:table;content:""}.rst-footer-buttons:after{clear:both}.rst-breadcrumbs-buttons{margin-top:12px;*zoom:1}.rst-breadcrumbs-buttons:after,.rst-breadcrumbs-buttons:before{display:table;content:""}.rst-breadcrumbs-buttons:after{clear:both}#search-results .search li{margin-bottom:24px;border-bottom:1px solid #e1e4e5;padding-bottom:24px}#search-results .search li:first-child{border-top:1px solid #e1e4e5;padding-top:24px}#search-results .search li a{font-size:120%;margin-bottom:12px;display:inline-block}#search-results .context{color:grey;font-size:90%}.genindextable li>ul{margin-left:24px}@media screen and (max-width:768px){.wy-body-for-nav{background:#fcfcfc}.wy-nav-top{display:block}.wy-nav-side{left:-300px}.wy-nav-side.shift{width:85%;left:0}.wy-menu.wy-menu-vertical,.wy-side-nav-search,.wy-side-scroll{width:auto}.wy-nav-content-wrap{margin-left:0}.wy-nav-content-wrap .wy-nav-content{padding:1.618em}.wy-nav-content-wrap.shift{position:fixed;min-width:100%;left:85%;top:0;height:100%;overflow:hidden}}@media screen and (min-width:1100px){.wy-nav-content-wrap{background:rgba(0,0,0,.05)}.wy-nav-content{margin:0;background:#fcfcfc}}@media print{.rst-versions,.wy-nav-side,footer{display:none}.wy-nav-content-wrap{margin-left:0}}.rst-versions{position:fixed;bottom:0;left:0;width:300px;color:#fcfcfc;background:#1f1d1d;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;z-index:400}.rst-versions a{color:#2980b9;text-decoration:none}.rst-versions .rst-badge-small{display:none}.rst-versions .rst-current-version{padding:12px;background-color:#272525;display:block;text-align:right;font-size:90%;cursor:pointer;color:#27ae60;*zoom:1}.rst-versions .rst-current-version:after,.rst-versions .rst-current-version:before{display:table;content:""}.rst-versions .rst-current-version:after{clear:both}.rst-content .code-block-caption .rst-versions .rst-current-version .headerlink,.rst-content .eqno .rst-versions .rst-current-version .headerlink,.rst-content .rst-versions .rst-current-version .admonition-title,.rst-content code.download .rst-versions .rst-current-version span:first-child,.rst-content dl dt .rst-versions .rst-current-version .headerlink,.rst-content h1 .rst-versions .rst-current-version .headerlink,.rst-content h2 .rst-versions .rst-current-version .headerlink,.rst-content h3 .rst-versions .rst-current-version .headerlink,.rst-content h4 .rst-versions .rst-current-version .headerlink,.rst-content h5 .rst-versions .rst-current-version .headerlink,.rst-content h6 .rst-versions .rst-current-version .headerlink,.rst-content p .rst-versions .rst-current-version .headerlink,.rst-content table>caption .rst-versions .rst-current-version .headerlink,.rst-content tt.download .rst-versions .rst-current-version span:first-child,.rst-versions .rst-current-version .fa,.rst-versions .rst-current-version .icon,.rst-versions .rst-current-version .rst-content .admonition-title,.rst-versions .rst-current-version .rst-content .code-block-caption .headerlink,.rst-versions .rst-current-version .rst-content .eqno .headerlink,.rst-versions .rst-current-version .rst-content code.download span:first-child,.rst-versions .rst-current-version .rst-content dl dt .headerlink,.rst-versions .rst-current-version .rst-content h1 .headerlink,.rst-versions .rst-current-version .rst-content h2 .headerlink,.rst-versions .rst-current-version .rst-content h3 .headerlink,.rst-versions .rst-current-version .rst-content h4 .headerlink,.rst-versions .rst-current-version .rst-content h5 .headerlink,.rst-versions .rst-current-version .rst-content h6 .headerlink,.rst-versions .rst-current-version .rst-content p .headerlink,.rst-versions .rst-current-version .rst-content table>caption .headerlink,.rst-versions .rst-current-version .rst-content tt.download span:first-child,.rst-versions .rst-current-version .wy-menu-vertical li button.toctree-expand,.wy-menu-vertical li .rst-versions .rst-current-version button.toctree-expand{color:#fcfcfc}.rst-versions .rst-current-version .fa-book,.rst-versions .rst-current-version .icon-book{float:left}.rst-versions .rst-current-version.rst-out-of-date{background-color:#e74c3c;color:#fff}.rst-versions .rst-current-version.rst-active-old-version{background-color:#f1c40f;color:#000}.rst-versions.shift-up{height:auto;max-height:100%;overflow-y:scroll}.rst-versions.shift-up .rst-other-versions{display:block}.rst-versions .rst-other-versions{font-size:90%;padding:12px;color:grey;display:none}.rst-versions .rst-other-versions hr{display:block;height:1px;border:0;margin:20px 0;padding:0;border-top:1px solid #413d3d}.rst-versions .rst-other-versions dd{display:inline-block;margin:0}.rst-versions .rst-other-versions dd a{display:inline-block;padding:6px;color:#fcfcfc}.rst-versions.rst-badge{width:auto;bottom:20px;right:20px;left:auto;border:none;max-width:300px;max-height:90%}.rst-versions.rst-badge .fa-book,.rst-versions.rst-badge .icon-book{float:none;line-height:30px}.rst-versions.rst-badge.shift-up .rst-current-version{text-align:right}.rst-versions.rst-badge.shift-up .rst-current-version .fa-book,.rst-versions.rst-badge.shift-up .rst-current-version .icon-book{float:left}.rst-versions.rst-badge>.rst-current-version{width:auto;height:30px;line-height:30px;padding:0 6px;display:block;text-align:center}@media screen and (max-width:768px){.rst-versions{width:85%;display:none}.rst-versions.shift{display:block}}.rst-content .toctree-wrapper>p.caption,.rst-content h1,.rst-content h2,.rst-content h3,.rst-content h4,.rst-content h5,.rst-content h6{margin-bottom:24px}.rst-content img{max-width:100%;height:auto}.rst-content div.figure,.rst-content figure{margin-bottom:24px}.rst-content div.figure .caption-text,.rst-content figure .caption-text{font-style:italic}.rst-content div.figure p:last-child.caption,.rst-content figure p:last-child.caption{margin-bottom:0}.rst-content div.figure.align-center,.rst-content figure.align-center{text-align:center}.rst-content .section>a>img,.rst-content .section>img,.rst-content section>a>img,.rst-content section>img{margin-bottom:24px}.rst-content abbr[title]{text-decoration:none}.rst-content.style-external-links a.reference.external:after{font-family:FontAwesome;content:"\f08e";color:#b3b3b3;vertical-align:super;font-size:60%;margin:0 .2em}.rst-content blockquote{margin-left:24px;line-height:24px;margin-bottom:24px}.rst-content pre.literal-block{white-space:pre;margin:0;padding:12px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;display:block;overflow:auto}.rst-content div[class^=highlight],.rst-content pre.literal-block{border:1px solid #e1e4e5;overflow-x:auto;margin:1px 0 24px}.rst-content div[class^=highlight] div[class^=highlight],.rst-content pre.literal-block div[class^=highlight]{padding:0;border:none;margin:0}.rst-content div[class^=highlight] td.code{width:100%}.rst-content .linenodiv pre{border-right:1px solid #e6e9ea;margin:0;padding:12px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;user-select:none;pointer-events:none}.rst-content div[class^=highlight] pre{white-space:pre;margin:0;padding:12px;display:block;overflow:auto}.rst-content div[class^=highlight] pre .hll{display:block;margin:0 -12px;padding:0 12px}.rst-content .linenodiv pre,.rst-content div[class^=highlight] pre,.rst-content pre.literal-block{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;font-size:12px;line-height:1.4}.rst-content div.highlight .gp,.rst-content div.highlight span.linenos{user-select:none;pointer-events:none}.rst-content div.highlight span.linenos{display:inline-block;padding-left:0;padding-right:12px;margin-right:12px;border-right:1px solid #e6e9ea}.rst-content .code-block-caption{font-style:italic;font-size:85%;line-height:1;padding:1em 0;text-align:center}@media print{.rst-content .codeblock,.rst-content div[class^=highlight],.rst-content div[class^=highlight] pre{white-space:pre-wrap}}.rst-content .admonition,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .danger,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning{clear:both}.rst-content .admonition-todo .last,.rst-content .admonition-todo>:last-child,.rst-content .admonition .last,.rst-content .admonition>:last-child,.rst-content .attention .last,.rst-content .attention>:last-child,.rst-content .caution .last,.rst-content .caution>:last-child,.rst-content .danger .last,.rst-content .danger>:last-child,.rst-content .error .last,.rst-content .error>:last-child,.rst-content .hint .last,.rst-content .hint>:last-child,.rst-content .important .last,.rst-content .important>:last-child,.rst-content .note .last,.rst-content .note>:last-child,.rst-content .seealso .last,.rst-content .seealso>:last-child,.rst-content .tip .last,.rst-content .tip>:last-child,.rst-content .warning .last,.rst-content .warning>:last-child{margin-bottom:0}.rst-content .admonition-title:before{margin-right:4px}.rst-content .admonition table{border-color:rgba(0,0,0,.1)}.rst-content .admonition table td,.rst-content .admonition table th{background:transparent!important;border-color:rgba(0,0,0,.1)!important}.rst-content .section ol.loweralpha,.rst-content .section ol.loweralpha>li,.rst-content .toctree-wrapper ol.loweralpha,.rst-content .toctree-wrapper ol.loweralpha>li,.rst-content section ol.loweralpha,.rst-content section ol.loweralpha>li{list-style:lower-alpha}.rst-content .section ol.upperalpha,.rst-content .section ol.upperalpha>li,.rst-content .toctree-wrapper ol.upperalpha,.rst-content .toctree-wrapper ol.upperalpha>li,.rst-content section ol.upperalpha,.rst-content section ol.upperalpha>li{list-style:upper-alpha}.rst-content .section ol li>*,.rst-content .section ul li>*,.rst-content .toctree-wrapper ol li>*,.rst-content .toctree-wrapper ul li>*,.rst-content section ol li>*,.rst-content section ul li>*{margin-top:12px;margin-bottom:12px}.rst-content .section ol li>:first-child,.rst-content .section ul li>:first-child,.rst-content .toctree-wrapper ol li>:first-child,.rst-content .toctree-wrapper ul li>:first-child,.rst-content section ol li>:first-child,.rst-content section ul li>:first-child{margin-top:0}.rst-content .section ol li>p,.rst-content .section ol li>p:last-child,.rst-content .section ul li>p,.rst-content .section ul li>p:last-child,.rst-content .toctree-wrapper ol li>p,.rst-content .toctree-wrapper ol li>p:last-child,.rst-content .toctree-wrapper ul li>p,.rst-content .toctree-wrapper ul li>p:last-child,.rst-content section ol li>p,.rst-content section ol li>p:last-child,.rst-content section ul li>p,.rst-content section ul li>p:last-child{margin-bottom:12px}.rst-content .section ol li>p:only-child,.rst-content .section ol li>p:only-child:last-child,.rst-content .section ul li>p:only-child,.rst-content .section ul li>p:only-child:last-child,.rst-content .toctree-wrapper ol li>p:only-child,.rst-content .toctree-wrapper ol li>p:only-child:last-child,.rst-content .toctree-wrapper ul li>p:only-child,.rst-content .toctree-wrapper ul li>p:only-child:last-child,.rst-content section ol li>p:only-child,.rst-content section ol li>p:only-child:last-child,.rst-content section ul li>p:only-child,.rst-content section ul li>p:only-child:last-child{margin-bottom:0}.rst-content .section ol li>ol,.rst-content .section ol li>ul,.rst-content .section ul li>ol,.rst-content .section ul li>ul,.rst-content .toctree-wrapper ol li>ol,.rst-content .toctree-wrapper ol li>ul,.rst-content .toctree-wrapper ul li>ol,.rst-content .toctree-wrapper ul li>ul,.rst-content section ol li>ol,.rst-content section ol li>ul,.rst-content section ul li>ol,.rst-content section ul li>ul{margin-bottom:12px}.rst-content .section ol.simple li>*,.rst-content .section ol.simple li ol,.rst-content .section ol.simple li ul,.rst-content .section ul.simple li>*,.rst-content .section ul.simple li ol,.rst-content .section ul.simple li ul,.rst-content .toctree-wrapper ol.simple li>*,.rst-content .toctree-wrapper ol.simple li ol,.rst-content .toctree-wrapper ol.simple li ul,.rst-content .toctree-wrapper ul.simple li>*,.rst-content .toctree-wrapper ul.simple li ol,.rst-content .toctree-wrapper ul.simple li ul,.rst-content section ol.simple li>*,.rst-content section ol.simple li ol,.rst-content section ol.simple li ul,.rst-content section ul.simple li>*,.rst-content section ul.simple li ol,.rst-content section ul.simple li ul{margin-top:0;margin-bottom:0}.rst-content .line-block{margin-left:0;margin-bottom:24px;line-height:24px}.rst-content .line-block .line-block{margin-left:24px;margin-bottom:0}.rst-content .topic-title{font-weight:700;margin-bottom:12px}.rst-content .toc-backref{color:#404040}.rst-content .align-right{float:right;margin:0 0 24px 24px}.rst-content .align-left{float:left;margin:0 24px 24px 0}.rst-content .align-center{margin:auto}.rst-content .align-center:not(table){display:block}.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content .toctree-wrapper>p.caption .headerlink,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink{opacity:0;font-size:14px;font-family:FontAwesome;margin-left:.5em}.rst-content .code-block-caption .headerlink:focus,.rst-content .code-block-caption:hover .headerlink,.rst-content .eqno .headerlink:focus,.rst-content .eqno:hover .headerlink,.rst-content .toctree-wrapper>p.caption .headerlink:focus,.rst-content .toctree-wrapper>p.caption:hover .headerlink,.rst-content dl dt .headerlink:focus,.rst-content dl dt:hover .headerlink,.rst-content h1 .headerlink:focus,.rst-content h1:hover .headerlink,.rst-content h2 .headerlink:focus,.rst-content h2:hover .headerlink,.rst-content h3 .headerlink:focus,.rst-content h3:hover .headerlink,.rst-content h4 .headerlink:focus,.rst-content h4:hover .headerlink,.rst-content h5 .headerlink:focus,.rst-content h5:hover .headerlink,.rst-content h6 .headerlink:focus,.rst-content h6:hover .headerlink,.rst-content p.caption .headerlink:focus,.rst-content p.caption:hover .headerlink,.rst-content p .headerlink:focus,.rst-content p:hover .headerlink,.rst-content table>caption .headerlink:focus,.rst-content table>caption:hover .headerlink{opacity:1}.rst-content .btn:focus{outline:2px solid}.rst-content table>caption .headerlink:after{font-size:12px}.rst-content .centered{text-align:center}.rst-content .sidebar{float:right;width:40%;display:block;margin:0 0 24px 24px;padding:24px;background:#f3f6f6;border:1px solid #e1e4e5}.rst-content .sidebar dl,.rst-content .sidebar p,.rst-content .sidebar ul{font-size:90%}.rst-content .sidebar .last,.rst-content .sidebar>:last-child{margin-bottom:0}.rst-content .sidebar .sidebar-title{display:block;font-family:Roboto Slab,ff-tisa-web-pro,Georgia,Arial,sans-serif;font-weight:700;background:#e1e4e5;padding:6px 12px;margin:-24px -24px 24px;font-size:100%}.rst-content .highlighted{background:#f1c40f;box-shadow:0 0 0 2px #f1c40f;display:inline;font-weight:700}.rst-content .citation-reference,.rst-content .footnote-reference{vertical-align:baseline;position:relative;top:-.4em;line-height:0;font-size:90%}.rst-content .hlist{width:100%}.rst-content dl dt span.classifier:before{content:" : "}.rst-content dl dt span.classifier-delimiter{display:none!important}html.writer-html4 .rst-content table.docutils.citation,html.writer-html4 .rst-content table.docutils.footnote{background:none;border:none}html.writer-html4 .rst-content table.docutils.citation td,html.writer-html4 .rst-content table.docutils.citation tr,html.writer-html4 .rst-content table.docutils.footnote td,html.writer-html4 .rst-content table.docutils.footnote tr{border:none;background-color:transparent!important;white-space:normal}html.writer-html4 .rst-content table.docutils.citation td.label,html.writer-html4 .rst-content table.docutils.footnote td.label{padding-left:0;padding-right:0;vertical-align:top}html.writer-html5 .rst-content dl.field-list,html.writer-html5 .rst-content dl.footnote{display:grid;grid-template-columns:max-content auto}html.writer-html5 .rst-content dl.field-list>dt,html.writer-html5 .rst-content dl.footnote>dt{padding-left:1rem}html.writer-html5 .rst-content dl.field-list>dt:after,html.writer-html5 .rst-content dl.footnote>dt:after{content:":"}html.writer-html5 .rst-content dl.field-list>dd,html.writer-html5 .rst-content dl.field-list>dt,html.writer-html5 .rst-content dl.footnote>dd,html.writer-html5 .rst-content dl.footnote>dt{margin-bottom:0}html.writer-html5 .rst-content dl.footnote{font-size:.9rem}html.writer-html5 .rst-content dl.footnote>dt{margin:0 .5rem .5rem 0;line-height:1.2rem;word-break:break-all;font-weight:400}html.writer-html5 .rst-content dl.footnote>dt>span.brackets{margin-right:.5rem}html.writer-html5 .rst-content dl.footnote>dt>span.brackets:before{content:"["}html.writer-html5 .rst-content dl.footnote>dt>span.brackets:after{content:"]"}html.writer-html5 .rst-content dl.footnote>dt>span.fn-backref{font-style:italic}html.writer-html5 .rst-content dl.footnote>dd{margin:0 0 .5rem;line-height:1.2rem}html.writer-html5 .rst-content dl.footnote>dd p,html.writer-html5 .rst-content dl.option-list kbd{font-size:.9rem}.rst-content table.docutils.footnote,html.writer-html4 .rst-content table.docutils.citation,html.writer-html5 .rst-content dl.footnote{color:grey}.rst-content table.docutils.footnote code,.rst-content table.docutils.footnote tt,html.writer-html4 .rst-content table.docutils.citation code,html.writer-html4 .rst-content table.docutils.citation tt,html.writer-html5 .rst-content dl.footnote code,html.writer-html5 .rst-content dl.footnote tt{color:#555}.rst-content .wy-table-responsive.citation,.rst-content .wy-table-responsive.footnote{margin-bottom:0}.rst-content .wy-table-responsive.citation+:not(.citation),.rst-content .wy-table-responsive.footnote+:not(.footnote){margin-top:24px}.rst-content .wy-table-responsive.citation:last-child,.rst-content .wy-table-responsive.footnote:last-child{margin-bottom:24px}.rst-content table.docutils th{border-color:#e1e4e5}html.writer-html5 .rst-content table.docutils th{border:1px solid #e1e4e5}html.writer-html5 .rst-content table.docutils td>p,html.writer-html5 .rst-content table.docutils th>p{line-height:1rem;margin-bottom:0;font-size:.9rem}.rst-content table.docutils td .last,.rst-content table.docutils td .last>:last-child{margin-bottom:0}.rst-content table.field-list,.rst-content table.field-list td{border:none}.rst-content table.field-list td p{font-size:inherit;line-height:inherit}.rst-content table.field-list td>strong{display:inline-block}.rst-content table.field-list .field-name{padding-right:10px;text-align:left;white-space:nowrap}.rst-content table.field-list .field-body{text-align:left}.rst-content code,.rst-content tt{color:#000;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;padding:2px 5px}.rst-content code big,.rst-content code em,.rst-content tt big,.rst-content tt em{font-size:100%!important;line-height:normal}.rst-content code.literal,.rst-content tt.literal{color:#e74c3c;white-space:normal}.rst-content code.xref,.rst-content tt.xref,a .rst-content code,a .rst-content tt{font-weight:700;color:#404040}.rst-content kbd,.rst-content pre,.rst-content samp{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace}.rst-content a code,.rst-content a tt{color:#2980b9}.rst-content dl{margin-bottom:24px}.rst-content dl dt{font-weight:700;margin-bottom:12px}.rst-content dl ol,.rst-content dl p,.rst-content dl table,.rst-content dl ul{margin-bottom:12px}.rst-content dl dd{margin:0 0 12px 24px;line-height:24px}html.writer-html4 .rst-content dl:not(.docutils),html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple){margin-bottom:24px}html.writer-html4 .rst-content dl:not(.docutils)>dt,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt{display:table;margin:6px 0;font-size:90%;line-height:normal;background:#e7f2fa;color:#2980b9;border-top:3px solid #6ab0de;padding:6px;position:relative}html.writer-html4 .rst-content dl:not(.docutils)>dt:before,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt:before{color:#6ab0de}html.writer-html4 .rst-content dl:not(.docutils)>dt .headerlink,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt .headerlink{color:#404040;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils) dl:not(.field-list)>dt,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) dl:not(.field-list)>dt{margin-bottom:6px;border:none;border-left:3px solid #ccc;background:#f0f0f0;color:#555}html.writer-html4 .rst-content dl:not(.docutils) dl:not(.field-list)>dt .headerlink,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) dl:not(.field-list)>dt .headerlink{color:#404040;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils)>dt:first-child,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt:first-child{margin-top:0}html.writer-html4 .rst-content dl:not(.docutils) code.descclassname,html.writer-html4 .rst-content dl:not(.docutils) code.descname,html.writer-html4 .rst-content dl:not(.docutils) tt.descclassname,html.writer-html4 .rst-content dl:not(.docutils) tt.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descname{background-color:transparent;border:none;padding:0;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils) code.descname,html.writer-html4 .rst-content dl:not(.docutils) tt.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descname{font-weight:700}html.writer-html4 .rst-content dl:not(.docutils) .optional,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .optional{display:inline-block;padding:0 4px;color:#000;font-weight:700}html.writer-html4 .rst-content dl:not(.docutils) .property,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .property{display:inline-block;padding-right:8px;max-width:100%}html.writer-html4 .rst-content dl:not(.docutils) .k,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .k{font-style:italic}html.writer-html4 .rst-content dl:not(.docutils) .descclassname,html.writer-html4 .rst-content dl:not(.docutils) .descname,html.writer-html4 .rst-content dl:not(.docutils) .sig-name,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .sig-name{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;color:#000}.rst-content .viewcode-back,.rst-content .viewcode-link{display:inline-block;color:#27ae60;font-size:80%;padding-left:24px}.rst-content .viewcode-back{display:block;float:right}.rst-content p.rubric{margin-bottom:12px;font-weight:700}.rst-content code.download,.rst-content tt.download{background:inherit;padding:inherit;font-weight:400;font-family:inherit;font-size:inherit;color:inherit;border:inherit;white-space:inherit}.rst-content code.download span:first-child,.rst-content tt.download span:first-child{-webkit-font-smoothing:subpixel-antialiased}.rst-content code.download span:first-child:before,.rst-content tt.download span:first-child:before{margin-right:4px}.rst-content .guilabel{border:1px solid #7fbbe3;background:#e7f2fa;font-size:80%;font-weight:700;border-radius:4px;padding:2.4px 6px;margin:auto 2px}.rst-content .versionmodified{font-style:italic}@media screen and (max-width:480px){.rst-content .sidebar{width:100%}}span[id*=MathJax-Span]{color:#404040}.math{text-align:center}@font-face{font-family:Lato;src:url(fonts/lato-normal.woff2?bd03a2cc277bbbc338d464e679fe9942) format("woff2"),url(fonts/lato-normal.woff?27bd77b9162d388cb8d4c4217c7c5e2a) format("woff");font-weight:400;font-style:normal;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-bold.woff2?cccb897485813c7c256901dbca54ecf2) format("woff2"),url(fonts/lato-bold.woff?d878b6c29b10beca227e9eef4246111b) format("woff");font-weight:700;font-style:normal;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-bold-italic.woff2?0b6bb6725576b072c5d0b02ecdd1900d) format("woff2"),url(fonts/lato-bold-italic.woff?9c7e4e9eb485b4a121c760e61bc3707c) format("woff");font-weight:700;font-style:italic;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-normal-italic.woff2?4eb103b4d12be57cb1d040ed5e162e9d) format("woff2"),url(fonts/lato-normal-italic.woff?f28f2d6482446544ef1ea1ccc6dd5892) format("woff");font-weight:400;font-style:italic;font-display:block}@font-face{font-family:Roboto Slab;font-style:normal;font-weight:400;src:url(fonts/Roboto-Slab-Regular.woff2?7abf5b8d04d26a2cafea937019bca958) format("woff2"),url(fonts/Roboto-Slab-Regular.woff?c1be9284088d487c5e3ff0a10a92e58c) format("woff");font-display:block}@font-face{font-family:Roboto Slab;font-style:normal;font-weight:700;src:url(fonts/Roboto-Slab-Bold.woff2?9984f4a9bda09be08e83f2506954adbe) format("woff2"),url(fonts/Roboto-Slab-Bold.woff?bed5564a116b05148e3b3bea6fb1162a) format("woff");font-display:block} \ No newline at end of file diff --git a/docs/_static/doctools.js b/docs/_static/doctools.js index daccd20..8cbf1b1 100644 --- a/docs/_static/doctools.js +++ b/docs/_static/doctools.js @@ -4,7 +4,7 @@ * * Sphinx JavaScript utilities for all documentation. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ @@ -29,9 +29,14 @@ if (!window.console || !console.firebug) { /** * small helper function to urldecode strings + * + * See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/decodeURIComponent#Decoding_query_parameters_from_a_URL */ jQuery.urldecode = function(x) { - return decodeURIComponent(x).replace(/\+/g, ' '); + if (!x) { + return x + } + return decodeURIComponent(x.replace(/\+/g, ' ')); }; /** @@ -285,9 +290,10 @@ var Documentation = { initOnKeyListeners: function() { $(document).keydown(function(event) { var activeElementType = document.activeElement.tagName; - // don't navigate when in search box or textarea + // don't navigate when in search box, textarea, dropdown or button if (activeElementType !== 'TEXTAREA' && activeElementType !== 'INPUT' && activeElementType !== 'SELECT' - && !event.altKey && !event.ctrlKey && !event.metaKey && !event.shiftKey) { + && activeElementType !== 'BUTTON' && !event.altKey && !event.ctrlKey && !event.metaKey + && !event.shiftKey) { switch (event.keyCode) { case 37: // left var prevHref = $('link[rel="prev"]').prop('href'); @@ -295,12 +301,14 @@ var Documentation = { window.location.href = prevHref; return false; } + break; case 39: // right var nextHref = $('link[rel="next"]').prop('href'); if (nextHref) { window.location.href = nextHref; return false; } + break; } } }); diff --git a/docs/_static/documentation_options.js b/docs/_static/documentation_options.js index 9bdd13b..2f08d25 100644 --- a/docs/_static/documentation_options.js +++ b/docs/_static/documentation_options.js @@ -1,6 +1,6 @@ var DOCUMENTATION_OPTIONS = { URL_ROOT: document.getElementById("documentation_options").getAttribute('data-url_root'), - VERSION: '0.7.0', + VERSION: '1.0.0', LANGUAGE: 'None', COLLAPSE_INDEX: false, BUILDER: 'html', diff --git a/docs/_static/graphviz.css b/docs/_static/graphviz.css index 8ab69e0..b340734 100644 --- a/docs/_static/graphviz.css +++ b/docs/_static/graphviz.css @@ -4,7 +4,7 @@ * * Sphinx stylesheet -- graphviz extension. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ diff --git a/docs/_static/js/badge_only.js b/docs/_static/js/badge_only.js new file mode 100644 index 0000000..526d723 --- /dev/null +++ b/docs/_static/js/badge_only.js @@ -0,0 +1 @@ +!function(e){var t={};function r(n){if(t[n])return t[n].exports;var o=t[n]={i:n,l:!1,exports:{}};return e[n].call(o.exports,o,o.exports,r),o.l=!0,o.exports}r.m=e,r.c=t,r.d=function(e,t,n){r.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:n})},r.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},r.t=function(e,t){if(1&t&&(e=r(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(r.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)r.d(n,o,function(t){return e[t]}.bind(null,o));return n},r.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return r.d(t,"a",t),t},r.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},r.p="",r(r.s=4)}({4:function(e,t,r){}}); \ No newline at end of file diff --git a/docs/_static/js/html5shiv-printshiv.min.js b/docs/_static/js/html5shiv-printshiv.min.js new file mode 100644 index 0000000..2b43bd0 --- /dev/null +++ b/docs/_static/js/html5shiv-printshiv.min.js @@ -0,0 +1,4 @@ +/** +* @preserve HTML5 Shiv 3.7.3-pre | @afarkas @jdalton @jon_neal @rem | MIT/GPL2 Licensed +*/ +!function(a,b){function c(a,b){var c=a.createElement("p"),d=a.getElementsByTagName("head")[0]||a.documentElement;return c.innerHTML="x",d.insertBefore(c.lastChild,d.firstChild)}function d(){var a=y.elements;return"string"==typeof a?a.split(" "):a}function e(a,b){var c=y.elements;"string"!=typeof c&&(c=c.join(" ")),"string"!=typeof a&&(a=a.join(" ")),y.elements=c+" "+a,j(b)}function f(a){var b=x[a[v]];return b||(b={},w++,a[v]=w,x[w]=b),b}function g(a,c,d){if(c||(c=b),q)return c.createElement(a);d||(d=f(c));var e;return e=d.cache[a]?d.cache[a].cloneNode():u.test(a)?(d.cache[a]=d.createElem(a)).cloneNode():d.createElem(a),!e.canHaveChildren||t.test(a)||e.tagUrn?e:d.frag.appendChild(e)}function h(a,c){if(a||(a=b),q)return a.createDocumentFragment();c=c||f(a);for(var e=c.frag.cloneNode(),g=0,h=d(),i=h.length;i>g;g++)e.createElement(h[g]);return e}function i(a,b){b.cache||(b.cache={},b.createElem=a.createElement,b.createFrag=a.createDocumentFragment,b.frag=b.createFrag()),a.createElement=function(c){return y.shivMethods?g(c,a,b):b.createElem(c)},a.createDocumentFragment=Function("h,f","return function(){var n=f.cloneNode(),c=n.createElement;h.shivMethods&&("+d().join().replace(/[\w\-:]+/g,function(a){return b.createElem(a),b.frag.createElement(a),'c("'+a+'")'})+");return n}")(y,b.frag)}function j(a){a||(a=b);var d=f(a);return!y.shivCSS||p||d.hasCSS||(d.hasCSS=!!c(a,"article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}mark{background:#FF0;color:#000}template{display:none}")),q||i(a,d),a}function k(a){for(var b,c=a.getElementsByTagName("*"),e=c.length,f=RegExp("^(?:"+d().join("|")+")$","i"),g=[];e--;)b=c[e],f.test(b.nodeName)&&g.push(b.applyElement(l(b)));return g}function l(a){for(var b,c=a.attributes,d=c.length,e=a.ownerDocument.createElement(A+":"+a.nodeName);d--;)b=c[d],b.specified&&e.setAttribute(b.nodeName,b.nodeValue);return e.style.cssText=a.style.cssText,e}function m(a){for(var b,c=a.split("{"),e=c.length,f=RegExp("(^|[\\s,>+~])("+d().join("|")+")(?=[[\\s,>+~#.:]|$)","gi"),g="$1"+A+"\\:$2";e--;)b=c[e]=c[e].split("}"),b[b.length-1]=b[b.length-1].replace(f,g),c[e]=b.join("}");return c.join("{")}function n(a){for(var b=a.length;b--;)a[b].removeNode()}function o(a){function b(){clearTimeout(g._removeSheetTimer),d&&d.removeNode(!0),d=null}var d,e,g=f(a),h=a.namespaces,i=a.parentWindow;return!B||a.printShived?a:("undefined"==typeof h[A]&&h.add(A),i.attachEvent("onbeforeprint",function(){b();for(var f,g,h,i=a.styleSheets,j=[],l=i.length,n=Array(l);l--;)n[l]=i[l];for(;h=n.pop();)if(!h.disabled&&z.test(h.media)){try{f=h.imports,g=f.length}catch(o){g=0}for(l=0;g>l;l++)n.push(f[l]);try{j.push(h.cssText)}catch(o){}}j=m(j.reverse().join("")),e=k(a),d=c(a,j)}),i.attachEvent("onafterprint",function(){n(e),clearTimeout(g._removeSheetTimer),g._removeSheetTimer=setTimeout(b,500)}),a.printShived=!0,a)}var p,q,r="3.7.3",s=a.html5||{},t=/^<|^(?:button|map|select|textarea|object|iframe|option|optgroup)$/i,u=/^(?:a|b|code|div|fieldset|h1|h2|h3|h4|h5|h6|i|label|li|ol|p|q|span|strong|style|table|tbody|td|th|tr|ul)$/i,v="_html5shiv",w=0,x={};!function(){try{var a=b.createElement("a");a.innerHTML="",p="hidden"in a,q=1==a.childNodes.length||function(){b.createElement("a");var a=b.createDocumentFragment();return"undefined"==typeof a.cloneNode||"undefined"==typeof a.createDocumentFragment||"undefined"==typeof a.createElement}()}catch(c){p=!0,q=!0}}();var y={elements:s.elements||"abbr article aside audio bdi canvas data datalist details dialog figcaption figure footer header hgroup main mark meter nav output picture progress section summary template time video",version:r,shivCSS:s.shivCSS!==!1,supportsUnknownElements:q,shivMethods:s.shivMethods!==!1,type:"default",shivDocument:j,createElement:g,createDocumentFragment:h,addElements:e};a.html5=y,j(b);var z=/^$|\b(?:all|print)\b/,A="html5shiv",B=!q&&function(){var c=b.documentElement;return!("undefined"==typeof b.namespaces||"undefined"==typeof b.parentWindow||"undefined"==typeof c.applyElement||"undefined"==typeof c.removeNode||"undefined"==typeof a.attachEvent)}();y.type+=" print",y.shivPrint=o,o(b),"object"==typeof module&&module.exports&&(module.exports=y)}("undefined"!=typeof window?window:this,document); \ No newline at end of file diff --git a/docs/_static/js/html5shiv.min.js b/docs/_static/js/html5shiv.min.js new file mode 100644 index 0000000..cd1c674 --- /dev/null +++ b/docs/_static/js/html5shiv.min.js @@ -0,0 +1,4 @@ +/** +* @preserve HTML5 Shiv 3.7.3 | @afarkas @jdalton @jon_neal @rem | MIT/GPL2 Licensed +*/ +!function(a,b){function c(a,b){var c=a.createElement("p"),d=a.getElementsByTagName("head")[0]||a.documentElement;return c.innerHTML="x",d.insertBefore(c.lastChild,d.firstChild)}function d(){var a=t.elements;return"string"==typeof a?a.split(" "):a}function e(a,b){var c=t.elements;"string"!=typeof c&&(c=c.join(" ")),"string"!=typeof a&&(a=a.join(" ")),t.elements=c+" "+a,j(b)}function f(a){var b=s[a[q]];return b||(b={},r++,a[q]=r,s[r]=b),b}function g(a,c,d){if(c||(c=b),l)return c.createElement(a);d||(d=f(c));var e;return e=d.cache[a]?d.cache[a].cloneNode():p.test(a)?(d.cache[a]=d.createElem(a)).cloneNode():d.createElem(a),!e.canHaveChildren||o.test(a)||e.tagUrn?e:d.frag.appendChild(e)}function h(a,c){if(a||(a=b),l)return a.createDocumentFragment();c=c||f(a);for(var e=c.frag.cloneNode(),g=0,h=d(),i=h.length;i>g;g++)e.createElement(h[g]);return e}function i(a,b){b.cache||(b.cache={},b.createElem=a.createElement,b.createFrag=a.createDocumentFragment,b.frag=b.createFrag()),a.createElement=function(c){return t.shivMethods?g(c,a,b):b.createElem(c)},a.createDocumentFragment=Function("h,f","return function(){var n=f.cloneNode(),c=n.createElement;h.shivMethods&&("+d().join().replace(/[\w\-:]+/g,function(a){return b.createElem(a),b.frag.createElement(a),'c("'+a+'")'})+");return n}")(t,b.frag)}function j(a){a||(a=b);var d=f(a);return!t.shivCSS||k||d.hasCSS||(d.hasCSS=!!c(a,"article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}mark{background:#FF0;color:#000}template{display:none}")),l||i(a,d),a}var k,l,m="3.7.3-pre",n=a.html5||{},o=/^<|^(?:button|map|select|textarea|object|iframe|option|optgroup)$/i,p=/^(?:a|b|code|div|fieldset|h1|h2|h3|h4|h5|h6|i|label|li|ol|p|q|span|strong|style|table|tbody|td|th|tr|ul)$/i,q="_html5shiv",r=0,s={};!function(){try{var a=b.createElement("a");a.innerHTML="",k="hidden"in a,l=1==a.childNodes.length||function(){b.createElement("a");var a=b.createDocumentFragment();return"undefined"==typeof a.cloneNode||"undefined"==typeof a.createDocumentFragment||"undefined"==typeof a.createElement}()}catch(c){k=!0,l=!0}}();var t={elements:n.elements||"abbr article aside audio bdi canvas data datalist details dialog figcaption figure footer header hgroup main mark meter nav output picture progress section summary template time video",version:m,shivCSS:n.shivCSS!==!1,supportsUnknownElements:l,shivMethods:n.shivMethods!==!1,type:"default",shivDocument:j,createElement:g,createDocumentFragment:h,addElements:e};a.html5=t,j(b),"object"==typeof module&&module.exports&&(module.exports=t)}("undefined"!=typeof window?window:this,document); \ No newline at end of file diff --git a/docs/_static/js/theme.js b/docs/_static/js/theme.js new file mode 100644 index 0000000..1fddb6e --- /dev/null +++ b/docs/_static/js/theme.js @@ -0,0 +1 @@ +!function(n){var e={};function t(i){if(e[i])return e[i].exports;var o=e[i]={i:i,l:!1,exports:{}};return n[i].call(o.exports,o,o.exports,t),o.l=!0,o.exports}t.m=n,t.c=e,t.d=function(n,e,i){t.o(n,e)||Object.defineProperty(n,e,{enumerable:!0,get:i})},t.r=function(n){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(n,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(n,"__esModule",{value:!0})},t.t=function(n,e){if(1&e&&(n=t(n)),8&e)return n;if(4&e&&"object"==typeof n&&n&&n.__esModule)return n;var i=Object.create(null);if(t.r(i),Object.defineProperty(i,"default",{enumerable:!0,value:n}),2&e&&"string"!=typeof n)for(var o in n)t.d(i,o,function(e){return n[e]}.bind(null,o));return i},t.n=function(n){var e=n&&n.__esModule?function(){return n.default}:function(){return n};return t.d(e,"a",e),e},t.o=function(n,e){return Object.prototype.hasOwnProperty.call(n,e)},t.p="",t(t.s=0)}([function(n,e,t){t(1),n.exports=t(3)},function(n,e,t){(function(){var e="undefined"!=typeof window?window.jQuery:t(2);n.exports.ThemeNav={navBar:null,win:null,winScroll:!1,winResize:!1,linkScroll:!1,winPosition:0,winHeight:null,docHeight:null,isRunning:!1,enable:function(n){var t=this;void 0===n&&(n=!0),t.isRunning||(t.isRunning=!0,e((function(e){t.init(e),t.reset(),t.win.on("hashchange",t.reset),n&&t.win.on("scroll",(function(){t.linkScroll||t.winScroll||(t.winScroll=!0,requestAnimationFrame((function(){t.onScroll()})))})),t.win.on("resize",(function(){t.winResize||(t.winResize=!0,requestAnimationFrame((function(){t.onResize()})))})),t.onResize()})))},enableSticky:function(){this.enable(!0)},init:function(n){n(document);var e=this;this.navBar=n("div.wy-side-scroll:first"),this.win=n(window),n(document).on("click","[data-toggle='wy-nav-top']",(function(){n("[data-toggle='wy-nav-shift']").toggleClass("shift"),n("[data-toggle='rst-versions']").toggleClass("shift")})).on("click",".wy-menu-vertical .current ul li a",(function(){var t=n(this);n("[data-toggle='wy-nav-shift']").removeClass("shift"),n("[data-toggle='rst-versions']").toggleClass("shift"),e.toggleCurrent(t),e.hashChange()})).on("click","[data-toggle='rst-current-version']",(function(){n("[data-toggle='rst-versions']").toggleClass("shift-up")})),n("table.docutils:not(.field-list,.footnote,.citation)").wrap("
"),n("table.docutils.footnote").wrap("
"),n("table.docutils.citation").wrap("
"),n(".wy-menu-vertical ul").not(".simple").siblings("a").each((function(){var t=n(this);expand=n(''),expand.on("click",(function(n){return e.toggleCurrent(t),n.stopPropagation(),!1})),t.prepend(expand)}))},reset:function(){var n=encodeURI(window.location.hash)||"#";try{var e=$(".wy-menu-vertical"),t=e.find('[href="'+n+'"]');if(0===t.length){var i=$('.document [id="'+n.substring(1)+'"]').closest("div.section");0===(t=e.find('[href="#'+i.attr("id")+'"]')).length&&(t=e.find('[href="#"]'))}if(t.length>0){$(".wy-menu-vertical .current").removeClass("current").attr("aria-expanded","false"),t.addClass("current").attr("aria-expanded","true"),t.closest("li.toctree-l1").parent().addClass("current").attr("aria-expanded","true");for(let n=1;n<=10;n++)t.closest("li.toctree-l"+n).addClass("current").attr("aria-expanded","true");t[0].scrollIntoView()}}catch(n){console.log("Error expanding nav for anchor",n)}},onScroll:function(){this.winScroll=!1;var n=this.win.scrollTop(),e=n+this.winHeight,t=this.navBar.scrollTop()+(n-this.winPosition);n<0||e>this.docHeight||(this.navBar.scrollTop(t),this.winPosition=n)},onResize:function(){this.winResize=!1,this.winHeight=this.win.height(),this.docHeight=$(document).height()},hashChange:function(){this.linkScroll=!0,this.win.one("hashchange",(function(){this.linkScroll=!1}))},toggleCurrent:function(n){var e=n.closest("li");e.siblings("li.current").removeClass("current").attr("aria-expanded","false"),e.siblings().find("li.current").removeClass("current").attr("aria-expanded","false");var t=e.find("> ul li");t.length&&(t.removeClass("current").attr("aria-expanded","false"),e.toggleClass("current").attr("aria-expanded",(function(n,e){return"true"==e?"false":"true"})))}},"undefined"!=typeof window&&(window.SphinxRtdTheme={Navigation:n.exports.ThemeNav,StickyNav:n.exports.ThemeNav}),function(){for(var n=0,e=["ms","moz","webkit","o"],t=0;t'); + var listItem = $('
  • '); var requestUrl = ""; var linkUrl = ""; if (DOCUMENTATION_OPTIONS.BUILDER === 'dirhtml') { @@ -273,28 +273,31 @@ var Search = { if (item[3]) { listItem.append($(' (' + item[3] + ')')); Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); } else if (DOCUMENTATION_OPTIONS.HAS_SOURCE) { $.ajax({url: requestUrl, dataType: "text", complete: function(jqxhr, textstatus) { var data = jqxhr.responseText; if (data !== '' && data !== undefined) { - listItem.append(Search.makeSearchSummary(data, searchterms, hlterms)); + var summary = Search.makeSearchSummary(data, searchterms, hlterms); + if (summary) { + listItem.append(summary); + } } Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); }}); } else { // no source available, just display title Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); } } // search finished, update title and status message @@ -379,6 +382,13 @@ var Search = { return results; }, + /** + * See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions + */ + escapeRegExp : function(string) { + return string.replace(/[.*+\-?^${}()|[\]\\]/g, '\\$&'); // $& means the whole matched string + }, + /** * search for full-text terms in the index */ @@ -402,13 +412,14 @@ var Search = { ]; // add support for partial matches if (word.length > 2) { + var word_regex = this.escapeRegExp(word); for (var w in terms) { - if (w.match(word) && !terms[word]) { + if (w.match(word_regex) && !terms[word]) { _o.push({files: terms[w], score: Scorer.partialTerm}) } } for (var w in titleterms) { - if (w.match(word) && !titleterms[word]) { + if (w.match(word_regex) && !titleterms[word]) { _o.push({files: titleterms[w], score: Scorer.partialTitle}) } } @@ -490,6 +501,9 @@ var Search = { */ makeSearchSummary : function(htmlText, keywords, hlwords) { var text = Search.htmlToText(htmlText); + if (text == "") { + return null; + } var textLower = text.toLowerCase(); var start = 0; $.each(keywords, function() { @@ -501,7 +515,7 @@ var Search = { var excerpt = ((start > 0) ? '...' : '') + $.trim(text.substr(start, 240)) + ((start + 240 - text.length) ? '...' : ''); - var rv = $('
    ').text(excerpt); + var rv = $('

    ').text(excerpt); $.each(hlwords, function() { rv = rv.highlightText(this, 'highlighted'); }); diff --git a/docs/_static/sidebar.js b/docs/_static/sidebar.js deleted file mode 100644 index 657f8be..0000000 --- a/docs/_static/sidebar.js +++ /dev/null @@ -1,159 +0,0 @@ -/* - * sidebar.js - * ~~~~~~~~~~ - * - * This script makes the Sphinx sidebar collapsible. - * - * .sphinxsidebar contains .sphinxsidebarwrapper. This script adds - * in .sphixsidebar, after .sphinxsidebarwrapper, the #sidebarbutton - * used to collapse and expand the sidebar. - * - * When the sidebar is collapsed the .sphinxsidebarwrapper is hidden - * and the width of the sidebar and the margin-left of the document - * are decreased. When the sidebar is expanded the opposite happens. - * This script saves a per-browser/per-session cookie used to - * remember the position of the sidebar among the pages. - * Once the browser is closed the cookie is deleted and the position - * reset to the default (expanded). - * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ - -$(function() { - - - - - - - - - // global elements used by the functions. - // the 'sidebarbutton' element is defined as global after its - // creation, in the add_sidebar_button function - var bodywrapper = $('.bodywrapper'); - var sidebar = $('.sphinxsidebar'); - var sidebarwrapper = $('.sphinxsidebarwrapper'); - - // for some reason, the document has no sidebar; do not run into errors - if (!sidebar.length) return; - - // original margin-left of the bodywrapper and width of the sidebar - // with the sidebar expanded - var bw_margin_expanded = bodywrapper.css('margin-left'); - var ssb_width_expanded = sidebar.width(); - - // margin-left of the bodywrapper and width of the sidebar - // with the sidebar collapsed - var bw_margin_collapsed = '.8em'; - var ssb_width_collapsed = '.8em'; - - // colors used by the current theme - var dark_color = $('.related').css('background-color'); - var light_color = $('.document').css('background-color'); - - function sidebar_is_collapsed() { - return sidebarwrapper.is(':not(:visible)'); - } - - function toggle_sidebar() { - if (sidebar_is_collapsed()) - expand_sidebar(); - else - collapse_sidebar(); - } - - function collapse_sidebar() { - sidebarwrapper.hide(); - sidebar.css('width', ssb_width_collapsed); - bodywrapper.css('margin-left', bw_margin_collapsed); - sidebarbutton.css({ - 'margin-left': '0', - 'height': bodywrapper.height() - }); - sidebarbutton.find('span').text('»'); - sidebarbutton.attr('title', _('Expand sidebar')); - document.cookie = 'sidebar=collapsed'; - } - - function expand_sidebar() { - bodywrapper.css('margin-left', bw_margin_expanded); - sidebar.css('width', ssb_width_expanded); - sidebarwrapper.show(); - sidebarbutton.css({ - 'margin-left': ssb_width_expanded-12, - 'height': bodywrapper.height() - }); - sidebarbutton.find('span').text('«'); - sidebarbutton.attr('title', _('Collapse sidebar')); - document.cookie = 'sidebar=expanded'; - } - - function add_sidebar_button() { - sidebarwrapper.css({ - 'float': 'left', - 'margin-right': '0', - 'width': ssb_width_expanded - 28 - }); - // create the button - sidebar.append( - '
    «
    ' - ); - var sidebarbutton = $('#sidebarbutton'); - light_color = sidebarbutton.css('background-color'); - // find the height of the viewport to center the '<<' in the page - var viewport_height; - if (window.innerHeight) - viewport_height = window.innerHeight; - else - viewport_height = $(window).height(); - sidebarbutton.find('span').css({ - 'display': 'block', - 'margin-top': (viewport_height - sidebar.position().top - 20) / 2 - }); - - sidebarbutton.click(toggle_sidebar); - sidebarbutton.attr('title', _('Collapse sidebar')); - sidebarbutton.css({ - 'color': '#FFFFFF', - 'border-left': '1px solid ' + dark_color, - 'font-size': '1.2em', - 'cursor': 'pointer', - 'height': bodywrapper.height(), - 'padding-top': '1px', - 'margin-left': ssb_width_expanded - 12 - }); - - sidebarbutton.hover( - function () { - $(this).css('background-color', dark_color); - }, - function () { - $(this).css('background-color', light_color); - } - ); - } - - function set_position_from_cookie() { - if (!document.cookie) - return; - var items = document.cookie.split(';'); - for(var k=0; k= 0 && sizeProperty <= MAX_ARRAY_INDEX; + } + } + + // Internal helper to generate a function to obtain property `key` from `obj`. + function shallowProperty(key) { + return function(obj) { + return obj == null ? void 0 : obj[key]; + }; + } + + // Internal helper to obtain the `byteLength` property of an object. + var getByteLength = shallowProperty('byteLength'); + + // Internal helper to determine whether we should spend extensive checks against + // `ArrayBuffer` et al. + var isBufferLike = createSizePropertyCheck(getByteLength); + + // Is a given value a typed array? + var typedArrayPattern = /\[object ((I|Ui)nt(8|16|32)|Float(32|64)|Uint8Clamped|Big(I|Ui)nt64)Array\]/; + function isTypedArray(obj) { + // `ArrayBuffer.isView` is the most future-proof, so use it when available. + // Otherwise, fall back on the above regular expression. + return nativeIsView ? (nativeIsView(obj) && !isDataView$1(obj)) : + isBufferLike(obj) && typedArrayPattern.test(toString.call(obj)); + } + + var isTypedArray$1 = supportsArrayBuffer ? isTypedArray : constant(false); + + // Internal helper to obtain the `length` property of an object. + var getLength = shallowProperty('length'); + + // Internal helper to create a simple lookup structure. + // `collectNonEnumProps` used to depend on `_.contains`, but this led to + // circular imports. `emulatedSet` is a one-off solution that only works for + // arrays of strings. + function emulatedSet(keys) { + var hash = {}; + for (var l = keys.length, i = 0; i < l; ++i) hash[keys[i]] = true; + return { + contains: function(key) { return hash[key]; }, + push: function(key) { + hash[key] = true; + return keys.push(key); + } + }; + } + + // Internal helper. Checks `keys` for the presence of keys in IE < 9 that won't + // be iterated by `for key in ...` and thus missed. Extends `keys` in place if + // needed. + function collectNonEnumProps(obj, keys) { + keys = emulatedSet(keys); + var nonEnumIdx = nonEnumerableProps.length; + var constructor = obj.constructor; + var proto = isFunction$1(constructor) && constructor.prototype || ObjProto; + + // Constructor is a special case. + var prop = 'constructor'; + if (has$1(obj, prop) && !keys.contains(prop)) keys.push(prop); + + while (nonEnumIdx--) { + prop = nonEnumerableProps[nonEnumIdx]; + if (prop in obj && obj[prop] !== proto[prop] && !keys.contains(prop)) { + keys.push(prop); + } + } + } + + // Retrieve the names of an object's own properties. + // Delegates to **ECMAScript 5**'s native `Object.keys`. + function keys(obj) { + if (!isObject(obj)) return []; + if (nativeKeys) return nativeKeys(obj); + var keys = []; + for (var key in obj) if (has$1(obj, key)) keys.push(key); + // Ahem, IE < 9. + if (hasEnumBug) collectNonEnumProps(obj, keys); + return keys; + } + + // Is a given array, string, or object empty? + // An "empty" object has no enumerable own-properties. + function isEmpty(obj) { + if (obj == null) return true; + // Skip the more expensive `toString`-based type checks if `obj` has no + // `.length`. + var length = getLength(obj); + if (typeof length == 'number' && ( + isArray(obj) || isString(obj) || isArguments$1(obj) + )) return length === 0; + return getLength(keys(obj)) === 0; + } + + // Returns whether an object has a given set of `key:value` pairs. + function isMatch(object, attrs) { + var _keys = keys(attrs), length = _keys.length; + if (object == null) return !length; + var obj = Object(object); + for (var i = 0; i < length; i++) { + var key = _keys[i]; + if (attrs[key] !== obj[key] || !(key in obj)) return false; + } + return true; + } + + // If Underscore is called as a function, it returns a wrapped object that can + // be used OO-style. This wrapper holds altered versions of all functions added + // through `_.mixin`. Wrapped objects may be chained. + function _$1(obj) { + if (obj instanceof _$1) return obj; + if (!(this instanceof _$1)) return new _$1(obj); + this._wrapped = obj; + } + + _$1.VERSION = VERSION; + + // Extracts the result from a wrapped and chained object. + _$1.prototype.value = function() { + return this._wrapped; + }; + + // Provide unwrapping proxies for some methods used in engine operations + // such as arithmetic and JSON stringification. + _$1.prototype.valueOf = _$1.prototype.toJSON = _$1.prototype.value; + + _$1.prototype.toString = function() { + return String(this._wrapped); + }; + + // Internal function to wrap or shallow-copy an ArrayBuffer, + // typed array or DataView to a new view, reusing the buffer. + function toBufferView(bufferSource) { + return new Uint8Array( + bufferSource.buffer || bufferSource, + bufferSource.byteOffset || 0, + getByteLength(bufferSource) + ); + } + + // We use this string twice, so give it a name for minification. + var tagDataView = '[object DataView]'; + + // Internal recursive comparison function for `_.isEqual`. + function eq(a, b, aStack, bStack) { + // Identical objects are equal. `0 === -0`, but they aren't identical. + // See the [Harmony `egal` proposal](https://wiki.ecmascript.org/doku.php?id=harmony:egal). + if (a === b) return a !== 0 || 1 / a === 1 / b; + // `null` or `undefined` only equal to itself (strict comparison). + if (a == null || b == null) return false; + // `NaN`s are equivalent, but non-reflexive. + if (a !== a) return b !== b; + // Exhaust primitive checks + var type = typeof a; + if (type !== 'function' && type !== 'object' && typeof b != 'object') return false; + return deepEq(a, b, aStack, bStack); + } + + // Internal recursive comparison function for `_.isEqual`. + function deepEq(a, b, aStack, bStack) { + // Unwrap any wrapped objects. + if (a instanceof _$1) a = a._wrapped; + if (b instanceof _$1) b = b._wrapped; + // Compare `[[Class]]` names. + var className = toString.call(a); + if (className !== toString.call(b)) return false; + // Work around a bug in IE 10 - Edge 13. + if (hasStringTagBug && className == '[object Object]' && isDataView$1(a)) { + if (!isDataView$1(b)) return false; + className = tagDataView; + } + switch (className) { + // These types are compared by value. + case '[object RegExp]': + // RegExps are coerced to strings for comparison (Note: '' + /a/i === '/a/i') + case '[object String]': + // Primitives and their corresponding object wrappers are equivalent; thus, `"5"` is + // equivalent to `new String("5")`. + return '' + a === '' + b; + case '[object Number]': + // `NaN`s are equivalent, but non-reflexive. + // Object(NaN) is equivalent to NaN. + if (+a !== +a) return +b !== +b; + // An `egal` comparison is performed for other numeric values. + return +a === 0 ? 1 / +a === 1 / b : +a === +b; + case '[object Date]': + case '[object Boolean]': + // Coerce dates and booleans to numeric primitive values. Dates are compared by their + // millisecond representations. Note that invalid dates with millisecond representations + // of `NaN` are not equivalent. + return +a === +b; + case '[object Symbol]': + return SymbolProto.valueOf.call(a) === SymbolProto.valueOf.call(b); + case '[object ArrayBuffer]': + case tagDataView: + // Coerce to typed array so we can fall through. + return deepEq(toBufferView(a), toBufferView(b), aStack, bStack); + } + + var areArrays = className === '[object Array]'; + if (!areArrays && isTypedArray$1(a)) { + var byteLength = getByteLength(a); + if (byteLength !== getByteLength(b)) return false; + if (a.buffer === b.buffer && a.byteOffset === b.byteOffset) return true; + areArrays = true; + } + if (!areArrays) { + if (typeof a != 'object' || typeof b != 'object') return false; + + // Objects with different constructors are not equivalent, but `Object`s or `Array`s + // from different frames are. + var aCtor = a.constructor, bCtor = b.constructor; + if (aCtor !== bCtor && !(isFunction$1(aCtor) && aCtor instanceof aCtor && + isFunction$1(bCtor) && bCtor instanceof bCtor) + && ('constructor' in a && 'constructor' in b)) { + return false; + } + } + // Assume equality for cyclic structures. The algorithm for detecting cyclic + // structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`. + + // Initializing stack of traversed objects. + // It's done here since we only need them for objects and arrays comparison. + aStack = aStack || []; + bStack = bStack || []; + var length = aStack.length; + while (length--) { + // Linear search. Performance is inversely proportional to the number of + // unique nested structures. + if (aStack[length] === a) return bStack[length] === b; + } + + // Add the first object to the stack of traversed objects. + aStack.push(a); + bStack.push(b); + + // Recursively compare objects and arrays. + if (areArrays) { + // Compare array lengths to determine if a deep comparison is necessary. + length = a.length; + if (length !== b.length) return false; + // Deep compare the contents, ignoring non-numeric properties. + while (length--) { + if (!eq(a[length], b[length], aStack, bStack)) return false; + } + } else { + // Deep compare objects. + var _keys = keys(a), key; + length = _keys.length; + // Ensure that both objects contain the same number of properties before comparing deep equality. + if (keys(b).length !== length) return false; + while (length--) { + // Deep compare each member + key = _keys[length]; + if (!(has$1(b, key) && eq(a[key], b[key], aStack, bStack))) return false; + } + } + // Remove the first object from the stack of traversed objects. + aStack.pop(); + bStack.pop(); + return true; + } + + // Perform a deep comparison to check if two objects are equal. + function isEqual(a, b) { + return eq(a, b); + } + + // Retrieve all the enumerable property names of an object. + function allKeys(obj) { + if (!isObject(obj)) return []; + var keys = []; + for (var key in obj) keys.push(key); + // Ahem, IE < 9. + if (hasEnumBug) collectNonEnumProps(obj, keys); + return keys; + } + + // Since the regular `Object.prototype.toString` type tests don't work for + // some types in IE 11, we use a fingerprinting heuristic instead, based + // on the methods. It's not great, but it's the best we got. + // The fingerprint method lists are defined below. + function ie11fingerprint(methods) { + var length = getLength(methods); + return function(obj) { + if (obj == null) return false; + // `Map`, `WeakMap` and `Set` have no enumerable keys. + var keys = allKeys(obj); + if (getLength(keys)) return false; + for (var i = 0; i < length; i++) { + if (!isFunction$1(obj[methods[i]])) return false; + } + // If we are testing against `WeakMap`, we need to ensure that + // `obj` doesn't have a `forEach` method in order to distinguish + // it from a regular `Map`. + return methods !== weakMapMethods || !isFunction$1(obj[forEachName]); + }; + } + + // In the interest of compact minification, we write + // each string in the fingerprints only once. + var forEachName = 'forEach', + hasName = 'has', + commonInit = ['clear', 'delete'], + mapTail = ['get', hasName, 'set']; + + // `Map`, `WeakMap` and `Set` each have slightly different + // combinations of the above sublists. + var mapMethods = commonInit.concat(forEachName, mapTail), + weakMapMethods = commonInit.concat(mapTail), + setMethods = ['add'].concat(commonInit, forEachName, hasName); + + var isMap = isIE11 ? ie11fingerprint(mapMethods) : tagTester('Map'); + + var isWeakMap = isIE11 ? ie11fingerprint(weakMapMethods) : tagTester('WeakMap'); + + var isSet = isIE11 ? ie11fingerprint(setMethods) : tagTester('Set'); + + var isWeakSet = tagTester('WeakSet'); + + // Retrieve the values of an object's properties. + function values(obj) { + var _keys = keys(obj); + var length = _keys.length; + var values = Array(length); + for (var i = 0; i < length; i++) { + values[i] = obj[_keys[i]]; + } + return values; + } + + // Convert an object into a list of `[key, value]` pairs. + // The opposite of `_.object` with one argument. + function pairs(obj) { + var _keys = keys(obj); + var length = _keys.length; + var pairs = Array(length); + for (var i = 0; i < length; i++) { + pairs[i] = [_keys[i], obj[_keys[i]]]; + } + return pairs; + } + + // Invert the keys and values of an object. The values must be serializable. + function invert(obj) { + var result = {}; + var _keys = keys(obj); + for (var i = 0, length = _keys.length; i < length; i++) { + result[obj[_keys[i]]] = _keys[i]; + } + return result; + } + + // Return a sorted list of the function names available on the object. + function functions(obj) { + var names = []; + for (var key in obj) { + if (isFunction$1(obj[key])) names.push(key); + } + return names.sort(); + } + + // An internal function for creating assigner functions. + function createAssigner(keysFunc, defaults) { + return function(obj) { + var length = arguments.length; + if (defaults) obj = Object(obj); + if (length < 2 || obj == null) return obj; + for (var index = 1; index < length; index++) { + var source = arguments[index], + keys = keysFunc(source), + l = keys.length; + for (var i = 0; i < l; i++) { + var key = keys[i]; + if (!defaults || obj[key] === void 0) obj[key] = source[key]; + } + } + return obj; + }; + } + + // Extend a given object with all the properties in passed-in object(s). + var extend = createAssigner(allKeys); + + // Assigns a given object with all the own properties in the passed-in + // object(s). + // (https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Object/assign) + var extendOwn = createAssigner(keys); + + // Fill in a given object with default properties. + var defaults = createAssigner(allKeys, true); + + // Create a naked function reference for surrogate-prototype-swapping. + function ctor() { + return function(){}; + } + + // An internal function for creating a new object that inherits from another. + function baseCreate(prototype) { + if (!isObject(prototype)) return {}; + if (nativeCreate) return nativeCreate(prototype); + var Ctor = ctor(); + Ctor.prototype = prototype; + var result = new Ctor; + Ctor.prototype = null; + return result; + } + + // Creates an object that inherits from the given prototype object. + // If additional properties are provided then they will be added to the + // created object. + function create(prototype, props) { + var result = baseCreate(prototype); + if (props) extendOwn(result, props); + return result; + } + + // Create a (shallow-cloned) duplicate of an object. + function clone(obj) { + if (!isObject(obj)) return obj; + return isArray(obj) ? obj.slice() : extend({}, obj); + } + + // Invokes `interceptor` with the `obj` and then returns `obj`. + // The primary purpose of this method is to "tap into" a method chain, in + // order to perform operations on intermediate results within the chain. + function tap(obj, interceptor) { + interceptor(obj); + return obj; + } + + // Normalize a (deep) property `path` to array. + // Like `_.iteratee`, this function can be customized. + function toPath$1(path) { + return isArray(path) ? path : [path]; + } + _$1.toPath = toPath$1; + + // Internal wrapper for `_.toPath` to enable minification. + // Similar to `cb` for `_.iteratee`. + function toPath(path) { + return _$1.toPath(path); + } + + // Internal function to obtain a nested property in `obj` along `path`. + function deepGet(obj, path) { + var length = path.length; + for (var i = 0; i < length; i++) { + if (obj == null) return void 0; + obj = obj[path[i]]; + } + return length ? obj : void 0; + } + + // Get the value of the (deep) property on `path` from `object`. + // If any property in `path` does not exist or if the value is + // `undefined`, return `defaultValue` instead. + // The `path` is normalized through `_.toPath`. + function get(object, path, defaultValue) { + var value = deepGet(object, toPath(path)); + return isUndefined(value) ? defaultValue : value; + } + + // Shortcut function for checking if an object has a given property directly on + // itself (in other words, not on a prototype). Unlike the internal `has` + // function, this public version can also traverse nested properties. + function has(obj, path) { + path = toPath(path); + var length = path.length; + for (var i = 0; i < length; i++) { + var key = path[i]; + if (!has$1(obj, key)) return false; + obj = obj[key]; + } + return !!length; + } + + // Keep the identity function around for default iteratees. + function identity(value) { + return value; + } + + // Returns a predicate for checking whether an object has a given set of + // `key:value` pairs. + function matcher(attrs) { + attrs = extendOwn({}, attrs); + return function(obj) { + return isMatch(obj, attrs); + }; + } + + // Creates a function that, when passed an object, will traverse that object’s + // properties down the given `path`, specified as an array of keys or indices. + function property(path) { + path = toPath(path); + return function(obj) { + return deepGet(obj, path); + }; + } + + // Internal function that returns an efficient (for current engines) version + // of the passed-in callback, to be repeatedly applied in other Underscore + // functions. + function optimizeCb(func, context, argCount) { + if (context === void 0) return func; + switch (argCount == null ? 3 : argCount) { + case 1: return function(value) { + return func.call(context, value); + }; + // The 2-argument case is omitted because we’re not using it. + case 3: return function(value, index, collection) { + return func.call(context, value, index, collection); + }; + case 4: return function(accumulator, value, index, collection) { + return func.call(context, accumulator, value, index, collection); + }; + } + return function() { + return func.apply(context, arguments); + }; + } + + // An internal function to generate callbacks that can be applied to each + // element in a collection, returning the desired result — either `_.identity`, + // an arbitrary callback, a property matcher, or a property accessor. + function baseIteratee(value, context, argCount) { + if (value == null) return identity; + if (isFunction$1(value)) return optimizeCb(value, context, argCount); + if (isObject(value) && !isArray(value)) return matcher(value); + return property(value); + } + + // External wrapper for our callback generator. Users may customize + // `_.iteratee` if they want additional predicate/iteratee shorthand styles. + // This abstraction hides the internal-only `argCount` argument. + function iteratee(value, context) { + return baseIteratee(value, context, Infinity); + } + _$1.iteratee = iteratee; + + // The function we call internally to generate a callback. It invokes + // `_.iteratee` if overridden, otherwise `baseIteratee`. + function cb(value, context, argCount) { + if (_$1.iteratee !== iteratee) return _$1.iteratee(value, context); + return baseIteratee(value, context, argCount); + } + + // Returns the results of applying the `iteratee` to each element of `obj`. + // In contrast to `_.map` it returns an object. + function mapObject(obj, iteratee, context) { + iteratee = cb(iteratee, context); + var _keys = keys(obj), + length = _keys.length, + results = {}; + for (var index = 0; index < length; index++) { + var currentKey = _keys[index]; + results[currentKey] = iteratee(obj[currentKey], currentKey, obj); + } + return results; + } + + // Predicate-generating function. Often useful outside of Underscore. + function noop(){} + + // Generates a function for a given object that returns a given property. + function propertyOf(obj) { + if (obj == null) return noop; + return function(path) { + return get(obj, path); + }; + } + + // Run a function **n** times. + function times(n, iteratee, context) { + var accum = Array(Math.max(0, n)); + iteratee = optimizeCb(iteratee, context, 1); + for (var i = 0; i < n; i++) accum[i] = iteratee(i); + return accum; + } + + // Return a random integer between `min` and `max` (inclusive). + function random(min, max) { + if (max == null) { + max = min; + min = 0; + } + return min + Math.floor(Math.random() * (max - min + 1)); + } + + // A (possibly faster) way to get the current timestamp as an integer. + var now = Date.now || function() { + return new Date().getTime(); + }; + + // Internal helper to generate functions for escaping and unescaping strings + // to/from HTML interpolation. + function createEscaper(map) { + var escaper = function(match) { + return map[match]; + }; + // Regexes for identifying a key that needs to be escaped. + var source = '(?:' + keys(map).join('|') + ')'; + var testRegexp = RegExp(source); + var replaceRegexp = RegExp(source, 'g'); + return function(string) { + string = string == null ? '' : '' + string; + return testRegexp.test(string) ? string.replace(replaceRegexp, escaper) : string; + }; + } + + // Internal list of HTML entities for escaping. + var escapeMap = { + '&': '&', + '<': '<', + '>': '>', + '"': '"', + "'": ''', + '`': '`' + }; + + // Function for escaping strings to HTML interpolation. + var _escape = createEscaper(escapeMap); + + // Internal list of HTML entities for unescaping. + var unescapeMap = invert(escapeMap); + + // Function for unescaping strings from HTML interpolation. + var _unescape = createEscaper(unescapeMap); + + // By default, Underscore uses ERB-style template delimiters. Change the + // following template settings to use alternative delimiters. + var templateSettings = _$1.templateSettings = { + evaluate: /<%([\s\S]+?)%>/g, + interpolate: /<%=([\s\S]+?)%>/g, + escape: /<%-([\s\S]+?)%>/g + }; + + // When customizing `_.templateSettings`, if you don't want to define an + // interpolation, evaluation or escaping regex, we need one that is + // guaranteed not to match. + var noMatch = /(.)^/; + + // Certain characters need to be escaped so that they can be put into a + // string literal. + var escapes = { + "'": "'", + '\\': '\\', + '\r': 'r', + '\n': 'n', + '\u2028': 'u2028', + '\u2029': 'u2029' + }; + + var escapeRegExp = /\\|'|\r|\n|\u2028|\u2029/g; + + function escapeChar(match) { + return '\\' + escapes[match]; + } + + // In order to prevent third-party code injection through + // `_.templateSettings.variable`, we test it against the following regular + // expression. It is intentionally a bit more liberal than just matching valid + // identifiers, but still prevents possible loopholes through defaults or + // destructuring assignment. + var bareIdentifier = /^\s*(\w|\$)+\s*$/; + + // JavaScript micro-templating, similar to John Resig's implementation. + // Underscore templating handles arbitrary delimiters, preserves whitespace, + // and correctly escapes quotes within interpolated code. + // NB: `oldSettings` only exists for backwards compatibility. + function template(text, settings, oldSettings) { + if (!settings && oldSettings) settings = oldSettings; + settings = defaults({}, settings, _$1.templateSettings); + + // Combine delimiters into one regular expression via alternation. + var matcher = RegExp([ + (settings.escape || noMatch).source, + (settings.interpolate || noMatch).source, + (settings.evaluate || noMatch).source + ].join('|') + '|$', 'g'); + + // Compile the template source, escaping string literals appropriately. + var index = 0; + var source = "__p+='"; + text.replace(matcher, function(match, escape, interpolate, evaluate, offset) { + source += text.slice(index, offset).replace(escapeRegExp, escapeChar); + index = offset + match.length; + + if (escape) { + source += "'+\n((__t=(" + escape + "))==null?'':_.escape(__t))+\n'"; + } else if (interpolate) { + source += "'+\n((__t=(" + interpolate + "))==null?'':__t)+\n'"; + } else if (evaluate) { + source += "';\n" + evaluate + "\n__p+='"; + } + + // Adobe VMs need the match returned to produce the correct offset. + return match; + }); + source += "';\n"; + + var argument = settings.variable; + if (argument) { + // Insure against third-party code injection. (CVE-2021-23358) + if (!bareIdentifier.test(argument)) throw new Error( + 'variable is not a bare identifier: ' + argument + ); + } else { + // If a variable is not specified, place data values in local scope. + source = 'with(obj||{}){\n' + source + '}\n'; + argument = 'obj'; + } + + source = "var __t,__p='',__j=Array.prototype.join," + + "print=function(){__p+=__j.call(arguments,'');};\n" + + source + 'return __p;\n'; + + var render; + try { + render = new Function(argument, '_', source); + } catch (e) { + e.source = source; + throw e; + } + + var template = function(data) { + return render.call(this, data, _$1); + }; + + // Provide the compiled source as a convenience for precompilation. + template.source = 'function(' + argument + '){\n' + source + '}'; + + return template; + } + + // Traverses the children of `obj` along `path`. If a child is a function, it + // is invoked with its parent as context. Returns the value of the final + // child, or `fallback` if any child is undefined. + function result(obj, path, fallback) { + path = toPath(path); + var length = path.length; + if (!length) { + return isFunction$1(fallback) ? fallback.call(obj) : fallback; + } + for (var i = 0; i < length; i++) { + var prop = obj == null ? void 0 : obj[path[i]]; + if (prop === void 0) { + prop = fallback; + i = length; // Ensure we don't continue iterating. + } + obj = isFunction$1(prop) ? prop.call(obj) : prop; + } + return obj; + } + + // Generate a unique integer id (unique within the entire client session). + // Useful for temporary DOM ids. + var idCounter = 0; + function uniqueId(prefix) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } + + // Start chaining a wrapped Underscore object. + function chain(obj) { + var instance = _$1(obj); + instance._chain = true; + return instance; + } + + // Internal function to execute `sourceFunc` bound to `context` with optional + // `args`. Determines whether to execute a function as a constructor or as a + // normal function. + function executeBound(sourceFunc, boundFunc, context, callingContext, args) { + if (!(callingContext instanceof boundFunc)) return sourceFunc.apply(context, args); + var self = baseCreate(sourceFunc.prototype); + var result = sourceFunc.apply(self, args); + if (isObject(result)) return result; + return self; + } + + // Partially apply a function by creating a version that has had some of its + // arguments pre-filled, without changing its dynamic `this` context. `_` acts + // as a placeholder by default, allowing any combination of arguments to be + // pre-filled. Set `_.partial.placeholder` for a custom placeholder argument. + var partial = restArguments(function(func, boundArgs) { + var placeholder = partial.placeholder; + var bound = function() { + var position = 0, length = boundArgs.length; + var args = Array(length); + for (var i = 0; i < length; i++) { + args[i] = boundArgs[i] === placeholder ? arguments[position++] : boundArgs[i]; + } + while (position < arguments.length) args.push(arguments[position++]); + return executeBound(func, bound, this, this, args); + }; + return bound; + }); + + partial.placeholder = _$1; + + // Create a function bound to a given object (assigning `this`, and arguments, + // optionally). + var bind = restArguments(function(func, context, args) { + if (!isFunction$1(func)) throw new TypeError('Bind must be called on a function'); + var bound = restArguments(function(callArgs) { + return executeBound(func, bound, context, this, args.concat(callArgs)); + }); + return bound; + }); + + // Internal helper for collection methods to determine whether a collection + // should be iterated as an array or as an object. + // Related: https://people.mozilla.org/~jorendorff/es6-draft.html#sec-tolength + // Avoids a very nasty iOS 8 JIT bug on ARM-64. #2094 + var isArrayLike = createSizePropertyCheck(getLength); + + // Internal implementation of a recursive `flatten` function. + function flatten$1(input, depth, strict, output) { + output = output || []; + if (!depth && depth !== 0) { + depth = Infinity; + } else if (depth <= 0) { + return output.concat(input); + } + var idx = output.length; + for (var i = 0, length = getLength(input); i < length; i++) { + var value = input[i]; + if (isArrayLike(value) && (isArray(value) || isArguments$1(value))) { + // Flatten current level of array or arguments object. + if (depth > 1) { + flatten$1(value, depth - 1, strict, output); + idx = output.length; + } else { + var j = 0, len = value.length; + while (j < len) output[idx++] = value[j++]; + } + } else if (!strict) { + output[idx++] = value; + } + } + return output; + } + + // Bind a number of an object's methods to that object. Remaining arguments + // are the method names to be bound. Useful for ensuring that all callbacks + // defined on an object belong to it. + var bindAll = restArguments(function(obj, keys) { + keys = flatten$1(keys, false, false); + var index = keys.length; + if (index < 1) throw new Error('bindAll must be passed function names'); + while (index--) { + var key = keys[index]; + obj[key] = bind(obj[key], obj); + } + return obj; + }); + + // Memoize an expensive function by storing its results. + function memoize(func, hasher) { + var memoize = function(key) { + var cache = memoize.cache; + var address = '' + (hasher ? hasher.apply(this, arguments) : key); + if (!has$1(cache, address)) cache[address] = func.apply(this, arguments); + return cache[address]; + }; + memoize.cache = {}; + return memoize; + } + + // Delays a function for the given number of milliseconds, and then calls + // it with the arguments supplied. + var delay = restArguments(function(func, wait, args) { + return setTimeout(function() { + return func.apply(null, args); + }, wait); + }); + + // Defers a function, scheduling it to run after the current call stack has + // cleared. + var defer = partial(delay, _$1, 1); + + // Returns a function, that, when invoked, will only be triggered at most once + // during a given window of time. Normally, the throttled function will run + // as much as it can, without ever going more than once per `wait` duration; + // but if you'd like to disable the execution on the leading edge, pass + // `{leading: false}`. To disable execution on the trailing edge, ditto. + function throttle(func, wait, options) { + var timeout, context, args, result; + var previous = 0; + if (!options) options = {}; + + var later = function() { + previous = options.leading === false ? 0 : now(); + timeout = null; + result = func.apply(context, args); + if (!timeout) context = args = null; + }; + + var throttled = function() { + var _now = now(); + if (!previous && options.leading === false) previous = _now; + var remaining = wait - (_now - previous); + context = this; + args = arguments; + if (remaining <= 0 || remaining > wait) { + if (timeout) { + clearTimeout(timeout); + timeout = null; + } + previous = _now; + result = func.apply(context, args); + if (!timeout) context = args = null; + } else if (!timeout && options.trailing !== false) { + timeout = setTimeout(later, remaining); + } + return result; + }; + + throttled.cancel = function() { + clearTimeout(timeout); + previous = 0; + timeout = context = args = null; + }; + + return throttled; + } + + // When a sequence of calls of the returned function ends, the argument + // function is triggered. The end of a sequence is defined by the `wait` + // parameter. If `immediate` is passed, the argument function will be + // triggered at the beginning of the sequence instead of at the end. + function debounce(func, wait, immediate) { + var timeout, previous, args, result, context; + + var later = function() { + var passed = now() - previous; + if (wait > passed) { + timeout = setTimeout(later, wait - passed); + } else { + timeout = null; + if (!immediate) result = func.apply(context, args); + // This check is needed because `func` can recursively invoke `debounced`. + if (!timeout) args = context = null; + } + }; + + var debounced = restArguments(function(_args) { + context = this; + args = _args; + previous = now(); + if (!timeout) { + timeout = setTimeout(later, wait); + if (immediate) result = func.apply(context, args); + } + return result; + }); + + debounced.cancel = function() { + clearTimeout(timeout); + timeout = args = context = null; + }; + + return debounced; + } + + // Returns the first function passed as an argument to the second, + // allowing you to adjust arguments, run code before and after, and + // conditionally execute the original function. + function wrap(func, wrapper) { + return partial(wrapper, func); + } + + // Returns a negated version of the passed-in predicate. + function negate(predicate) { + return function() { + return !predicate.apply(this, arguments); + }; + } + + // Returns a function that is the composition of a list of functions, each + // consuming the return value of the function that follows. + function compose() { + var args = arguments; + var start = args.length - 1; + return function() { + var i = start; + var result = args[start].apply(this, arguments); + while (i--) result = args[i].call(this, result); + return result; + }; + } + + // Returns a function that will only be executed on and after the Nth call. + function after(times, func) { + return function() { + if (--times < 1) { + return func.apply(this, arguments); + } + }; + } + + // Returns a function that will only be executed up to (but not including) the + // Nth call. + function before(times, func) { + var memo; + return function() { + if (--times > 0) { + memo = func.apply(this, arguments); + } + if (times <= 1) func = null; + return memo; + }; + } + + // Returns a function that will be executed at most one time, no matter how + // often you call it. Useful for lazy initialization. + var once = partial(before, 2); + + // Returns the first key on an object that passes a truth test. + function findKey(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = keys(obj), key; + for (var i = 0, length = _keys.length; i < length; i++) { + key = _keys[i]; + if (predicate(obj[key], key, obj)) return key; + } + } + + // Internal function to generate `_.findIndex` and `_.findLastIndex`. + function createPredicateIndexFinder(dir) { + return function(array, predicate, context) { + predicate = cb(predicate, context); + var length = getLength(array); + var index = dir > 0 ? 0 : length - 1; + for (; index >= 0 && index < length; index += dir) { + if (predicate(array[index], index, array)) return index; + } + return -1; + }; + } + + // Returns the first index on an array-like that passes a truth test. + var findIndex = createPredicateIndexFinder(1); + + // Returns the last index on an array-like that passes a truth test. + var findLastIndex = createPredicateIndexFinder(-1); + + // Use a comparator function to figure out the smallest index at which + // an object should be inserted so as to maintain order. Uses binary search. + function sortedIndex(array, obj, iteratee, context) { + iteratee = cb(iteratee, context, 1); + var value = iteratee(obj); + var low = 0, high = getLength(array); + while (low < high) { + var mid = Math.floor((low + high) / 2); + if (iteratee(array[mid]) < value) low = mid + 1; else high = mid; + } + return low; + } + + // Internal function to generate the `_.indexOf` and `_.lastIndexOf` functions. + function createIndexFinder(dir, predicateFind, sortedIndex) { + return function(array, item, idx) { + var i = 0, length = getLength(array); + if (typeof idx == 'number') { + if (dir > 0) { + i = idx >= 0 ? idx : Math.max(idx + length, i); + } else { + length = idx >= 0 ? Math.min(idx + 1, length) : idx + length + 1; + } + } else if (sortedIndex && idx && length) { + idx = sortedIndex(array, item); + return array[idx] === item ? idx : -1; + } + if (item !== item) { + idx = predicateFind(slice.call(array, i, length), isNaN$1); + return idx >= 0 ? idx + i : -1; + } + for (idx = dir > 0 ? i : length - 1; idx >= 0 && idx < length; idx += dir) { + if (array[idx] === item) return idx; + } + return -1; + }; + } + + // Return the position of the first occurrence of an item in an array, + // or -1 if the item is not included in the array. + // If the array is large and already in sort order, pass `true` + // for **isSorted** to use binary search. + var indexOf = createIndexFinder(1, findIndex, sortedIndex); + + // Return the position of the last occurrence of an item in an array, + // or -1 if the item is not included in the array. + var lastIndexOf = createIndexFinder(-1, findLastIndex); + + // Return the first value which passes a truth test. + function find(obj, predicate, context) { + var keyFinder = isArrayLike(obj) ? findIndex : findKey; + var key = keyFinder(obj, predicate, context); + if (key !== void 0 && key !== -1) return obj[key]; + } + + // Convenience version of a common use case of `_.find`: getting the first + // object containing specific `key:value` pairs. + function findWhere(obj, attrs) { + return find(obj, matcher(attrs)); + } + + // The cornerstone for collection functions, an `each` + // implementation, aka `forEach`. + // Handles raw objects in addition to array-likes. Treats all + // sparse array-likes as if they were dense. + function each(obj, iteratee, context) { + iteratee = optimizeCb(iteratee, context); + var i, length; + if (isArrayLike(obj)) { + for (i = 0, length = obj.length; i < length; i++) { + iteratee(obj[i], i, obj); + } + } else { + var _keys = keys(obj); + for (i = 0, length = _keys.length; i < length; i++) { + iteratee(obj[_keys[i]], _keys[i], obj); + } + } + return obj; + } + + // Return the results of applying the iteratee to each element. + function map(obj, iteratee, context) { + iteratee = cb(iteratee, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length, + results = Array(length); + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + results[index] = iteratee(obj[currentKey], currentKey, obj); + } + return results; + } + + // Internal helper to create a reducing function, iterating left or right. + function createReduce(dir) { + // Wrap code that reassigns argument variables in a separate function than + // the one that accesses `arguments.length` to avoid a perf hit. (#1991) + var reducer = function(obj, iteratee, memo, initial) { + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length, + index = dir > 0 ? 0 : length - 1; + if (!initial) { + memo = obj[_keys ? _keys[index] : index]; + index += dir; + } + for (; index >= 0 && index < length; index += dir) { + var currentKey = _keys ? _keys[index] : index; + memo = iteratee(memo, obj[currentKey], currentKey, obj); + } + return memo; + }; + + return function(obj, iteratee, memo, context) { + var initial = arguments.length >= 3; + return reducer(obj, optimizeCb(iteratee, context, 4), memo, initial); + }; + } + + // **Reduce** builds up a single result from a list of values, aka `inject`, + // or `foldl`. + var reduce = createReduce(1); + + // The right-associative version of reduce, also known as `foldr`. + var reduceRight = createReduce(-1); + + // Return all the elements that pass a truth test. + function filter(obj, predicate, context) { + var results = []; + predicate = cb(predicate, context); + each(obj, function(value, index, list) { + if (predicate(value, index, list)) results.push(value); + }); + return results; + } + + // Return all the elements for which a truth test fails. + function reject(obj, predicate, context) { + return filter(obj, negate(cb(predicate)), context); + } + + // Determine whether all of the elements pass a truth test. + function every(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length; + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + if (!predicate(obj[currentKey], currentKey, obj)) return false; + } + return true; + } + + // Determine if at least one element in the object passes a truth test. + function some(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length; + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + if (predicate(obj[currentKey], currentKey, obj)) return true; + } + return false; + } + + // Determine if the array or object contains a given item (using `===`). + function contains(obj, item, fromIndex, guard) { + if (!isArrayLike(obj)) obj = values(obj); + if (typeof fromIndex != 'number' || guard) fromIndex = 0; + return indexOf(obj, item, fromIndex) >= 0; + } + + // Invoke a method (with arguments) on every item in a collection. + var invoke = restArguments(function(obj, path, args) { + var contextPath, func; + if (isFunction$1(path)) { + func = path; + } else { + path = toPath(path); + contextPath = path.slice(0, -1); + path = path[path.length - 1]; + } + return map(obj, function(context) { + var method = func; + if (!method) { + if (contextPath && contextPath.length) { + context = deepGet(context, contextPath); + } + if (context == null) return void 0; + method = context[path]; + } + return method == null ? method : method.apply(context, args); + }); + }); + + // Convenience version of a common use case of `_.map`: fetching a property. + function pluck(obj, key) { + return map(obj, property(key)); + } + + // Convenience version of a common use case of `_.filter`: selecting only + // objects containing specific `key:value` pairs. + function where(obj, attrs) { + return filter(obj, matcher(attrs)); + } + + // Return the maximum element (or element-based computation). + function max(obj, iteratee, context) { + var result = -Infinity, lastComputed = -Infinity, + value, computed; + if (iteratee == null || typeof iteratee == 'number' && typeof obj[0] != 'object' && obj != null) { + obj = isArrayLike(obj) ? obj : values(obj); + for (var i = 0, length = obj.length; i < length; i++) { + value = obj[i]; + if (value != null && value > result) { + result = value; + } + } + } else { + iteratee = cb(iteratee, context); + each(obj, function(v, index, list) { + computed = iteratee(v, index, list); + if (computed > lastComputed || computed === -Infinity && result === -Infinity) { + result = v; + lastComputed = computed; + } + }); + } + return result; + } + + // Return the minimum element (or element-based computation). + function min(obj, iteratee, context) { + var result = Infinity, lastComputed = Infinity, + value, computed; + if (iteratee == null || typeof iteratee == 'number' && typeof obj[0] != 'object' && obj != null) { + obj = isArrayLike(obj) ? obj : values(obj); + for (var i = 0, length = obj.length; i < length; i++) { + value = obj[i]; + if (value != null && value < result) { + result = value; + } + } + } else { + iteratee = cb(iteratee, context); + each(obj, function(v, index, list) { + computed = iteratee(v, index, list); + if (computed < lastComputed || computed === Infinity && result === Infinity) { + result = v; + lastComputed = computed; + } + }); + } + return result; + } + + // Sample **n** random values from a collection using the modern version of the + // [Fisher-Yates shuffle](https://en.wikipedia.org/wiki/Fisher–Yates_shuffle). + // If **n** is not specified, returns a single random element. + // The internal `guard` argument allows it to work with `_.map`. + function sample(obj, n, guard) { + if (n == null || guard) { + if (!isArrayLike(obj)) obj = values(obj); + return obj[random(obj.length - 1)]; + } + var sample = isArrayLike(obj) ? clone(obj) : values(obj); + var length = getLength(sample); + n = Math.max(Math.min(n, length), 0); + var last = length - 1; + for (var index = 0; index < n; index++) { + var rand = random(index, last); + var temp = sample[index]; + sample[index] = sample[rand]; + sample[rand] = temp; + } + return sample.slice(0, n); + } + + // Shuffle a collection. + function shuffle(obj) { + return sample(obj, Infinity); + } + + // Sort the object's values by a criterion produced by an iteratee. + function sortBy(obj, iteratee, context) { + var index = 0; + iteratee = cb(iteratee, context); + return pluck(map(obj, function(value, key, list) { + return { + value: value, + index: index++, + criteria: iteratee(value, key, list) + }; + }).sort(function(left, right) { + var a = left.criteria; + var b = right.criteria; + if (a !== b) { + if (a > b || a === void 0) return 1; + if (a < b || b === void 0) return -1; + } + return left.index - right.index; + }), 'value'); + } + + // An internal function used for aggregate "group by" operations. + function group(behavior, partition) { + return function(obj, iteratee, context) { + var result = partition ? [[], []] : {}; + iteratee = cb(iteratee, context); + each(obj, function(value, index) { + var key = iteratee(value, index, obj); + behavior(result, value, key); + }); + return result; + }; + } + + // Groups the object's values by a criterion. Pass either a string attribute + // to group by, or a function that returns the criterion. + var groupBy = group(function(result, value, key) { + if (has$1(result, key)) result[key].push(value); else result[key] = [value]; + }); + + // Indexes the object's values by a criterion, similar to `_.groupBy`, but for + // when you know that your index values will be unique. + var indexBy = group(function(result, value, key) { + result[key] = value; + }); + + // Counts instances of an object that group by a certain criterion. Pass + // either a string attribute to count by, or a function that returns the + // criterion. + var countBy = group(function(result, value, key) { + if (has$1(result, key)) result[key]++; else result[key] = 1; + }); + + // Split a collection into two arrays: one whose elements all pass the given + // truth test, and one whose elements all do not pass the truth test. + var partition = group(function(result, value, pass) { + result[pass ? 0 : 1].push(value); + }, true); + + // Safely create a real, live array from anything iterable. + var reStrSymbol = /[^\ud800-\udfff]|[\ud800-\udbff][\udc00-\udfff]|[\ud800-\udfff]/g; + function toArray(obj) { + if (!obj) return []; + if (isArray(obj)) return slice.call(obj); + if (isString(obj)) { + // Keep surrogate pair characters together. + return obj.match(reStrSymbol); + } + if (isArrayLike(obj)) return map(obj, identity); + return values(obj); + } + + // Return the number of elements in a collection. + function size(obj) { + if (obj == null) return 0; + return isArrayLike(obj) ? obj.length : keys(obj).length; + } + + // Internal `_.pick` helper function to determine whether `key` is an enumerable + // property name of `obj`. + function keyInObj(value, key, obj) { + return key in obj; + } + + // Return a copy of the object only containing the allowed properties. + var pick = restArguments(function(obj, keys) { + var result = {}, iteratee = keys[0]; + if (obj == null) return result; + if (isFunction$1(iteratee)) { + if (keys.length > 1) iteratee = optimizeCb(iteratee, keys[1]); + keys = allKeys(obj); + } else { + iteratee = keyInObj; + keys = flatten$1(keys, false, false); + obj = Object(obj); + } + for (var i = 0, length = keys.length; i < length; i++) { + var key = keys[i]; + var value = obj[key]; + if (iteratee(value, key, obj)) result[key] = value; + } + return result; + }); + + // Return a copy of the object without the disallowed properties. + var omit = restArguments(function(obj, keys) { + var iteratee = keys[0], context; + if (isFunction$1(iteratee)) { + iteratee = negate(iteratee); + if (keys.length > 1) context = keys[1]; + } else { + keys = map(flatten$1(keys, false, false), String); + iteratee = function(value, key) { + return !contains(keys, key); + }; + } + return pick(obj, iteratee, context); + }); + + // Returns everything but the last entry of the array. Especially useful on + // the arguments object. Passing **n** will return all the values in + // the array, excluding the last N. + function initial(array, n, guard) { + return slice.call(array, 0, Math.max(0, array.length - (n == null || guard ? 1 : n))); + } + + // Get the first element of an array. Passing **n** will return the first N + // values in the array. The **guard** check allows it to work with `_.map`. + function first(array, n, guard) { + if (array == null || array.length < 1) return n == null || guard ? void 0 : []; + if (n == null || guard) return array[0]; + return initial(array, array.length - n); + } + + // Returns everything but the first entry of the `array`. Especially useful on + // the `arguments` object. Passing an **n** will return the rest N values in the + // `array`. + function rest(array, n, guard) { + return slice.call(array, n == null || guard ? 1 : n); + } + + // Get the last element of an array. Passing **n** will return the last N + // values in the array. + function last(array, n, guard) { + if (array == null || array.length < 1) return n == null || guard ? void 0 : []; + if (n == null || guard) return array[array.length - 1]; + return rest(array, Math.max(0, array.length - n)); + } + + // Trim out all falsy values from an array. + function compact(array) { + return filter(array, Boolean); + } + + // Flatten out an array, either recursively (by default), or up to `depth`. + // Passing `true` or `false` as `depth` means `1` or `Infinity`, respectively. + function flatten(array, depth) { + return flatten$1(array, depth, false); + } + + // Take the difference between one array and a number of other arrays. + // Only the elements present in just the first array will remain. + var difference = restArguments(function(array, rest) { + rest = flatten$1(rest, true, true); + return filter(array, function(value){ + return !contains(rest, value); + }); + }); + + // Return a version of the array that does not contain the specified value(s). + var without = restArguments(function(array, otherArrays) { + return difference(array, otherArrays); + }); + + // Produce a duplicate-free version of the array. If the array has already + // been sorted, you have the option of using a faster algorithm. + // The faster algorithm will not work with an iteratee if the iteratee + // is not a one-to-one function, so providing an iteratee will disable + // the faster algorithm. + function uniq(array, isSorted, iteratee, context) { + if (!isBoolean(isSorted)) { + context = iteratee; + iteratee = isSorted; + isSorted = false; + } + if (iteratee != null) iteratee = cb(iteratee, context); + var result = []; + var seen = []; + for (var i = 0, length = getLength(array); i < length; i++) { + var value = array[i], + computed = iteratee ? iteratee(value, i, array) : value; + if (isSorted && !iteratee) { + if (!i || seen !== computed) result.push(value); + seen = computed; + } else if (iteratee) { + if (!contains(seen, computed)) { + seen.push(computed); + result.push(value); + } + } else if (!contains(result, value)) { + result.push(value); + } + } + return result; + } + + // Produce an array that contains the union: each distinct element from all of + // the passed-in arrays. + var union = restArguments(function(arrays) { + return uniq(flatten$1(arrays, true, true)); + }); + + // Produce an array that contains every item shared between all the + // passed-in arrays. + function intersection(array) { + var result = []; + var argsLength = arguments.length; + for (var i = 0, length = getLength(array); i < length; i++) { + var item = array[i]; + if (contains(result, item)) continue; + var j; + for (j = 1; j < argsLength; j++) { + if (!contains(arguments[j], item)) break; + } + if (j === argsLength) result.push(item); + } + return result; + } + + // Complement of zip. Unzip accepts an array of arrays and groups + // each array's elements on shared indices. + function unzip(array) { + var length = array && max(array, getLength).length || 0; + var result = Array(length); + + for (var index = 0; index < length; index++) { + result[index] = pluck(array, index); + } + return result; + } + + // Zip together multiple lists into a single array -- elements that share + // an index go together. + var zip = restArguments(unzip); + + // Converts lists into objects. Pass either a single array of `[key, value]` + // pairs, or two parallel arrays of the same length -- one of keys, and one of + // the corresponding values. Passing by pairs is the reverse of `_.pairs`. + function object(list, values) { + var result = {}; + for (var i = 0, length = getLength(list); i < length; i++) { + if (values) { + result[list[i]] = values[i]; + } else { + result[list[i][0]] = list[i][1]; + } + } + return result; + } + + // Generate an integer Array containing an arithmetic progression. A port of + // the native Python `range()` function. See + // [the Python documentation](https://docs.python.org/library/functions.html#range). + function range(start, stop, step) { + if (stop == null) { + stop = start || 0; + start = 0; + } + if (!step) { + step = stop < start ? -1 : 1; + } + + var length = Math.max(Math.ceil((stop - start) / step), 0); + var range = Array(length); + + for (var idx = 0; idx < length; idx++, start += step) { + range[idx] = start; + } + + return range; + } + + // Chunk a single array into multiple arrays, each containing `count` or fewer + // items. + function chunk(array, count) { + if (count == null || count < 1) return []; + var result = []; + var i = 0, length = array.length; + while (i < length) { + result.push(slice.call(array, i, i += count)); + } + return result; + } + + // Helper function to continue chaining intermediate results. + function chainResult(instance, obj) { + return instance._chain ? _$1(obj).chain() : obj; + } + + // Add your own custom functions to the Underscore object. + function mixin(obj) { + each(functions(obj), function(name) { + var func = _$1[name] = obj[name]; + _$1.prototype[name] = function() { + var args = [this._wrapped]; + push.apply(args, arguments); + return chainResult(this, func.apply(_$1, args)); + }; + }); + return _$1; + } + + // Add all mutator `Array` functions to the wrapper. + each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) { + var method = ArrayProto[name]; + _$1.prototype[name] = function() { + var obj = this._wrapped; + if (obj != null) { + method.apply(obj, arguments); + if ((name === 'shift' || name === 'splice') && obj.length === 0) { + delete obj[0]; + } + } + return chainResult(this, obj); + }; + }); + + // Add all accessor `Array` functions to the wrapper. + each(['concat', 'join', 'slice'], function(name) { + var method = ArrayProto[name]; + _$1.prototype[name] = function() { + var obj = this._wrapped; + if (obj != null) obj = method.apply(obj, arguments); + return chainResult(this, obj); + }; + }); + + // Named Exports + + var allExports = { + __proto__: null, + VERSION: VERSION, + restArguments: restArguments, + isObject: isObject, + isNull: isNull, + isUndefined: isUndefined, + isBoolean: isBoolean, + isElement: isElement, + isString: isString, + isNumber: isNumber, + isDate: isDate, + isRegExp: isRegExp, + isError: isError, + isSymbol: isSymbol, + isArrayBuffer: isArrayBuffer, + isDataView: isDataView$1, + isArray: isArray, + isFunction: isFunction$1, + isArguments: isArguments$1, + isFinite: isFinite$1, + isNaN: isNaN$1, + isTypedArray: isTypedArray$1, + isEmpty: isEmpty, + isMatch: isMatch, + isEqual: isEqual, + isMap: isMap, + isWeakMap: isWeakMap, + isSet: isSet, + isWeakSet: isWeakSet, + keys: keys, + allKeys: allKeys, + values: values, + pairs: pairs, + invert: invert, + functions: functions, + methods: functions, + extend: extend, + extendOwn: extendOwn, + assign: extendOwn, + defaults: defaults, + create: create, + clone: clone, + tap: tap, + get: get, + has: has, + mapObject: mapObject, + identity: identity, + constant: constant, + noop: noop, + toPath: toPath$1, + property: property, + propertyOf: propertyOf, + matcher: matcher, + matches: matcher, + times: times, + random: random, + now: now, + escape: _escape, + unescape: _unescape, + templateSettings: templateSettings, + template: template, + result: result, + uniqueId: uniqueId, + chain: chain, + iteratee: iteratee, + partial: partial, + bind: bind, + bindAll: bindAll, + memoize: memoize, + delay: delay, + defer: defer, + throttle: throttle, + debounce: debounce, + wrap: wrap, + negate: negate, + compose: compose, + after: after, + before: before, + once: once, + findKey: findKey, + findIndex: findIndex, + findLastIndex: findLastIndex, + sortedIndex: sortedIndex, + indexOf: indexOf, + lastIndexOf: lastIndexOf, + find: find, + detect: find, + findWhere: findWhere, + each: each, + forEach: each, + map: map, + collect: map, + reduce: reduce, + foldl: reduce, + inject: reduce, + reduceRight: reduceRight, + foldr: reduceRight, + filter: filter, + select: filter, + reject: reject, + every: every, + all: every, + some: some, + any: some, + contains: contains, + includes: contains, + include: contains, + invoke: invoke, + pluck: pluck, + where: where, + max: max, + min: min, + shuffle: shuffle, + sample: sample, + sortBy: sortBy, + groupBy: groupBy, + indexBy: indexBy, + countBy: countBy, + partition: partition, + toArray: toArray, + size: size, + pick: pick, + omit: omit, + first: first, + head: first, + take: first, + initial: initial, + last: last, + rest: rest, + tail: rest, + drop: rest, + compact: compact, + flatten: flatten, + without: without, + uniq: uniq, + unique: uniq, + union: union, + intersection: intersection, + difference: difference, + unzip: unzip, + transpose: unzip, + zip: zip, + object: object, + range: range, + chunk: chunk, + mixin: mixin, + 'default': _$1 + }; + + // Default Export + + // Add all of the Underscore functions to the wrapper object. + var _ = mixin(allExports); + // Legacy Node.js API. + _._ = _; + + return _; + +}))); +//# sourceMappingURL=underscore-umd.js.map diff --git a/docs/_static/underscore-1.3.1.js b/docs/_static/underscore-1.3.1.js deleted file mode 100644 index 208d4cd..0000000 --- a/docs/_static/underscore-1.3.1.js +++ /dev/null @@ -1,999 +0,0 @@ -// Underscore.js 1.3.1 -// (c) 2009-2012 Jeremy Ashkenas, DocumentCloud Inc. -// Underscore is freely distributable under the MIT license. -// Portions of Underscore are inspired or borrowed from Prototype, -// Oliver Steele's Functional, and John Resig's Micro-Templating. -// For all details and documentation: -// http://documentcloud.github.com/underscore - -(function() { - - // Baseline setup - // -------------- - - // Establish the root object, `window` in the browser, or `global` on the server. - var root = this; - - // Save the previous value of the `_` variable. - var previousUnderscore = root._; - - // Establish the object that gets returned to break out of a loop iteration. - var breaker = {}; - - // Save bytes in the minified (but not gzipped) version: - var ArrayProto = Array.prototype, ObjProto = Object.prototype, FuncProto = Function.prototype; - - // Create quick reference variables for speed access to core prototypes. - var slice = ArrayProto.slice, - unshift = ArrayProto.unshift, - toString = ObjProto.toString, - hasOwnProperty = ObjProto.hasOwnProperty; - - // All **ECMAScript 5** native function implementations that we hope to use - // are declared here. - var - nativeForEach = ArrayProto.forEach, - nativeMap = ArrayProto.map, - nativeReduce = ArrayProto.reduce, - nativeReduceRight = ArrayProto.reduceRight, - nativeFilter = ArrayProto.filter, - nativeEvery = ArrayProto.every, - nativeSome = ArrayProto.some, - nativeIndexOf = ArrayProto.indexOf, - nativeLastIndexOf = ArrayProto.lastIndexOf, - nativeIsArray = Array.isArray, - nativeKeys = Object.keys, - nativeBind = FuncProto.bind; - - // Create a safe reference to the Underscore object for use below. - var _ = function(obj) { return new wrapper(obj); }; - - // Export the Underscore object for **Node.js**, with - // backwards-compatibility for the old `require()` API. If we're in - // the browser, add `_` as a global object via a string identifier, - // for Closure Compiler "advanced" mode. - if (typeof exports !== 'undefined') { - if (typeof module !== 'undefined' && module.exports) { - exports = module.exports = _; - } - exports._ = _; - } else { - root['_'] = _; - } - - // Current version. - _.VERSION = '1.3.1'; - - // Collection Functions - // -------------------- - - // The cornerstone, an `each` implementation, aka `forEach`. - // Handles objects with the built-in `forEach`, arrays, and raw objects. - // Delegates to **ECMAScript 5**'s native `forEach` if available. - var each = _.each = _.forEach = function(obj, iterator, context) { - if (obj == null) return; - if (nativeForEach && obj.forEach === nativeForEach) { - obj.forEach(iterator, context); - } else if (obj.length === +obj.length) { - for (var i = 0, l = obj.length; i < l; i++) { - if (i in obj && iterator.call(context, obj[i], i, obj) === breaker) return; - } - } else { - for (var key in obj) { - if (_.has(obj, key)) { - if (iterator.call(context, obj[key], key, obj) === breaker) return; - } - } - } - }; - - // Return the results of applying the iterator to each element. - // Delegates to **ECMAScript 5**'s native `map` if available. - _.map = _.collect = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - if (nativeMap && obj.map === nativeMap) return obj.map(iterator, context); - each(obj, function(value, index, list) { - results[results.length] = iterator.call(context, value, index, list); - }); - if (obj.length === +obj.length) results.length = obj.length; - return results; - }; - - // **Reduce** builds up a single result from a list of values, aka `inject`, - // or `foldl`. Delegates to **ECMAScript 5**'s native `reduce` if available. - _.reduce = _.foldl = _.inject = function(obj, iterator, memo, context) { - var initial = arguments.length > 2; - if (obj == null) obj = []; - if (nativeReduce && obj.reduce === nativeReduce) { - if (context) iterator = _.bind(iterator, context); - return initial ? obj.reduce(iterator, memo) : obj.reduce(iterator); - } - each(obj, function(value, index, list) { - if (!initial) { - memo = value; - initial = true; - } else { - memo = iterator.call(context, memo, value, index, list); - } - }); - if (!initial) throw new TypeError('Reduce of empty array with no initial value'); - return memo; - }; - - // The right-associative version of reduce, also known as `foldr`. - // Delegates to **ECMAScript 5**'s native `reduceRight` if available. - _.reduceRight = _.foldr = function(obj, iterator, memo, context) { - var initial = arguments.length > 2; - if (obj == null) obj = []; - if (nativeReduceRight && obj.reduceRight === nativeReduceRight) { - if (context) iterator = _.bind(iterator, context); - return initial ? obj.reduceRight(iterator, memo) : obj.reduceRight(iterator); - } - var reversed = _.toArray(obj).reverse(); - if (context && !initial) iterator = _.bind(iterator, context); - return initial ? _.reduce(reversed, iterator, memo, context) : _.reduce(reversed, iterator); - }; - - // Return the first value which passes a truth test. Aliased as `detect`. - _.find = _.detect = function(obj, iterator, context) { - var result; - any(obj, function(value, index, list) { - if (iterator.call(context, value, index, list)) { - result = value; - return true; - } - }); - return result; - }; - - // Return all the elements that pass a truth test. - // Delegates to **ECMAScript 5**'s native `filter` if available. - // Aliased as `select`. - _.filter = _.select = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - if (nativeFilter && obj.filter === nativeFilter) return obj.filter(iterator, context); - each(obj, function(value, index, list) { - if (iterator.call(context, value, index, list)) results[results.length] = value; - }); - return results; - }; - - // Return all the elements for which a truth test fails. - _.reject = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - each(obj, function(value, index, list) { - if (!iterator.call(context, value, index, list)) results[results.length] = value; - }); - return results; - }; - - // Determine whether all of the elements match a truth test. - // Delegates to **ECMAScript 5**'s native `every` if available. - // Aliased as `all`. - _.every = _.all = function(obj, iterator, context) { - var result = true; - if (obj == null) return result; - if (nativeEvery && obj.every === nativeEvery) return obj.every(iterator, context); - each(obj, function(value, index, list) { - if (!(result = result && iterator.call(context, value, index, list))) return breaker; - }); - return result; - }; - - // Determine if at least one element in the object matches a truth test. - // Delegates to **ECMAScript 5**'s native `some` if available. - // Aliased as `any`. - var any = _.some = _.any = function(obj, iterator, context) { - iterator || (iterator = _.identity); - var result = false; - if (obj == null) return result; - if (nativeSome && obj.some === nativeSome) return obj.some(iterator, context); - each(obj, function(value, index, list) { - if (result || (result = iterator.call(context, value, index, list))) return breaker; - }); - return !!result; - }; - - // Determine if a given value is included in the array or object using `===`. - // Aliased as `contains`. - _.include = _.contains = function(obj, target) { - var found = false; - if (obj == null) return found; - if (nativeIndexOf && obj.indexOf === nativeIndexOf) return obj.indexOf(target) != -1; - found = any(obj, function(value) { - return value === target; - }); - return found; - }; - - // Invoke a method (with arguments) on every item in a collection. - _.invoke = function(obj, method) { - var args = slice.call(arguments, 2); - return _.map(obj, function(value) { - return (_.isFunction(method) ? method || value : value[method]).apply(value, args); - }); - }; - - // Convenience version of a common use case of `map`: fetching a property. - _.pluck = function(obj, key) { - return _.map(obj, function(value){ return value[key]; }); - }; - - // Return the maximum element or (element-based computation). - _.max = function(obj, iterator, context) { - if (!iterator && _.isArray(obj)) return Math.max.apply(Math, obj); - if (!iterator && _.isEmpty(obj)) return -Infinity; - var result = {computed : -Infinity}; - each(obj, function(value, index, list) { - var computed = iterator ? iterator.call(context, value, index, list) : value; - computed >= result.computed && (result = {value : value, computed : computed}); - }); - return result.value; - }; - - // Return the minimum element (or element-based computation). - _.min = function(obj, iterator, context) { - if (!iterator && _.isArray(obj)) return Math.min.apply(Math, obj); - if (!iterator && _.isEmpty(obj)) return Infinity; - var result = {computed : Infinity}; - each(obj, function(value, index, list) { - var computed = iterator ? iterator.call(context, value, index, list) : value; - computed < result.computed && (result = {value : value, computed : computed}); - }); - return result.value; - }; - - // Shuffle an array. - _.shuffle = function(obj) { - var shuffled = [], rand; - each(obj, function(value, index, list) { - if (index == 0) { - shuffled[0] = value; - } else { - rand = Math.floor(Math.random() * (index + 1)); - shuffled[index] = shuffled[rand]; - shuffled[rand] = value; - } - }); - return shuffled; - }; - - // Sort the object's values by a criterion produced by an iterator. - _.sortBy = function(obj, iterator, context) { - return _.pluck(_.map(obj, function(value, index, list) { - return { - value : value, - criteria : iterator.call(context, value, index, list) - }; - }).sort(function(left, right) { - var a = left.criteria, b = right.criteria; - return a < b ? -1 : a > b ? 1 : 0; - }), 'value'); - }; - - // Groups the object's values by a criterion. Pass either a string attribute - // to group by, or a function that returns the criterion. - _.groupBy = function(obj, val) { - var result = {}; - var iterator = _.isFunction(val) ? val : function(obj) { return obj[val]; }; - each(obj, function(value, index) { - var key = iterator(value, index); - (result[key] || (result[key] = [])).push(value); - }); - return result; - }; - - // Use a comparator function to figure out at what index an object should - // be inserted so as to maintain order. Uses binary search. - _.sortedIndex = function(array, obj, iterator) { - iterator || (iterator = _.identity); - var low = 0, high = array.length; - while (low < high) { - var mid = (low + high) >> 1; - iterator(array[mid]) < iterator(obj) ? low = mid + 1 : high = mid; - } - return low; - }; - - // Safely convert anything iterable into a real, live array. - _.toArray = function(iterable) { - if (!iterable) return []; - if (iterable.toArray) return iterable.toArray(); - if (_.isArray(iterable)) return slice.call(iterable); - if (_.isArguments(iterable)) return slice.call(iterable); - return _.values(iterable); - }; - - // Return the number of elements in an object. - _.size = function(obj) { - return _.toArray(obj).length; - }; - - // Array Functions - // --------------- - - // Get the first element of an array. Passing **n** will return the first N - // values in the array. Aliased as `head`. The **guard** check allows it to work - // with `_.map`. - _.first = _.head = function(array, n, guard) { - return (n != null) && !guard ? slice.call(array, 0, n) : array[0]; - }; - - // Returns everything but the last entry of the array. Especcialy useful on - // the arguments object. Passing **n** will return all the values in - // the array, excluding the last N. The **guard** check allows it to work with - // `_.map`. - _.initial = function(array, n, guard) { - return slice.call(array, 0, array.length - ((n == null) || guard ? 1 : n)); - }; - - // Get the last element of an array. Passing **n** will return the last N - // values in the array. The **guard** check allows it to work with `_.map`. - _.last = function(array, n, guard) { - if ((n != null) && !guard) { - return slice.call(array, Math.max(array.length - n, 0)); - } else { - return array[array.length - 1]; - } - }; - - // Returns everything but the first entry of the array. Aliased as `tail`. - // Especially useful on the arguments object. Passing an **index** will return - // the rest of the values in the array from that index onward. The **guard** - // check allows it to work with `_.map`. - _.rest = _.tail = function(array, index, guard) { - return slice.call(array, (index == null) || guard ? 1 : index); - }; - - // Trim out all falsy values from an array. - _.compact = function(array) { - return _.filter(array, function(value){ return !!value; }); - }; - - // Return a completely flattened version of an array. - _.flatten = function(array, shallow) { - return _.reduce(array, function(memo, value) { - if (_.isArray(value)) return memo.concat(shallow ? value : _.flatten(value)); - memo[memo.length] = value; - return memo; - }, []); - }; - - // Return a version of the array that does not contain the specified value(s). - _.without = function(array) { - return _.difference(array, slice.call(arguments, 1)); - }; - - // Produce a duplicate-free version of the array. If the array has already - // been sorted, you have the option of using a faster algorithm. - // Aliased as `unique`. - _.uniq = _.unique = function(array, isSorted, iterator) { - var initial = iterator ? _.map(array, iterator) : array; - var result = []; - _.reduce(initial, function(memo, el, i) { - if (0 == i || (isSorted === true ? _.last(memo) != el : !_.include(memo, el))) { - memo[memo.length] = el; - result[result.length] = array[i]; - } - return memo; - }, []); - return result; - }; - - // Produce an array that contains the union: each distinct element from all of - // the passed-in arrays. - _.union = function() { - return _.uniq(_.flatten(arguments, true)); - }; - - // Produce an array that contains every item shared between all the - // passed-in arrays. (Aliased as "intersect" for back-compat.) - _.intersection = _.intersect = function(array) { - var rest = slice.call(arguments, 1); - return _.filter(_.uniq(array), function(item) { - return _.every(rest, function(other) { - return _.indexOf(other, item) >= 0; - }); - }); - }; - - // Take the difference between one array and a number of other arrays. - // Only the elements present in just the first array will remain. - _.difference = function(array) { - var rest = _.flatten(slice.call(arguments, 1)); - return _.filter(array, function(value){ return !_.include(rest, value); }); - }; - - // Zip together multiple lists into a single array -- elements that share - // an index go together. - _.zip = function() { - var args = slice.call(arguments); - var length = _.max(_.pluck(args, 'length')); - var results = new Array(length); - for (var i = 0; i < length; i++) results[i] = _.pluck(args, "" + i); - return results; - }; - - // If the browser doesn't supply us with indexOf (I'm looking at you, **MSIE**), - // we need this function. Return the position of the first occurrence of an - // item in an array, or -1 if the item is not included in the array. - // Delegates to **ECMAScript 5**'s native `indexOf` if available. - // If the array is large and already in sort order, pass `true` - // for **isSorted** to use binary search. - _.indexOf = function(array, item, isSorted) { - if (array == null) return -1; - var i, l; - if (isSorted) { - i = _.sortedIndex(array, item); - return array[i] === item ? i : -1; - } - if (nativeIndexOf && array.indexOf === nativeIndexOf) return array.indexOf(item); - for (i = 0, l = array.length; i < l; i++) if (i in array && array[i] === item) return i; - return -1; - }; - - // Delegates to **ECMAScript 5**'s native `lastIndexOf` if available. - _.lastIndexOf = function(array, item) { - if (array == null) return -1; - if (nativeLastIndexOf && array.lastIndexOf === nativeLastIndexOf) return array.lastIndexOf(item); - var i = array.length; - while (i--) if (i in array && array[i] === item) return i; - return -1; - }; - - // Generate an integer Array containing an arithmetic progression. A port of - // the native Python `range()` function. See - // [the Python documentation](http://docs.python.org/library/functions.html#range). - _.range = function(start, stop, step) { - if (arguments.length <= 1) { - stop = start || 0; - start = 0; - } - step = arguments[2] || 1; - - var len = Math.max(Math.ceil((stop - start) / step), 0); - var idx = 0; - var range = new Array(len); - - while(idx < len) { - range[idx++] = start; - start += step; - } - - return range; - }; - - // Function (ahem) Functions - // ------------------ - - // Reusable constructor function for prototype setting. - var ctor = function(){}; - - // Create a function bound to a given object (assigning `this`, and arguments, - // optionally). Binding with arguments is also known as `curry`. - // Delegates to **ECMAScript 5**'s native `Function.bind` if available. - // We check for `func.bind` first, to fail fast when `func` is undefined. - _.bind = function bind(func, context) { - var bound, args; - if (func.bind === nativeBind && nativeBind) return nativeBind.apply(func, slice.call(arguments, 1)); - if (!_.isFunction(func)) throw new TypeError; - args = slice.call(arguments, 2); - return bound = function() { - if (!(this instanceof bound)) return func.apply(context, args.concat(slice.call(arguments))); - ctor.prototype = func.prototype; - var self = new ctor; - var result = func.apply(self, args.concat(slice.call(arguments))); - if (Object(result) === result) return result; - return self; - }; - }; - - // Bind all of an object's methods to that object. Useful for ensuring that - // all callbacks defined on an object belong to it. - _.bindAll = function(obj) { - var funcs = slice.call(arguments, 1); - if (funcs.length == 0) funcs = _.functions(obj); - each(funcs, function(f) { obj[f] = _.bind(obj[f], obj); }); - return obj; - }; - - // Memoize an expensive function by storing its results. - _.memoize = function(func, hasher) { - var memo = {}; - hasher || (hasher = _.identity); - return function() { - var key = hasher.apply(this, arguments); - return _.has(memo, key) ? memo[key] : (memo[key] = func.apply(this, arguments)); - }; - }; - - // Delays a function for the given number of milliseconds, and then calls - // it with the arguments supplied. - _.delay = function(func, wait) { - var args = slice.call(arguments, 2); - return setTimeout(function(){ return func.apply(func, args); }, wait); - }; - - // Defers a function, scheduling it to run after the current call stack has - // cleared. - _.defer = function(func) { - return _.delay.apply(_, [func, 1].concat(slice.call(arguments, 1))); - }; - - // Returns a function, that, when invoked, will only be triggered at most once - // during a given window of time. - _.throttle = function(func, wait) { - var context, args, timeout, throttling, more; - var whenDone = _.debounce(function(){ more = throttling = false; }, wait); - return function() { - context = this; args = arguments; - var later = function() { - timeout = null; - if (more) func.apply(context, args); - whenDone(); - }; - if (!timeout) timeout = setTimeout(later, wait); - if (throttling) { - more = true; - } else { - func.apply(context, args); - } - whenDone(); - throttling = true; - }; - }; - - // Returns a function, that, as long as it continues to be invoked, will not - // be triggered. The function will be called after it stops being called for - // N milliseconds. - _.debounce = function(func, wait) { - var timeout; - return function() { - var context = this, args = arguments; - var later = function() { - timeout = null; - func.apply(context, args); - }; - clearTimeout(timeout); - timeout = setTimeout(later, wait); - }; - }; - - // Returns a function that will be executed at most one time, no matter how - // often you call it. Useful for lazy initialization. - _.once = function(func) { - var ran = false, memo; - return function() { - if (ran) return memo; - ran = true; - return memo = func.apply(this, arguments); - }; - }; - - // Returns the first function passed as an argument to the second, - // allowing you to adjust arguments, run code before and after, and - // conditionally execute the original function. - _.wrap = function(func, wrapper) { - return function() { - var args = [func].concat(slice.call(arguments, 0)); - return wrapper.apply(this, args); - }; - }; - - // Returns a function that is the composition of a list of functions, each - // consuming the return value of the function that follows. - _.compose = function() { - var funcs = arguments; - return function() { - var args = arguments; - for (var i = funcs.length - 1; i >= 0; i--) { - args = [funcs[i].apply(this, args)]; - } - return args[0]; - }; - }; - - // Returns a function that will only be executed after being called N times. - _.after = function(times, func) { - if (times <= 0) return func(); - return function() { - if (--times < 1) { return func.apply(this, arguments); } - }; - }; - - // Object Functions - // ---------------- - - // Retrieve the names of an object's properties. - // Delegates to **ECMAScript 5**'s native `Object.keys` - _.keys = nativeKeys || function(obj) { - if (obj !== Object(obj)) throw new TypeError('Invalid object'); - var keys = []; - for (var key in obj) if (_.has(obj, key)) keys[keys.length] = key; - return keys; - }; - - // Retrieve the values of an object's properties. - _.values = function(obj) { - return _.map(obj, _.identity); - }; - - // Return a sorted list of the function names available on the object. - // Aliased as `methods` - _.functions = _.methods = function(obj) { - var names = []; - for (var key in obj) { - if (_.isFunction(obj[key])) names.push(key); - } - return names.sort(); - }; - - // Extend a given object with all the properties in passed-in object(s). - _.extend = function(obj) { - each(slice.call(arguments, 1), function(source) { - for (var prop in source) { - obj[prop] = source[prop]; - } - }); - return obj; - }; - - // Fill in a given object with default properties. - _.defaults = function(obj) { - each(slice.call(arguments, 1), function(source) { - for (var prop in source) { - if (obj[prop] == null) obj[prop] = source[prop]; - } - }); - return obj; - }; - - // Create a (shallow-cloned) duplicate of an object. - _.clone = function(obj) { - if (!_.isObject(obj)) return obj; - return _.isArray(obj) ? obj.slice() : _.extend({}, obj); - }; - - // Invokes interceptor with the obj, and then returns obj. - // The primary purpose of this method is to "tap into" a method chain, in - // order to perform operations on intermediate results within the chain. - _.tap = function(obj, interceptor) { - interceptor(obj); - return obj; - }; - - // Internal recursive comparison function. - function eq(a, b, stack) { - // Identical objects are equal. `0 === -0`, but they aren't identical. - // See the Harmony `egal` proposal: http://wiki.ecmascript.org/doku.php?id=harmony:egal. - if (a === b) return a !== 0 || 1 / a == 1 / b; - // A strict comparison is necessary because `null == undefined`. - if (a == null || b == null) return a === b; - // Unwrap any wrapped objects. - if (a._chain) a = a._wrapped; - if (b._chain) b = b._wrapped; - // Invoke a custom `isEqual` method if one is provided. - if (a.isEqual && _.isFunction(a.isEqual)) return a.isEqual(b); - if (b.isEqual && _.isFunction(b.isEqual)) return b.isEqual(a); - // Compare `[[Class]]` names. - var className = toString.call(a); - if (className != toString.call(b)) return false; - switch (className) { - // Strings, numbers, dates, and booleans are compared by value. - case '[object String]': - // Primitives and their corresponding object wrappers are equivalent; thus, `"5"` is - // equivalent to `new String("5")`. - return a == String(b); - case '[object Number]': - // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for - // other numeric values. - return a != +a ? b != +b : (a == 0 ? 1 / a == 1 / b : a == +b); - case '[object Date]': - case '[object Boolean]': - // Coerce dates and booleans to numeric primitive values. Dates are compared by their - // millisecond representations. Note that invalid dates with millisecond representations - // of `NaN` are not equivalent. - return +a == +b; - // RegExps are compared by their source patterns and flags. - case '[object RegExp]': - return a.source == b.source && - a.global == b.global && - a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase; - } - if (typeof a != 'object' || typeof b != 'object') return false; - // Assume equality for cyclic structures. The algorithm for detecting cyclic - // structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`. - var length = stack.length; - while (length--) { - // Linear search. Performance is inversely proportional to the number of - // unique nested structures. - if (stack[length] == a) return true; - } - // Add the first object to the stack of traversed objects. - stack.push(a); - var size = 0, result = true; - // Recursively compare objects and arrays. - if (className == '[object Array]') { - // Compare array lengths to determine if a deep comparison is necessary. - size = a.length; - result = size == b.length; - if (result) { - // Deep compare the contents, ignoring non-numeric properties. - while (size--) { - // Ensure commutative equality for sparse arrays. - if (!(result = size in a == size in b && eq(a[size], b[size], stack))) break; - } - } - } else { - // Objects with different constructors are not equivalent. - if ('constructor' in a != 'constructor' in b || a.constructor != b.constructor) return false; - // Deep compare objects. - for (var key in a) { - if (_.has(a, key)) { - // Count the expected number of properties. - size++; - // Deep compare each member. - if (!(result = _.has(b, key) && eq(a[key], b[key], stack))) break; - } - } - // Ensure that both objects contain the same number of properties. - if (result) { - for (key in b) { - if (_.has(b, key) && !(size--)) break; - } - result = !size; - } - } - // Remove the first object from the stack of traversed objects. - stack.pop(); - return result; - } - - // Perform a deep comparison to check if two objects are equal. - _.isEqual = function(a, b) { - return eq(a, b, []); - }; - - // Is a given array, string, or object empty? - // An "empty" object has no enumerable own-properties. - _.isEmpty = function(obj) { - if (_.isArray(obj) || _.isString(obj)) return obj.length === 0; - for (var key in obj) if (_.has(obj, key)) return false; - return true; - }; - - // Is a given value a DOM element? - _.isElement = function(obj) { - return !!(obj && obj.nodeType == 1); - }; - - // Is a given value an array? - // Delegates to ECMA5's native Array.isArray - _.isArray = nativeIsArray || function(obj) { - return toString.call(obj) == '[object Array]'; - }; - - // Is a given variable an object? - _.isObject = function(obj) { - return obj === Object(obj); - }; - - // Is a given variable an arguments object? - _.isArguments = function(obj) { - return toString.call(obj) == '[object Arguments]'; - }; - if (!_.isArguments(arguments)) { - _.isArguments = function(obj) { - return !!(obj && _.has(obj, 'callee')); - }; - } - - // Is a given value a function? - _.isFunction = function(obj) { - return toString.call(obj) == '[object Function]'; - }; - - // Is a given value a string? - _.isString = function(obj) { - return toString.call(obj) == '[object String]'; - }; - - // Is a given value a number? - _.isNumber = function(obj) { - return toString.call(obj) == '[object Number]'; - }; - - // Is the given value `NaN`? - _.isNaN = function(obj) { - // `NaN` is the only value for which `===` is not reflexive. - return obj !== obj; - }; - - // Is a given value a boolean? - _.isBoolean = function(obj) { - return obj === true || obj === false || toString.call(obj) == '[object Boolean]'; - }; - - // Is a given value a date? - _.isDate = function(obj) { - return toString.call(obj) == '[object Date]'; - }; - - // Is the given value a regular expression? - _.isRegExp = function(obj) { - return toString.call(obj) == '[object RegExp]'; - }; - - // Is a given value equal to null? - _.isNull = function(obj) { - return obj === null; - }; - - // Is a given variable undefined? - _.isUndefined = function(obj) { - return obj === void 0; - }; - - // Has own property? - _.has = function(obj, key) { - return hasOwnProperty.call(obj, key); - }; - - // Utility Functions - // ----------------- - - // Run Underscore.js in *noConflict* mode, returning the `_` variable to its - // previous owner. Returns a reference to the Underscore object. - _.noConflict = function() { - root._ = previousUnderscore; - return this; - }; - - // Keep the identity function around for default iterators. - _.identity = function(value) { - return value; - }; - - // Run a function **n** times. - _.times = function (n, iterator, context) { - for (var i = 0; i < n; i++) iterator.call(context, i); - }; - - // Escape a string for HTML interpolation. - _.escape = function(string) { - return (''+string).replace(/&/g, '&').replace(//g, '>').replace(/"/g, '"').replace(/'/g, ''').replace(/\//g,'/'); - }; - - // Add your own custom functions to the Underscore object, ensuring that - // they're correctly added to the OOP wrapper as well. - _.mixin = function(obj) { - each(_.functions(obj), function(name){ - addToWrapper(name, _[name] = obj[name]); - }); - }; - - // Generate a unique integer id (unique within the entire client session). - // Useful for temporary DOM ids. - var idCounter = 0; - _.uniqueId = function(prefix) { - var id = idCounter++; - return prefix ? prefix + id : id; - }; - - // By default, Underscore uses ERB-style template delimiters, change the - // following template settings to use alternative delimiters. - _.templateSettings = { - evaluate : /<%([\s\S]+?)%>/g, - interpolate : /<%=([\s\S]+?)%>/g, - escape : /<%-([\s\S]+?)%>/g - }; - - // When customizing `templateSettings`, if you don't want to define an - // interpolation, evaluation or escaping regex, we need one that is - // guaranteed not to match. - var noMatch = /.^/; - - // Within an interpolation, evaluation, or escaping, remove HTML escaping - // that had been previously added. - var unescape = function(code) { - return code.replace(/\\\\/g, '\\').replace(/\\'/g, "'"); - }; - - // JavaScript micro-templating, similar to John Resig's implementation. - // Underscore templating handles arbitrary delimiters, preserves whitespace, - // and correctly escapes quotes within interpolated code. - _.template = function(str, data) { - var c = _.templateSettings; - var tmpl = 'var __p=[],print=function(){__p.push.apply(__p,arguments);};' + - 'with(obj||{}){__p.push(\'' + - str.replace(/\\/g, '\\\\') - .replace(/'/g, "\\'") - .replace(c.escape || noMatch, function(match, code) { - return "',_.escape(" + unescape(code) + "),'"; - }) - .replace(c.interpolate || noMatch, function(match, code) { - return "'," + unescape(code) + ",'"; - }) - .replace(c.evaluate || noMatch, function(match, code) { - return "');" + unescape(code).replace(/[\r\n\t]/g, ' ') + ";__p.push('"; - }) - .replace(/\r/g, '\\r') - .replace(/\n/g, '\\n') - .replace(/\t/g, '\\t') - + "');}return __p.join('');"; - var func = new Function('obj', '_', tmpl); - if (data) return func(data, _); - return function(data) { - return func.call(this, data, _); - }; - }; - - // Add a "chain" function, which will delegate to the wrapper. - _.chain = function(obj) { - return _(obj).chain(); - }; - - // The OOP Wrapper - // --------------- - - // If Underscore is called as a function, it returns a wrapped object that - // can be used OO-style. This wrapper holds altered versions of all the - // underscore functions. Wrapped objects may be chained. - var wrapper = function(obj) { this._wrapped = obj; }; - - // Expose `wrapper.prototype` as `_.prototype` - _.prototype = wrapper.prototype; - - // Helper function to continue chaining intermediate results. - var result = function(obj, chain) { - return chain ? _(obj).chain() : obj; - }; - - // A method to easily add functions to the OOP wrapper. - var addToWrapper = function(name, func) { - wrapper.prototype[name] = function() { - var args = slice.call(arguments); - unshift.call(args, this._wrapped); - return result(func.apply(_, args), this._chain); - }; - }; - - // Add all of the Underscore functions to the wrapper object. - _.mixin(_); - - // Add all mutator Array functions to the wrapper. - each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) { - var method = ArrayProto[name]; - wrapper.prototype[name] = function() { - var wrapped = this._wrapped; - method.apply(wrapped, arguments); - var length = wrapped.length; - if ((name == 'shift' || name == 'splice') && length === 0) delete wrapped[0]; - return result(wrapped, this._chain); - }; - }); - - // Add all accessor Array functions to the wrapper. - each(['concat', 'join', 'slice'], function(name) { - var method = ArrayProto[name]; - wrapper.prototype[name] = function() { - return result(method.apply(this._wrapped, arguments), this._chain); - }; - }); - - // Start chaining a wrapped Underscore object. - wrapper.prototype.chain = function() { - this._chain = true; - return this; - }; - - // Extracts the result from a wrapped and chained object. - wrapper.prototype.value = function() { - return this._wrapped; - }; - -}).call(this); diff --git a/docs/_static/underscore.js b/docs/_static/underscore.js index 5b55f32..cf177d4 100644 --- a/docs/_static/underscore.js +++ b/docs/_static/underscore.js @@ -1,31 +1,6 @@ -// Underscore.js 1.3.1 -// (c) 2009-2012 Jeremy Ashkenas, DocumentCloud Inc. -// Underscore is freely distributable under the MIT license. -// Portions of Underscore are inspired or borrowed from Prototype, -// Oliver Steele's Functional, and John Resig's Micro-Templating. -// For all details and documentation: -// http://documentcloud.github.com/underscore -(function(){function q(a,c,d){if(a===c)return a!==0||1/a==1/c;if(a==null||c==null)return a===c;if(a._chain)a=a._wrapped;if(c._chain)c=c._wrapped;if(a.isEqual&&b.isFunction(a.isEqual))return a.isEqual(c);if(c.isEqual&&b.isFunction(c.isEqual))return c.isEqual(a);var e=l.call(a);if(e!=l.call(c))return false;switch(e){case "[object String]":return a==String(c);case "[object Number]":return a!=+a?c!=+c:a==0?1/a==1/c:a==+c;case "[object Date]":case "[object Boolean]":return+a==+c;case "[object RegExp]":return a.source== -c.source&&a.global==c.global&&a.multiline==c.multiline&&a.ignoreCase==c.ignoreCase}if(typeof a!="object"||typeof c!="object")return false;for(var f=d.length;f--;)if(d[f]==a)return true;d.push(a);var f=0,g=true;if(e=="[object Array]"){if(f=a.length,g=f==c.length)for(;f--;)if(!(g=f in a==f in c&&q(a[f],c[f],d)))break}else{if("constructor"in a!="constructor"in c||a.constructor!=c.constructor)return false;for(var h in a)if(b.has(a,h)&&(f++,!(g=b.has(c,h)&&q(a[h],c[h],d))))break;if(g){for(h in c)if(b.has(c, -h)&&!f--)break;g=!f}}d.pop();return g}var r=this,G=r._,n={},k=Array.prototype,o=Object.prototype,i=k.slice,H=k.unshift,l=o.toString,I=o.hasOwnProperty,w=k.forEach,x=k.map,y=k.reduce,z=k.reduceRight,A=k.filter,B=k.every,C=k.some,p=k.indexOf,D=k.lastIndexOf,o=Array.isArray,J=Object.keys,s=Function.prototype.bind,b=function(a){return new m(a)};if(typeof exports!=="undefined"){if(typeof module!=="undefined"&&module.exports)exports=module.exports=b;exports._=b}else r._=b;b.VERSION="1.3.1";var j=b.each= -b.forEach=function(a,c,d){if(a!=null)if(w&&a.forEach===w)a.forEach(c,d);else if(a.length===+a.length)for(var e=0,f=a.length;e2;a== -null&&(a=[]);if(y&&a.reduce===y)return e&&(c=b.bind(c,e)),f?a.reduce(c,d):a.reduce(c);j(a,function(a,b,i){f?d=c.call(e,d,a,b,i):(d=a,f=true)});if(!f)throw new TypeError("Reduce of empty array with no initial value");return d};b.reduceRight=b.foldr=function(a,c,d,e){var f=arguments.length>2;a==null&&(a=[]);if(z&&a.reduceRight===z)return e&&(c=b.bind(c,e)),f?a.reduceRight(c,d):a.reduceRight(c);var g=b.toArray(a).reverse();e&&!f&&(c=b.bind(c,e));return f?b.reduce(g,c,d,e):b.reduce(g,c)};b.find=b.detect= -function(a,c,b){var e;E(a,function(a,g,h){if(c.call(b,a,g,h))return e=a,true});return e};b.filter=b.select=function(a,c,b){var e=[];if(a==null)return e;if(A&&a.filter===A)return a.filter(c,b);j(a,function(a,g,h){c.call(b,a,g,h)&&(e[e.length]=a)});return e};b.reject=function(a,c,b){var e=[];if(a==null)return e;j(a,function(a,g,h){c.call(b,a,g,h)||(e[e.length]=a)});return e};b.every=b.all=function(a,c,b){var e=true;if(a==null)return e;if(B&&a.every===B)return a.every(c,b);j(a,function(a,g,h){if(!(e= -e&&c.call(b,a,g,h)))return n});return e};var E=b.some=b.any=function(a,c,d){c||(c=b.identity);var e=false;if(a==null)return e;if(C&&a.some===C)return a.some(c,d);j(a,function(a,b,h){if(e||(e=c.call(d,a,b,h)))return n});return!!e};b.include=b.contains=function(a,c){var b=false;if(a==null)return b;return p&&a.indexOf===p?a.indexOf(c)!=-1:b=E(a,function(a){return a===c})};b.invoke=function(a,c){var d=i.call(arguments,2);return b.map(a,function(a){return(b.isFunction(c)?c||a:a[c]).apply(a,d)})};b.pluck= -function(a,c){return b.map(a,function(a){return a[c]})};b.max=function(a,c,d){if(!c&&b.isArray(a))return Math.max.apply(Math,a);if(!c&&b.isEmpty(a))return-Infinity;var e={computed:-Infinity};j(a,function(a,b,h){b=c?c.call(d,a,b,h):a;b>=e.computed&&(e={value:a,computed:b})});return e.value};b.min=function(a,c,d){if(!c&&b.isArray(a))return Math.min.apply(Math,a);if(!c&&b.isEmpty(a))return Infinity;var e={computed:Infinity};j(a,function(a,b,h){b=c?c.call(d,a,b,h):a;bd?1:0}),"value")};b.groupBy=function(a,c){var d={},e=b.isFunction(c)?c:function(a){return a[c]};j(a,function(a,b){var c=e(a,b);(d[c]||(d[c]=[])).push(a)});return d};b.sortedIndex=function(a, -c,d){d||(d=b.identity);for(var e=0,f=a.length;e>1;d(a[g])=0})})};b.difference=function(a){var c=b.flatten(i.call(arguments,1));return b.filter(a,function(a){return!b.include(c,a)})};b.zip=function(){for(var a=i.call(arguments),c=b.max(b.pluck(a,"length")),d=Array(c),e=0;e=0;d--)b=[a[d].apply(this,b)];return b[0]}}; -b.after=function(a,b){return a<=0?b():function(){if(--a<1)return b.apply(this,arguments)}};b.keys=J||function(a){if(a!==Object(a))throw new TypeError("Invalid object");var c=[],d;for(d in a)b.has(a,d)&&(c[c.length]=d);return c};b.values=function(a){return b.map(a,b.identity)};b.functions=b.methods=function(a){var c=[],d;for(d in a)b.isFunction(a[d])&&c.push(d);return c.sort()};b.extend=function(a){j(i.call(arguments,1),function(b){for(var d in b)a[d]=b[d]});return a};b.defaults=function(a){j(i.call(arguments, -1),function(b){for(var d in b)a[d]==null&&(a[d]=b[d])});return a};b.clone=function(a){return!b.isObject(a)?a:b.isArray(a)?a.slice():b.extend({},a)};b.tap=function(a,b){b(a);return a};b.isEqual=function(a,b){return q(a,b,[])};b.isEmpty=function(a){if(b.isArray(a)||b.isString(a))return a.length===0;for(var c in a)if(b.has(a,c))return false;return true};b.isElement=function(a){return!!(a&&a.nodeType==1)};b.isArray=o||function(a){return l.call(a)=="[object Array]"};b.isObject=function(a){return a===Object(a)}; -b.isArguments=function(a){return l.call(a)=="[object Arguments]"};if(!b.isArguments(arguments))b.isArguments=function(a){return!(!a||!b.has(a,"callee"))};b.isFunction=function(a){return l.call(a)=="[object Function]"};b.isString=function(a){return l.call(a)=="[object String]"};b.isNumber=function(a){return l.call(a)=="[object Number]"};b.isNaN=function(a){return a!==a};b.isBoolean=function(a){return a===true||a===false||l.call(a)=="[object Boolean]"};b.isDate=function(a){return l.call(a)=="[object Date]"}; -b.isRegExp=function(a){return l.call(a)=="[object RegExp]"};b.isNull=function(a){return a===null};b.isUndefined=function(a){return a===void 0};b.has=function(a,b){return I.call(a,b)};b.noConflict=function(){r._=G;return this};b.identity=function(a){return a};b.times=function(a,b,d){for(var e=0;e/g,">").replace(/"/g,""").replace(/'/g,"'").replace(/\//g,"/")};b.mixin=function(a){j(b.functions(a), -function(c){K(c,b[c]=a[c])})};var L=0;b.uniqueId=function(a){var b=L++;return a?a+b:b};b.templateSettings={evaluate:/<%([\s\S]+?)%>/g,interpolate:/<%=([\s\S]+?)%>/g,escape:/<%-([\s\S]+?)%>/g};var t=/.^/,u=function(a){return a.replace(/\\\\/g,"\\").replace(/\\'/g,"'")};b.template=function(a,c){var d=b.templateSettings,d="var __p=[],print=function(){__p.push.apply(__p,arguments);};with(obj||{}){__p.push('"+a.replace(/\\/g,"\\\\").replace(/'/g,"\\'").replace(d.escape||t,function(a,b){return"',_.escape("+ -u(b)+"),'"}).replace(d.interpolate||t,function(a,b){return"',"+u(b)+",'"}).replace(d.evaluate||t,function(a,b){return"');"+u(b).replace(/[\r\n\t]/g," ")+";__p.push('"}).replace(/\r/g,"\\r").replace(/\n/g,"\\n").replace(/\t/g,"\\t")+"');}return __p.join('');",e=new Function("obj","_",d);return c?e(c,b):function(a){return e.call(this,a,b)}};b.chain=function(a){return b(a).chain()};var m=function(a){this._wrapped=a};b.prototype=m.prototype;var v=function(a,c){return c?b(a).chain():a},K=function(a,c){m.prototype[a]= -function(){var a=i.call(arguments);H.call(a,this._wrapped);return v(c.apply(b,a),this._chain)}};b.mixin(b);j("pop,push,reverse,shift,sort,splice,unshift".split(","),function(a){var b=k[a];m.prototype[a]=function(){var d=this._wrapped;b.apply(d,arguments);var e=d.length;(a=="shift"||a=="splice")&&e===0&&delete d[0];return v(d,this._chain)}});j(["concat","join","slice"],function(a){var b=k[a];m.prototype[a]=function(){return v(b.apply(this._wrapped,arguments),this._chain)}});m.prototype.chain=function(){this._chain= -true;return this};m.prototype.value=function(){return this._wrapped}}).call(this); +!function(n,r){"object"==typeof exports&&"undefined"!=typeof module?module.exports=r():"function"==typeof define&&define.amd?define("underscore",r):(n="undefined"!=typeof globalThis?globalThis:n||self,function(){var t=n._,e=n._=r();e.noConflict=function(){return n._=t,e}}())}(this,(function(){ +// Underscore.js 1.13.1 +// https://underscorejs.org +// (c) 2009-2021 Jeremy Ashkenas, Julian Gonggrijp, and DocumentCloud and Investigative Reporters & Editors +// Underscore may be freely distributed under the MIT license. +var n="1.13.1",r="object"==typeof self&&self.self===self&&self||"object"==typeof global&&global.global===global&&global||Function("return this")()||{},t=Array.prototype,e=Object.prototype,u="undefined"!=typeof Symbol?Symbol.prototype:null,o=t.push,i=t.slice,a=e.toString,f=e.hasOwnProperty,c="undefined"!=typeof ArrayBuffer,l="undefined"!=typeof DataView,s=Array.isArray,p=Object.keys,v=Object.create,h=c&&ArrayBuffer.isView,y=isNaN,d=isFinite,g=!{toString:null}.propertyIsEnumerable("toString"),b=["valueOf","isPrototypeOf","toString","propertyIsEnumerable","hasOwnProperty","toLocaleString"],m=Math.pow(2,53)-1;function j(n,r){return r=null==r?n.length-1:+r,function(){for(var t=Math.max(arguments.length-r,0),e=Array(t),u=0;u=0&&t<=m}}function J(n){return function(r){return null==r?void 0:r[n]}}var G=J("byteLength"),H=K(G),Q=/\[object ((I|Ui)nt(8|16|32)|Float(32|64)|Uint8Clamped|Big(I|Ui)nt64)Array\]/;var X=c?function(n){return h?h(n)&&!q(n):H(n)&&Q.test(a.call(n))}:C(!1),Y=J("length");function Z(n,r){r=function(n){for(var r={},t=n.length,e=0;e":">",'"':""","'":"'","`":"`"},Cn=Ln($n),Kn=Ln(_n($n)),Jn=tn.templateSettings={evaluate:/<%([\s\S]+?)%>/g,interpolate:/<%=([\s\S]+?)%>/g,escape:/<%-([\s\S]+?)%>/g},Gn=/(.)^/,Hn={"'":"'","\\":"\\","\r":"r","\n":"n","\u2028":"u2028","\u2029":"u2029"},Qn=/\\|'|\r|\n|\u2028|\u2029/g;function Xn(n){return"\\"+Hn[n]}var Yn=/^\s*(\w|\$)+\s*$/;var Zn=0;function nr(n,r,t,e,u){if(!(e instanceof r))return n.apply(t,u);var o=Mn(n.prototype),i=n.apply(o,u);return _(i)?i:o}var rr=j((function(n,r){var t=rr.placeholder,e=function(){for(var u=0,o=r.length,i=Array(o),a=0;a1)ur(a,r-1,t,e),u=e.length;else for(var f=0,c=a.length;f0&&(t=r.apply(this,arguments)),n<=1&&(r=null),t}}var lr=rr(cr,2);function sr(n,r,t){r=qn(r,t);for(var e,u=nn(n),o=0,i=u.length;o0?0:u-1;o>=0&&o0?a=o>=0?o:Math.max(o+f,a):f=o>=0?Math.min(o+1,f):o+f+1;else if(t&&o&&f)return e[o=t(e,u)]===u?o:-1;if(u!=u)return(o=r(i.call(e,a,f),$))>=0?o+a:-1;for(o=n>0?a:f-1;o>=0&&o0?0:i-1;for(u||(e=r[o?o[a]:a],a+=n);a>=0&&a=3;return r(n,Fn(t,u,4),e,o)}}var Ar=wr(1),xr=wr(-1);function Sr(n,r,t){var e=[];return r=qn(r,t),jr(n,(function(n,t,u){r(n,t,u)&&e.push(n)})),e}function Or(n,r,t){r=qn(r,t);for(var e=!er(n)&&nn(n),u=(e||n).length,o=0;o=0}var Br=j((function(n,r,t){var e,u;return D(r)?u=r:(r=Nn(r),e=r.slice(0,-1),r=r[r.length-1]),_r(n,(function(n){var o=u;if(!o){if(e&&e.length&&(n=In(n,e)),null==n)return;o=n[r]}return null==o?o:o.apply(n,t)}))}));function Nr(n,r){return _r(n,Rn(r))}function Ir(n,r,t){var e,u,o=-1/0,i=-1/0;if(null==r||"number"==typeof r&&"object"!=typeof n[0]&&null!=n)for(var a=0,f=(n=er(n)?n:jn(n)).length;ao&&(o=e);else r=qn(r,t),jr(n,(function(n,t,e){((u=r(n,t,e))>i||u===-1/0&&o===-1/0)&&(o=n,i=u)}));return o}function Tr(n,r,t){if(null==r||t)return er(n)||(n=jn(n)),n[Wn(n.length-1)];var e=er(n)?En(n):jn(n),u=Y(e);r=Math.max(Math.min(r,u),0);for(var o=u-1,i=0;i1&&(e=Fn(e,r[1])),r=an(n)):(e=qr,r=ur(r,!1,!1),n=Object(n));for(var u=0,o=r.length;u1&&(t=r[1])):(r=_r(ur(r,!1,!1),String),e=function(n,t){return!Er(r,t)}),Ur(n,e,t)}));function zr(n,r,t){return i.call(n,0,Math.max(0,n.length-(null==r||t?1:r)))}function Lr(n,r,t){return null==n||n.length<1?null==r||t?void 0:[]:null==r||t?n[0]:zr(n,n.length-r)}function $r(n,r,t){return i.call(n,null==r||t?1:r)}var Cr=j((function(n,r){return r=ur(r,!0,!0),Sr(n,(function(n){return!Er(r,n)}))})),Kr=j((function(n,r){return Cr(n,r)}));function Jr(n,r,t,e){A(r)||(e=t,t=r,r=!1),null!=t&&(t=qn(t,e));for(var u=[],o=[],i=0,a=Y(n);ir?(e&&(clearTimeout(e),e=null),a=c,i=n.apply(u,o),e||(u=o=null)):e||!1===t.trailing||(e=setTimeout(f,l)),i};return c.cancel=function(){clearTimeout(e),a=0,e=u=o=null},c},debounce:function(n,r,t){var e,u,o,i,a,f=function(){var c=zn()-u;r>c?e=setTimeout(f,r-c):(e=null,t||(i=n.apply(a,o)),e||(o=a=null))},c=j((function(c){return a=this,o=c,u=zn(),e||(e=setTimeout(f,r),t&&(i=n.apply(a,o))),i}));return c.cancel=function(){clearTimeout(e),e=o=a=null},c},wrap:function(n,r){return rr(r,n)},negate:fr,compose:function(){var n=arguments,r=n.length-1;return function(){for(var t=r,e=n[r].apply(this,arguments);t--;)e=n[t].call(this,e);return e}},after:function(n,r){return function(){if(--n<1)return r.apply(this,arguments)}},before:cr,once:lr,findKey:sr,findIndex:vr,findLastIndex:hr,sortedIndex:yr,indexOf:gr,lastIndexOf:br,find:mr,detect:mr,findWhere:function(n,r){return mr(n,Dn(r))},each:jr,forEach:jr,map:_r,collect:_r,reduce:Ar,foldl:Ar,inject:Ar,reduceRight:xr,foldr:xr,filter:Sr,select:Sr,reject:function(n,r,t){return Sr(n,fr(qn(r)),t)},every:Or,all:Or,some:Mr,any:Mr,contains:Er,includes:Er,include:Er,invoke:Br,pluck:Nr,where:function(n,r){return Sr(n,Dn(r))},max:Ir,min:function(n,r,t){var e,u,o=1/0,i=1/0;if(null==r||"number"==typeof r&&"object"!=typeof n[0]&&null!=n)for(var a=0,f=(n=er(n)?n:jn(n)).length;ae||void 0===t)return 1;if(t + + + - - - - - reactors — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + reactors — reactors_sdk 1.0.0 documentation + + + + + + + + + + - - + + + +
    + -
    -
    -
    -
    - -
    -

    reactors

    +
    + + - - - - +
    +
    + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.agaveutils.html b/docs/api-ref/reactors.agaveutils.html index c5687a7..48742ee 100644 --- a/docs/api-ref/reactors.agaveutils.html +++ b/docs/api-ref/reactors.agaveutils.html @@ -1,64 +1,103 @@ - - - - - - - reactors.agaveutils package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + + reactors.agaveutils package — reactors_sdk 1.0.0 documentation + + + + + + + + + + - + - - - -
    -
    -
    -
    - -
    -

    reactors.agaveutils package

    -
    -

    Submodules

    + + + +
    + + +
    + +
    +
    +
    + +
    -
    -

    reactors.agaveutils.entity module

    +
    +
    + +
    +

    reactors.agaveutils package

    +
    +

    Submodules

    +
    +
    +

    reactors.agaveutils.entity module

    Functions for working with Agave namespace entities

    -
    -reactors.agaveutils.entity.is_appid(textString, useApi=False, agaveClient=None)
    +
    +reactors.agaveutils.entity.is_appid(textString, useApi=False, agaveClient=None)

    Validate whether textString is an Agave appId

    Positional parameters: textString: str - the candidate text string

    @@ -67,20 +106,20 @@

    Submodules -

    reactors.agaveutils.files module

    +

    +
    +

    reactors.agaveutils.files module

    Helper functions for common filesystem operations with Agave

    -
    -reactors.agaveutils.files.agave_download_file(agaveClient, agaveAbsolutePath, systemId, localFilename='downloaded', sync=True, timeOut=300)
    +
    +reactors.agaveutils.files.agave_download_file(agaveClient, agaveAbsolutePath, systemId, localFilename='downloaded', sync=True, timeOut=300)

    Download an Agave-hosted file to cwd()

    Currently, always a synchronous task.

    -
    -reactors.agaveutils.files.agave_mkdir(agaveClient, dirName, systemId, basePath='/', sync=False, timeOut=300)
    +
    +reactors.agaveutils.files.agave_mkdir(agaveClient, dirName, systemId, basePath='/', sync=False, timeOut=300)

    Creates a directory dirName on a storage system at basePath

    Like mkdir -p this is imdepotent. It will create the child path tree so long as paths are specified correctly, but will do @@ -88,8 +127,8 @@

    Submodules -
    -reactors.agaveutils.files.agave_upload_file(agaveClient, agaveDestPath, systemId, uploadFile, sync=True, timeOut=300)
    +
    +reactors.agaveutils.files.agave_upload_file(agaveClient, agaveDestPath, systemId, uploadFile, sync=True, timeOut=300)

    Upload a file to Agave-managed remote storage.

    If sync is True, the function will wait for the upload to complete before returning. Raises exceptions on importData @@ -97,8 +136,8 @@

    Submodules -
    -reactors.agaveutils.files.get(agaveClient, agaveAbsolutePath, systemId, localFilename, retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.get(agaveClient, agaveAbsolutePath, systemId, localFilename, retries=5, delay=1, multiplier=2)

    files-get with retry and exponential backoff

    Parameters
    @@ -119,8 +158,8 @@

    Submodules -
    -reactors.agaveutils.files.mkdir(agaveClient, dirName, systemId, basePath='/', retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.mkdir(agaveClient, dirName, systemId, basePath='/', retries=5, delay=1, multiplier=2)

    files-mkdir with retry and exponential backoff

    Parameters
    @@ -141,231 +180,187 @@

    Submodules -
    -reactors.agaveutils.files.process_agave_httperror(http_error_object)
    +
    +reactors.agaveutils.files.process_agave_httperror(http_error_object)

    -
    -reactors.agaveutils.files.put(agaveClient, agaveDestPath, systemId, uploadFile, retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.put(agaveClient, agaveDestPath, systemId, uploadFile, retries=5, delay=1, multiplier=2)
    -
    -reactors.agaveutils.files.random() → x in the interval [0, 1).
    +
    +reactors.agaveutils.files.random() x in the interval [0, 1).
    -
    -reactors.agaveutils.files.wait_for_file_status(agaveClient, agaveWatchPath, systemId, maxTime=300)
    +
    +reactors.agaveutils.files.wait_for_file_status(agaveClient, agaveWatchPath, systemId, maxTime=300)

    Synchronously wait for a file’s status to reach a terminal state.

    Returns an exception and the final state if it timeout is exceeded. Uses exponential backoff to avoid overloading the files server with poll requests. Returns True on success.

    -

    -
    -

    reactors.agaveutils.reactors module

    +
    +
    +

    reactors.agaveutils.reactors module

    Functions for working with TACC Reactors

    -
    -reactors.agaveutils.reactors.message_reactor(agaveClient, actorId, message, environment={}, ignoreErrors=True, sync=False, senderTags=True, timeOut=300)
    +
    +reactors.agaveutils.reactors.message_reactor(agaveClient, actorId, message, environment={}, ignoreErrors=True, sync=False, senderTags=True, timeOut=300)

    Send a message to an Abaco actor by its ID

    Returns execution ID. If ignoreErrors is True, this is fire-and-forget. Otherwise, failures raise an Exception to handled by the caller.

    -
    -
    -

    reactors.agaveutils.recursive module

    + +
    +

    reactors.agaveutils.recursive module

    Recursively apply permission grants using AgavePy

    -
    -class reactors.agaveutils.recursive.PemAgent(agaveClient, loglevel='INFO')
    +
    +class reactors.agaveutils.recursive.PemAgent(agaveClient, loglevel='INFO')

    Bases: object

    Specialized Agave class for doing recursive pem management

    -
    -enumerate2(sequence)
    +
    +enumerate2(sequence)
    -
    -grant(system, abspath, username='world', pem='READ', recursive=False, permissive=True)
    +
    +grant(system, abspath, username='world', pem='READ', recursive=False, permissive=True)

    Recursively crawl abspath and grant pem

    -
    -listdir(system, fpath)
    +
    +listdir(system, fpath)
    -
    -updatepem(system, fpath, username, pem, rec=False, permissive=True)
    +
    +updatepem(system, fpath, username, pem, rec=False, permissive=True)

    Send an pems update request

    -
    -walk(root, dirs, files, system, username, pem='READ', rec=False)
    +
    +walk(root, dirs, files, system, username, pem='READ', rec=False)
    -
    -reactors.agaveutils.recursive.random() → x in the interval [0, 1).
    +
    +reactors.agaveutils.recursive.random() x in the interval [0, 1).
    -
    -
    -

    reactors.agaveutils.uri module

    + +
    +

    reactors.agaveutils.uri module

    Functions for working with Agave, HTTP, and TACC S3 URIs

    -
    -reactors.agaveutils.uri.agave_uri_from_http(httpURI=None)
    +
    +reactors.agaveutils.uri.agave_uri_from_http(httpURI=None)

    Convert an HTTP(s) URI to its agave:// format * Do not use yet

    -
    -reactors.agaveutils.uri.from_agave_uri(uri=None, Validate=False)
    +
    +reactors.agaveutils.uri.from_agave_uri(uri=None, Validate=False)

    Parse an Agave URI into a tuple (systemId, directoryPath, fileName)

    Validation that it points to a real resource is not implemented. The same caveats about validation apply here as in to_agave_uri()

    -
    -reactors.agaveutils.uri.from_tacc_s3_uri(uri=None, Validate=False)
    +
    +reactors.agaveutils.uri.from_tacc_s3_uri(uri=None, Validate=False)

    Parse a TACC S3 URI into a tuple (systemId, directoryPath, (fileName))

    Validation that it points to a real resource is not implemented. The same caveats about validation apply here as in to_agave_uri()

    -
    -reactors.agaveutils.uri.http_uri_from_agave(agaveURI=None, linkType='media', userName='public')
    +
    +reactors.agaveutils.uri.http_uri_from_agave(agaveURI=None, linkType='media', userName='public')

    Returns an http(s) media URL for data movement or download * Do not use yet.

    -
    -reactors.agaveutils.uri.to_agave_uri(systemId=None, dirPath=None, fileName=None, validate=False)
    +
    +reactors.agaveutils.uri.to_agave_uri(systemId=None, dirPath=None, fileName=None, validate=False)

    Construct an Agave URI for system ID, path, (filename)

    Validation that URI points to a real resource is not implemented. Should we choose to do this, it will be expensive since it will involve at least one API call.

    -
    -
    -

    reactors.agaveutils.utils module

    + +
    +

    reactors.agaveutils.utils module

    Helper functions for working with Agave and Reactors APIs

    `python from agaveutils import * `

    -
    -reactors.agaveutils.utils.get_api_server(ag)
    +
    +reactors.agaveutils.utils.get_api_server(ag)

    Get current API server URI

    -
    -reactors.agaveutils.utils.get_api_token(ag)
    +
    +reactors.agaveutils.utils.get_api_token(ag)

    Get API access_token

    -
    -reactors.agaveutils.utils.get_api_username(ag)
    +
    +reactors.agaveutils.utils.get_api_username(ag)

    Get current API username

    -
    -
    -

    Module contents

    -
    -
    + +
    +

    Module contents

    +
    + -
    +
    -
    -
    - - - - + +
    + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.aliases.agavedb.html b/docs/api-ref/reactors.aliases.agavedb.html deleted file mode 100644 index 6144337..0000000 --- a/docs/api-ref/reactors.aliases.agavedb.html +++ /dev/null @@ -1,470 +0,0 @@ - - - - - - - - reactors.aliases.agavedb package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases.agavedb package

    - -
    -

    Submodules

    -
    -
    -

    reactors.aliases.agavedb.keyval module

    -

    AgaveDB is multiuser-aware key/value store built using the Agave metadata web service API.

    -

    The library interface is modeled on pickledb, which is inspired by Redis. Eventually, it will support Agave-based permissions and sharing. If you need a more -document-oriented solution, you can utilize the underlying Agave metadata service.

    -

    Usage: -`python -from agavedb import AgaveKeyValStore -`

    -
    -
    -class reactors.aliases.agavedb.keyval.AgaveKeyValStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: object

    -

    An AgaveKeyValStore instance. Requires an active Agave client

    -
    -
    -classmethod create_key_name()
    -

    Create a unique, human-friendly key name

    -
    - -
    -
    -deldb()
    -

    Delete all user-owned keys

    -
    - -
    -
    -classmethod from_text_pem(pem)
    -
    - -
    -
    -get(key)
    -

    Get the value of a key

    -
    - -
    -
    -getacls(key, user=None)
    -

    Get the ACLs for a given key

    -

    Keywork parameters: -user - str - Return ACL only for this username

    -
    - -
    -
    -getall(sort_aliases=True)
    -

    Return a list of all keys user owns or has access to

    -
    - -
    -
    -rem(key)
    -

    Delete a key (assuming it is owned by the user)

    -
    - -
    -
    -remacl(key, user)
    -

    Remove an ACL on a key for a given user

    -

    Positional parameters: -key - str - Key to manage permissions on -user - str - Username whose ACL should be dropped

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -set(key, value)
    -

    Set the string or numeric value of a key

    -
    - -
    -
    -setacl(key, acl)
    -

    Set an ACL on a given key

    -

    Positional parameters: -key - str - Key to manage permissions on -acl - dict - Valid permissions object

    -

    {‘read’: bool, ‘write’: bool}

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -classmethod to_text_pem(acl)
    -
    - -
    -
    -classmethod validate_acl(acl, permissive=False)
    -

    Validate an ACL object as a dict

    -

    Failure raises Exception unless permissive is True -* Does not validate that username exists

    -
    - -
    - -
    -
    -

    reactors.aliases.agavedb.uniqueid module

    -

    Generate Abaco-style human-readable UUIDs

    -

    Uses the hashids library and strong random -number generator. These UUIDs are nearly as -unique as UUID4 but are much more readable.

    -
    -
    -reactors.aliases.agavedb.uniqueid.get_id()
    -

    Generate a hash id

    -
    - -
    -
    -reactors.aliases.agavedb.uniqueid.is_hashid(identifier)
    -

    Tries to validate a UUID

    -
    - -
    -
    -

    Module contents

    -
    -
    -class reactors.aliases.agavedb.Agave(**kwargs)
    -

    Bases: agavepy.interactive.clients.ClientCommands, agavepy.interactive.tokens.TokenCommands, agavepy.interactive.deprecated.DeprecatedCommands

    -
    -
    -PARAMS = [('username', False, 'username', None), ('password', False, 'password', None), ('token_username', False, 'token_username', None), ('jwt', False, 'jwt', None), ('jwt_header_name', False, 'header_name', None), ('api_server', False, 'api_server', 'https://api.tacc.utexas.edu'), ('tenant_id', False, 'tenant_id', None), ('expires_in', False, 'expires_in', None), ('expires_at', False, 'expires_at', None), ('created_at', False, 'created_at', None), ('client_name', False, 'client_name', None), ('api_key', False, 'api_key', None), ('api_secret', False, 'api_secret', None), ('token', False, '_token', None), ('refresh_token', False, '_refresh_token', None), ('use_nonce', False, 'use_nonce', False), ('resources', False, 'resources', None), ('verify', False, 'verify', True), ('token_callback', False, 'token_callback', None), ('proxies', False, 'proxies', {})]
    -
    - -
    -
    -classmethod agpy_path()
    -

    Return path to an .agpy file

    -
    - -
    -
    -can_refresh = True
    -
    - -
    -
    -clients_ari()
    -
    - -
    -
    -download_uri(uri, local_path)
    -

    Convenience method to download an agave URL or jobs output URL to an -absolute path on the local file system.

    -
    - -
    -
    -full_ari()
    -
    - -
    -
    -geturl(url)
    -

    Make get request to url using the client access token and retry if token has expired. -:param url: str -:return:

    -
    - -
    -
    -jwt_ari()
    -
    - -
    -
    -nonce_ari()
    -
    - -
    -
    -refresh_aris()
    -
    - -
    -
    -resource(auth_type, *args)
    -
    - -
    -
    -classmethod restore(api_key=None, client_name=None, tenant_id=None, token=None, api_server=None, cache_client=True)
    -

    Public API to load an Agave client from an external source

    -
    - -
    -
    -set_client(key, secret)
    -
    -
    Return type
    -

    None

    -
    -
    -
    - -
    -
    -classmethod tapis_cache_path()
    -

    Return the path to the credentials cache directory

    -
    - -
    -
    -classmethod tapis_current_path()
    -

    Return path to the current cached credential

    -
    - -
    -
    -classmethod tapis_sessions_path()
    -

    Return path to the current sessions cache

    -
    - -
    -
    -to_dict()
    -

    Return a dictionary representing this client.

    -
    - -
    - -
    -
    -class reactors.aliases.agavedb.AgaveKeyValStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: object

    -

    An AgaveKeyValStore instance. Requires an active Agave client

    -
    -
    -classmethod create_key_name()
    -

    Create a unique, human-friendly key name

    -
    - -
    -
    -deldb()
    -

    Delete all user-owned keys

    -
    - -
    -
    -classmethod from_text_pem(pem)
    -
    - -
    -
    -get(key)
    -

    Get the value of a key

    -
    - -
    -
    -getacls(key, user=None)
    -

    Get the ACLs for a given key

    -

    Keywork parameters: -user - str - Return ACL only for this username

    -
    - -
    -
    -getall(sort_aliases=True)
    -

    Return a list of all keys user owns or has access to

    -
    - -
    -
    -rem(key)
    -

    Delete a key (assuming it is owned by the user)

    -
    - -
    -
    -remacl(key, user)
    -

    Remove an ACL on a key for a given user

    -

    Positional parameters: -key - str - Key to manage permissions on -user - str - Username whose ACL should be dropped

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -set(key, value)
    -

    Set the string or numeric value of a key

    -
    - -
    -
    -setacl(key, acl)
    -

    Set an ACL on a given key

    -

    Positional parameters: -key - str - Key to manage permissions on -acl - dict - Valid permissions object

    -

    {‘read’: bool, ‘write’: bool}

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -classmethod to_text_pem(acl)
    -
    - -
    -
    -classmethod validate_acl(acl, permissive=False)
    -

    Validate an ACL object as a dict

    -

    Failure raises Exception unless permissive is True -* Does not validate that username exists

    -
    - -
    - -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docs/api-ref/reactors.aliases.agavedb.tests.html b/docs/api-ref/reactors.aliases.agavedb.tests.html deleted file mode 100644 index a806a82..0000000 --- a/docs/api-ref/reactors.aliases.agavedb.tests.html +++ /dev/null @@ -1,289 +0,0 @@ - - - - - - - - reactors.aliases.agavedb.tests package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases.agavedb.tests package

    -
    -

    Submodules

    -
    -
    -

    reactors.aliases.agavedb.tests.agavefixtures module

    -
    -
    -reactors.aliases.agavedb.tests.agavefixtures.agave(credentials)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.agavefixtures.credentials()
    -

    Load credentials for testing session

    -

    Order: user credential store, test file, env

    -
    - -
    -
    -

    reactors.aliases.agavedb.tests.test_keyval module

    -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_key()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_key_acl()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_user()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_value()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.keyvalstore(agave, prefix)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.prefix()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_acl_from_world(keyvalstore, fake_key_acl, fake_value, fake_user, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_add_acl(keyvalstore, fake_key_acl, fake_value, fake_user, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_data(credentials)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_get_nonexistent(keyvalstore, credentials)
    -

    test get on a key that doesn’t exist

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_getall(keyvalstore, credentials)
    -

    getall - validate that an array is returned

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_key_valid(keyvalstore, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_list_acl(keyvalstore, fake_key_acl, fake_value, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_fwd(keyvalstore, prefix, credentials)
    -

    _namespace

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_rev_namespace(keyvalstore, credentials, prefix)
    -

    _namespace_rev

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_rev_wo_namespace(keyvalstore, credentials, prefix)
    -

    _namespace_rev

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_remall(keyvalstore)
    -

    verify that we can delete our session-specific entries

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_set_get_rem(keyvalstore, credentials)
    -

    test key set/get/delete cycle

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_username(keyvalstore, credentials)
    -

    verify that agavedb and test view of username is same

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_validate_acl(keyvalstore, test_data)
    -

    run through various ACL forms

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_value_valid_type(keyvalstore, credentials)
    -

    valid values for keys

    -
    - -
    -
    -

    reactors.aliases.agavedb.tests.testdata module

    -
    -
    -class reactors.aliases.agavedb.tests.testdata.TestData(credentials)
    -

    Bases: object

    -
    -
    -data(key=None)
    -
    - -
    -
    -file_to_json(filename)
    -
    - -
    - -
    -
    -

    Module contents

    -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docs/api-ref/reactors.aliases.html b/docs/api-ref/reactors.aliases.html deleted file mode 100644 index 9073661..0000000 --- a/docs/api-ref/reactors.aliases.html +++ /dev/null @@ -1,223 +0,0 @@ - - - - - - - - reactors.aliases package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases package

    - -
    -

    Submodules

    -
    -
    -

    reactors.aliases.store module

    -

    Manage and retrieve alias-to-actor_id mappings

    -

    Built on AgaveDB which in turn builds on Agave Metatadata

    -
    -
    -class reactors.aliases.store.AliasStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: agavedb.keyval.AgaveKeyValStore

    -
    -
    -get_alias_acls(alias, username=None)
    -

    List ACLs for an alias, optionally filtering by username

    -
    - -
    -
    -get_aliases(sort_aliases=True)
    -

    Fetch all aliases as a alphabetically-sorted list

    -
    - -
    -
    -get_name(alias)
    -

    Get a speciifc alias => entity mapping

    -

    Implements a ‘me’ alias to return self

    -
    - -
    -
    -put_alias_acl(alias, acl)
    -

    Add ACLs to an alias

    -
    - -
    -
    -rem_alias(alias)
    -

    Delete an alias from the database

    -
    - -
    -
    -rem_alias_acl(alias, username=None)
    -

    Entirely remove a user’s ACL for a given key

    -
    - -
    -
    -rem_all_aliases()
    -

    Removes all aliases owned by current user

    -
    - -
    -
    -set_alias(alias, name)
    -

    Create or update actor => alias mapping

    -
    - -
    - -
    -
    -reactors.aliases.store.to_unicode(input)
    -

    Trivial unicode encoder

    -
    - -
    -
    -

    Module contents

    -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docs/api-ref/reactors.cli.html b/docs/api-ref/reactors.cli.html new file mode 100644 index 0000000..3f4a06f --- /dev/null +++ b/docs/api-ref/reactors.cli.html @@ -0,0 +1,158 @@ + + + + + + + reactors.cli package — reactors_sdk 1.0.0 documentation + + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.cli package

    +
    +

    Submodules

    +
    +
    +

    reactors.cli.run module

    +
    +
    +reactors.cli.run.docstring(fn)
    +
    + +
    +
    +reactors.cli.run.load_function(module='/reactor.py', function='main')
    +
    + +
    +
    +reactors.cli.run.run(module='/reactor.py', function='main', args=None)
    +

    Load and run a function from a script or module

    +
    + +
    +
    +

    reactors.cli.usage module

    +
    +
    +reactors.cli.usage.usage(args=None)
    +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    + +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.html b/docs/api-ref/reactors.html index a80bf5b..e5bf101 100644 --- a/docs/api-ref/reactors.html +++ b/docs/api-ref/reactors.html @@ -1,56 +1,95 @@ - - - - - - - reactors package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + + reactors package — reactors_sdk 1.0.0 documentation + + + + + + + + + + - - + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors package

    +
    +

    Subpackages

    -
    -
    -

    Submodules

    -
    -
    -

    reactors.jsonmessages module

    -
    -
    -reactors.jsonmessages.validate_message(messagedict, messageschema='/Users/TASethanho/tacc/projects/sd2e/python-reactors/src/reactors/message.jsonschema', permissive=True)
    -

    Validate dictonary derived from JSON string against a schema

    -

    Positional arguments: -messagedict - dict - JSON-derived object

    -

    Keyword arguments: -messageschema - str - path to the requisite JSON schema file -permissive - bool - swallow validation errors [True]

    -
    - -
    -
    -

    reactors.process module

    -

    Run subprocesses from within Python

    -
    -
    -reactors.process.run(command_list=[], permissive=False, shell=False, timeout=None)
    -

    Run a child or subshell process.

    -

    Parameters: -exec_params - list - Parameters in exec form -permissive - bool - Ignore errors -shell - bool - Execute command by way of a shell

    -
    -
    Usage:

    # List system logs directory -params=[‘ls’, ‘-alth’, ‘/var/log’] -process.run(params)

    -
    -
    -

    Returns an AttrDict of response attributes.

    -
    - -
    -
    -

    reactors.runtime module

    +
    +
    +

    Submodules

    +
    +
    +

    reactors.config module

    +

    Manages configuration from environment and files

    -
    -reactors.runtime.random() → x in the interval [0, 1).
    +
    +reactors.config.get_redaction_strings(redactions=None, agave_client=None, namespace=None)
    -
    -
    -

    reactors.storage module

    -

    Utility library for supporting container-local, -global POSIX, and eventually, object and document -storage for TACC Reactors

    -
    -
    -

    reactors.uniqueid module

    -

    Generate an Abaco-style UUID

    -
    -
    -reactors.uniqueid.get_id()
    -

    Generate a hash id

    -
    -
    -
    -reactors.uniqueid.is_hashid(identifier)
    -

    Tries to validate a UUID

    -
    - -
    -
    -

    reactors.utils module

    -
    -
    -class reactors.utils.Reactor(redactions=[])
    -

    Bases: object

    -

    Helper class providing a client-side API for the Actors service

    -
    -
    -add_nonce(permission='READ', maxuses=1, actorId=None)
    -

    Add a new nonce.

    -

    Positional arguments: -None

    -

    Keyword arguments: -username: str - a valid TACC.cloud username or role account -permission: str - a valid Abaco permission level -maxuses: int (-1,inf) - maximum number of uses for a given nonce -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -create_webhook(permission='EXECUTE', maxuses=- 1, actorId=None)
    -

    Create a .actor.messages URI suitable for use in integrations

    -

    Default is to grant EXECUTE with unlimited uses.

    -
    - -
    -
    -delete_all_nonces(actorId=None)
    -

    Delete all nonces from an actor

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -delete_nonce(nonceId, actorId=None)
    -

    Delete an specific nonce by its ID

    -

    Positional arguments: -nonceId: str - a valid TACC.cloud username or role account

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -delete_webhook(webhook, actorId=None)
    -

    ‘Delete’ an actor-specific webhook by deleting its nonce

    -

    A key assumption is that webhook was constructed by create_webhook or -its equivalent, as this method sensitive to case and url structure

    -
    - -
    -
    -elapsed()
    -

    Returns elapsed time in microseconds since Reactor was initialized

    -
    - -
    -
    -get_attr(attribute=None, actorId=None)
    -

    Retrieve dict of attributes for an actor

    -

    Parameters: -attribute - str - Any top-level key in the Actor API model -actorId - str - Which actor (if not self) to fetch. Defaults to

    -
    -

    the actor’s own ID, allowing introspection.

    -
    -
    - -
    -
    -get_nonce(nonceId, actorId=None)
    -

    Get an specific nonce by its ID

    -

    Positional arguments: -nonceId: str - a valid TACC.cloud username or role account

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -list_nonces(actorId=None)
    -

    List all nonces

    -

    Positional arguments: -None

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -on_failure(failMessage='Failure', exceptionObject=None)
    -

    Log message and exit 0

    -
    - -
    -
    -on_success(successMessage='Success')
    -

    Log message and exit 0

    -
    - -
    -
    -resolve_actor_alias(alias)
    -

    Look up the identifier for a alias string

    -
    -
    Arguments

    alias (str): An alias, actorId, appId, or the me/self shortcut

    -
    -
    Returns:

    str: The resolved identifier

    -
    -
    -

    On error: -Returns value of text

    -
    -
    Note:

    Does basic optimization of returning an app ID or abaco actorId -if they are passed, as we can safely assume those are not aliases.

    -
    -
    -
    - -
    -
    -send_message(actorId, message, environment={}, ignoreErrors=True, senderTags=True, retryMaxAttempts=5, retryDelay=1, sync=False)
    -

    Send a message to an Abaco actor by ID, platform alias, or defined alias

    -
    -
    Arguments:

    actorId (str): An actorId or alias -message (str/dict) : Message to send

    -
    -
    Keyword Arguments:

    ignoreErrors: bool - only mark failures by logging not exception -environment: dict - environment variables to pass as url params -senderTags: bool - send provenance and session vars along -retryDelay: int - seconds between retries on send failure -retryMax: int - number of times (up to global MAX_RETRIES) to retry -sync: bool - not implemented - wait for message to execute

    -
    -
    Returns:

    str: The excecutionId of the resulting execution

    -
    -
    Raises:

    AgaveError: Raised if ignoreErrors is True

    -
    -
    -
    - -
    -
    -validate_message(messagedict, messageschema='/message.jsonschema', permissive=True)
    -

    Validate dictonary derived from JSON against a JSON schema

    -

    Positional arguments: -messagedict - dict - JSON-derived object

    -

    Keyword arguments: -messageschema - str - path to the requisite JSON schema file -permissive - bool - swallow validation errors [True]

    -
    - +
    +reactors.config.parse_boolean(s)
    +

    Parse values of Python basic types into equivalent Boolean.

    -
    -reactors.utils.get_client_with_mock_support()
    -

    Get the current Actor API client

    -

    Returns the Abaco actor’s client if running deployed. Attempts to -bootstrap a client from supplied credentials if running in local or -debug mode.

    +
    +reactors.config.read_config(namespace=None, places_list=None, update=True, env=True)
    +

    Override tacconfig’s broken right-favoring merge

    + +
    +

    reactors.utils module

    -
    -reactors.utils.get_context_with_mock_support(agave_client)
    -

    Return the current Actor context

    -

    Return the Abaco actor’s environment context if running deployed. Creates -a test context based on inferred or mocked values if running in local or -debug mode.

    +
    +reactors.utils.get_host_ip()
    +

    Returns current IP address of host

    -
    -reactors.utils.get_token_with_mock_support(client)
    -

    Find current Oauth2 access token from context or mock

    +
    +reactors.utils.microseconds()
    +

    Returns current time in microseconds

    -
    -reactors.utils.microseconds()
    -
    - -
    -
    -reactors.utils.random() → x in the interval [0, 1).
    -
    - -
    -
    -reactors.utils.read_config(namespace='_REACTOR', places_list=['/Users/TASethanho/tacc/projects/sd2e/python-reactors/src/reactors', '/', '/Users/TASethanho/tacc/projects/sd2e/python-reactors/docsrc'], update=True, env=True)
    -

    Override tacconfig’s broken right-favoring merge

    +
    +reactors.utils.utcnow()
    +

    Returns a text-formatted UTC date

    +

    Example: 2018-01-05T18:40:55.290790+00:00

    -
    -
    -reactors.utils.set_os_environ_from_client(agave_client)
    -

    Set environment vars to client values

    -
    +
    +
    +

    reactors.version module

    +
    +
    +

    Module contents

    +
    + -
    -
    -reactors.utils.set_os_environ_from_mock(context)
    -

    Set environment vars to mocked values

    -
    -
    -
    -reactors.utils.utcnow()
    -

    Return a text-formatted UTC date

    -

    example: 2018-01-05T18:40:55.290790+00:00

    -
    +
    +
    +
    -
    -

    reactors.version module

    -
    -
    -

    Module contents

    -
    -
    +
    +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    -
    -
    -
    - - -
    - - - - + + + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.logtypes.html b/docs/api-ref/reactors.logtypes.html index abb062d..dc366c4 100644 --- a/docs/api-ref/reactors.logtypes.html +++ b/docs/api-ref/reactors.logtypes.html @@ -1,262 +1,330 @@ - + + + - - - - - reactors.logtypes package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + reactors.logtypes package — reactors_sdk 1.0.0 documentation + + + + + + + + + + - - - - -
    -
    -
    -
    - -
    -

    reactors.logtypes package

    -
    -

    Submodules

    -
    -
    -

    reactors.logtypes.logstash module

    + + + + + +
    + + +
    + +
    +
    +
    + +
    -
    -

    reactors.logtypes.logstash_futures_session module

    +
    +
    + +
    +

    reactors.logtypes package

    +
    +

    Submodules

    +
    +
    +

    reactors.logtypes.loggly module

    +
    +
    +

    reactors.logtypes.loggly_futures_session module

    -
    -class reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler(config, client_secret)
    +
    +class reactors.logtypes.loggly_futures_session.LogglyHandler(url)
    +

    Bases: logging.Handler

    +

    Send logs to Loggly HTTPS handler

    +
    +
    +emit(record)
    +

    Do whatever it takes to actually log the specified logging record.

    +

    This version is intended to be implemented by subclasses and so +raises a NotImplementedError.

    +
    + +
    +
    +get_full_message(record)
    +
    + +
    + +
    +
    +reactors.logtypes.loggly_futures_session.bg_cb(sess, resp)
    +

    Noop the response so logging is fire-and-forget

    +
    + +
    +
    +reactors.logtypes.loggly_futures_session.response_hook_noop(resp, *args, **kwargs)
    +

    Noop the response so logging is fire-and-forget

    +
    + +
    +
    +

    reactors.logtypes.logstash module

    +
    +
    +

    reactors.logtypes.logstash_futures_session module

    +
    +
    +class reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler(config, client_secret)

    Bases: logging.Handler

    Py2-3.4 compatible method to send logs to LogStash HTTP handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -reactors.logtypes.logstash_futures_session.bg_cb(sess, resp)
    +
    +reactors.logtypes.logstash_futures_session.bg_cb(sess, resp)

    Noop the response so logging is fire-and-forget

    -
    -reactors.logtypes.logstash_futures_session.response_hook_noop(resp, *args, **kwargs)
    +
    +reactors.logtypes.logstash_futures_session.response_hook_noop(resp, *args, **kwargs)

    Noop the response so logging is fire-and-forget

    -
    -
    -

    reactors.logtypes.logstash_sync module

    +
    +
    +

    reactors.logtypes.logstash_sync module

    -
    -class reactors.logtypes.logstash_sync.LogstashPlaintextHandler(config, client_secret)
    +
    +class reactors.logtypes.logstash_sync.LogstashPlaintextHandler(config, client_secret)

    Bases: logging.Handler

    Forwards logs on to LogStash HTTP handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -
    -

    reactors.logtypes.main module

    + +
    +

    reactors.logtypes.main module

    Set up a logger with optional support for a logfile and STDERR reporting

    Usage: logger = get_logger(name, log_level, log_file)

    -
    -class reactors.logtypes.main.RedactingFormatter(orig_formatter, patterns)
    -

    Bases: object

    +
    +class reactors.logtypes.main.RedactingFormatter(*args, patterns=None, **kwargs)
    +

    Bases: logging.Formatter

    Specialized formatter used to sanitize log messages

    -
    -format(record)
    -
    +
    +converter()
    +
    +
    gmtime([seconds]) -> (tm_year, tm_mon, tm_mday, tm_hour, tm_min,

    tm_sec, tm_wday, tm_yday, tm_isdst)

    +
    +
    +

    Convert seconds since the Epoch to a time tuple expressing UTC (a.k.a. +GMT). When ‘seconds’ is not passed in, convert the current time instead.

    +

    If the platform supports the tm_gmtoff and tm_zone, they are available as +attributes only.

    +
    + +
    +
    +format(record)
    +

    Format the specified record as text.

    +

    The record’s attribute dictionary is used as the operand to a +string formatting operation which yields the returned string. +Before formatting the dictionary, a couple of preparatory steps +are carried out. The message attribute of the record is computed +using LogRecord.getMessage(). If the formatting string uses the +time (as determined by a call to usesTime(), formatTime() is +called to format the event time. If there is exception information, +it is formatted using formatException() and appended to the message.

    +
    -
    -reactors.logtypes.main.get_log_file(name)
    +
    +reactors.logtypes.main.get_log_file(name)
    -
    -reactors.logtypes.main.get_log_file_strategy()
    +
    +reactors.logtypes.main.get_log_file_strategy()
    -
    -reactors.logtypes.main.get_logger(name, subname=None, log_level='DEBUG', log_file=None, redactions=[], timestamp=False)
    +
    +reactors.logtypes.main.get_logger(name, subname=None, log_level='DEBUG', log_file=None, redactions=[], timestamp=False)

    Legacy alias to get_stderr_logger

    -
    -reactors.logtypes.main.get_screen_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    +
    +reactors.logtypes.main.get_loggly_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    +

    Returns a logger object that can post to Loggly

    +
    + +
    +
    +reactors.logtypes.main.get_screen_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    -
    -reactors.logtypes.main.get_slack_logger(name, subname, settings={}, redactions=[], timestamp=False)
    +
    +reactors.logtypes.main.get_slack_logger(name, subname, settings={}, redactions=[], timestamp=False)

    Returns a logger object that can post to Slack

    -
    -
    -

    reactors.logtypes.slack module

    + +
    +

    reactors.logtypes.slack module

    -
    -class reactors.logtypes.slack.SlackHandler(config)
    +
    +class reactors.logtypes.slack.SlackHandler(config)

    Bases: logging.Handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -reactors.logtypes.slack.bg_cb(sess, resp)
    +
    +reactors.logtypes.slack.bg_cb(sess, resp)

    Don’t do anything with the response

    -
    -
    -

    Module contents

    -
    -
    + +
    +

    Module contents

    +
    + -
    +
    -
    -
    - - - - + +
    + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.runtime.html b/docs/api-ref/reactors.runtime.html new file mode 100644 index 0000000..6b10c4b --- /dev/null +++ b/docs/api-ref/reactors.runtime.html @@ -0,0 +1,514 @@ + + + + + + + reactors.runtime package — reactors_sdk 1.0.0 documentation + + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.runtime package

    +
    +

    Submodules

    +
    +
    +

    reactors.runtime.abaco module

    +

    Abaco-related vars and helper functions

    +
    +
    +reactors.runtime.abaco.is_hashid(identifier)
    +

    Validates a string presented as an Abaco identifier

    +
    + +
    +
    +reactors.runtime.abaco.load_client(permissive=False)
    +

    Gets the current Tapis API client

    +

    Returns the Abaco actor’s client if running deployed. Attempts to +bootstrap a client from supplied credentials if running in local or +debug mode.

    +
    + +
    +
    +reactors.runtime.abaco.load_context(enable_mocks=True)
    +
    + +
    +
    +reactors.runtime.abaco.new_hashid()
    +

    Generates a valid Abaco-style hash id

    +
    + +
    +
    +

    reactors.runtime.base module

    +

    Reactor base class

    +
    +
    +class reactors.runtime.base.BaseReactor(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: object

    +
    +
    +CONFIG_NAMESPACE = '_REACTOR'
    +
    + +
    +
    +EXIT_CODE = 1
    +
    + +
    +
    +MOCK_ENABLED = True
    +
    + +
    +
    +NICKNAME_SEP = '-'
    +
    + +
    +
    +NICKNAME_WORDS = 2
    +
    + +
    +
    +TAPIS_OPTIONAL = False
    +
    + +
    +
    +elapsed()
    +

    Returns elapsed time in microseconds since Reactor was initialized

    +
    + +
    +
    +on_failure(failMessage='Failure', exceptionObject=None)
    +

    Log message and exit 0

    +
    + +
    +
    +on_success(successMessage='Success')
    +

    Log message and exit 0

    +
    + +
    + +
    +
    +

    reactors.runtime.messaging module

    +

    Derived Reactor class implementing inter-actor messages

    +
    +
    +class reactors.runtime.messaging.Messaging(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +MAX_ELAPSED = 300
    +
    + +
    +
    +MAX_RETRIES = 5
    +
    + +
    +
    +RETRY_DELAY = 1.0
    +
    + +
    +
    +RETRY_MAX_DELAY = 32.0
    +
    + +
    +
    +actor_property(property=None, actor_id=None)
    +

    Retrieve an actor property from Abaco API

    +

    Parameters: +property - str - Any top-level key in the Actor API model +actorId - str - Which actor (if not self) to fetch. Defaults to

    +
    +

    the actor’s own ID, allowing introspection.

    +
    +
    + +
    +
    +message_provenance(senderTags=True)
    +

    Captures provenance attributes for current execution

    +
    + +
    +
    +message_vars(passed_envs={}, sender_envs={}, senderTags=True)
    +

    Private method to merge user- and platform-specific environments

    +
    + +
    +
    +resolve_alias(alias)
    +

    Look up the identifier for a alias string

    +
    +
    Arguments

    alias (str): An alias, actorId, appId, or the me/self shortcut

    +
    +
    Returns:

    str: The resolved identifier

    +
    +
    +

    On error: +Returns value of text

    +
    +
    Note:

    Does basic optimization of returning an app ID or abaco actorId +if they are passed, as we can safely assume those are not aliases.

    +
    +
    +
    + +
    +
    +send_message(actorId, message, environment={}, ignoreErrors=True, senderTags=True, retryMaxAttempts=None, retryDelay=None, sync=False)
    +

    Send a message to an Abaco actor by ID or alias

    +
    +
    Arguments:

    actorId (str): An actorId or alias +message (str/dict) : Message to send

    +
    +
    Keyword Arguments:

    ignoreErrors: bool - only mark failures by logging not exception +environment: dict - environment variables to pass as url params +senderTags: bool - send provenance and session as urlparams with message +retryDelay: int - seconds between retries on send failure +retryMax: int - number of times (up to global MAX_RETRIES) to retry +sync: bool - not implemented - wait for message to execute

    +
    +
    Returns:

    str: The executionId of the resulting execution

    +
    +
    Raises:

    AgaveError: Raised if ignoreErrors is True

    +
    +
    +
    + +
    + +
    +
    +

    reactors.runtime.reactor module

    +

    Composition of mix-in classes into Reactor class

    +
    +
    +class reactors.runtime.reactor.Reactor(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.messaging.Messaging, reactors.runtime.validating.Validation, reactors.runtime.webhooks.Webhooks

    +
    + +
    +
    +

    reactors.runtime.sessions module

    +

    Code having to do with actor sessions

    +
    +
    +reactors.runtime.sessions.get_session(context, default=None)
    +
    + +
    +
    +

    reactors.runtime.validating module

    +

    Derived Reactor class implementing validations

    +
    +
    +class reactors.runtime.validating.Validation(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +AUTO_VALIDATE_BINARY = False
    +
    + +
    +
    +AUTO_VALIDATE_CONTEXT = True
    +
    + +
    +
    +AUTO_VALIDATE_MESSAGE = True
    +
    + +
    +
    +classify_binary()
    +

    Determine what kind of binary was sent

    +
    + +
    +
    +classify_context()
    +

    Determine which schemas match the current context

    +
    + +
    +
    +classify_message()
    +

    Determine which schemas match the current JSON message

    +
    + +
    +
    +validate(check_context=True, check_message=True, check_binary=False, permissive=True)
    +

    Perform all validations using default settings

    +
    + +
    +
    +validate_binary(validator=None, permissive=True)
    +

    (Stub) Verify Actor binary FIFO contents

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    validator - func - user function for validating a binary [binary.validator_function] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    +
    +validate_context(schema=None, permissive=True)
    +

    Validate Actor context using a JSON schema

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    schema - str - override path to a JSON schema file [/schemas/context.jsonschema] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    +
    +validate_message(message=None, schema=None, permissive=True)
    +

    Validate Actor message against a JSON schema

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    message - dict - representation of a JSON message +schema - str - override path to a JSON schema file [/schemas/message.jsonschema] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    + +
    +
    +

    reactors.runtime.webhooks module

    +

    Derived Reactor class implementing webhooks and nonces

    +
    +
    +class reactors.runtime.webhooks.Webhooks(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +DEFAULT_NONCE_MAX_USES = -1
    +
    + +
    +
    +DEFAULT_NONCE_PERMISSION = 'EXECUTE'
    +
    + +
    +
    +add_nonce(permission='READ', maxuses=1, actorId=None)
    +

    Add a new nonce.

    +
    +
    Positional arguments:

    None

    +
    +
    Keyword arguments:

    username: str - a valid TACC.cloud username or role account +permission: str - a valid Abaco permission level +maxuses: int (-1,inf) - maximum number of uses for a given nonce +actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +create_webhook(permission='EXECUTE', maxuses=- 1, actorId=None)
    +

    Create an actor/messages URI for use with external integrations

    +
    + +
    +
    +delete_all_nonces(actorId=None)
    +

    Delete all nonces from an actor

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +delete_nonce(nonceId, actorId=None)
    +

    Delete an specific nonce by its ID

    +
    +
    Positional arguments:

    nonceId: str - a valid TACC.cloud username or role account

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +delete_webhook(webhook, actorId=None)
    +

    ‘Delete’ an actor-specific webhook by deleting its nonce

    +

    A key assumption is that webhook was constructed by create_webhook or +its equivalent, as this method sensitive to case and url structure

    +
    + +
    +
    +get_nonce(nonceId, actorId=None)
    +

    Get an specific nonce by its ID

    +
    +
    Positional arguments:

    nonceId: str - a valid TACC.cloud username or role account

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +list_nonces(actorId=None)
    +

    List all nonces

    +
    +
    Positional arguments:

    None

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    + +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docs/api-ref/reactors.validation.html b/docs/api-ref/reactors.validation.html new file mode 100644 index 0000000..0f4b869 --- /dev/null +++ b/docs/api-ref/reactors.validation.html @@ -0,0 +1,329 @@ + + + + + + + reactors.validation package — reactors_sdk 1.0.0 documentation + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.validation package

    +
    +

    Submodules

    +
    +
    +

    reactors.validation.binary module

    +

    Implements binary validation

    +
    +
    +reactors.validation.binary.classify_binary(binary, validators=None, permissive=True)
    +
    + +
    +
    +reactors.validation.binary.validate(binary, permissive=True)
    +
    + +
    +
    +reactors.validation.binary.validate_binary(binary, validator, permissive=True)
    +
    + +
    +
    +

    reactors.validation.context module

    +

    Implements context validation

    +
    +
    +reactors.validation.context.classify_context(context, schemas=None, min_allowed=0, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a context matches.

    +
    + +
    +
    +reactors.validation.context.validate(context, permissive=True)
    +

    Verifies that a context is valid

    +
    + +
    +
    +reactors.validation.context.validate_context(context, schema, check_formats=True, permissive=True)
    +

    Validates that a document conforms to the given context JSON schema.

    +
    +
    Arguments

    context (dict): Abaco context loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +

    reactors.validation.jsondoc module

    +

    Classes and functions for working with and validating JSON messages

    +
    +
    +reactors.validation.jsondoc.classify_document(message, schemas=None, min_allowed=1, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a document matches.

    +
    + +
    +
    +reactors.validation.jsondoc.find_schema_files(dirname='schemas', filename_glob='*.jsonschema', static_paths=None)
    +

    Searches defined filesystem locations for JSON schema files

    +
    + +
    +
    +class reactors.validation.jsondoc.formatChecker
    +

    Bases: jsonschema._format.FormatChecker

    +

    Enables python-jsonschema to validate format fields

    +
    + +
    +
    +reactors.validation.jsondoc.id_for_schema(schema_as_dict)
    +

    Generates a hash-based identifier for a schema document

    +
    + +
    +
    +reactors.validation.jsondoc.is_default(schema_as_dict)
    +

    Return true if a JSONschema is the built-in default

    +
    + +
    +
    +reactors.validation.jsondoc.load_schema(schema, inject_id=True, force_additional_properties=False)
    +

    Loads a schema from a URL, file path, or dictionary

    +
    +
    Arguments

    schema (str|dict): Schema reference +inject_id (bool): Whether to force the schema to contain an $id property +force_additional_properties (bool): Whether to force the schema to accept additional properties

    +
    +
    Returns:

    dict: A dictionary containing the JSON schema

    +
    +
    On error:

    Returns value of text

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.load_schemas(schemas, inject_id=True, force_additional_properties=False)
    +

    Loads list of schema URLs, file paths, and dictionaries

    +
    +
    Arguments

    schemas (list): List of schema references +inject_id (bool): Whether to force the schema to contain an $id property +force_additional_properties (bool): Whether to force the schema to accept additional properties

    +
    +
    Returns:

    list: A list of JSON schemas

    +
    +
    On error:

    N/A

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.schema_from_url(url, inject_id=True)
    +

    Fetches a schema document from a URL.

    +
    + +
    +
    +reactors.validation.jsondoc.schema_id(schema)
    +

    Returns the identifier from a JSON schema.

    +
    + +
    +
    +reactors.validation.jsondoc.schema_ids(schemas)
    +

    Returns the identifiers from a list of JSON schemas

    +
    + +
    +
    +reactors.validation.jsondoc.validate_document(message, schema, check_formats=True, permissive=True)
    +

    Validates that a document conforms to the given JSON schema.

    +
    +
    Arguments

    message (dict): JSON document loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.vars_from_schema(schema, filter_private=False, private_prefix='_')
    +

    Transforms a JSON schema into list of dict representations

    +

    Note: This does not (and cannot) resolve JSON $ref subproperties

    +
    + +
    +
    +

    reactors.validation.message module

    +

    Implements JSON message validation

    +
    +
    +reactors.validation.message.classify_message(message, schemas=None, min_allowed=0, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a message matches.

    +
    + +
    +
    +reactors.validation.message.find_message_schema_files(dirname='message_schemas', filename_glob='*.jsonschema', static_paths=['/message_schemas/default.jsonschema', '/message_schemas/message.jsonschema', '/schemas/message.jsonschema', '/message.jsonschema', '/Users/eho/tacc/projects/sd2e/python-reactors/src/reactors/validation/message.jsonschema'])
    +

    Searches defined filesystem locations for JSON schema files defining Abaco message formats

    +
    + +
    +
    +reactors.validation.message.validate(message, permissive=True)
    +

    Verifies that a message is valid according to one of the schemas

    +
    + +
    +
    +reactors.validation.message.validate_message(message, schema, check_formats=True, permissive=True)
    +

    Validates that a message conforms to the given message JSON schema.

    +
    +
    Arguments

    message (dict): Abaco message loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docs/genindex.html b/docs/genindex.html index cf59969..9a2cf0f 100644 --- a/docs/genindex.html +++ b/docs/genindex.html @@ -1,43 +1,68 @@ - - - - - - - Index — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + Index — reactors_sdk 1.0.0 documentation + + + + + + + + + + - - - -
    -
    -
    -
    - + + + +
    + + +
    + +
    +
    +
    +
      +
    • »
    • +
    • Index
    • +
    • +
    • +
    +
    +
    +
    +
    +

    Index

    @@ -51,8 +76,6 @@

    Index

    | G | H | I - | J - | K | L | M | N @@ -69,11 +92,9 @@

    Index

    A

    @@ -101,9 +118,13 @@

    A

    B

    + + + + + + + + + + + + + + +
        - reactors.aliases + reactors.cli
        - reactors.aliases.agavedb + reactors.cli.run
        - reactors.aliases.agavedb.keyval + reactors.cli.usage
        - reactors.aliases.agavedb.tests + reactors.config
        - reactors.aliases.agavedb.tests.agavefixtures + reactors.logtypes
        - reactors.aliases.agavedb.tests.test_keyval + reactors.logtypes.loggly
        - reactors.aliases.agavedb.tests.testdata + reactors.logtypes.loggly_futures_session
        - reactors.aliases.agavedb.uniqueid + reactors.logtypes.logstash
        - reactors.aliases.store + reactors.logtypes.logstash_futures_session
        - reactors.jsonmessages + reactors.logtypes.logstash_sync
        - reactors.logtypes + reactors.logtypes.main
        - reactors.logtypes.logstash + reactors.logtypes.slack
        - reactors.logtypes.logstash_futures_session + reactors.runtime
        - reactors.logtypes.logstash_sync + reactors.runtime.abaco
        - reactors.logtypes.main + reactors.runtime.base
        - reactors.logtypes.slack + reactors.runtime.messaging
        - reactors.process + reactors.runtime.reactor
        - reactors.runtime + reactors.runtime.sessions
        - reactors.storage + reactors.runtime.validating
        - reactors.uniqueid + reactors.runtime.webhooks
        reactors.utils
        + reactors.validation +
        + reactors.validation.binary +
        + reactors.validation.context +
        + reactors.validation.jsondoc +
        + reactors.validation.message +
        @@ -206,42 +256,31 @@

    Python Module Index

    -
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    - -
    -
    - - - + +
    + + + \ No newline at end of file diff --git a/docs/search.html b/docs/search.html index fea5971..b659b0d 100644 --- a/docs/search.html +++ b/docs/search.html @@ -1,96 +1,116 @@ - - - - - - - Search — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + Search — reactors_sdk 1.0.0 documentation + + + + + + + + + + + - - - + + - - + +
    + + +
    + +
    +
    +
    +
      +
    • »
    • +
    • Search
    • +
    • +
    • +
    +
    +
    +
    +
    + + +
    -
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    - -
    -
    - - - + +
    + + + + + + + + \ No newline at end of file diff --git a/docs/searchindex.js b/docs/searchindex.js index deff784..661489c 100644 --- a/docs/searchindex.js +++ b/docs/searchindex.js @@ -1 +1 @@ -Search.setIndex({docnames:["api-ref/modules","api-ref/reactors","api-ref/reactors.agaveutils","api-ref/reactors.aliases","api-ref/reactors.aliases.agavedb","api-ref/reactors.aliases.agavedb.tests","api-ref/reactors.logtypes","index"],envversion:{"sphinx.domains.c":2,"sphinx.domains.changeset":1,"sphinx.domains.citation":1,"sphinx.domains.cpp":3,"sphinx.domains.index":1,"sphinx.domains.javascript":2,"sphinx.domains.math":2,"sphinx.domains.python":2,"sphinx.domains.rst":2,"sphinx.domains.std":1,sphinx:56},filenames:["api-ref/modules.rst","api-ref/reactors.rst","api-ref/reactors.agaveutils.rst","api-ref/reactors.aliases.rst","api-ref/reactors.aliases.agavedb.rst","api-ref/reactors.aliases.agavedb.tests.rst","api-ref/reactors.logtypes.rst","index.rst"],objects:{"":{reactors:[1,0,0,"-"]},"reactors.agaveutils":{entity:[2,0,0,"-"],files:[2,0,0,"-"],reactors:[2,0,0,"-"],recursive:[2,0,0,"-"],uri:[2,0,0,"-"],utils:[2,0,0,"-"]},"reactors.agaveutils.entity":{is_appid:[2,1,1,""]},"reactors.agaveutils.files":{agave_download_file:[2,1,1,""],agave_mkdir:[2,1,1,""],agave_upload_file:[2,1,1,""],get:[2,1,1,""],mkdir:[2,1,1,""],process_agave_httperror:[2,1,1,""],put:[2,1,1,""],random:[2,1,1,""],wait_for_file_status:[2,1,1,""]},"reactors.agaveutils.reactors":{message_reactor:[2,1,1,""]},"reactors.agaveutils.recursive":{PemAgent:[2,2,1,""],random:[2,1,1,""]},"reactors.agaveutils.recursive.PemAgent":{enumerate2:[2,3,1,""],grant:[2,3,1,""],listdir:[2,3,1,""],updatepem:[2,3,1,""],walk:[2,3,1,""]},"reactors.agaveutils.uri":{agave_uri_from_http:[2,1,1,""],from_agave_uri:[2,1,1,""],from_tacc_s3_uri:[2,1,1,""],http_uri_from_agave:[2,1,1,""],to_agave_uri:[2,1,1,""]},"reactors.agaveutils.utils":{get_api_server:[2,1,1,""],get_api_token:[2,1,1,""],get_api_username:[2,1,1,""]},"reactors.aliases":{agavedb:[4,0,0,"-"],store:[3,0,0,"-"]},"reactors.aliases.agavedb":{Agave:[4,2,1,""],AgaveKeyValStore:[4,2,1,""],keyval:[4,0,0,"-"],tests:[5,0,0,"-"],uniqueid:[4,0,0,"-"]},"reactors.aliases.agavedb.Agave":{PARAMS:[4,4,1,""],agpy_path:[4,3,1,""],can_refresh:[4,4,1,""],clients_ari:[4,3,1,""],download_uri:[4,3,1,""],full_ari:[4,3,1,""],geturl:[4,3,1,""],jwt_ari:[4,3,1,""],nonce_ari:[4,3,1,""],refresh_aris:[4,3,1,""],resource:[4,3,1,""],restore:[4,3,1,""],set_client:[4,3,1,""],tapis_cache_path:[4,3,1,""],tapis_current_path:[4,3,1,""],tapis_sessions_path:[4,3,1,""],to_dict:[4,3,1,""]},"reactors.aliases.agavedb.AgaveKeyValStore":{create_key_name:[4,3,1,""],deldb:[4,3,1,""],from_text_pem:[4,3,1,""],get:[4,3,1,""],getacls:[4,3,1,""],getall:[4,3,1,""],rem:[4,3,1,""],remacl:[4,3,1,""],set:[4,3,1,""],setacl:[4,3,1,""],to_text_pem:[4,3,1,""],validate_acl:[4,3,1,""]},"reactors.aliases.agavedb.keyval":{AgaveKeyValStore:[4,2,1,""]},"reactors.aliases.agavedb.keyval.AgaveKeyValStore":{create_key_name:[4,3,1,""],deldb:[4,3,1,""],from_text_pem:[4,3,1,""],get:[4,3,1,""],getacls:[4,3,1,""],getall:[4,3,1,""],rem:[4,3,1,""],remacl:[4,3,1,""],set:[4,3,1,""],setacl:[4,3,1,""],to_text_pem:[4,3,1,""],validate_acl:[4,3,1,""]},"reactors.aliases.agavedb.tests":{agavefixtures:[5,0,0,"-"],test_keyval:[5,0,0,"-"],testdata:[5,0,0,"-"]},"reactors.aliases.agavedb.tests.agavefixtures":{agave:[5,1,1,""],credentials:[5,1,1,""]},"reactors.aliases.agavedb.tests.test_keyval":{fake_key:[5,1,1,""],fake_key_acl:[5,1,1,""],fake_user:[5,1,1,""],fake_value:[5,1,1,""],keyvalstore:[5,1,1,""],prefix:[5,1,1,""],test_acl_from_world:[5,1,1,""],test_add_acl:[5,1,1,""],test_data:[5,1,1,""],test_get_nonexistent:[5,1,1,""],test_getall:[5,1,1,""],test_key_valid:[5,1,1,""],test_list_acl:[5,1,1,""],test_namespace_fwd:[5,1,1,""],test_namespace_rev_namespace:[5,1,1,""],test_namespace_rev_wo_namespace:[5,1,1,""],test_remall:[5,1,1,""],test_set_get_rem:[5,1,1,""],test_username:[5,1,1,""],test_validate_acl:[5,1,1,""],test_value_valid_type:[5,1,1,""]},"reactors.aliases.agavedb.tests.testdata":{TestData:[5,2,1,""]},"reactors.aliases.agavedb.tests.testdata.TestData":{data:[5,3,1,""],file_to_json:[5,3,1,""]},"reactors.aliases.agavedb.uniqueid":{get_id:[4,1,1,""],is_hashid:[4,1,1,""]},"reactors.aliases.store":{AliasStore:[3,2,1,""],to_unicode:[3,1,1,""]},"reactors.aliases.store.AliasStore":{get_alias_acls:[3,3,1,""],get_aliases:[3,3,1,""],get_name:[3,3,1,""],put_alias_acl:[3,3,1,""],rem_alias:[3,3,1,""],rem_alias_acl:[3,3,1,""],rem_all_aliases:[3,3,1,""],set_alias:[3,3,1,""]},"reactors.jsonmessages":{validate_message:[1,1,1,""]},"reactors.logtypes":{logstash:[6,0,0,"-"],logstash_futures_session:[6,0,0,"-"],logstash_sync:[6,0,0,"-"],main:[6,0,0,"-"],slack:[6,0,0,"-"]},"reactors.logtypes.logstash_futures_session":{LogstashPlaintextHandler:[6,2,1,""],bg_cb:[6,1,1,""],response_hook_noop:[6,1,1,""]},"reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.logtypes.logstash_sync":{LogstashPlaintextHandler:[6,2,1,""]},"reactors.logtypes.logstash_sync.LogstashPlaintextHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.logtypes.main":{RedactingFormatter:[6,2,1,""],get_log_file:[6,1,1,""],get_log_file_strategy:[6,1,1,""],get_logger:[6,1,1,""],get_screen_logger:[6,1,1,""],get_slack_logger:[6,1,1,""]},"reactors.logtypes.main.RedactingFormatter":{format:[6,3,1,""]},"reactors.logtypes.slack":{SlackHandler:[6,2,1,""],bg_cb:[6,1,1,""]},"reactors.logtypes.slack.SlackHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.process":{run:[1,1,1,""]},"reactors.runtime":{random:[1,1,1,""]},"reactors.uniqueid":{get_id:[1,1,1,""],is_hashid:[1,1,1,""]},"reactors.utils":{Reactor:[1,2,1,""],get_client_with_mock_support:[1,1,1,""],get_context_with_mock_support:[1,1,1,""],get_token_with_mock_support:[1,1,1,""],microseconds:[1,1,1,""],random:[1,1,1,""],read_config:[1,1,1,""],set_os_environ_from_client:[1,1,1,""],set_os_environ_from_mock:[1,1,1,""],utcnow:[1,1,1,""]},"reactors.utils.Reactor":{add_nonce:[1,3,1,""],create_webhook:[1,3,1,""],delete_all_nonces:[1,3,1,""],delete_nonce:[1,3,1,""],delete_webhook:[1,3,1,""],elapsed:[1,3,1,""],get_attr:[1,3,1,""],get_nonce:[1,3,1,""],list_nonces:[1,3,1,""],on_failure:[1,3,1,""],on_success:[1,3,1,""],resolve_actor_alias:[1,3,1,""],send_message:[1,3,1,""],validate_message:[1,3,1,""]},reactors:{agaveutils:[2,0,0,"-"],aliases:[3,0,0,"-"],jsonmessages:[1,0,0,"-"],logtypes:[6,0,0,"-"],process:[1,0,0,"-"],runtime:[1,0,0,"-"],storage:[1,0,0,"-"],uniqueid:[1,0,0,"-"],utils:[1,0,0,"-"],version:[1,0,0,"-"]}},objnames:{"0":["py","module","Python module"],"1":["py","function","Python function"],"2":["py","class","Python class"],"3":["py","method","Python method"],"4":["py","attribute","Python attribute"]},objtypes:{"0":"py:module","1":"py:function","2":"py:class","3":"py:method","4":"py:attribute"},terms:{"05t18":1,"2018":1,"290790":1,"300":2,"boolean":4,"case":1,"class":[1,2,3,4,5,6],"default":1,"final":2,"function":2,"import":[2,4],"int":1,"long":2,"new":[1,2],"public":[2,4],"return":[1,2,3,4,5,6],"true":[1,2,3,4],"try":2,"var":1,Not:2,The:[1,2,4],These:4,Uses:[2,4],_namespac:5,_namespace_rev:5,_reactor:1,_refresh_token:4,_token:4,abaco:[1,2,4],about:2,absolut:[2,4],abspath:2,access:[1,4],access_token:2,account:1,acl:[3,4,5],activ:4,actor:[1,2,3],actor_id:3,actorid:[1,2],actual:6,add:[1,3],add_nonc:1,against:1,agav:[2,3,4,5],agave_cli:1,agave_download_fil:2,agave_mkdir:2,agave_upload_fil:2,agave_uri_from_http:2,agaveabsolutepath:2,agavecli:[2,3,4],agavedb:[1,3],agavedestpath:2,agaveerror:[1,2],agavefixtur:[3,4],agavekeyvalstor:[3,4],agavepi:[2,4],agaveuri:2,agaveutil:[0,1],agavewatchpath:2,agpi:4,agpy_path:4,alia:[1,3,6],alias:[0,1],aliasprefix:[3,4],aliasstor:3,all:[1,2,3,4],allow:1,along:1,alphabet:3,alreadi:2,alth:1,alwai:2,ani:1,anoth:2,anyth:6,api:[1,2,4,7],api_kei:4,api_secret:4,api_serv:4,app:[1,2],appid:[1,2],appli:2,arg:[4,6],argument:1,arrai:5,assum:[1,4],assumpt:1,attempt:[1,2],attrdict:1,attribut:1,auth_typ:4,authent:2,avoid:2,awar:4,backoff:2,base:[1,2,3,4,5,6],basepath:2,basic:1,befor:2,between:1,bg_cb:6,bool:[1,2,4],bootstrap:1,broken:1,build:3,built:[3,4],cach:4,cache_cli:4,call:2,caller:2,can:[1,4,5,6],can_refresh:4,candid:2,caveat:2,child:[1,2],choos:2,classmethod:4,client:[1,2,4],client_nam:4,client_secret:6,clientcommand:4,clients_ari:4,cloud:1,command:1,command_list:1,common:2,compat:6,complet:2,config:6,construct:[1,2],contain:1,content:0,context:1,conveni:4,convert:2,correctli:2,crawl:2,creat:[1,2,3,4],create_key_nam:4,create_webhook:1,created_at:4,creation:2,credenti:[1,4,5],current:[1,2,3,4],cwd:2,cycl:5,data:[2,5],databas:3,date:1,debug:[1,6],defin:1,delai:2,deldb:4,delet:[1,3,4,5],delete_all_nonc:1,delete_nonc:1,delete_webhook:1,deploi:1,deprec:4,deprecatedcommand:4,deriv:1,destin:2,dict:[1,4],dictionari:4,dictonari:1,dir:2,directori:[1,2,4],directorypath:2,dirnam:2,dirpath:2,docsrc:1,document:[1,4],doe:[1,4],doesn:5,doing:2,don:6,download:[2,4],download_uri:4,drop:4,edu:4,elaps:1,emit:6,encod:3,entir:3,entiti:[0,1,3],entri:5,enumerate2:2,env:[1,5],environ:[1,2],equival:1,error:[1,2,3,4],eventu:[1,4],exampl:1,excecutionid:1,exceed:2,except:[1,2,4],exceptionobject:1,exec:1,exec_param:1,execut:[1,2],exist:[4,5],exit:1,expens:2,expir:4,expires_at:4,expires_in:4,exponenti:2,extern:4,failmessag:1,failur:[1,2,4],fake_kei:5,fake_key_acl:5,fake_us:5,fake_valu:5,fals:[1,2,4,6],favor:1,fetch:[1,3],field:6,file:[0,1,4,5],file_to_json:5,filenam:[2,5],filesystem:2,filter:3,find:1,fire:[2,6],forget:[2,6],form:[1,5],format:[1,2,6],formatt:6,forward:6,fpath:2,friendli:4,from:[1,2,3,4],from_agave_uri:2,from_tacc_s3_uri:2,from_text_pem:4,full_ari:4,gener:[1,4],get:[1,2,3,4,5],get_alias:3,get_alias_acl:3,get_api_serv:2,get_api_token:2,get_api_usernam:2,get_attr:1,get_client_with_mock_support:1,get_context_with_mock_support:1,get_full_messag:6,get_id:[1,4],get_log_fil:6,get_log_file_strategi:6,get_logg:6,get_nam:3,get_nonc:1,get_screen_logg:6,get_slack_logg:6,get_stderr_logg:6,get_token_with_mock_support:1,getacl:4,getal:[4,5],geturl:4,given:[1,3,4],global:1,grant:[1,2],handl:2,handler:6,has:4,hash:[1,4],hashid:4,header_nam:4,helper:[1,2],here:2,host:2,http:[2,4,6],http_error_object:2,http_uri_from_agav:2,httperror:2,httpuri:2,human:4,identifi:[1,4],ignor:1,ignoreerror:[1,2],imdepot:2,implement:[1,2,3,6],importdata:2,index:7,inf:1,infer:1,info:2,initi:[1,2],input:3,inspir:4,instanc:4,integr:1,intend:6,interact:4,interfac:4,interv:[1,2],introspect:1,involv:2,is_appid:2,is_hashid:[1,4],its:[1,2],job:4,json:1,jsonmessag:0,jsonschema:1,jwt:4,jwt_ari:4,jwt_header_nam:4,kei:[1,3,4,5],keyprefix:[3,4],keyval:[1,3],keyvalstor:5,keyword:1,keywork:4,kvs_v3:[3,4],kwarg:[4,6],least:2,legaci:6,level:1,librari:[1,4],like:2,linktyp:2,list:[1,3,4],list_nonc:1,listdir:2,load:[4,5],local:[1,4],local_path:4,localfilenam:2,log:[1,6],log_fil:6,log_level:6,logfil:6,logger:6,loglevel:[2,3,4],logstash:[0,1],logstash_asyncio:[0,1],logstash_futures_sess:[0,1],logstash_sync:[0,1],logstashplaintexthandl:6,logtyp:[0,1],look:[1,2],main:[0,1],make:[2,4],manag:[2,3,4],map:3,mark:1,max_retri:1,maximum:1,maxtim:2,maxus:1,media:2,merg:1,messag:[1,2,6],message_reactor:2,messagedict:1,messageschema:1,metadata:4,metatadata:3,method:[1,4,6],microsecond:1,mkdir:2,mock:1,mode:1,model:[1,4],modul:[0,7],more:4,movement:2,much:4,multipli:2,multius:4,name:[2,3,4,6],namespac:[1,2],nearli:4,need:4,nonc:1,nonce_ari:4,nonceid:1,none:[1,2,3,4,5,6],noop:6,note:1,noth:2,notimplementederror:6,number:[1,2,4],numer:4,oauth2:1,object:[1,2,4,5,6],on_failur:1,on_success:1,one:2,onli:[1,4],oper:2,optim:1,option:[3,6],order:5,orient:4,orig_formatt:6,otherwis:2,our:5,output:4,overload:2,overrid:1,own:[1,3,4],packag:[0,7],page:7,param:[1,4],paramet:[1,2,4],parent:2,pars:2,pass:1,password:4,path:[1,2,4],pattern:6,pem:[2,4],pemag:2,permiss:[1,2,4],pickledb:4,place:2,places_list:1,platform:1,point:2,poll:2,posit:[1,2,4],posix:1,post:6,prefix:5,process:0,process_agave_httperror:2,project:1,proven:1,provid:1,proxi:4,put:2,put_alias_acl:3,py2:6,python:[1,2,4],rais:[1,2,4,6],random:[1,2,4],reach:2,read:[1,2,4],read_config:1,readabl:4,real:2,rec:2,record:6,recurs:[0,1],redact:[1,6],redactingformatt:6,redi:4,refer:7,refresh_ari:4,refresh_token:4,rem:4,rem_alia:3,rem_alias_acl:3,rem_all_alias:3,remacl:4,remot:2,remov:[3,4],report:6,repres:4,request:[2,4],requir:[2,4],requisit:1,resid:2,resolv:1,resolve_actor_alia:1,resourc:[2,4],resp:6,respons:[1,6],response_hook_noop:6,restor:4,result:1,retri:[1,2,4],retriev:[1,3],retrydelai:1,retrymax:1,retrymaxattempt:1,right:1,role:1,root:2,run:[1,5],runtim:0,safe:1,same:[2,5],sanit:6,schema:1,sd2e:1,search:7,second:1,secret:4,self:[1,3],send:[1,2,6],send_messag:1,sendertag:[1,2],sensit:1,sequenc:2,server:2,servic:[1,4],sess:6,session:[1,4,5],set:[1,4,5,6],set_alia:3,set_client:4,set_os_environ_from_cli:1,set_os_environ_from_mock:1,setacl:4,share:4,shell:1,shortcut:1,should:[2,4],side:1,sinc:[1,2],slack:[0,1],slackhandl:6,solut:4,sort:3,sort_alias:[3,4],sourc:4,special:[2,6],specif:[1,5],specifi:[2,6],speciifc:3,src:1,state:2,statu:2,stderr:6,storag:[0,2],storagesystem:2,store:[0,1,4,5],str:[1,2,4],string:[1,2,4],strong:4,structur:1,style:[1,4],subclass:6,submodul:0,subnam:6,subpackag:0,subprocess:1,subshel:1,success:[1,2,4],successmessag:1,suitabl:1,suppli:1,support:[1,4,6],swallow:1,sync:[1,2],synchron:2,system:[1,2,4],systemid:2,tacc:[1,2,4],tacconfig:1,take:6,tapis_cache_path:4,tapis_current_path:4,tapis_sessions_path:4,tasethanho:1,task:2,tenant_id:4,termin:2,test:[1,3,4],test_acl_from_world:5,test_add_acl:5,test_data:5,test_get_nonexist:5,test_getal:5,test_key_valid:5,test_keyv:[3,4],test_list_acl:5,test_namespace_fwd:5,test_namespace_rev_namespac:5,test_namespace_rev_wo_namespac:5,test_remal:5,test_set_get_rem:5,test_usernam:5,test_validate_acl:5,test_value_valid_typ:5,testdata:[3,4],text:[1,2],textstr:2,thei:1,thi:[1,2,4,6],those:1,through:5,time:[1,2],timeout:[1,2],timestamp:6,to_agave_uri:2,to_dict:4,to_text_pem:4,to_unicod:3,token:[1,4],token_callback:4,token_usernam:4,tokencommand:4,top:1,tree:2,tri:[1,4],trivial:3,tupl:2,turn:3,type:4,uid:1,underli:4,unicod:3,uniqu:4,uniqueid:[0,3],unless:4,unlimit:1,updat:[1,2,3],updatepem:2,upload:2,uploadfil:2,uri:[0,1,4],url:[1,2,4],usag:[1,4,6],use:[1,2],use_nonc:4,useapi:2,used:6,user:[1,3,4,5],usernam:[1,2,3,4,5],uses:1,using:[2,4],utc:1,utcnow:1,utexa:4,util:[0,4],uuid4:4,uuid:[1,4],valid:[1,2,4,5],validate_acl:4,validate_messag:1,valu:[1,4,5],variabl:1,variou:5,verifi:[4,5],version:[0,6],via:2,view:5,wai:1,wait:[1,2],wait_for_file_statu:2,walk:2,web:4,webhook:1,whatev:6,where:2,whether:2,which:[1,3,4],whose:4,within:1,work:2,world:2,write:4,yet:2,you:4},titles:["reactors","reactors package","reactors.agaveutils package","reactors.aliases package","reactors.aliases.agavedb package","reactors.aliases.agavedb.tests package","reactors.logtypes package","Welcome to Reactors SDK documentation!"],titleterms:{agavedb:[4,5],agavefixtur:5,agaveutil:2,alias:[3,4,5],content:[1,2,3,4,5,6],document:7,entiti:2,file:2,indic:7,jsonmessag:1,keyval:4,logstash:6,logstash_asyncio:6,logstash_futures_sess:6,logstash_sync:6,logtyp:6,main:6,modul:[1,2,3,4,5,6],packag:[1,2,3,4,5,6],process:1,reactor:[0,1,2,3,4,5,6,7],recurs:2,runtim:1,sdk:7,slack:6,storag:1,store:3,submodul:[1,2,3,4,5,6],subpackag:[1,3,4],tabl:7,test:5,test_keyv:5,testdata:5,uniqueid:[1,4],uri:2,util:[1,2],version:1,welcom:7}}) \ No newline at end of file +Search.setIndex({docnames:["api-ref/modules","api-ref/reactors","api-ref/reactors.agaveutils","api-ref/reactors.cli","api-ref/reactors.logtypes","api-ref/reactors.runtime","api-ref/reactors.validation","index"],envversion:{"sphinx.domains.c":2,"sphinx.domains.changeset":1,"sphinx.domains.citation":1,"sphinx.domains.cpp":4,"sphinx.domains.index":1,"sphinx.domains.javascript":2,"sphinx.domains.math":2,"sphinx.domains.python":3,"sphinx.domains.rst":2,"sphinx.domains.std":2,sphinx:56},filenames:["api-ref/modules.rst","api-ref/reactors.rst","api-ref/reactors.agaveutils.rst","api-ref/reactors.cli.rst","api-ref/reactors.logtypes.rst","api-ref/reactors.runtime.rst","api-ref/reactors.validation.rst","index.rst"],objects:{"":{reactors:[1,0,0,"-"]},"reactors.agaveutils":{entity:[2,0,0,"-"],files:[2,0,0,"-"],reactors:[2,0,0,"-"],recursive:[2,0,0,"-"],uri:[2,0,0,"-"],utils:[2,0,0,"-"]},"reactors.agaveutils.entity":{is_appid:[2,1,1,""]},"reactors.agaveutils.files":{agave_download_file:[2,1,1,""],agave_mkdir:[2,1,1,""],agave_upload_file:[2,1,1,""],get:[2,1,1,""],mkdir:[2,1,1,""],process_agave_httperror:[2,1,1,""],put:[2,1,1,""],random:[2,1,1,""],wait_for_file_status:[2,1,1,""]},"reactors.agaveutils.reactors":{message_reactor:[2,1,1,""]},"reactors.agaveutils.recursive":{PemAgent:[2,2,1,""],random:[2,1,1,""]},"reactors.agaveutils.recursive.PemAgent":{enumerate2:[2,3,1,""],grant:[2,3,1,""],listdir:[2,3,1,""],updatepem:[2,3,1,""],walk:[2,3,1,""]},"reactors.agaveutils.uri":{agave_uri_from_http:[2,1,1,""],from_agave_uri:[2,1,1,""],from_tacc_s3_uri:[2,1,1,""],http_uri_from_agave:[2,1,1,""],to_agave_uri:[2,1,1,""]},"reactors.agaveutils.utils":{get_api_server:[2,1,1,""],get_api_token:[2,1,1,""],get_api_username:[2,1,1,""]},"reactors.cli":{run:[3,0,0,"-"],usage:[3,0,0,"-"]},"reactors.cli.run":{docstring:[3,1,1,""],load_function:[3,1,1,""],run:[3,1,1,""]},"reactors.cli.usage":{usage:[3,1,1,""]},"reactors.config":{get_redaction_strings:[1,1,1,""],parse_boolean:[1,1,1,""],read_config:[1,1,1,""]},"reactors.logtypes":{loggly:[4,0,0,"-"],loggly_futures_session:[4,0,0,"-"],logstash:[4,0,0,"-"],logstash_futures_session:[4,0,0,"-"],logstash_sync:[4,0,0,"-"],main:[4,0,0,"-"],slack:[4,0,0,"-"]},"reactors.logtypes.loggly_futures_session":{LogglyHandler:[4,2,1,""],bg_cb:[4,1,1,""],response_hook_noop:[4,1,1,""]},"reactors.logtypes.loggly_futures_session.LogglyHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.logstash_futures_session":{LogstashPlaintextHandler:[4,2,1,""],bg_cb:[4,1,1,""],response_hook_noop:[4,1,1,""]},"reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.logstash_sync":{LogstashPlaintextHandler:[4,2,1,""]},"reactors.logtypes.logstash_sync.LogstashPlaintextHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.main":{RedactingFormatter:[4,2,1,""],get_log_file:[4,1,1,""],get_log_file_strategy:[4,1,1,""],get_logger:[4,1,1,""],get_loggly_logger:[4,1,1,""],get_screen_logger:[4,1,1,""],get_slack_logger:[4,1,1,""]},"reactors.logtypes.main.RedactingFormatter":{converter:[4,3,1,""],format:[4,3,1,""]},"reactors.logtypes.slack":{SlackHandler:[4,2,1,""],bg_cb:[4,1,1,""]},"reactors.logtypes.slack.SlackHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.runtime":{abaco:[5,0,0,"-"],base:[5,0,0,"-"],messaging:[5,0,0,"-"],reactor:[5,0,0,"-"],sessions:[5,0,0,"-"],validating:[5,0,0,"-"],webhooks:[5,0,0,"-"]},"reactors.runtime.abaco":{is_hashid:[5,1,1,""],load_client:[5,1,1,""],load_context:[5,1,1,""],new_hashid:[5,1,1,""]},"reactors.runtime.base":{BaseReactor:[5,2,1,""]},"reactors.runtime.base.BaseReactor":{CONFIG_NAMESPACE:[5,4,1,""],EXIT_CODE:[5,4,1,""],MOCK_ENABLED:[5,4,1,""],NICKNAME_SEP:[5,4,1,""],NICKNAME_WORDS:[5,4,1,""],TAPIS_OPTIONAL:[5,4,1,""],elapsed:[5,3,1,""],on_failure:[5,3,1,""],on_success:[5,3,1,""]},"reactors.runtime.messaging":{Messaging:[5,2,1,""]},"reactors.runtime.messaging.Messaging":{MAX_ELAPSED:[5,4,1,""],MAX_RETRIES:[5,4,1,""],RETRY_DELAY:[5,4,1,""],RETRY_MAX_DELAY:[5,4,1,""],actor_property:[5,3,1,""],message_provenance:[5,3,1,""],message_vars:[5,3,1,""],resolve_alias:[5,3,1,""],send_message:[5,3,1,""]},"reactors.runtime.reactor":{Reactor:[5,2,1,""]},"reactors.runtime.sessions":{get_session:[5,1,1,""]},"reactors.runtime.validating":{Validation:[5,2,1,""]},"reactors.runtime.validating.Validation":{AUTO_VALIDATE_BINARY:[5,4,1,""],AUTO_VALIDATE_CONTEXT:[5,4,1,""],AUTO_VALIDATE_MESSAGE:[5,4,1,""],classify_binary:[5,3,1,""],classify_context:[5,3,1,""],classify_message:[5,3,1,""],validate:[5,3,1,""],validate_binary:[5,3,1,""],validate_context:[5,3,1,""],validate_message:[5,3,1,""]},"reactors.runtime.webhooks":{Webhooks:[5,2,1,""]},"reactors.runtime.webhooks.Webhooks":{DEFAULT_NONCE_MAX_USES:[5,4,1,""],DEFAULT_NONCE_PERMISSION:[5,4,1,""],add_nonce:[5,3,1,""],create_webhook:[5,3,1,""],delete_all_nonces:[5,3,1,""],delete_nonce:[5,3,1,""],delete_webhook:[5,3,1,""],get_nonce:[5,3,1,""],list_nonces:[5,3,1,""]},"reactors.utils":{get_host_ip:[1,1,1,""],microseconds:[1,1,1,""],utcnow:[1,1,1,""]},"reactors.validation":{binary:[6,0,0,"-"],context:[6,0,0,"-"],jsondoc:[6,0,0,"-"],message:[6,0,0,"-"]},"reactors.validation.binary":{classify_binary:[6,1,1,""],validate:[6,1,1,""],validate_binary:[6,1,1,""]},"reactors.validation.context":{classify_context:[6,1,1,""],validate:[6,1,1,""],validate_context:[6,1,1,""]},"reactors.validation.jsondoc":{classify_document:[6,1,1,""],find_schema_files:[6,1,1,""],formatChecker:[6,2,1,""],id_for_schema:[6,1,1,""],is_default:[6,1,1,""],load_schema:[6,1,1,""],load_schemas:[6,1,1,""],schema_from_url:[6,1,1,""],schema_id:[6,1,1,""],schema_ids:[6,1,1,""],validate_document:[6,1,1,""],vars_from_schema:[6,1,1,""]},"reactors.validation.message":{classify_message:[6,1,1,""],find_message_schema_files:[6,1,1,""],validate:[6,1,1,""],validate_message:[6,1,1,""]},reactors:{agaveutils:[2,0,0,"-"],cli:[3,0,0,"-"],config:[1,0,0,"-"],logtypes:[4,0,0,"-"],runtime:[5,0,0,"-"],utils:[1,0,0,"-"],validation:[6,0,0,"-"],version:[1,0,0,"-"]}},objnames:{"0":["py","module","Python module"],"1":["py","function","Python function"],"2":["py","class","Python class"],"3":["py","method","Python method"],"4":["py","attribute","Python attribute"]},objtypes:{"0":"py:module","1":"py:function","2":"py:class","3":"py:method","4":"py:attribute"},terms:{"0":[2,5,6],"00":1,"01":1,"05t18":1,"1":[2,5,6],"2":[2,5],"2018":1,"290790":1,"3":4,"300":[2,5],"32":5,"4":4,"40":1,"5":[2,5],"55":1,"boolean":1,"case":5,"class":[2,4,5,6],"default":[5,6],"do":[2,4,5],"final":2,"function":[2,3,5,6],"import":2,"int":5,"long":2,"new":[2,5],"public":2,"return":[1,2,4,5,6],"true":[1,2,5,6],"try":2,"var":5,A:[5,6],If:[2,4],It:2,Not:2,On:[5,6],The:[2,4,5],_:6,_format:6,_reactor:5,abaco:[0,1,2,6],about:2,absolut:2,abspath:2,accept:6,access_token:2,accord:6,account:5,actor:[2,5],actor_id:5,actor_properti:5,actorid:[2,5],actual:4,add:5,add_nonc:5,addit:6,address:1,ag:2,against:5,agav:2,agave_cli:1,agave_download_fil:2,agave_mkdir:2,agave_upload_fil:2,agave_uri_from_http:2,agaveabsolutepath:2,agavecli:2,agavedestpath:2,agaveerror:[2,5],agavepi:2,agaveuri:2,agaveutil:[0,1],agavewatchpath:2,alia:[4,5],alias:5,all:[2,5],allow:5,alreadi:2,alwai:2,an:[2,5,6],ani:[5,6],anoth:2,anyth:4,api:[2,5],app:[2,5],append:4,appid:[2,5],appli:2,ar:[2,4,5],arg:[3,4],argument:[5,6],assum:5,assumpt:5,attempt:[2,5],attribut:[4,5],authent:2,auto_validate_binari:5,auto_validate_context:5,auto_validate_messag:5,avail:4,avoid:2,backoff:2,base:[0,1,2,4,6],basepath:2,basereactor:5,basic:[1,5],befor:[2,4],between:5,bg_cb:4,binari:[0,1,5],bool:[2,5,6],bootstrap:5,broken:1,built:6,call:[2,4],caller:2,can:[4,5],candid:2,cannot:6,captur:5,carri:4,caveat:2,check_binari:5,check_context:5,check_format:6,check_messag:5,child:2,choos:2,classifi:6,classify_binari:[5,6],classify_context:[5,6],classify_docu:6,classify_messag:[5,6],cli:[0,1],client:[2,5],client_secret:4,cloud:5,code:5,common:2,compat:4,complet:2,composit:5,comput:4,config:[0,4],config_namespac:5,configur:1,conform:6,construct:[2,5],contain:6,content:0,context:[0,1,5],convert:[2,4],correctli:2,coupl:4,crawl:2,creat:[2,5],create_webhook:5,creation:2,credenti:5,current:[1,2,4,5],cwd:2,data:2,date:1,debug:[4,5],default_nonce_max_us:5,default_nonce_permiss:5,defin:6,delai:2,delet:5,delete_all_nonc:5,delete_nonc:5,delete_webhook:5,deploi:5,deriv:5,destin:2,determin:[4,5],dict:[5,6],dictionari:[4,6],dir:2,directori:2,directorypath:2,dirnam:[2,6],dirpath:2,docstr:3,document:6,doe:[5,6],don:4,download:2,eho:6,elaps:5,emit:4,enabl:6,enable_mock:5,enforc:6,entiti:[0,1],enumerate2:2,env:1,environ:[1,2,5],epoch:4,equival:[1,5],error:[2,5,6],event:4,exampl:1,exceed:2,except:[2,4,5,6],exceptionobject:5,execut:[2,5],executionid:5,exit:5,exit_cod:5,expens:2,exponenti:2,express:4,extern:5,failmessag:5,failur:[2,5],fals:[2,4,5,6],favor:1,fetch:[5,6],field:[4,6],fifo:5,file:[0,1,5,6],filenam:2,filename_glob:6,filesystem:[2,6],filter_priv:6,find_message_schema_fil:6,find_schema_fil:6,fire:[2,4],fn:3,forc:6,force_additional_properti:6,forget:[2,4],format:[1,2,4,6],formatcheck:6,formatexcept:4,formatt:4,formattim:4,forward:4,fpath:2,from:[1,2,3,5,6],from_agave_uri:2,from_tacc_s3_uri:2,func:5,gener:[5,6],get:[2,5],get_api_serv:2,get_api_token:2,get_api_usernam:2,get_full_messag:4,get_host_ip:1,get_log_fil:4,get_log_file_strategi:4,get_logg:4,get_loggly_logg:4,get_nonc:5,get_redaction_str:1,get_screen_logg:4,get_sess:5,get_slack_logg:4,get_stderr_logg:4,getmessag:4,given:[5,6],global:5,gmt:4,gmtime:4,grant:2,handl:2,handler:4,hash:[5,6],have:5,helper:[2,5],here:2,host:[1,2],http:[2,4],http_error_object:2,http_uri_from_agav:2,httperror:2,httpuri:2,id:[2,5,6],id_for_schema:6,identifi:[5,6],ignoreerror:[2,5],imdepot:2,implement:[2,4,5,6],importdata:2,index:7,inf:5,info:2,inform:4,initi:[2,5],inject_id:6,instead:4,integr:5,intend:4,inter:5,interv:2,introspect:5,involv:2,ip:1,is_appid:2,is_default:6,is_hashid:5,its:[2,5],json:[5,6],jsondoc:[0,1],jsonschema:[5,6],k:4,kei:5,keyword:5,kind:5,kwarg:[4,5],least:2,legaci:4,level:5,like:2,linktyp:2,list:[5,6],list_nonc:5,listdir:2,load:[3,6],load_client:5,load_context:5,load_funct:3,load_schema:6,local:5,localfilenam:2,locat:6,log:[4,5],log_fil:4,log_level:4,logfil:4,logger:4,loggli:[0,1],loggly_futures_sess:[0,1],logglyhandl:4,loglevel:2,logrecord:4,logstash:[0,1],logstash_futures_sess:[0,1],logstash_sync:[0,1],logstashplaintexthandl:4,logtyp:[0,1],look:[2,5],main:[0,1,3],make:2,manag:[1,2],mark:5,match:[5,6],max_allow:6,max_elaps:5,max_retri:5,maximum:5,maxtim:2,maxus:5,me:5,media:2,merg:[1,5],messag:[0,1,2,4],message_proven:5,message_reactor:2,message_schema:6,message_var:5,method:[4,5],microsecond:[1,5],min_allow:6,mix:5,mkdir:2,mock_en:5,mode:5,model:5,modul:[0,7],movement:2,multipli:2,n:6,name:[2,4],namespac:[1,2,5],new_hashid:5,nickname_sep:5,nickname_word:5,nonc:5,nonceid:5,none:[1,2,3,4,5,6],noop:4,note:[5,6],noth:2,notimplementederror:4,number:[2,5],object:[2,4,5],on_failur:5,on_success:5,one:[2,6],onli:[4,5],oper:[2,4],operand:4,optim:5,option:4,otherwis:2,out:4,overload:2,overrid:[1,5],own:5,p:2,packag:[0,7],page:7,param:5,paramet:[2,5],parent:2,pars:[1,2],parse_boolean:1,pass:[4,5],passed_env:5,path:[2,5,6],pattern:4,pem:2,pemag:2,perform:5,permiss:[2,5,6],place:2,places_list:1,platform:[4,5],point:2,poll:2,posit:[2,5],post:4,preparatori:4,present:5,privat:5,private_prefix:6,process_agave_httperror:2,project:6,properti:[5,6],proven:5,provid:6,put:2,py2:4,py:3,python:[1,2,6],rais:[2,4,5,6],random:2,rather:6,reach:2,read:[2,5],read_config:1,real:2,rec:2,record:4,recurs:[0,1],redact:[1,4,5],redactingformatt:4,ref:6,refer:6,relat:5,remot:2,report:4,represent:[5,6],request:2,requir:2,resid:2,resolv:[5,6],resolve_alia:5,resourc:2,resp:4,respons:4,response_hook_noop:4,result:5,retri:[2,5],retriev:5,retry_delai:5,retry_max_delai:5,retrydelai:5,retrymax:5,retrymaxattempt:5,right:1,role:5,root:2,run:[0,1,5],runtim:[0,1],s3:2,s:[1,2,4,5],safe:5,same:2,sanit:4,schema:[5,6],schema_as_dict:6,schema_from_url:6,schema_id:6,script:3,sd2e:6,search:[6,7],second:[4,5],self:5,send:[2,4,5],send_messag:5,sender_env:5,sendertag:[2,5],sensit:5,sent:5,sequenc:2,server:2,sess:4,session:[0,1],set:[4,5],shortcut:5,should:2,sinc:[2,4,5],slack:[0,1],slackhandl:4,so:[2,4],special:[2,4],specif:5,specifi:[2,4],src:6,state:2,static_path:6,statu:2,stderr:4,step:4,storag:2,storagesystem:2,str:[2,5,6],string:[2,4,5],structur:5,stub:5,style:5,subclass:4,submodul:0,subnam:4,subpackag:0,subproperti:6,succeed:6,success:[2,5],successmessag:5,suppli:5,support:4,swallow:5,sync:[2,5],synchron:2,system:2,systemid:2,t:4,tacc:[2,5,6],tacconfig:1,take:4,tapi:5,tapis_opt:5,task:2,termin:2,text:[1,2,4,5,6],textstr:2,than:6,thei:[4,5],thi:[2,4,5,6],those:5,time:[1,2,4,5],timeout:2,timestamp:4,tm_gmtoff:4,tm_hour:4,tm_isdst:4,tm_mdai:4,tm_min:4,tm_mon:4,tm_sec:4,tm_wdai:4,tm_ydai:4,tm_year:4,tm_zone:4,to_agave_uri:2,top:5,transform:6,tree:2,tupl:[2,4],type:1,uid:5,up:[2,4,5],updat:[1,2],updatepem:2,upload:2,uploadfil:2,uri:[0,1,5],url:[2,4,5,6],urlparam:5,us:[2,4,5],usag:[0,1,4],useapi:2,user:[5,6],usernam:[2,5],usestim:4,utc:[1,4],utcnow:1,util:0,valid:[0,1,2],validate_binari:[5,6],validate_context:[5,6],validate_docu:6,validate_messag:[5,6],validationerror:6,validator_funct:5,valu:[1,5,6],variabl:5,vars_from_schema:6,verifi:[5,6],version:[0,4],via:2,wa:5,wait:[2,5],wait_for_file_statu:2,walk:2,we:[2,5],webhook:[0,1],what:5,whatev:4,when:4,where:2,whether:[2,6],which:[4,5,6],work:[2,6],world:2,x:2,yet:2,yield:4},titles:["reactors","reactors package","reactors.agaveutils package","reactors.cli package","reactors.logtypes package","reactors.runtime package","reactors.validation package","Welcome to Reactors SDK documentation!"],titleterms:{abaco:5,agaveutil:2,api:7,base:5,binari:6,cli:3,config:1,content:[1,2,3,4,5,6],context:6,document:7,entiti:2,file:2,indic:7,jsondoc:6,loggli:4,loggly_futures_sess:4,logstash:4,logstash_futures_sess:4,logstash_sync:4,logtyp:4,main:4,messag:[5,6],modul:[1,2,3,4,5,6],packag:[1,2,3,4,5,6],reactor:[0,1,2,3,4,5,6,7],recurs:2,refer:7,run:3,runtim:5,sdk:7,session:5,slack:4,submodul:[1,2,3,4,5,6],subpackag:1,tabl:7,uri:2,usag:3,util:[1,2],valid:[5,6],version:1,webhook:5,welcom:7}}) \ No newline at end of file diff --git a/docsrc/Makefile b/docsrc/Makefile index 5b2b9d6..0bf1934 100644 --- a/docsrc/Makefile +++ b/docsrc/Makefile @@ -5,6 +5,7 @@ # from the environment for the first two. GRAPHVIZ_DOT_ARGS ?= -D graphviz_dot_args="-Gratio=compress" SPHINXOPTS ?= $(GRAPHVIZ_DOT_ARGS) +SPHINXAUTOBUILD ?= sphinx-autobuild SPHINXBUILD ?= sphinx-build PKGDIR ?= ../src/reactors SOURCEDIR = . @@ -30,3 +31,5 @@ api-ref: clean: rm -rf $(GITHUB_DIR)/* $(BUILDDIR)/* +livehtml: + @$(SPHINXAUTOBUILD) -b html $(SPHINXOPTS) "$(SOURCEDIR)" "$(BUILDDIR)/html" \ No newline at end of file diff --git a/docsrc/_build/doctrees/api-ref/modules.doctree b/docsrc/_build/doctrees/api-ref/modules.doctree index b426f52..103135a 100644 Binary files a/docsrc/_build/doctrees/api-ref/modules.doctree and b/docsrc/_build/doctrees/api-ref/modules.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.agaveutils.doctree b/docsrc/_build/doctrees/api-ref/reactors.agaveutils.doctree index a36646e..2a46963 100644 Binary files a/docsrc/_build/doctrees/api-ref/reactors.agaveutils.doctree and b/docsrc/_build/doctrees/api-ref/reactors.agaveutils.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.doctree b/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.doctree deleted file mode 100644 index be4e6b3..0000000 Binary files a/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.doctree and /dev/null differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.tests.doctree b/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.tests.doctree deleted file mode 100644 index 0c312c4..0000000 Binary files a/docsrc/_build/doctrees/api-ref/reactors.aliases.agavedb.tests.doctree and /dev/null differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.aliases.doctree b/docsrc/_build/doctrees/api-ref/reactors.aliases.doctree deleted file mode 100644 index 8ea53d9..0000000 Binary files a/docsrc/_build/doctrees/api-ref/reactors.aliases.doctree and /dev/null differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.cli.doctree b/docsrc/_build/doctrees/api-ref/reactors.cli.doctree new file mode 100644 index 0000000..e72781c Binary files /dev/null and b/docsrc/_build/doctrees/api-ref/reactors.cli.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.doctree b/docsrc/_build/doctrees/api-ref/reactors.doctree index 9275bd1..e4be4a8 100644 Binary files a/docsrc/_build/doctrees/api-ref/reactors.doctree and b/docsrc/_build/doctrees/api-ref/reactors.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.logtypes.doctree b/docsrc/_build/doctrees/api-ref/reactors.logtypes.doctree index 2b1a521..08ca8b0 100644 Binary files a/docsrc/_build/doctrees/api-ref/reactors.logtypes.doctree and b/docsrc/_build/doctrees/api-ref/reactors.logtypes.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.runtime.doctree b/docsrc/_build/doctrees/api-ref/reactors.runtime.doctree new file mode 100644 index 0000000..77061c8 Binary files /dev/null and b/docsrc/_build/doctrees/api-ref/reactors.runtime.doctree differ diff --git a/docsrc/_build/doctrees/api-ref/reactors.validation.doctree b/docsrc/_build/doctrees/api-ref/reactors.validation.doctree new file mode 100644 index 0000000..e74ecf6 Binary files /dev/null and b/docsrc/_build/doctrees/api-ref/reactors.validation.doctree differ diff --git a/docsrc/_build/doctrees/environment.pickle b/docsrc/_build/doctrees/environment.pickle index 41a17fb..bc3172e 100644 Binary files a/docsrc/_build/doctrees/environment.pickle and b/docsrc/_build/doctrees/environment.pickle differ diff --git a/docsrc/_build/doctrees/index.doctree b/docsrc/_build/doctrees/index.doctree index 2165056..032f99a 100644 Binary files a/docsrc/_build/doctrees/index.doctree and b/docsrc/_build/doctrees/index.doctree differ diff --git a/docsrc/_build/html/.buildinfo b/docsrc/_build/html/.buildinfo index 78a79ba..b1f188c 100644 --- a/docsrc/_build/html/.buildinfo +++ b/docsrc/_build/html/.buildinfo @@ -1,4 +1,4 @@ # Sphinx build info version 1 # This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done. -config: 69e3b12298528aa9ff69b6802fed3003 +config: 095d582e7e5fa0b1df167abd5045d911 tags: 645f666f9bcd5a90fca523b33c5a78b7 diff --git a/docsrc/_build/html/.doctrees/api-ref/modules.doctree b/docsrc/_build/html/.doctrees/api-ref/modules.doctree new file mode 100644 index 0000000..103135a Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/modules.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.agaveutils.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.agaveutils.doctree new file mode 100644 index 0000000..2a46963 Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.agaveutils.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.cli.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.cli.doctree new file mode 100644 index 0000000..e72781c Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.cli.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.doctree new file mode 100644 index 0000000..e4be4a8 Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.logtypes.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.logtypes.doctree new file mode 100644 index 0000000..08ca8b0 Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.logtypes.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.runtime.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.runtime.doctree new file mode 100644 index 0000000..77061c8 Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.runtime.doctree differ diff --git a/docsrc/_build/html/.doctrees/api-ref/reactors.validation.doctree b/docsrc/_build/html/.doctrees/api-ref/reactors.validation.doctree new file mode 100644 index 0000000..e74ecf6 Binary files /dev/null and b/docsrc/_build/html/.doctrees/api-ref/reactors.validation.doctree differ diff --git a/docsrc/_build/html/.doctrees/environment.pickle b/docsrc/_build/html/.doctrees/environment.pickle new file mode 100644 index 0000000..5b4965f Binary files /dev/null and b/docsrc/_build/html/.doctrees/environment.pickle differ diff --git a/docsrc/_build/html/.doctrees/getting-started/index.doctree b/docsrc/_build/html/.doctrees/getting-started/index.doctree new file mode 100644 index 0000000..e8cd44b Binary files /dev/null and b/docsrc/_build/html/.doctrees/getting-started/index.doctree differ diff --git a/docsrc/_build/html/.doctrees/index.doctree b/docsrc/_build/html/.doctrees/index.doctree new file mode 100644 index 0000000..810a0bc Binary files /dev/null and b/docsrc/_build/html/.doctrees/index.doctree differ diff --git a/docsrc/_build/html/.doctrees/logging/index.doctree b/docsrc/_build/html/.doctrees/logging/index.doctree new file mode 100644 index 0000000..a498ffb Binary files /dev/null and b/docsrc/_build/html/.doctrees/logging/index.doctree differ diff --git a/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.rst.txt deleted file mode 100644 index 71f303d..0000000 --- a/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.rst.txt +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb package -================================ - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb.tests - -Submodules ----------- - -reactors.aliases.agavedb.keyval module --------------------------------------- - -.. automodule:: reactors.aliases.agavedb.keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.uniqueid module ----------------------------------------- - -.. automodule:: reactors.aliases.agavedb.uniqueid - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt deleted file mode 100644 index 6bf5367..0000000 --- a/docsrc/_build/html/_sources/api-ref/reactors.aliases.agavedb.tests.rst.txt +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb.tests package -====================================== - -Submodules ----------- - -reactors.aliases.agavedb.tests.agavefixtures module ---------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.agavefixtures - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.test\_keyval module --------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.test_keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.testdata module ----------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.testdata - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb.tests - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.aliases.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.aliases.rst.txt deleted file mode 100644 index db80925..0000000 --- a/docsrc/_build/html/_sources/api-ref/reactors.aliases.rst.txt +++ /dev/null @@ -1,29 +0,0 @@ -reactors.aliases package -======================== - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb - -Submodules ----------- - -reactors.aliases.store module ------------------------------ - -.. automodule:: reactors.aliases.store - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.cli.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.cli.rst.txt new file mode 100644 index 0000000..b669b8c --- /dev/null +++ b/docsrc/_build/html/_sources/api-ref/reactors.cli.rst.txt @@ -0,0 +1,29 @@ +reactors.cli package +==================== + +Submodules +---------- + +reactors.cli.run module +----------------------- + +.. automodule:: reactors.cli.run + :members: + :undoc-members: + :show-inheritance: + +reactors.cli.usage module +------------------------- + +.. automodule:: reactors.cli.usage + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.cli + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.logtypes.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.logtypes.rst.txt index e9aaf9f..d00a94f 100644 --- a/docsrc/_build/html/_sources/api-ref/reactors.logtypes.rst.txt +++ b/docsrc/_build/html/_sources/api-ref/reactors.logtypes.rst.txt @@ -4,18 +4,26 @@ reactors.logtypes package Submodules ---------- -reactors.logtypes.logstash module ---------------------------------- +reactors.logtypes.loggly module +------------------------------- -.. automodule:: reactors.logtypes.logstash +.. automodule:: reactors.logtypes.loggly :members: :undoc-members: :show-inheritance: -reactors.logtypes.logstash\_asyncio module ------------------------------------------- +reactors.logtypes.loggly\_futures\_session module +------------------------------------------------- -.. automodule:: reactors.logtypes.logstash_asyncio +.. automodule:: reactors.logtypes.loggly_futures_session + :members: + :undoc-members: + :show-inheritance: + +reactors.logtypes.logstash module +--------------------------------- + +.. automodule:: reactors.logtypes.logstash :members: :undoc-members: :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.rst.txt index aba558d..f5c0b2e 100644 --- a/docsrc/_build/html/_sources/api-ref/reactors.rst.txt +++ b/docsrc/_build/html/_sources/api-ref/reactors.rst.txt @@ -8,48 +8,18 @@ Subpackages :maxdepth: 4 reactors.agaveutils - reactors.aliases + reactors.cli reactors.logtypes + reactors.runtime + reactors.validation Submodules ---------- -reactors.jsonmessages module ----------------------------- +reactors.config module +---------------------- -.. automodule:: reactors.jsonmessages - :members: - :undoc-members: - :show-inheritance: - -reactors.process module ------------------------ - -.. automodule:: reactors.process - :members: - :undoc-members: - :show-inheritance: - -reactors.runtime module ------------------------ - -.. automodule:: reactors.runtime - :members: - :undoc-members: - :show-inheritance: - -reactors.storage module ------------------------ - -.. automodule:: reactors.storage - :members: - :undoc-members: - :show-inheritance: - -reactors.uniqueid module ------------------------- - -.. automodule:: reactors.uniqueid +.. automodule:: reactors.config :members: :undoc-members: :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.runtime.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.runtime.rst.txt new file mode 100644 index 0000000..853efa1 --- /dev/null +++ b/docsrc/_build/html/_sources/api-ref/reactors.runtime.rst.txt @@ -0,0 +1,69 @@ +reactors.runtime package +======================== + +Submodules +---------- + +reactors.runtime.abaco module +----------------------------- + +.. automodule:: reactors.runtime.abaco + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.base module +---------------------------- + +.. automodule:: reactors.runtime.base + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.messaging module +--------------------------------- + +.. automodule:: reactors.runtime.messaging + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.reactor module +------------------------------- + +.. automodule:: reactors.runtime.reactor + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.sessions module +-------------------------------- + +.. automodule:: reactors.runtime.sessions + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.validating module +---------------------------------- + +.. automodule:: reactors.runtime.validating + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.webhooks module +-------------------------------- + +.. automodule:: reactors.runtime.webhooks + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.runtime + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/_build/html/_sources/api-ref/reactors.validation.rst.txt b/docsrc/_build/html/_sources/api-ref/reactors.validation.rst.txt new file mode 100644 index 0000000..0225729 --- /dev/null +++ b/docsrc/_build/html/_sources/api-ref/reactors.validation.rst.txt @@ -0,0 +1,45 @@ +reactors.validation package +=========================== + +Submodules +---------- + +reactors.validation.binary module +--------------------------------- + +.. automodule:: reactors.validation.binary + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.context module +---------------------------------- + +.. automodule:: reactors.validation.context + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.jsondoc module +---------------------------------- + +.. automodule:: reactors.validation.jsondoc + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.message module +---------------------------------- + +.. automodule:: reactors.validation.message + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.validation + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/_build/html/_sources/getting-started/index.md.txt b/docsrc/_build/html/_sources/getting-started/index.md.txt new file mode 100644 index 0000000..9b7c248 --- /dev/null +++ b/docsrc/_build/html/_sources/getting-started/index.md.txt @@ -0,0 +1,3 @@ +# Getting Started + +This tutorial will provide a quick tutorial for usage of the `python-reactors` package. \ No newline at end of file diff --git a/docsrc/_build/html/_sources/index.rst.txt b/docsrc/_build/html/_sources/index.rst.txt index 5e7fc37..ed81c70 100644 --- a/docsrc/_build/html/_sources/index.rst.txt +++ b/docsrc/_build/html/_sources/index.rst.txt @@ -8,7 +8,15 @@ Welcome to Reactors SDK documentation! .. toctree:: :maxdepth: 2 - :caption: API Reference: + :caption: Reactors SDK + + getting-started/index.md + logging/index.md + + +.. toctree:: + :maxdepth: 2 + :caption: API Reference api-ref/modules.rst diff --git a/docsrc/_build/html/_sources/logging/index.md.txt b/docsrc/_build/html/_sources/logging/index.md.txt new file mode 100644 index 0000000..9f0f036 --- /dev/null +++ b/docsrc/_build/html/_sources/logging/index.md.txt @@ -0,0 +1,3 @@ +# Logging with Reactors + +In this section, we will review logging with Reactors, including logging to 3rd party services such as Slack and Loggly. \ No newline at end of file diff --git a/docsrc/_build/html/_static/basic.css b/docsrc/_build/html/_static/basic.css index 24bc73e..912859b 100644 --- a/docsrc/_build/html/_static/basic.css +++ b/docsrc/_build/html/_static/basic.css @@ -4,7 +4,7 @@ * * Sphinx stylesheet -- basic theme. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ @@ -130,7 +130,7 @@ ul.search li a { font-weight: bold; } -ul.search li div.context { +ul.search li p.context { color: #888; margin: 2px 0 0 30px; text-align: left; @@ -277,25 +277,25 @@ p.rubric { font-weight: bold; } -img.align-left, .figure.align-left, object.align-left { +img.align-left, figure.align-left, .figure.align-left, object.align-left { clear: left; float: left; margin-right: 1em; } -img.align-right, .figure.align-right, object.align-right { +img.align-right, figure.align-right, .figure.align-right, object.align-right { clear: right; float: right; margin-left: 1em; } -img.align-center, .figure.align-center, object.align-center { +img.align-center, figure.align-center, .figure.align-center, object.align-center { display: block; margin-left: auto; margin-right: auto; } -img.align-default, .figure.align-default { +img.align-default, figure.align-default, .figure.align-default { display: block; margin-left: auto; margin-right: auto; @@ -319,7 +319,8 @@ img.align-default, .figure.align-default { /* -- sidebars -------------------------------------------------------------- */ -div.sidebar { +div.sidebar, +aside.sidebar { margin: 0 0 0.5em 1em; border: 1px solid #ddb; padding: 7px; @@ -377,12 +378,14 @@ div.body p.centered { /* -- content of sidebars/topics/admonitions -------------------------------- */ div.sidebar > :last-child, +aside.sidebar > :last-child, div.topic > :last-child, div.admonition > :last-child { margin-bottom: 0; } div.sidebar::after, +aside.sidebar::after, div.topic::after, div.admonition::after, blockquote::after { @@ -455,20 +458,22 @@ td > :last-child { /* -- figures --------------------------------------------------------------- */ -div.figure { +div.figure, figure { margin: 0.5em; padding: 0.5em; } -div.figure p.caption { +div.figure p.caption, figcaption { padding: 0.3em; } -div.figure p.caption span.caption-number { +div.figure p.caption span.caption-number, +figcaption span.caption-number { font-style: italic; } -div.figure p.caption span.caption-text { +div.figure p.caption span.caption-text, +figcaption span.caption-text { } /* -- field list styles ----------------------------------------------------- */ @@ -503,6 +508,63 @@ table.hlist td { vertical-align: top; } +/* -- object description styles --------------------------------------------- */ + +.sig { + font-family: 'Consolas', 'Menlo', 'DejaVu Sans Mono', 'Bitstream Vera Sans Mono', monospace; +} + +.sig-name, code.descname { + background-color: transparent; + font-weight: bold; +} + +.sig-name { + font-size: 1.1em; +} + +code.descname { + font-size: 1.2em; +} + +.sig-prename, code.descclassname { + background-color: transparent; +} + +.optional { + font-size: 1.3em; +} + +.sig-paren { + font-size: larger; +} + +.sig-param.n { + font-style: italic; +} + +/* C++ specific styling */ + +.sig-inline.c-texpr, +.sig-inline.cpp-texpr { + font-family: unset; +} + +.sig.c .k, .sig.c .kt, +.sig.cpp .k, .sig.cpp .kt { + color: #0033B3; +} + +.sig.c .m, +.sig.cpp .m { + color: #1750EB; +} + +.sig.c .s, .sig.c .sc, +.sig.cpp .s, .sig.cpp .sc { + color: #067D17; +} + /* -- other body styles ----------------------------------------------------- */ @@ -629,14 +691,6 @@ dl.glossary dt { font-size: 1.1em; } -.optional { - font-size: 1.3em; -} - -.sig-paren { - font-size: larger; -} - .versionmodified { font-style: italic; } @@ -764,8 +818,13 @@ div.code-block-caption code { } table.highlighttable td.linenos, -div.doctest > div.highlight span.gp { /* gp: Generic.Prompt */ - user-select: none; +span.linenos, +div.highlight span.gp { /* gp: Generic.Prompt */ + user-select: none; + -webkit-user-select: text; /* Safari fallback only */ + -webkit-user-select: none; /* Chrome/Safari */ + -moz-user-select: none; /* Firefox */ + -ms-user-select: none; /* IE10+ */ } div.code-block-caption span.caption-number { @@ -780,16 +839,6 @@ div.literal-block-wrapper { margin: 1em 0; } -code.descname { - background-color: transparent; - font-weight: bold; - font-size: 1.2em; -} - -code.descclassname { - background-color: transparent; -} - code.xref, a code { background-color: transparent; font-weight: bold; diff --git a/docsrc/_build/html/_static/classic.css b/docsrc/_build/html/_static/classic.css deleted file mode 100644 index cceb67a..0000000 --- a/docsrc/_build/html/_static/classic.css +++ /dev/null @@ -1,266 +0,0 @@ -/* - * classic.css_t - * ~~~~~~~~~~~~~ - * - * Sphinx stylesheet -- classic theme. - * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ - -@import url("basic.css"); - -/* -- page layout ----------------------------------------------------------- */ - -html { - /* CSS hack for macOS's scrollbar (see #1125) */ - background-color: #FFFFFF; -} - -body { - font-family: sans-serif; - font-size: 100%; - background-color: #11303d; - color: #000; - margin: 0; - padding: 0; -} - -div.document { - background-color: #1c4e63; -} - -div.documentwrapper { - float: left; - width: 100%; -} - -div.bodywrapper { - margin: 0 0 0 230px; -} - -div.body { - background-color: #ffffff; - color: #000000; - padding: 0 20px 30px 20px; -} - -div.footer { - color: #ffffff; - width: 100%; - padding: 9px 0 9px 0; - text-align: center; - font-size: 75%; -} - -div.footer a { - color: #ffffff; - text-decoration: underline; -} - -div.related { - background-color: #133f52; - line-height: 30px; - color: #ffffff; -} - -div.related a { - color: #ffffff; -} - -div.sphinxsidebar { -} - -div.sphinxsidebar h3 { - font-family: 'Trebuchet MS', sans-serif; - color: #ffffff; - font-size: 1.4em; - font-weight: normal; - margin: 0; - padding: 0; -} - -div.sphinxsidebar h3 a { - color: #ffffff; -} - -div.sphinxsidebar h4 { - font-family: 'Trebuchet MS', sans-serif; - color: #ffffff; - font-size: 1.3em; - font-weight: normal; - margin: 5px 0 0 0; - padding: 0; -} - -div.sphinxsidebar p { - color: #ffffff; -} - -div.sphinxsidebar p.topless { - margin: 5px 10px 10px 10px; -} - -div.sphinxsidebar ul { - margin: 10px; - padding: 0; - color: #ffffff; -} - -div.sphinxsidebar a { - color: #98dbcc; -} - -div.sphinxsidebar input { - border: 1px solid #98dbcc; - font-family: sans-serif; - font-size: 1em; -} - - - -/* -- hyperlink styles ------------------------------------------------------ */ - -a { - color: #355f7c; - text-decoration: none; -} - -a:visited { - color: #355f7c; - text-decoration: none; -} - -a:hover { - text-decoration: underline; -} - - - -/* -- body styles ----------------------------------------------------------- */ - -div.body h1, -div.body h2, -div.body h3, -div.body h4, -div.body h5, -div.body h6 { - font-family: 'Trebuchet MS', sans-serif; - background-color: #f2f2f2; - font-weight: normal; - color: #20435c; - border-bottom: 1px solid #ccc; - margin: 20px -20px 10px -20px; - padding: 3px 0 3px 10px; -} - -div.body h1 { margin-top: 0; font-size: 200%; } -div.body h2 { font-size: 160%; } -div.body h3 { font-size: 140%; } -div.body h4 { font-size: 120%; } -div.body h5 { font-size: 110%; } -div.body h6 { font-size: 100%; } - -a.headerlink { - color: #c60f0f; - font-size: 0.8em; - padding: 0 4px 0 4px; - text-decoration: none; -} - -a.headerlink:hover { - background-color: #c60f0f; - color: white; -} - -div.body p, div.body dd, div.body li, div.body blockquote { - text-align: justify; - line-height: 130%; -} - -div.admonition p.admonition-title + p { - display: inline; -} - -div.admonition p { - margin-bottom: 5px; -} - -div.admonition pre { - margin-bottom: 5px; -} - -div.admonition ul, div.admonition ol { - margin-bottom: 5px; -} - -div.note { - background-color: #eee; - border: 1px solid #ccc; -} - -div.seealso { - background-color: #ffc; - border: 1px solid #ff6; -} - -div.topic { - background-color: #eee; -} - -div.warning { - background-color: #ffe4e4; - border: 1px solid #f66; -} - -p.admonition-title { - display: inline; -} - -p.admonition-title:after { - content: ":"; -} - -pre { - padding: 5px; - background-color: unset; - color: unset; - line-height: 120%; - border: 1px solid #ac9; - border-left: none; - border-right: none; -} - -code { - background-color: #ecf0f3; - padding: 0 1px 0 1px; - font-size: 0.95em; -} - -th, dl.field-list > dt { - background-color: #ede; -} - -.warning code { - background: #efc2c2; -} - -.note code { - background: #d6d6d6; -} - -.viewcode-back { - font-family: sans-serif; -} - -div.viewcode-block:target { - background-color: #f4debf; - border-top: 1px solid #ac9; - border-bottom: 1px solid #ac9; -} - -div.code-block-caption { - color: #efefef; - background-color: #1c4e63; -} \ No newline at end of file diff --git a/docsrc/_build/html/_static/css/badge_only.css b/docsrc/_build/html/_static/css/badge_only.css new file mode 100644 index 0000000..e380325 --- /dev/null +++ b/docsrc/_build/html/_static/css/badge_only.css @@ -0,0 +1 @@ +.fa:before{-webkit-font-smoothing:antialiased}.clearfix{*zoom:1}.clearfix:after,.clearfix:before{display:table;content:""}.clearfix:after{clear:both}@font-face{font-family:FontAwesome;font-style:normal;font-weight:400;src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713?#iefix) format("embedded-opentype"),url(fonts/fontawesome-webfont.woff2?af7ae505a9eed503f8b8e6982036873e) format("woff2"),url(fonts/fontawesome-webfont.woff?fee66e712a8a08eef5805a46892932ad) format("woff"),url(fonts/fontawesome-webfont.ttf?b06871f281fee6b241d60582ae9369b9) format("truetype"),url(fonts/fontawesome-webfont.svg?912ec66d7572ff821749319396470bde#FontAwesome) format("svg")}.fa:before{font-family:FontAwesome;font-style:normal;font-weight:400;line-height:1}.fa:before,a .fa{text-decoration:inherit}.fa:before,a .fa,li .fa{display:inline-block}li .fa-large:before{width:1.875em}ul.fas{list-style-type:none;margin-left:2em;text-indent:-.8em}ul.fas li .fa{width:.8em}ul.fas li .fa-large:before{vertical-align:baseline}.fa-book:before,.icon-book:before{content:"\f02d"}.fa-caret-down:before,.icon-caret-down:before{content:"\f0d7"}.fa-caret-up:before,.icon-caret-up:before{content:"\f0d8"}.fa-caret-left:before,.icon-caret-left:before{content:"\f0d9"}.fa-caret-right:before,.icon-caret-right:before{content:"\f0da"}.rst-versions{position:fixed;bottom:0;left:0;width:300px;color:#fcfcfc;background:#1f1d1d;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;z-index:400}.rst-versions a{color:#2980b9;text-decoration:none}.rst-versions .rst-badge-small{display:none}.rst-versions .rst-current-version{padding:12px;background-color:#272525;display:block;text-align:right;font-size:90%;cursor:pointer;color:#27ae60}.rst-versions .rst-current-version:after{clear:both;content:"";display:block}.rst-versions .rst-current-version .fa{color:#fcfcfc}.rst-versions .rst-current-version .fa-book,.rst-versions .rst-current-version .icon-book{float:left}.rst-versions .rst-current-version.rst-out-of-date{background-color:#e74c3c;color:#fff}.rst-versions .rst-current-version.rst-active-old-version{background-color:#f1c40f;color:#000}.rst-versions.shift-up{height:auto;max-height:100%;overflow-y:scroll}.rst-versions.shift-up .rst-other-versions{display:block}.rst-versions .rst-other-versions{font-size:90%;padding:12px;color:grey;display:none}.rst-versions .rst-other-versions hr{display:block;height:1px;border:0;margin:20px 0;padding:0;border-top:1px solid #413d3d}.rst-versions .rst-other-versions dd{display:inline-block;margin:0}.rst-versions .rst-other-versions dd a{display:inline-block;padding:6px;color:#fcfcfc}.rst-versions.rst-badge{width:auto;bottom:20px;right:20px;left:auto;border:none;max-width:300px;max-height:90%}.rst-versions.rst-badge .fa-book,.rst-versions.rst-badge .icon-book{float:none;line-height:30px}.rst-versions.rst-badge.shift-up .rst-current-version{text-align:right}.rst-versions.rst-badge.shift-up .rst-current-version .fa-book,.rst-versions.rst-badge.shift-up .rst-current-version .icon-book{float:left}.rst-versions.rst-badge>.rst-current-version{width:auto;height:30px;line-height:30px;padding:0 6px;display:block;text-align:center}@media screen and (max-width:768px){.rst-versions{width:85%;display:none}.rst-versions.shift{display:block}} \ No newline at end of file diff --git a/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff new file mode 100644 index 0000000..6cb6000 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff2 b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff2 new file mode 100644 index 0000000..7059e23 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Bold.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff new file mode 100644 index 0000000..f815f63 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff2 b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff2 new file mode 100644 index 0000000..f2c76e5 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/Roboto-Slab-Regular.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.eot b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.eot new file mode 100644 index 0000000..e9f60ca Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.eot differ diff --git a/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.svg b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.svg new file mode 100644 index 0000000..855c845 --- /dev/null +++ b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.svg @@ -0,0 +1,2671 @@ + + + + +Created by FontForge 20120731 at Mon Oct 24 17:37:40 2016 + By ,,, +Copyright Dave Gandy 2016. All rights reserved. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.ttf b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.ttf new file mode 100644 index 0000000..35acda2 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.ttf differ diff --git a/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff new file mode 100644 index 0000000..400014a Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff2 b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff2 new file mode 100644 index 0000000..4d13fc6 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/fontawesome-webfont.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff b/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff new file mode 100644 index 0000000..88ad05b Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff2 b/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff2 new file mode 100644 index 0000000..c4e3d80 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-bold-italic.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-bold.woff b/docsrc/_build/html/_static/css/fonts/lato-bold.woff new file mode 100644 index 0000000..c6dff51 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-bold.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-bold.woff2 b/docsrc/_build/html/_static/css/fonts/lato-bold.woff2 new file mode 100644 index 0000000..bb19504 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-bold.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff b/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff new file mode 100644 index 0000000..76114bc Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff2 b/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff2 new file mode 100644 index 0000000..3404f37 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-normal-italic.woff2 differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-normal.woff b/docsrc/_build/html/_static/css/fonts/lato-normal.woff new file mode 100644 index 0000000..ae1307f Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-normal.woff differ diff --git a/docsrc/_build/html/_static/css/fonts/lato-normal.woff2 b/docsrc/_build/html/_static/css/fonts/lato-normal.woff2 new file mode 100644 index 0000000..3bf9843 Binary files /dev/null and b/docsrc/_build/html/_static/css/fonts/lato-normal.woff2 differ diff --git a/docsrc/_build/html/_static/css/theme.css b/docsrc/_build/html/_static/css/theme.css new file mode 100644 index 0000000..0d9ae7e --- /dev/null +++ b/docsrc/_build/html/_static/css/theme.css @@ -0,0 +1,4 @@ +html{box-sizing:border-box}*,:after,:before{box-sizing:inherit}article,aside,details,figcaption,figure,footer,header,hgroup,nav,section{display:block}audio,canvas,video{display:inline-block;*display:inline;*zoom:1}[hidden],audio:not([controls]){display:none}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:100%;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}body{margin:0}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:700}blockquote{margin:0}dfn{font-style:italic}ins{background:#ff9;text-decoration:none}ins,mark{color:#000}mark{background:#ff0;font-style:italic;font-weight:700}.rst-content code,.rst-content tt,code,kbd,pre,samp{font-family:monospace,serif;_font-family:courier new,monospace;font-size:1em}pre{white-space:pre}q{quotes:none}q:after,q:before{content:"";content:none}small{font-size:85%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sup{top:-.5em}sub{bottom:-.25em}dl,ol,ul{margin:0;padding:0;list-style:none;list-style-image:none}li{list-style:none}dd{margin:0}img{border:0;-ms-interpolation-mode:bicubic;vertical-align:middle;max-width:100%}svg:not(:root){overflow:hidden}figure,form{margin:0}label{cursor:pointer}button,input,select,textarea{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle}button,input{line-height:normal}button,input[type=button],input[type=reset],input[type=submit]{cursor:pointer;-webkit-appearance:button;*overflow:visible}button[disabled],input[disabled]{cursor:default}input[type=search]{-webkit-appearance:textfield;-moz-box-sizing:content-box;-webkit-box-sizing:content-box;box-sizing:content-box}textarea{resize:vertical}table{border-collapse:collapse;border-spacing:0}td{vertical-align:top}.chromeframe{margin:.2em 0;background:#ccc;color:#000;padding:.2em 0}.ir{display:block;border:0;text-indent:-999em;overflow:hidden;background-color:transparent;background-repeat:no-repeat;text-align:left;direction:ltr;*line-height:0}.ir br{display:none}.hidden{display:none!important;visibility:hidden}.visuallyhidden{border:0;clip:rect(0 0 0 0);height:1px;margin:-1px;overflow:hidden;padding:0;position:absolute;width:1px}.visuallyhidden.focusable:active,.visuallyhidden.focusable:focus{clip:auto;height:auto;margin:0;overflow:visible;position:static;width:auto}.invisible{visibility:hidden}.relative{position:relative}big,small{font-size:100%}@media print{body,html,section{background:none!important}*{box-shadow:none!important;text-shadow:none!important;filter:none!important;-ms-filter:none!important}a,a:visited{text-decoration:underline}.ir a:after,a[href^="#"]:after,a[href^="javascript:"]:after{content:""}blockquote,pre{page-break-inside:avoid}thead{display:table-header-group}img,tr{page-break-inside:avoid}img{max-width:100%!important}@page{margin:.5cm}.rst-content .toctree-wrapper>p.caption,h2,h3,p{orphans:3;widows:3}.rst-content .toctree-wrapper>p.caption,h2,h3{page-break-after:avoid}}.btn,.fa:before,.icon:before,.rst-content .admonition,.rst-content .admonition-title:before,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .code-block-caption .headerlink:before,.rst-content .danger,.rst-content .eqno .headerlink:before,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning,.rst-content code.download span:first-child:before,.rst-content dl dt .headerlink:before,.rst-content h1 .headerlink:before,.rst-content h2 .headerlink:before,.rst-content h3 .headerlink:before,.rst-content h4 .headerlink:before,.rst-content h5 .headerlink:before,.rst-content h6 .headerlink:before,.rst-content p.caption .headerlink:before,.rst-content p .headerlink:before,.rst-content table>caption .headerlink:before,.rst-content tt.download span:first-child:before,.wy-alert,.wy-dropdown .caret:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before,.wy-menu-vertical li.current>a,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a,.wy-menu-vertical li.on a button.toctree-expand:before,.wy-menu-vertical li button.toctree-expand:before,.wy-nav-top a,.wy-side-nav-search .wy-dropdown>a,.wy-side-nav-search>a,input[type=color],input[type=date],input[type=datetime-local],input[type=datetime],input[type=email],input[type=month],input[type=number],input[type=password],input[type=search],input[type=tel],input[type=text],input[type=time],input[type=url],input[type=week],select,textarea{-webkit-font-smoothing:antialiased}.clearfix{*zoom:1}.clearfix:after,.clearfix:before{display:table;content:""}.clearfix:after{clear:both}/*! + * Font Awesome 4.7.0 by @davegandy - http://fontawesome.io - @fontawesome + * License - http://fontawesome.io/license (Font: SIL OFL 1.1, CSS: MIT License) + */@font-face{font-family:FontAwesome;src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713);src:url(fonts/fontawesome-webfont.eot?674f50d287a8c48dc19ba404d20fe713?#iefix&v=4.7.0) format("embedded-opentype"),url(fonts/fontawesome-webfont.woff2?af7ae505a9eed503f8b8e6982036873e) format("woff2"),url(fonts/fontawesome-webfont.woff?fee66e712a8a08eef5805a46892932ad) format("woff"),url(fonts/fontawesome-webfont.ttf?b06871f281fee6b241d60582ae9369b9) format("truetype"),url(fonts/fontawesome-webfont.svg?912ec66d7572ff821749319396470bde#fontawesomeregular) format("svg");font-weight:400;font-style:normal}.fa,.icon,.rst-content .admonition-title,.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content code.download span:first-child,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink,.rst-content tt.download span:first-child,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li button.toctree-expand{display:inline-block;font:normal normal normal 14px/1 FontAwesome;font-size:inherit;text-rendering:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.fa-lg{font-size:1.33333em;line-height:.75em;vertical-align:-15%}.fa-2x{font-size:2em}.fa-3x{font-size:3em}.fa-4x{font-size:4em}.fa-5x{font-size:5em}.fa-fw{width:1.28571em;text-align:center}.fa-ul{padding-left:0;margin-left:2.14286em;list-style-type:none}.fa-ul>li{position:relative}.fa-li{position:absolute;left:-2.14286em;width:2.14286em;top:.14286em;text-align:center}.fa-li.fa-lg{left:-1.85714em}.fa-border{padding:.2em .25em .15em;border:.08em solid #eee;border-radius:.1em}.fa-pull-left{float:left}.fa-pull-right{float:right}.fa-pull-left.icon,.fa.fa-pull-left,.rst-content .code-block-caption .fa-pull-left.headerlink,.rst-content .eqno .fa-pull-left.headerlink,.rst-content .fa-pull-left.admonition-title,.rst-content code.download span.fa-pull-left:first-child,.rst-content dl dt .fa-pull-left.headerlink,.rst-content h1 .fa-pull-left.headerlink,.rst-content h2 .fa-pull-left.headerlink,.rst-content h3 .fa-pull-left.headerlink,.rst-content h4 .fa-pull-left.headerlink,.rst-content h5 .fa-pull-left.headerlink,.rst-content h6 .fa-pull-left.headerlink,.rst-content p .fa-pull-left.headerlink,.rst-content table>caption .fa-pull-left.headerlink,.rst-content tt.download span.fa-pull-left:first-child,.wy-menu-vertical li.current>a button.fa-pull-left.toctree-expand,.wy-menu-vertical li.on a button.fa-pull-left.toctree-expand,.wy-menu-vertical li button.fa-pull-left.toctree-expand{margin-right:.3em}.fa-pull-right.icon,.fa.fa-pull-right,.rst-content .code-block-caption .fa-pull-right.headerlink,.rst-content .eqno .fa-pull-right.headerlink,.rst-content .fa-pull-right.admonition-title,.rst-content code.download span.fa-pull-right:first-child,.rst-content dl dt .fa-pull-right.headerlink,.rst-content h1 .fa-pull-right.headerlink,.rst-content h2 .fa-pull-right.headerlink,.rst-content h3 .fa-pull-right.headerlink,.rst-content h4 .fa-pull-right.headerlink,.rst-content h5 .fa-pull-right.headerlink,.rst-content h6 .fa-pull-right.headerlink,.rst-content p .fa-pull-right.headerlink,.rst-content table>caption .fa-pull-right.headerlink,.rst-content tt.download span.fa-pull-right:first-child,.wy-menu-vertical li.current>a button.fa-pull-right.toctree-expand,.wy-menu-vertical li.on a button.fa-pull-right.toctree-expand,.wy-menu-vertical li button.fa-pull-right.toctree-expand{margin-left:.3em}.pull-right{float:right}.pull-left{float:left}.fa.pull-left,.pull-left.icon,.rst-content .code-block-caption .pull-left.headerlink,.rst-content .eqno .pull-left.headerlink,.rst-content .pull-left.admonition-title,.rst-content code.download span.pull-left:first-child,.rst-content dl dt .pull-left.headerlink,.rst-content h1 .pull-left.headerlink,.rst-content h2 .pull-left.headerlink,.rst-content h3 .pull-left.headerlink,.rst-content h4 .pull-left.headerlink,.rst-content h5 .pull-left.headerlink,.rst-content h6 .pull-left.headerlink,.rst-content p .pull-left.headerlink,.rst-content table>caption .pull-left.headerlink,.rst-content tt.download span.pull-left:first-child,.wy-menu-vertical li.current>a button.pull-left.toctree-expand,.wy-menu-vertical li.on a button.pull-left.toctree-expand,.wy-menu-vertical li button.pull-left.toctree-expand{margin-right:.3em}.fa.pull-right,.pull-right.icon,.rst-content .code-block-caption .pull-right.headerlink,.rst-content .eqno .pull-right.headerlink,.rst-content .pull-right.admonition-title,.rst-content code.download span.pull-right:first-child,.rst-content dl dt .pull-right.headerlink,.rst-content h1 .pull-right.headerlink,.rst-content h2 .pull-right.headerlink,.rst-content h3 .pull-right.headerlink,.rst-content h4 .pull-right.headerlink,.rst-content h5 .pull-right.headerlink,.rst-content h6 .pull-right.headerlink,.rst-content p .pull-right.headerlink,.rst-content table>caption .pull-right.headerlink,.rst-content tt.download span.pull-right:first-child,.wy-menu-vertical li.current>a button.pull-right.toctree-expand,.wy-menu-vertical li.on a button.pull-right.toctree-expand,.wy-menu-vertical li button.pull-right.toctree-expand{margin-left:.3em}.fa-spin{-webkit-animation:fa-spin 2s linear infinite;animation:fa-spin 2s linear infinite}.fa-pulse{-webkit-animation:fa-spin 1s steps(8) infinite;animation:fa-spin 1s steps(8) infinite}@-webkit-keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}to{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}@keyframes fa-spin{0%{-webkit-transform:rotate(0deg);transform:rotate(0deg)}to{-webkit-transform:rotate(359deg);transform:rotate(359deg)}}.fa-rotate-90{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=1)";-webkit-transform:rotate(90deg);-ms-transform:rotate(90deg);transform:rotate(90deg)}.fa-rotate-180{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2)";-webkit-transform:rotate(180deg);-ms-transform:rotate(180deg);transform:rotate(180deg)}.fa-rotate-270{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=3)";-webkit-transform:rotate(270deg);-ms-transform:rotate(270deg);transform:rotate(270deg)}.fa-flip-horizontal{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=0, mirror=1)";-webkit-transform:scaleX(-1);-ms-transform:scaleX(-1);transform:scaleX(-1)}.fa-flip-vertical{-ms-filter:"progid:DXImageTransform.Microsoft.BasicImage(rotation=2, mirror=1)";-webkit-transform:scaleY(-1);-ms-transform:scaleY(-1);transform:scaleY(-1)}:root .fa-flip-horizontal,:root .fa-flip-vertical,:root .fa-rotate-90,:root .fa-rotate-180,:root .fa-rotate-270{filter:none}.fa-stack{position:relative;display:inline-block;width:2em;height:2em;line-height:2em;vertical-align:middle}.fa-stack-1x,.fa-stack-2x{position:absolute;left:0;width:100%;text-align:center}.fa-stack-1x{line-height:inherit}.fa-stack-2x{font-size:2em}.fa-inverse{color:#fff}.fa-glass:before{content:""}.fa-music:before{content:""}.fa-search:before,.icon-search:before{content:""}.fa-envelope-o:before{content:""}.fa-heart:before{content:""}.fa-star:before{content:""}.fa-star-o:before{content:""}.fa-user:before{content:""}.fa-film:before{content:""}.fa-th-large:before{content:""}.fa-th:before{content:""}.fa-th-list:before{content:""}.fa-check:before{content:""}.fa-close:before,.fa-remove:before,.fa-times:before{content:""}.fa-search-plus:before{content:""}.fa-search-minus:before{content:""}.fa-power-off:before{content:""}.fa-signal:before{content:""}.fa-cog:before,.fa-gear:before{content:""}.fa-trash-o:before{content:""}.fa-home:before,.icon-home:before{content:""}.fa-file-o:before{content:""}.fa-clock-o:before{content:""}.fa-road:before{content:""}.fa-download:before,.rst-content code.download span:first-child:before,.rst-content tt.download span:first-child:before{content:""}.fa-arrow-circle-o-down:before{content:""}.fa-arrow-circle-o-up:before{content:""}.fa-inbox:before{content:""}.fa-play-circle-o:before{content:""}.fa-repeat:before,.fa-rotate-right:before{content:""}.fa-refresh:before{content:""}.fa-list-alt:before{content:""}.fa-lock:before{content:""}.fa-flag:before{content:""}.fa-headphones:before{content:""}.fa-volume-off:before{content:""}.fa-volume-down:before{content:""}.fa-volume-up:before{content:""}.fa-qrcode:before{content:""}.fa-barcode:before{content:""}.fa-tag:before{content:""}.fa-tags:before{content:""}.fa-book:before,.icon-book:before{content:""}.fa-bookmark:before{content:""}.fa-print:before{content:""}.fa-camera:before{content:""}.fa-font:before{content:""}.fa-bold:before{content:""}.fa-italic:before{content:""}.fa-text-height:before{content:""}.fa-text-width:before{content:""}.fa-align-left:before{content:""}.fa-align-center:before{content:""}.fa-align-right:before{content:""}.fa-align-justify:before{content:""}.fa-list:before{content:""}.fa-dedent:before,.fa-outdent:before{content:""}.fa-indent:before{content:""}.fa-video-camera:before{content:""}.fa-image:before,.fa-photo:before,.fa-picture-o:before{content:""}.fa-pencil:before{content:""}.fa-map-marker:before{content:""}.fa-adjust:before{content:""}.fa-tint:before{content:""}.fa-edit:before,.fa-pencil-square-o:before{content:""}.fa-share-square-o:before{content:""}.fa-check-square-o:before{content:""}.fa-arrows:before{content:""}.fa-step-backward:before{content:""}.fa-fast-backward:before{content:""}.fa-backward:before{content:""}.fa-play:before{content:""}.fa-pause:before{content:""}.fa-stop:before{content:""}.fa-forward:before{content:""}.fa-fast-forward:before{content:""}.fa-step-forward:before{content:""}.fa-eject:before{content:""}.fa-chevron-left:before{content:""}.fa-chevron-right:before{content:""}.fa-plus-circle:before{content:""}.fa-minus-circle:before{content:""}.fa-times-circle:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before{content:""}.fa-check-circle:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before{content:""}.fa-question-circle:before{content:""}.fa-info-circle:before{content:""}.fa-crosshairs:before{content:""}.fa-times-circle-o:before{content:""}.fa-check-circle-o:before{content:""}.fa-ban:before{content:""}.fa-arrow-left:before{content:""}.fa-arrow-right:before{content:""}.fa-arrow-up:before{content:""}.fa-arrow-down:before{content:""}.fa-mail-forward:before,.fa-share:before{content:""}.fa-expand:before{content:""}.fa-compress:before{content:""}.fa-plus:before{content:""}.fa-minus:before{content:""}.fa-asterisk:before{content:""}.fa-exclamation-circle:before,.rst-content .admonition-title:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before{content:""}.fa-gift:before{content:""}.fa-leaf:before{content:""}.fa-fire:before,.icon-fire:before{content:""}.fa-eye:before{content:""}.fa-eye-slash:before{content:""}.fa-exclamation-triangle:before,.fa-warning:before{content:""}.fa-plane:before{content:""}.fa-calendar:before{content:""}.fa-random:before{content:""}.fa-comment:before{content:""}.fa-magnet:before{content:""}.fa-chevron-up:before{content:""}.fa-chevron-down:before{content:""}.fa-retweet:before{content:""}.fa-shopping-cart:before{content:""}.fa-folder:before{content:""}.fa-folder-open:before{content:""}.fa-arrows-v:before{content:""}.fa-arrows-h:before{content:""}.fa-bar-chart-o:before,.fa-bar-chart:before{content:""}.fa-twitter-square:before{content:""}.fa-facebook-square:before{content:""}.fa-camera-retro:before{content:""}.fa-key:before{content:""}.fa-cogs:before,.fa-gears:before{content:""}.fa-comments:before{content:""}.fa-thumbs-o-up:before{content:""}.fa-thumbs-o-down:before{content:""}.fa-star-half:before{content:""}.fa-heart-o:before{content:""}.fa-sign-out:before{content:""}.fa-linkedin-square:before{content:""}.fa-thumb-tack:before{content:""}.fa-external-link:before{content:""}.fa-sign-in:before{content:""}.fa-trophy:before{content:""}.fa-github-square:before{content:""}.fa-upload:before{content:""}.fa-lemon-o:before{content:""}.fa-phone:before{content:""}.fa-square-o:before{content:""}.fa-bookmark-o:before{content:""}.fa-phone-square:before{content:""}.fa-twitter:before{content:""}.fa-facebook-f:before,.fa-facebook:before{content:""}.fa-github:before,.icon-github:before{content:""}.fa-unlock:before{content:""}.fa-credit-card:before{content:""}.fa-feed:before,.fa-rss:before{content:""}.fa-hdd-o:before{content:""}.fa-bullhorn:before{content:""}.fa-bell:before{content:""}.fa-certificate:before{content:""}.fa-hand-o-right:before{content:""}.fa-hand-o-left:before{content:""}.fa-hand-o-up:before{content:""}.fa-hand-o-down:before{content:""}.fa-arrow-circle-left:before,.icon-circle-arrow-left:before{content:""}.fa-arrow-circle-right:before,.icon-circle-arrow-right:before{content:""}.fa-arrow-circle-up:before{content:""}.fa-arrow-circle-down:before{content:""}.fa-globe:before{content:""}.fa-wrench:before{content:""}.fa-tasks:before{content:""}.fa-filter:before{content:""}.fa-briefcase:before{content:""}.fa-arrows-alt:before{content:""}.fa-group:before,.fa-users:before{content:""}.fa-chain:before,.fa-link:before,.icon-link:before{content:""}.fa-cloud:before{content:""}.fa-flask:before{content:""}.fa-cut:before,.fa-scissors:before{content:""}.fa-copy:before,.fa-files-o:before{content:""}.fa-paperclip:before{content:""}.fa-floppy-o:before,.fa-save:before{content:""}.fa-square:before{content:""}.fa-bars:before,.fa-navicon:before,.fa-reorder:before{content:""}.fa-list-ul:before{content:""}.fa-list-ol:before{content:""}.fa-strikethrough:before{content:""}.fa-underline:before{content:""}.fa-table:before{content:""}.fa-magic:before{content:""}.fa-truck:before{content:""}.fa-pinterest:before{content:""}.fa-pinterest-square:before{content:""}.fa-google-plus-square:before{content:""}.fa-google-plus:before{content:""}.fa-money:before{content:""}.fa-caret-down:before,.icon-caret-down:before,.wy-dropdown .caret:before{content:""}.fa-caret-up:before{content:""}.fa-caret-left:before{content:""}.fa-caret-right:before{content:""}.fa-columns:before{content:""}.fa-sort:before,.fa-unsorted:before{content:""}.fa-sort-desc:before,.fa-sort-down:before{content:""}.fa-sort-asc:before,.fa-sort-up:before{content:""}.fa-envelope:before{content:""}.fa-linkedin:before{content:""}.fa-rotate-left:before,.fa-undo:before{content:""}.fa-gavel:before,.fa-legal:before{content:""}.fa-dashboard:before,.fa-tachometer:before{content:""}.fa-comment-o:before{content:""}.fa-comments-o:before{content:""}.fa-bolt:before,.fa-flash:before{content:""}.fa-sitemap:before{content:""}.fa-umbrella:before{content:""}.fa-clipboard:before,.fa-paste:before{content:""}.fa-lightbulb-o:before{content:""}.fa-exchange:before{content:""}.fa-cloud-download:before{content:""}.fa-cloud-upload:before{content:""}.fa-user-md:before{content:""}.fa-stethoscope:before{content:""}.fa-suitcase:before{content:""}.fa-bell-o:before{content:""}.fa-coffee:before{content:""}.fa-cutlery:before{content:""}.fa-file-text-o:before{content:""}.fa-building-o:before{content:""}.fa-hospital-o:before{content:""}.fa-ambulance:before{content:""}.fa-medkit:before{content:""}.fa-fighter-jet:before{content:""}.fa-beer:before{content:""}.fa-h-square:before{content:""}.fa-plus-square:before{content:""}.fa-angle-double-left:before{content:""}.fa-angle-double-right:before{content:""}.fa-angle-double-up:before{content:""}.fa-angle-double-down:before{content:""}.fa-angle-left:before{content:""}.fa-angle-right:before{content:""}.fa-angle-up:before{content:""}.fa-angle-down:before{content:""}.fa-desktop:before{content:""}.fa-laptop:before{content:""}.fa-tablet:before{content:""}.fa-mobile-phone:before,.fa-mobile:before{content:""}.fa-circle-o:before{content:""}.fa-quote-left:before{content:""}.fa-quote-right:before{content:""}.fa-spinner:before{content:""}.fa-circle:before{content:""}.fa-mail-reply:before,.fa-reply:before{content:""}.fa-github-alt:before{content:""}.fa-folder-o:before{content:""}.fa-folder-open-o:before{content:""}.fa-smile-o:before{content:""}.fa-frown-o:before{content:""}.fa-meh-o:before{content:""}.fa-gamepad:before{content:""}.fa-keyboard-o:before{content:""}.fa-flag-o:before{content:""}.fa-flag-checkered:before{content:""}.fa-terminal:before{content:""}.fa-code:before{content:""}.fa-mail-reply-all:before,.fa-reply-all:before{content:""}.fa-star-half-empty:before,.fa-star-half-full:before,.fa-star-half-o:before{content:""}.fa-location-arrow:before{content:""}.fa-crop:before{content:""}.fa-code-fork:before{content:""}.fa-chain-broken:before,.fa-unlink:before{content:""}.fa-question:before{content:""}.fa-info:before{content:""}.fa-exclamation:before{content:""}.fa-superscript:before{content:""}.fa-subscript:before{content:""}.fa-eraser:before{content:""}.fa-puzzle-piece:before{content:""}.fa-microphone:before{content:""}.fa-microphone-slash:before{content:""}.fa-shield:before{content:""}.fa-calendar-o:before{content:""}.fa-fire-extinguisher:before{content:""}.fa-rocket:before{content:""}.fa-maxcdn:before{content:""}.fa-chevron-circle-left:before{content:""}.fa-chevron-circle-right:before{content:""}.fa-chevron-circle-up:before{content:""}.fa-chevron-circle-down:before{content:""}.fa-html5:before{content:""}.fa-css3:before{content:""}.fa-anchor:before{content:""}.fa-unlock-alt:before{content:""}.fa-bullseye:before{content:""}.fa-ellipsis-h:before{content:""}.fa-ellipsis-v:before{content:""}.fa-rss-square:before{content:""}.fa-play-circle:before{content:""}.fa-ticket:before{content:""}.fa-minus-square:before{content:""}.fa-minus-square-o:before,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a button.toctree-expand:before{content:""}.fa-level-up:before{content:""}.fa-level-down:before{content:""}.fa-check-square:before{content:""}.fa-pencil-square:before{content:""}.fa-external-link-square:before{content:""}.fa-share-square:before{content:""}.fa-compass:before{content:""}.fa-caret-square-o-down:before,.fa-toggle-down:before{content:""}.fa-caret-square-o-up:before,.fa-toggle-up:before{content:""}.fa-caret-square-o-right:before,.fa-toggle-right:before{content:""}.fa-eur:before,.fa-euro:before{content:""}.fa-gbp:before{content:""}.fa-dollar:before,.fa-usd:before{content:""}.fa-inr:before,.fa-rupee:before{content:""}.fa-cny:before,.fa-jpy:before,.fa-rmb:before,.fa-yen:before{content:""}.fa-rouble:before,.fa-rub:before,.fa-ruble:before{content:""}.fa-krw:before,.fa-won:before{content:""}.fa-bitcoin:before,.fa-btc:before{content:""}.fa-file:before{content:""}.fa-file-text:before{content:""}.fa-sort-alpha-asc:before{content:""}.fa-sort-alpha-desc:before{content:""}.fa-sort-amount-asc:before{content:""}.fa-sort-amount-desc:before{content:""}.fa-sort-numeric-asc:before{content:""}.fa-sort-numeric-desc:before{content:""}.fa-thumbs-up:before{content:""}.fa-thumbs-down:before{content:""}.fa-youtube-square:before{content:""}.fa-youtube:before{content:""}.fa-xing:before{content:""}.fa-xing-square:before{content:""}.fa-youtube-play:before{content:""}.fa-dropbox:before{content:""}.fa-stack-overflow:before{content:""}.fa-instagram:before{content:""}.fa-flickr:before{content:""}.fa-adn:before{content:""}.fa-bitbucket:before,.icon-bitbucket:before{content:""}.fa-bitbucket-square:before{content:""}.fa-tumblr:before{content:""}.fa-tumblr-square:before{content:""}.fa-long-arrow-down:before{content:""}.fa-long-arrow-up:before{content:""}.fa-long-arrow-left:before{content:""}.fa-long-arrow-right:before{content:""}.fa-apple:before{content:""}.fa-windows:before{content:""}.fa-android:before{content:""}.fa-linux:before{content:""}.fa-dribbble:before{content:""}.fa-skype:before{content:""}.fa-foursquare:before{content:""}.fa-trello:before{content:""}.fa-female:before{content:""}.fa-male:before{content:""}.fa-gittip:before,.fa-gratipay:before{content:""}.fa-sun-o:before{content:""}.fa-moon-o:before{content:""}.fa-archive:before{content:""}.fa-bug:before{content:""}.fa-vk:before{content:""}.fa-weibo:before{content:""}.fa-renren:before{content:""}.fa-pagelines:before{content:""}.fa-stack-exchange:before{content:""}.fa-arrow-circle-o-right:before{content:""}.fa-arrow-circle-o-left:before{content:""}.fa-caret-square-o-left:before,.fa-toggle-left:before{content:""}.fa-dot-circle-o:before{content:""}.fa-wheelchair:before{content:""}.fa-vimeo-square:before{content:""}.fa-try:before,.fa-turkish-lira:before{content:""}.fa-plus-square-o:before,.wy-menu-vertical li button.toctree-expand:before{content:""}.fa-space-shuttle:before{content:""}.fa-slack:before{content:""}.fa-envelope-square:before{content:""}.fa-wordpress:before{content:""}.fa-openid:before{content:""}.fa-bank:before,.fa-institution:before,.fa-university:before{content:""}.fa-graduation-cap:before,.fa-mortar-board:before{content:""}.fa-yahoo:before{content:""}.fa-google:before{content:""}.fa-reddit:before{content:""}.fa-reddit-square:before{content:""}.fa-stumbleupon-circle:before{content:""}.fa-stumbleupon:before{content:""}.fa-delicious:before{content:""}.fa-digg:before{content:""}.fa-pied-piper-pp:before{content:""}.fa-pied-piper-alt:before{content:""}.fa-drupal:before{content:""}.fa-joomla:before{content:""}.fa-language:before{content:""}.fa-fax:before{content:""}.fa-building:before{content:""}.fa-child:before{content:""}.fa-paw:before{content:""}.fa-spoon:before{content:""}.fa-cube:before{content:""}.fa-cubes:before{content:""}.fa-behance:before{content:""}.fa-behance-square:before{content:""}.fa-steam:before{content:""}.fa-steam-square:before{content:""}.fa-recycle:before{content:""}.fa-automobile:before,.fa-car:before{content:""}.fa-cab:before,.fa-taxi:before{content:""}.fa-tree:before{content:""}.fa-spotify:before{content:""}.fa-deviantart:before{content:""}.fa-soundcloud:before{content:""}.fa-database:before{content:""}.fa-file-pdf-o:before{content:""}.fa-file-word-o:before{content:""}.fa-file-excel-o:before{content:""}.fa-file-powerpoint-o:before{content:""}.fa-file-image-o:before,.fa-file-photo-o:before,.fa-file-picture-o:before{content:""}.fa-file-archive-o:before,.fa-file-zip-o:before{content:""}.fa-file-audio-o:before,.fa-file-sound-o:before{content:""}.fa-file-movie-o:before,.fa-file-video-o:before{content:""}.fa-file-code-o:before{content:""}.fa-vine:before{content:""}.fa-codepen:before{content:""}.fa-jsfiddle:before{content:""}.fa-life-bouy:before,.fa-life-buoy:before,.fa-life-ring:before,.fa-life-saver:before,.fa-support:before{content:""}.fa-circle-o-notch:before{content:""}.fa-ra:before,.fa-rebel:before,.fa-resistance:before{content:""}.fa-empire:before,.fa-ge:before{content:""}.fa-git-square:before{content:""}.fa-git:before{content:""}.fa-hacker-news:before,.fa-y-combinator-square:before,.fa-yc-square:before{content:""}.fa-tencent-weibo:before{content:""}.fa-qq:before{content:""}.fa-wechat:before,.fa-weixin:before{content:""}.fa-paper-plane:before,.fa-send:before{content:""}.fa-paper-plane-o:before,.fa-send-o:before{content:""}.fa-history:before{content:""}.fa-circle-thin:before{content:""}.fa-header:before{content:""}.fa-paragraph:before{content:""}.fa-sliders:before{content:""}.fa-share-alt:before{content:""}.fa-share-alt-square:before{content:""}.fa-bomb:before{content:""}.fa-futbol-o:before,.fa-soccer-ball-o:before{content:""}.fa-tty:before{content:""}.fa-binoculars:before{content:""}.fa-plug:before{content:""}.fa-slideshare:before{content:""}.fa-twitch:before{content:""}.fa-yelp:before{content:""}.fa-newspaper-o:before{content:""}.fa-wifi:before{content:""}.fa-calculator:before{content:""}.fa-paypal:before{content:""}.fa-google-wallet:before{content:""}.fa-cc-visa:before{content:""}.fa-cc-mastercard:before{content:""}.fa-cc-discover:before{content:""}.fa-cc-amex:before{content:""}.fa-cc-paypal:before{content:""}.fa-cc-stripe:before{content:""}.fa-bell-slash:before{content:""}.fa-bell-slash-o:before{content:""}.fa-trash:before{content:""}.fa-copyright:before{content:""}.fa-at:before{content:""}.fa-eyedropper:before{content:""}.fa-paint-brush:before{content:""}.fa-birthday-cake:before{content:""}.fa-area-chart:before{content:""}.fa-pie-chart:before{content:""}.fa-line-chart:before{content:""}.fa-lastfm:before{content:""}.fa-lastfm-square:before{content:""}.fa-toggle-off:before{content:""}.fa-toggle-on:before{content:""}.fa-bicycle:before{content:""}.fa-bus:before{content:""}.fa-ioxhost:before{content:""}.fa-angellist:before{content:""}.fa-cc:before{content:""}.fa-ils:before,.fa-shekel:before,.fa-sheqel:before{content:""}.fa-meanpath:before{content:""}.fa-buysellads:before{content:""}.fa-connectdevelop:before{content:""}.fa-dashcube:before{content:""}.fa-forumbee:before{content:""}.fa-leanpub:before{content:""}.fa-sellsy:before{content:""}.fa-shirtsinbulk:before{content:""}.fa-simplybuilt:before{content:""}.fa-skyatlas:before{content:""}.fa-cart-plus:before{content:""}.fa-cart-arrow-down:before{content:""}.fa-diamond:before{content:""}.fa-ship:before{content:""}.fa-user-secret:before{content:""}.fa-motorcycle:before{content:""}.fa-street-view:before{content:""}.fa-heartbeat:before{content:""}.fa-venus:before{content:""}.fa-mars:before{content:""}.fa-mercury:before{content:""}.fa-intersex:before,.fa-transgender:before{content:""}.fa-transgender-alt:before{content:""}.fa-venus-double:before{content:""}.fa-mars-double:before{content:""}.fa-venus-mars:before{content:""}.fa-mars-stroke:before{content:""}.fa-mars-stroke-v:before{content:""}.fa-mars-stroke-h:before{content:""}.fa-neuter:before{content:""}.fa-genderless:before{content:""}.fa-facebook-official:before{content:""}.fa-pinterest-p:before{content:""}.fa-whatsapp:before{content:""}.fa-server:before{content:""}.fa-user-plus:before{content:""}.fa-user-times:before{content:""}.fa-bed:before,.fa-hotel:before{content:""}.fa-viacoin:before{content:""}.fa-train:before{content:""}.fa-subway:before{content:""}.fa-medium:before{content:""}.fa-y-combinator:before,.fa-yc:before{content:""}.fa-optin-monster:before{content:""}.fa-opencart:before{content:""}.fa-expeditedssl:before{content:""}.fa-battery-4:before,.fa-battery-full:before,.fa-battery:before{content:""}.fa-battery-3:before,.fa-battery-three-quarters:before{content:""}.fa-battery-2:before,.fa-battery-half:before{content:""}.fa-battery-1:before,.fa-battery-quarter:before{content:""}.fa-battery-0:before,.fa-battery-empty:before{content:""}.fa-mouse-pointer:before{content:""}.fa-i-cursor:before{content:""}.fa-object-group:before{content:""}.fa-object-ungroup:before{content:""}.fa-sticky-note:before{content:""}.fa-sticky-note-o:before{content:""}.fa-cc-jcb:before{content:""}.fa-cc-diners-club:before{content:""}.fa-clone:before{content:""}.fa-balance-scale:before{content:""}.fa-hourglass-o:before{content:""}.fa-hourglass-1:before,.fa-hourglass-start:before{content:""}.fa-hourglass-2:before,.fa-hourglass-half:before{content:""}.fa-hourglass-3:before,.fa-hourglass-end:before{content:""}.fa-hourglass:before{content:""}.fa-hand-grab-o:before,.fa-hand-rock-o:before{content:""}.fa-hand-paper-o:before,.fa-hand-stop-o:before{content:""}.fa-hand-scissors-o:before{content:""}.fa-hand-lizard-o:before{content:""}.fa-hand-spock-o:before{content:""}.fa-hand-pointer-o:before{content:""}.fa-hand-peace-o:before{content:""}.fa-trademark:before{content:""}.fa-registered:before{content:""}.fa-creative-commons:before{content:""}.fa-gg:before{content:""}.fa-gg-circle:before{content:""}.fa-tripadvisor:before{content:""}.fa-odnoklassniki:before{content:""}.fa-odnoklassniki-square:before{content:""}.fa-get-pocket:before{content:""}.fa-wikipedia-w:before{content:""}.fa-safari:before{content:""}.fa-chrome:before{content:""}.fa-firefox:before{content:""}.fa-opera:before{content:""}.fa-internet-explorer:before{content:""}.fa-television:before,.fa-tv:before{content:""}.fa-contao:before{content:""}.fa-500px:before{content:""}.fa-amazon:before{content:""}.fa-calendar-plus-o:before{content:""}.fa-calendar-minus-o:before{content:""}.fa-calendar-times-o:before{content:""}.fa-calendar-check-o:before{content:""}.fa-industry:before{content:""}.fa-map-pin:before{content:""}.fa-map-signs:before{content:""}.fa-map-o:before{content:""}.fa-map:before{content:""}.fa-commenting:before{content:""}.fa-commenting-o:before{content:""}.fa-houzz:before{content:""}.fa-vimeo:before{content:""}.fa-black-tie:before{content:""}.fa-fonticons:before{content:""}.fa-reddit-alien:before{content:""}.fa-edge:before{content:""}.fa-credit-card-alt:before{content:""}.fa-codiepie:before{content:""}.fa-modx:before{content:""}.fa-fort-awesome:before{content:""}.fa-usb:before{content:""}.fa-product-hunt:before{content:""}.fa-mixcloud:before{content:""}.fa-scribd:before{content:""}.fa-pause-circle:before{content:""}.fa-pause-circle-o:before{content:""}.fa-stop-circle:before{content:""}.fa-stop-circle-o:before{content:""}.fa-shopping-bag:before{content:""}.fa-shopping-basket:before{content:""}.fa-hashtag:before{content:""}.fa-bluetooth:before{content:""}.fa-bluetooth-b:before{content:""}.fa-percent:before{content:""}.fa-gitlab:before,.icon-gitlab:before{content:""}.fa-wpbeginner:before{content:""}.fa-wpforms:before{content:""}.fa-envira:before{content:""}.fa-universal-access:before{content:""}.fa-wheelchair-alt:before{content:""}.fa-question-circle-o:before{content:""}.fa-blind:before{content:""}.fa-audio-description:before{content:""}.fa-volume-control-phone:before{content:""}.fa-braille:before{content:""}.fa-assistive-listening-systems:before{content:""}.fa-american-sign-language-interpreting:before,.fa-asl-interpreting:before{content:""}.fa-deaf:before,.fa-deafness:before,.fa-hard-of-hearing:before{content:""}.fa-glide:before{content:""}.fa-glide-g:before{content:""}.fa-sign-language:before,.fa-signing:before{content:""}.fa-low-vision:before{content:""}.fa-viadeo:before{content:""}.fa-viadeo-square:before{content:""}.fa-snapchat:before{content:""}.fa-snapchat-ghost:before{content:""}.fa-snapchat-square:before{content:""}.fa-pied-piper:before{content:""}.fa-first-order:before{content:""}.fa-yoast:before{content:""}.fa-themeisle:before{content:""}.fa-google-plus-circle:before,.fa-google-plus-official:before{content:""}.fa-fa:before,.fa-font-awesome:before{content:""}.fa-handshake-o:before{content:""}.fa-envelope-open:before{content:""}.fa-envelope-open-o:before{content:""}.fa-linode:before{content:""}.fa-address-book:before{content:""}.fa-address-book-o:before{content:""}.fa-address-card:before,.fa-vcard:before{content:""}.fa-address-card-o:before,.fa-vcard-o:before{content:""}.fa-user-circle:before{content:""}.fa-user-circle-o:before{content:""}.fa-user-o:before{content:""}.fa-id-badge:before{content:""}.fa-drivers-license:before,.fa-id-card:before{content:""}.fa-drivers-license-o:before,.fa-id-card-o:before{content:""}.fa-quora:before{content:""}.fa-free-code-camp:before{content:""}.fa-telegram:before{content:""}.fa-thermometer-4:before,.fa-thermometer-full:before,.fa-thermometer:before{content:""}.fa-thermometer-3:before,.fa-thermometer-three-quarters:before{content:""}.fa-thermometer-2:before,.fa-thermometer-half:before{content:""}.fa-thermometer-1:before,.fa-thermometer-quarter:before{content:""}.fa-thermometer-0:before,.fa-thermometer-empty:before{content:""}.fa-shower:before{content:""}.fa-bath:before,.fa-bathtub:before,.fa-s15:before{content:""}.fa-podcast:before{content:""}.fa-window-maximize:before{content:""}.fa-window-minimize:before{content:""}.fa-window-restore:before{content:""}.fa-times-rectangle:before,.fa-window-close:before{content:""}.fa-times-rectangle-o:before,.fa-window-close-o:before{content:""}.fa-bandcamp:before{content:""}.fa-grav:before{content:""}.fa-etsy:before{content:""}.fa-imdb:before{content:""}.fa-ravelry:before{content:""}.fa-eercast:before{content:""}.fa-microchip:before{content:""}.fa-snowflake-o:before{content:""}.fa-superpowers:before{content:""}.fa-wpexplorer:before{content:""}.fa-meetup:before{content:""}.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}.fa,.icon,.rst-content .admonition-title,.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content code.download span:first-child,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink,.rst-content tt.download span:first-child,.wy-dropdown .caret,.wy-inline-validate.wy-inline-validate-danger .wy-input-context,.wy-inline-validate.wy-inline-validate-info .wy-input-context,.wy-inline-validate.wy-inline-validate-success .wy-input-context,.wy-inline-validate.wy-inline-validate-warning .wy-input-context,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li button.toctree-expand{font-family:inherit}.fa:before,.icon:before,.rst-content .admonition-title:before,.rst-content .code-block-caption .headerlink:before,.rst-content .eqno .headerlink:before,.rst-content code.download span:first-child:before,.rst-content dl dt .headerlink:before,.rst-content h1 .headerlink:before,.rst-content h2 .headerlink:before,.rst-content h3 .headerlink:before,.rst-content h4 .headerlink:before,.rst-content h5 .headerlink:before,.rst-content h6 .headerlink:before,.rst-content p.caption .headerlink:before,.rst-content p .headerlink:before,.rst-content table>caption .headerlink:before,.rst-content tt.download span:first-child:before,.wy-dropdown .caret:before,.wy-inline-validate.wy-inline-validate-danger .wy-input-context:before,.wy-inline-validate.wy-inline-validate-info .wy-input-context:before,.wy-inline-validate.wy-inline-validate-success .wy-input-context:before,.wy-inline-validate.wy-inline-validate-warning .wy-input-context:before,.wy-menu-vertical li.current>a button.toctree-expand:before,.wy-menu-vertical li.on a button.toctree-expand:before,.wy-menu-vertical li button.toctree-expand:before{font-family:FontAwesome;display:inline-block;font-style:normal;font-weight:400;line-height:1;text-decoration:inherit}.rst-content .code-block-caption a .headerlink,.rst-content .eqno a .headerlink,.rst-content a .admonition-title,.rst-content code.download a span:first-child,.rst-content dl dt a .headerlink,.rst-content h1 a .headerlink,.rst-content h2 a .headerlink,.rst-content h3 a .headerlink,.rst-content h4 a .headerlink,.rst-content h5 a .headerlink,.rst-content h6 a .headerlink,.rst-content p.caption a .headerlink,.rst-content p a .headerlink,.rst-content table>caption a .headerlink,.rst-content tt.download a span:first-child,.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand,.wy-menu-vertical li a button.toctree-expand,a .fa,a .icon,a .rst-content .admonition-title,a .rst-content .code-block-caption .headerlink,a .rst-content .eqno .headerlink,a .rst-content code.download span:first-child,a .rst-content dl dt .headerlink,a .rst-content h1 .headerlink,a .rst-content h2 .headerlink,a .rst-content h3 .headerlink,a .rst-content h4 .headerlink,a .rst-content h5 .headerlink,a .rst-content h6 .headerlink,a .rst-content p.caption .headerlink,a .rst-content p .headerlink,a .rst-content table>caption .headerlink,a .rst-content tt.download span:first-child,a .wy-menu-vertical li button.toctree-expand{display:inline-block;text-decoration:inherit}.btn .fa,.btn .icon,.btn .rst-content .admonition-title,.btn .rst-content .code-block-caption .headerlink,.btn .rst-content .eqno .headerlink,.btn .rst-content code.download span:first-child,.btn .rst-content dl dt .headerlink,.btn .rst-content h1 .headerlink,.btn .rst-content h2 .headerlink,.btn .rst-content h3 .headerlink,.btn .rst-content h4 .headerlink,.btn .rst-content h5 .headerlink,.btn .rst-content h6 .headerlink,.btn .rst-content p .headerlink,.btn .rst-content table>caption .headerlink,.btn .rst-content tt.download span:first-child,.btn .wy-menu-vertical li.current>a button.toctree-expand,.btn .wy-menu-vertical li.on a button.toctree-expand,.btn .wy-menu-vertical li button.toctree-expand,.nav .fa,.nav .icon,.nav .rst-content .admonition-title,.nav .rst-content .code-block-caption .headerlink,.nav .rst-content .eqno .headerlink,.nav .rst-content code.download span:first-child,.nav .rst-content dl dt .headerlink,.nav .rst-content h1 .headerlink,.nav .rst-content h2 .headerlink,.nav .rst-content h3 .headerlink,.nav .rst-content h4 .headerlink,.nav .rst-content h5 .headerlink,.nav .rst-content h6 .headerlink,.nav .rst-content p .headerlink,.nav .rst-content table>caption .headerlink,.nav .rst-content tt.download span:first-child,.nav .wy-menu-vertical li.current>a button.toctree-expand,.nav .wy-menu-vertical li.on a button.toctree-expand,.nav .wy-menu-vertical li button.toctree-expand,.rst-content .btn .admonition-title,.rst-content .code-block-caption .btn .headerlink,.rst-content .code-block-caption .nav .headerlink,.rst-content .eqno .btn .headerlink,.rst-content .eqno .nav .headerlink,.rst-content .nav .admonition-title,.rst-content code.download .btn span:first-child,.rst-content code.download .nav span:first-child,.rst-content dl dt .btn .headerlink,.rst-content dl dt .nav .headerlink,.rst-content h1 .btn .headerlink,.rst-content h1 .nav .headerlink,.rst-content h2 .btn .headerlink,.rst-content h2 .nav .headerlink,.rst-content h3 .btn .headerlink,.rst-content h3 .nav .headerlink,.rst-content h4 .btn .headerlink,.rst-content h4 .nav .headerlink,.rst-content h5 .btn .headerlink,.rst-content h5 .nav .headerlink,.rst-content h6 .btn .headerlink,.rst-content h6 .nav .headerlink,.rst-content p .btn .headerlink,.rst-content p .nav .headerlink,.rst-content table>caption .btn .headerlink,.rst-content table>caption .nav .headerlink,.rst-content tt.download .btn span:first-child,.rst-content tt.download .nav span:first-child,.wy-menu-vertical li .btn button.toctree-expand,.wy-menu-vertical li.current>a .btn button.toctree-expand,.wy-menu-vertical li.current>a .nav button.toctree-expand,.wy-menu-vertical li .nav button.toctree-expand,.wy-menu-vertical li.on a .btn button.toctree-expand,.wy-menu-vertical li.on a .nav button.toctree-expand{display:inline}.btn .fa-large.icon,.btn .fa.fa-large,.btn .rst-content .code-block-caption .fa-large.headerlink,.btn .rst-content .eqno .fa-large.headerlink,.btn .rst-content .fa-large.admonition-title,.btn .rst-content code.download span.fa-large:first-child,.btn .rst-content dl dt .fa-large.headerlink,.btn .rst-content h1 .fa-large.headerlink,.btn .rst-content h2 .fa-large.headerlink,.btn .rst-content h3 .fa-large.headerlink,.btn .rst-content h4 .fa-large.headerlink,.btn .rst-content h5 .fa-large.headerlink,.btn .rst-content h6 .fa-large.headerlink,.btn .rst-content p .fa-large.headerlink,.btn .rst-content table>caption .fa-large.headerlink,.btn .rst-content tt.download span.fa-large:first-child,.btn .wy-menu-vertical li button.fa-large.toctree-expand,.nav .fa-large.icon,.nav .fa.fa-large,.nav .rst-content .code-block-caption .fa-large.headerlink,.nav .rst-content .eqno .fa-large.headerlink,.nav .rst-content .fa-large.admonition-title,.nav .rst-content code.download span.fa-large:first-child,.nav .rst-content dl dt .fa-large.headerlink,.nav .rst-content h1 .fa-large.headerlink,.nav .rst-content h2 .fa-large.headerlink,.nav .rst-content h3 .fa-large.headerlink,.nav .rst-content h4 .fa-large.headerlink,.nav .rst-content h5 .fa-large.headerlink,.nav .rst-content h6 .fa-large.headerlink,.nav .rst-content p .fa-large.headerlink,.nav .rst-content table>caption .fa-large.headerlink,.nav .rst-content tt.download span.fa-large:first-child,.nav .wy-menu-vertical li button.fa-large.toctree-expand,.rst-content .btn .fa-large.admonition-title,.rst-content .code-block-caption .btn .fa-large.headerlink,.rst-content .code-block-caption .nav .fa-large.headerlink,.rst-content .eqno .btn .fa-large.headerlink,.rst-content .eqno .nav .fa-large.headerlink,.rst-content .nav .fa-large.admonition-title,.rst-content code.download .btn span.fa-large:first-child,.rst-content code.download .nav span.fa-large:first-child,.rst-content dl dt .btn .fa-large.headerlink,.rst-content dl dt .nav .fa-large.headerlink,.rst-content h1 .btn .fa-large.headerlink,.rst-content h1 .nav .fa-large.headerlink,.rst-content h2 .btn .fa-large.headerlink,.rst-content h2 .nav .fa-large.headerlink,.rst-content h3 .btn .fa-large.headerlink,.rst-content h3 .nav .fa-large.headerlink,.rst-content h4 .btn .fa-large.headerlink,.rst-content h4 .nav .fa-large.headerlink,.rst-content h5 .btn .fa-large.headerlink,.rst-content h5 .nav .fa-large.headerlink,.rst-content h6 .btn .fa-large.headerlink,.rst-content h6 .nav .fa-large.headerlink,.rst-content p .btn .fa-large.headerlink,.rst-content p .nav .fa-large.headerlink,.rst-content table>caption .btn .fa-large.headerlink,.rst-content table>caption .nav .fa-large.headerlink,.rst-content tt.download .btn span.fa-large:first-child,.rst-content tt.download .nav span.fa-large:first-child,.wy-menu-vertical li .btn button.fa-large.toctree-expand,.wy-menu-vertical li .nav button.fa-large.toctree-expand{line-height:.9em}.btn .fa-spin.icon,.btn .fa.fa-spin,.btn .rst-content .code-block-caption .fa-spin.headerlink,.btn .rst-content .eqno .fa-spin.headerlink,.btn .rst-content .fa-spin.admonition-title,.btn .rst-content code.download span.fa-spin:first-child,.btn .rst-content dl dt .fa-spin.headerlink,.btn .rst-content h1 .fa-spin.headerlink,.btn .rst-content h2 .fa-spin.headerlink,.btn .rst-content h3 .fa-spin.headerlink,.btn .rst-content h4 .fa-spin.headerlink,.btn .rst-content h5 .fa-spin.headerlink,.btn .rst-content h6 .fa-spin.headerlink,.btn .rst-content p .fa-spin.headerlink,.btn .rst-content table>caption .fa-spin.headerlink,.btn .rst-content tt.download span.fa-spin:first-child,.btn .wy-menu-vertical li button.fa-spin.toctree-expand,.nav .fa-spin.icon,.nav .fa.fa-spin,.nav .rst-content .code-block-caption .fa-spin.headerlink,.nav .rst-content .eqno .fa-spin.headerlink,.nav .rst-content .fa-spin.admonition-title,.nav .rst-content code.download span.fa-spin:first-child,.nav .rst-content dl dt .fa-spin.headerlink,.nav .rst-content h1 .fa-spin.headerlink,.nav .rst-content h2 .fa-spin.headerlink,.nav .rst-content h3 .fa-spin.headerlink,.nav .rst-content h4 .fa-spin.headerlink,.nav .rst-content h5 .fa-spin.headerlink,.nav .rst-content h6 .fa-spin.headerlink,.nav .rst-content p .fa-spin.headerlink,.nav .rst-content table>caption .fa-spin.headerlink,.nav .rst-content tt.download span.fa-spin:first-child,.nav .wy-menu-vertical li button.fa-spin.toctree-expand,.rst-content .btn .fa-spin.admonition-title,.rst-content .code-block-caption .btn .fa-spin.headerlink,.rst-content .code-block-caption .nav .fa-spin.headerlink,.rst-content .eqno .btn .fa-spin.headerlink,.rst-content .eqno .nav .fa-spin.headerlink,.rst-content .nav .fa-spin.admonition-title,.rst-content code.download .btn span.fa-spin:first-child,.rst-content code.download .nav span.fa-spin:first-child,.rst-content dl dt .btn .fa-spin.headerlink,.rst-content dl dt .nav .fa-spin.headerlink,.rst-content h1 .btn .fa-spin.headerlink,.rst-content h1 .nav .fa-spin.headerlink,.rst-content h2 .btn .fa-spin.headerlink,.rst-content h2 .nav .fa-spin.headerlink,.rst-content h3 .btn .fa-spin.headerlink,.rst-content h3 .nav .fa-spin.headerlink,.rst-content h4 .btn .fa-spin.headerlink,.rst-content h4 .nav .fa-spin.headerlink,.rst-content h5 .btn .fa-spin.headerlink,.rst-content h5 .nav .fa-spin.headerlink,.rst-content h6 .btn .fa-spin.headerlink,.rst-content h6 .nav .fa-spin.headerlink,.rst-content p .btn .fa-spin.headerlink,.rst-content p .nav .fa-spin.headerlink,.rst-content table>caption .btn .fa-spin.headerlink,.rst-content table>caption .nav .fa-spin.headerlink,.rst-content tt.download .btn span.fa-spin:first-child,.rst-content tt.download .nav span.fa-spin:first-child,.wy-menu-vertical li .btn button.fa-spin.toctree-expand,.wy-menu-vertical li .nav button.fa-spin.toctree-expand{display:inline-block}.btn.fa:before,.btn.icon:before,.rst-content .btn.admonition-title:before,.rst-content .code-block-caption .btn.headerlink:before,.rst-content .eqno .btn.headerlink:before,.rst-content code.download span.btn:first-child:before,.rst-content dl dt .btn.headerlink:before,.rst-content h1 .btn.headerlink:before,.rst-content h2 .btn.headerlink:before,.rst-content h3 .btn.headerlink:before,.rst-content h4 .btn.headerlink:before,.rst-content h5 .btn.headerlink:before,.rst-content h6 .btn.headerlink:before,.rst-content p .btn.headerlink:before,.rst-content table>caption .btn.headerlink:before,.rst-content tt.download span.btn:first-child:before,.wy-menu-vertical li button.btn.toctree-expand:before{opacity:.5;-webkit-transition:opacity .05s ease-in;-moz-transition:opacity .05s ease-in;transition:opacity .05s ease-in}.btn.fa:hover:before,.btn.icon:hover:before,.rst-content .btn.admonition-title:hover:before,.rst-content .code-block-caption .btn.headerlink:hover:before,.rst-content .eqno .btn.headerlink:hover:before,.rst-content code.download span.btn:first-child:hover:before,.rst-content dl dt .btn.headerlink:hover:before,.rst-content h1 .btn.headerlink:hover:before,.rst-content h2 .btn.headerlink:hover:before,.rst-content h3 .btn.headerlink:hover:before,.rst-content h4 .btn.headerlink:hover:before,.rst-content h5 .btn.headerlink:hover:before,.rst-content h6 .btn.headerlink:hover:before,.rst-content p .btn.headerlink:hover:before,.rst-content table>caption .btn.headerlink:hover:before,.rst-content tt.download span.btn:first-child:hover:before,.wy-menu-vertical li button.btn.toctree-expand:hover:before{opacity:1}.btn-mini .fa:before,.btn-mini .icon:before,.btn-mini .rst-content .admonition-title:before,.btn-mini .rst-content .code-block-caption .headerlink:before,.btn-mini .rst-content .eqno .headerlink:before,.btn-mini .rst-content code.download span:first-child:before,.btn-mini .rst-content dl dt .headerlink:before,.btn-mini .rst-content h1 .headerlink:before,.btn-mini .rst-content h2 .headerlink:before,.btn-mini .rst-content h3 .headerlink:before,.btn-mini .rst-content h4 .headerlink:before,.btn-mini .rst-content h5 .headerlink:before,.btn-mini .rst-content h6 .headerlink:before,.btn-mini .rst-content p .headerlink:before,.btn-mini .rst-content table>caption .headerlink:before,.btn-mini .rst-content tt.download span:first-child:before,.btn-mini .wy-menu-vertical li button.toctree-expand:before,.rst-content .btn-mini .admonition-title:before,.rst-content .code-block-caption .btn-mini .headerlink:before,.rst-content .eqno .btn-mini .headerlink:before,.rst-content code.download .btn-mini span:first-child:before,.rst-content dl dt .btn-mini .headerlink:before,.rst-content h1 .btn-mini .headerlink:before,.rst-content h2 .btn-mini .headerlink:before,.rst-content h3 .btn-mini .headerlink:before,.rst-content h4 .btn-mini .headerlink:before,.rst-content h5 .btn-mini .headerlink:before,.rst-content h6 .btn-mini .headerlink:before,.rst-content p .btn-mini .headerlink:before,.rst-content table>caption .btn-mini .headerlink:before,.rst-content tt.download .btn-mini span:first-child:before,.wy-menu-vertical li .btn-mini button.toctree-expand:before{font-size:14px;vertical-align:-15%}.rst-content .admonition,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .danger,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning,.wy-alert{padding:12px;line-height:24px;margin-bottom:24px;background:#e7f2fa}.rst-content .admonition-title,.wy-alert-title{font-weight:700;display:block;color:#fff;background:#6ab0de;padding:6px 12px;margin:-12px -12px 12px}.rst-content .danger,.rst-content .error,.rst-content .wy-alert-danger.admonition,.rst-content .wy-alert-danger.admonition-todo,.rst-content .wy-alert-danger.attention,.rst-content .wy-alert-danger.caution,.rst-content .wy-alert-danger.hint,.rst-content .wy-alert-danger.important,.rst-content .wy-alert-danger.note,.rst-content .wy-alert-danger.seealso,.rst-content .wy-alert-danger.tip,.rst-content .wy-alert-danger.warning,.wy-alert.wy-alert-danger{background:#fdf3f2}.rst-content .danger .admonition-title,.rst-content .danger .wy-alert-title,.rst-content .error .admonition-title,.rst-content .error .wy-alert-title,.rst-content .wy-alert-danger.admonition-todo .admonition-title,.rst-content .wy-alert-danger.admonition-todo .wy-alert-title,.rst-content .wy-alert-danger.admonition .admonition-title,.rst-content .wy-alert-danger.admonition .wy-alert-title,.rst-content .wy-alert-danger.attention .admonition-title,.rst-content .wy-alert-danger.attention .wy-alert-title,.rst-content .wy-alert-danger.caution .admonition-title,.rst-content .wy-alert-danger.caution .wy-alert-title,.rst-content .wy-alert-danger.hint .admonition-title,.rst-content .wy-alert-danger.hint .wy-alert-title,.rst-content .wy-alert-danger.important .admonition-title,.rst-content .wy-alert-danger.important .wy-alert-title,.rst-content .wy-alert-danger.note .admonition-title,.rst-content .wy-alert-danger.note .wy-alert-title,.rst-content .wy-alert-danger.seealso .admonition-title,.rst-content .wy-alert-danger.seealso .wy-alert-title,.rst-content .wy-alert-danger.tip .admonition-title,.rst-content .wy-alert-danger.tip .wy-alert-title,.rst-content .wy-alert-danger.warning .admonition-title,.rst-content .wy-alert-danger.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-danger .admonition-title,.wy-alert.wy-alert-danger .rst-content .admonition-title,.wy-alert.wy-alert-danger .wy-alert-title{background:#f29f97}.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .warning,.rst-content .wy-alert-warning.admonition,.rst-content .wy-alert-warning.danger,.rst-content .wy-alert-warning.error,.rst-content .wy-alert-warning.hint,.rst-content .wy-alert-warning.important,.rst-content .wy-alert-warning.note,.rst-content .wy-alert-warning.seealso,.rst-content .wy-alert-warning.tip,.wy-alert.wy-alert-warning{background:#ffedcc}.rst-content .admonition-todo .admonition-title,.rst-content .admonition-todo .wy-alert-title,.rst-content .attention .admonition-title,.rst-content .attention .wy-alert-title,.rst-content .caution .admonition-title,.rst-content .caution .wy-alert-title,.rst-content .warning .admonition-title,.rst-content .warning .wy-alert-title,.rst-content .wy-alert-warning.admonition .admonition-title,.rst-content .wy-alert-warning.admonition .wy-alert-title,.rst-content .wy-alert-warning.danger .admonition-title,.rst-content .wy-alert-warning.danger .wy-alert-title,.rst-content .wy-alert-warning.error .admonition-title,.rst-content .wy-alert-warning.error .wy-alert-title,.rst-content .wy-alert-warning.hint .admonition-title,.rst-content .wy-alert-warning.hint .wy-alert-title,.rst-content .wy-alert-warning.important .admonition-title,.rst-content .wy-alert-warning.important .wy-alert-title,.rst-content .wy-alert-warning.note .admonition-title,.rst-content .wy-alert-warning.note .wy-alert-title,.rst-content .wy-alert-warning.seealso .admonition-title,.rst-content .wy-alert-warning.seealso .wy-alert-title,.rst-content .wy-alert-warning.tip .admonition-title,.rst-content .wy-alert-warning.tip .wy-alert-title,.rst-content .wy-alert.wy-alert-warning .admonition-title,.wy-alert.wy-alert-warning .rst-content .admonition-title,.wy-alert.wy-alert-warning .wy-alert-title{background:#f0b37e}.rst-content .note,.rst-content .seealso,.rst-content .wy-alert-info.admonition,.rst-content .wy-alert-info.admonition-todo,.rst-content .wy-alert-info.attention,.rst-content .wy-alert-info.caution,.rst-content .wy-alert-info.danger,.rst-content .wy-alert-info.error,.rst-content .wy-alert-info.hint,.rst-content .wy-alert-info.important,.rst-content .wy-alert-info.tip,.rst-content .wy-alert-info.warning,.wy-alert.wy-alert-info{background:#e7f2fa}.rst-content .note .admonition-title,.rst-content .note .wy-alert-title,.rst-content .seealso .admonition-title,.rst-content .seealso .wy-alert-title,.rst-content .wy-alert-info.admonition-todo .admonition-title,.rst-content .wy-alert-info.admonition-todo .wy-alert-title,.rst-content .wy-alert-info.admonition .admonition-title,.rst-content .wy-alert-info.admonition .wy-alert-title,.rst-content .wy-alert-info.attention .admonition-title,.rst-content .wy-alert-info.attention .wy-alert-title,.rst-content .wy-alert-info.caution .admonition-title,.rst-content .wy-alert-info.caution .wy-alert-title,.rst-content .wy-alert-info.danger .admonition-title,.rst-content .wy-alert-info.danger .wy-alert-title,.rst-content .wy-alert-info.error .admonition-title,.rst-content .wy-alert-info.error .wy-alert-title,.rst-content .wy-alert-info.hint .admonition-title,.rst-content .wy-alert-info.hint .wy-alert-title,.rst-content .wy-alert-info.important .admonition-title,.rst-content .wy-alert-info.important .wy-alert-title,.rst-content .wy-alert-info.tip .admonition-title,.rst-content .wy-alert-info.tip .wy-alert-title,.rst-content .wy-alert-info.warning .admonition-title,.rst-content .wy-alert-info.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-info .admonition-title,.wy-alert.wy-alert-info .rst-content .admonition-title,.wy-alert.wy-alert-info .wy-alert-title{background:#6ab0de}.rst-content .hint,.rst-content .important,.rst-content .tip,.rst-content .wy-alert-success.admonition,.rst-content .wy-alert-success.admonition-todo,.rst-content .wy-alert-success.attention,.rst-content .wy-alert-success.caution,.rst-content .wy-alert-success.danger,.rst-content .wy-alert-success.error,.rst-content .wy-alert-success.note,.rst-content .wy-alert-success.seealso,.rst-content .wy-alert-success.warning,.wy-alert.wy-alert-success{background:#dbfaf4}.rst-content .hint .admonition-title,.rst-content .hint .wy-alert-title,.rst-content .important .admonition-title,.rst-content .important .wy-alert-title,.rst-content .tip .admonition-title,.rst-content .tip .wy-alert-title,.rst-content .wy-alert-success.admonition-todo .admonition-title,.rst-content .wy-alert-success.admonition-todo .wy-alert-title,.rst-content .wy-alert-success.admonition .admonition-title,.rst-content .wy-alert-success.admonition .wy-alert-title,.rst-content .wy-alert-success.attention .admonition-title,.rst-content .wy-alert-success.attention .wy-alert-title,.rst-content .wy-alert-success.caution .admonition-title,.rst-content .wy-alert-success.caution .wy-alert-title,.rst-content .wy-alert-success.danger .admonition-title,.rst-content .wy-alert-success.danger .wy-alert-title,.rst-content .wy-alert-success.error .admonition-title,.rst-content .wy-alert-success.error .wy-alert-title,.rst-content .wy-alert-success.note .admonition-title,.rst-content .wy-alert-success.note .wy-alert-title,.rst-content .wy-alert-success.seealso .admonition-title,.rst-content .wy-alert-success.seealso .wy-alert-title,.rst-content .wy-alert-success.warning .admonition-title,.rst-content .wy-alert-success.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-success .admonition-title,.wy-alert.wy-alert-success .rst-content .admonition-title,.wy-alert.wy-alert-success .wy-alert-title{background:#1abc9c}.rst-content .wy-alert-neutral.admonition,.rst-content .wy-alert-neutral.admonition-todo,.rst-content .wy-alert-neutral.attention,.rst-content .wy-alert-neutral.caution,.rst-content .wy-alert-neutral.danger,.rst-content .wy-alert-neutral.error,.rst-content .wy-alert-neutral.hint,.rst-content .wy-alert-neutral.important,.rst-content .wy-alert-neutral.note,.rst-content .wy-alert-neutral.seealso,.rst-content .wy-alert-neutral.tip,.rst-content .wy-alert-neutral.warning,.wy-alert.wy-alert-neutral{background:#f3f6f6}.rst-content .wy-alert-neutral.admonition-todo .admonition-title,.rst-content .wy-alert-neutral.admonition-todo .wy-alert-title,.rst-content .wy-alert-neutral.admonition .admonition-title,.rst-content .wy-alert-neutral.admonition .wy-alert-title,.rst-content .wy-alert-neutral.attention .admonition-title,.rst-content .wy-alert-neutral.attention .wy-alert-title,.rst-content .wy-alert-neutral.caution .admonition-title,.rst-content .wy-alert-neutral.caution .wy-alert-title,.rst-content .wy-alert-neutral.danger .admonition-title,.rst-content .wy-alert-neutral.danger .wy-alert-title,.rst-content .wy-alert-neutral.error .admonition-title,.rst-content .wy-alert-neutral.error .wy-alert-title,.rst-content .wy-alert-neutral.hint .admonition-title,.rst-content .wy-alert-neutral.hint .wy-alert-title,.rst-content .wy-alert-neutral.important .admonition-title,.rst-content .wy-alert-neutral.important .wy-alert-title,.rst-content .wy-alert-neutral.note .admonition-title,.rst-content .wy-alert-neutral.note .wy-alert-title,.rst-content .wy-alert-neutral.seealso .admonition-title,.rst-content .wy-alert-neutral.seealso .wy-alert-title,.rst-content .wy-alert-neutral.tip .admonition-title,.rst-content .wy-alert-neutral.tip .wy-alert-title,.rst-content .wy-alert-neutral.warning .admonition-title,.rst-content .wy-alert-neutral.warning .wy-alert-title,.rst-content .wy-alert.wy-alert-neutral .admonition-title,.wy-alert.wy-alert-neutral .rst-content .admonition-title,.wy-alert.wy-alert-neutral .wy-alert-title{color:#404040;background:#e1e4e5}.rst-content .wy-alert-neutral.admonition-todo a,.rst-content .wy-alert-neutral.admonition a,.rst-content .wy-alert-neutral.attention a,.rst-content .wy-alert-neutral.caution a,.rst-content .wy-alert-neutral.danger a,.rst-content .wy-alert-neutral.error a,.rst-content .wy-alert-neutral.hint a,.rst-content .wy-alert-neutral.important a,.rst-content .wy-alert-neutral.note a,.rst-content .wy-alert-neutral.seealso a,.rst-content .wy-alert-neutral.tip a,.rst-content .wy-alert-neutral.warning a,.wy-alert.wy-alert-neutral a{color:#2980b9}.rst-content .admonition-todo p:last-child,.rst-content .admonition p:last-child,.rst-content .attention p:last-child,.rst-content .caution p:last-child,.rst-content .danger p:last-child,.rst-content .error p:last-child,.rst-content .hint p:last-child,.rst-content .important p:last-child,.rst-content .note p:last-child,.rst-content .seealso p:last-child,.rst-content .tip p:last-child,.rst-content .warning p:last-child,.wy-alert p:last-child{margin-bottom:0}.wy-tray-container{position:fixed;bottom:0;left:0;z-index:600}.wy-tray-container li{display:block;width:300px;background:transparent;color:#fff;text-align:center;box-shadow:0 5px 5px 0 rgba(0,0,0,.1);padding:0 24px;min-width:20%;opacity:0;height:0;line-height:56px;overflow:hidden;-webkit-transition:all .3s ease-in;-moz-transition:all .3s ease-in;transition:all .3s ease-in}.wy-tray-container li.wy-tray-item-success{background:#27ae60}.wy-tray-container li.wy-tray-item-info{background:#2980b9}.wy-tray-container li.wy-tray-item-warning{background:#e67e22}.wy-tray-container li.wy-tray-item-danger{background:#e74c3c}.wy-tray-container li.on{opacity:1;height:56px}@media screen and (max-width:768px){.wy-tray-container{bottom:auto;top:0;width:100%}.wy-tray-container li{width:100%}}button{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle;cursor:pointer;line-height:normal;-webkit-appearance:button;*overflow:visible}button::-moz-focus-inner,input::-moz-focus-inner{border:0;padding:0}button[disabled]{cursor:default}.btn{display:inline-block;border-radius:2px;line-height:normal;white-space:nowrap;text-align:center;cursor:pointer;font-size:100%;padding:6px 12px 8px;color:#fff;border:1px solid rgba(0,0,0,.1);background-color:#27ae60;text-decoration:none;font-weight:400;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;box-shadow:inset 0 1px 2px -1px hsla(0,0%,100%,.5),inset 0 -2px 0 0 rgba(0,0,0,.1);outline-none:false;vertical-align:middle;*display:inline;zoom:1;-webkit-user-drag:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;-webkit-transition:all .1s linear;-moz-transition:all .1s linear;transition:all .1s linear}.btn-hover{background:#2e8ece;color:#fff}.btn:hover{background:#2cc36b;color:#fff}.btn:focus{background:#2cc36b;outline:0}.btn:active{box-shadow:inset 0 -1px 0 0 rgba(0,0,0,.05),inset 0 2px 0 0 rgba(0,0,0,.1);padding:8px 12px 6px}.btn:visited{color:#fff}.btn-disabled,.btn-disabled:active,.btn-disabled:focus,.btn-disabled:hover,.btn:disabled{background-image:none;filter:progid:DXImageTransform.Microsoft.gradient(enabled = false);filter:alpha(opacity=40);opacity:.4;cursor:not-allowed;box-shadow:none}.btn::-moz-focus-inner{padding:0;border:0}.btn-small{font-size:80%}.btn-info{background-color:#2980b9!important}.btn-info:hover{background-color:#2e8ece!important}.btn-neutral{background-color:#f3f6f6!important;color:#404040!important}.btn-neutral:hover{background-color:#e5ebeb!important;color:#404040}.btn-neutral:visited{color:#404040!important}.btn-success{background-color:#27ae60!important}.btn-success:hover{background-color:#295!important}.btn-danger{background-color:#e74c3c!important}.btn-danger:hover{background-color:#ea6153!important}.btn-warning{background-color:#e67e22!important}.btn-warning:hover{background-color:#e98b39!important}.btn-invert{background-color:#222}.btn-invert:hover{background-color:#2f2f2f!important}.btn-link{background-color:transparent!important;color:#2980b9;box-shadow:none;border-color:transparent!important}.btn-link:active,.btn-link:hover{background-color:transparent!important;color:#409ad5!important;box-shadow:none}.btn-link:visited{color:#9b59b6}.wy-btn-group .btn,.wy-control .btn{vertical-align:middle}.wy-btn-group{margin-bottom:24px;*zoom:1}.wy-btn-group:after,.wy-btn-group:before{display:table;content:""}.wy-btn-group:after{clear:both}.wy-dropdown{position:relative;display:inline-block}.wy-dropdown-active .wy-dropdown-menu{display:block}.wy-dropdown-menu{position:absolute;left:0;display:none;float:left;top:100%;min-width:100%;background:#fcfcfc;z-index:100;border:1px solid #cfd7dd;box-shadow:0 2px 2px 0 rgba(0,0,0,.1);padding:12px}.wy-dropdown-menu>dd>a{display:block;clear:both;color:#404040;white-space:nowrap;font-size:90%;padding:0 12px;cursor:pointer}.wy-dropdown-menu>dd>a:hover{background:#2980b9;color:#fff}.wy-dropdown-menu>dd.divider{border-top:1px solid #cfd7dd;margin:6px 0}.wy-dropdown-menu>dd.search{padding-bottom:12px}.wy-dropdown-menu>dd.search input[type=search]{width:100%}.wy-dropdown-menu>dd.call-to-action{background:#e3e3e3;text-transform:uppercase;font-weight:500;font-size:80%}.wy-dropdown-menu>dd.call-to-action:hover{background:#e3e3e3}.wy-dropdown-menu>dd.call-to-action .btn{color:#fff}.wy-dropdown.wy-dropdown-up .wy-dropdown-menu{bottom:100%;top:auto;left:auto;right:0}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu{background:#fcfcfc;margin-top:2px}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu a{padding:6px 12px}.wy-dropdown.wy-dropdown-bubble .wy-dropdown-menu a:hover{background:#2980b9;color:#fff}.wy-dropdown.wy-dropdown-left .wy-dropdown-menu{right:0;left:auto;text-align:right}.wy-dropdown-arrow:before{content:" ";border-bottom:5px solid #f5f5f5;border-left:5px solid transparent;border-right:5px solid transparent;position:absolute;display:block;top:-4px;left:50%;margin-left:-3px}.wy-dropdown-arrow.wy-dropdown-arrow-left:before{left:11px}.wy-form-stacked select{display:block}.wy-form-aligned .wy-help-inline,.wy-form-aligned input,.wy-form-aligned label,.wy-form-aligned select,.wy-form-aligned textarea{display:inline-block;*display:inline;*zoom:1;vertical-align:middle}.wy-form-aligned .wy-control-group>label{display:inline-block;vertical-align:middle;width:10em;margin:6px 12px 0 0;float:left}.wy-form-aligned .wy-control{float:left}.wy-form-aligned .wy-control label{display:block}.wy-form-aligned .wy-control select{margin-top:6px}fieldset{margin:0}fieldset,legend{border:0;padding:0}legend{width:100%;white-space:normal;margin-bottom:24px;font-size:150%;*margin-left:-7px}label,legend{display:block}label{margin:0 0 .3125em;color:#333;font-size:90%}input,select,textarea{font-size:100%;margin:0;vertical-align:baseline;*vertical-align:middle}.wy-control-group{margin-bottom:24px;max-width:1200px;margin-left:auto;margin-right:auto;*zoom:1}.wy-control-group:after,.wy-control-group:before{display:table;content:""}.wy-control-group:after{clear:both}.wy-control-group.wy-control-group-required>label:after{content:" *";color:#e74c3c}.wy-control-group .wy-form-full,.wy-control-group .wy-form-halves,.wy-control-group .wy-form-thirds{padding-bottom:12px}.wy-control-group .wy-form-full input[type=color],.wy-control-group .wy-form-full input[type=date],.wy-control-group .wy-form-full input[type=datetime-local],.wy-control-group .wy-form-full input[type=datetime],.wy-control-group .wy-form-full input[type=email],.wy-control-group .wy-form-full input[type=month],.wy-control-group .wy-form-full input[type=number],.wy-control-group .wy-form-full input[type=password],.wy-control-group .wy-form-full input[type=search],.wy-control-group .wy-form-full input[type=tel],.wy-control-group .wy-form-full input[type=text],.wy-control-group .wy-form-full input[type=time],.wy-control-group .wy-form-full input[type=url],.wy-control-group .wy-form-full input[type=week],.wy-control-group .wy-form-full select,.wy-control-group .wy-form-halves input[type=color],.wy-control-group .wy-form-halves input[type=date],.wy-control-group .wy-form-halves input[type=datetime-local],.wy-control-group .wy-form-halves input[type=datetime],.wy-control-group .wy-form-halves input[type=email],.wy-control-group .wy-form-halves input[type=month],.wy-control-group .wy-form-halves input[type=number],.wy-control-group .wy-form-halves input[type=password],.wy-control-group .wy-form-halves input[type=search],.wy-control-group .wy-form-halves input[type=tel],.wy-control-group .wy-form-halves input[type=text],.wy-control-group .wy-form-halves input[type=time],.wy-control-group .wy-form-halves input[type=url],.wy-control-group .wy-form-halves input[type=week],.wy-control-group .wy-form-halves select,.wy-control-group .wy-form-thirds input[type=color],.wy-control-group .wy-form-thirds input[type=date],.wy-control-group .wy-form-thirds input[type=datetime-local],.wy-control-group .wy-form-thirds input[type=datetime],.wy-control-group .wy-form-thirds input[type=email],.wy-control-group .wy-form-thirds input[type=month],.wy-control-group .wy-form-thirds input[type=number],.wy-control-group .wy-form-thirds input[type=password],.wy-control-group .wy-form-thirds input[type=search],.wy-control-group .wy-form-thirds input[type=tel],.wy-control-group .wy-form-thirds input[type=text],.wy-control-group .wy-form-thirds input[type=time],.wy-control-group .wy-form-thirds input[type=url],.wy-control-group .wy-form-thirds input[type=week],.wy-control-group .wy-form-thirds select{width:100%}.wy-control-group .wy-form-full{float:left;display:block;width:100%;margin-right:0}.wy-control-group .wy-form-full:last-child{margin-right:0}.wy-control-group .wy-form-halves{float:left;display:block;margin-right:2.35765%;width:48.82117%}.wy-control-group .wy-form-halves:last-child,.wy-control-group .wy-form-halves:nth-of-type(2n){margin-right:0}.wy-control-group .wy-form-halves:nth-of-type(odd){clear:left}.wy-control-group .wy-form-thirds{float:left;display:block;margin-right:2.35765%;width:31.76157%}.wy-control-group .wy-form-thirds:last-child,.wy-control-group .wy-form-thirds:nth-of-type(3n){margin-right:0}.wy-control-group .wy-form-thirds:nth-of-type(3n+1){clear:left}.wy-control-group.wy-control-group-no-input .wy-control,.wy-control-no-input{margin:6px 0 0;font-size:90%}.wy-control-no-input{display:inline-block}.wy-control-group.fluid-input input[type=color],.wy-control-group.fluid-input input[type=date],.wy-control-group.fluid-input input[type=datetime-local],.wy-control-group.fluid-input input[type=datetime],.wy-control-group.fluid-input input[type=email],.wy-control-group.fluid-input input[type=month],.wy-control-group.fluid-input input[type=number],.wy-control-group.fluid-input input[type=password],.wy-control-group.fluid-input input[type=search],.wy-control-group.fluid-input input[type=tel],.wy-control-group.fluid-input input[type=text],.wy-control-group.fluid-input input[type=time],.wy-control-group.fluid-input input[type=url],.wy-control-group.fluid-input input[type=week]{width:100%}.wy-form-message-inline{padding-left:.3em;color:#666;font-size:90%}.wy-form-message{display:block;color:#999;font-size:70%;margin-top:.3125em;font-style:italic}.wy-form-message p{font-size:inherit;font-style:italic;margin-bottom:6px}.wy-form-message p:last-child{margin-bottom:0}input{line-height:normal}input[type=button],input[type=reset],input[type=submit]{-webkit-appearance:button;cursor:pointer;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;*overflow:visible}input[type=color],input[type=date],input[type=datetime-local],input[type=datetime],input[type=email],input[type=month],input[type=number],input[type=password],input[type=search],input[type=tel],input[type=text],input[type=time],input[type=url],input[type=week]{-webkit-appearance:none;padding:6px;display:inline-block;border:1px solid #ccc;font-size:80%;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;box-shadow:inset 0 1px 3px #ddd;border-radius:0;-webkit-transition:border .3s linear;-moz-transition:border .3s linear;transition:border .3s linear}input[type=datetime-local]{padding:.34375em .625em}input[disabled]{cursor:default}input[type=checkbox],input[type=radio]{padding:0;margin-right:.3125em;*height:13px;*width:13px}input[type=checkbox],input[type=radio],input[type=search]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type=search]::-webkit-search-cancel-button,input[type=search]::-webkit-search-decoration{-webkit-appearance:none}input[type=color]:focus,input[type=date]:focus,input[type=datetime-local]:focus,input[type=datetime]:focus,input[type=email]:focus,input[type=month]:focus,input[type=number]:focus,input[type=password]:focus,input[type=search]:focus,input[type=tel]:focus,input[type=text]:focus,input[type=time]:focus,input[type=url]:focus,input[type=week]:focus{outline:0;outline:thin dotted\9;border-color:#333}input.no-focus:focus{border-color:#ccc!important}input[type=checkbox]:focus,input[type=file]:focus,input[type=radio]:focus{outline:thin dotted #333;outline:1px auto #129fea}input[type=color][disabled],input[type=date][disabled],input[type=datetime-local][disabled],input[type=datetime][disabled],input[type=email][disabled],input[type=month][disabled],input[type=number][disabled],input[type=password][disabled],input[type=search][disabled],input[type=tel][disabled],input[type=text][disabled],input[type=time][disabled],input[type=url][disabled],input[type=week][disabled]{cursor:not-allowed;background-color:#fafafa}input:focus:invalid,select:focus:invalid,textarea:focus:invalid{color:#e74c3c;border:1px solid #e74c3c}input:focus:invalid:focus,select:focus:invalid:focus,textarea:focus:invalid:focus{border-color:#e74c3c}input[type=checkbox]:focus:invalid:focus,input[type=file]:focus:invalid:focus,input[type=radio]:focus:invalid:focus{outline-color:#e74c3c}input.wy-input-large{padding:12px;font-size:100%}textarea{overflow:auto;vertical-align:top;width:100%;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif}select,textarea{padding:.5em .625em;display:inline-block;border:1px solid #ccc;font-size:80%;box-shadow:inset 0 1px 3px #ddd;-webkit-transition:border .3s linear;-moz-transition:border .3s linear;transition:border .3s linear}select{border:1px solid #ccc;background-color:#fff}select[multiple]{height:auto}select:focus,textarea:focus{outline:0}input[readonly],select[disabled],select[readonly],textarea[disabled],textarea[readonly]{cursor:not-allowed;background-color:#fafafa}input[type=checkbox][disabled],input[type=radio][disabled]{cursor:not-allowed}.wy-checkbox,.wy-radio{margin:6px 0;color:#404040;display:block}.wy-checkbox input,.wy-radio input{vertical-align:baseline}.wy-form-message-inline{display:inline-block;*display:inline;*zoom:1;vertical-align:middle}.wy-input-prefix,.wy-input-suffix{white-space:nowrap;padding:6px}.wy-input-prefix .wy-input-context,.wy-input-suffix .wy-input-context{line-height:27px;padding:0 8px;display:inline-block;font-size:80%;background-color:#f3f6f6;border:1px solid #ccc;color:#999}.wy-input-suffix .wy-input-context{border-left:0}.wy-input-prefix .wy-input-context{border-right:0}.wy-switch{position:relative;display:block;height:24px;margin-top:12px;cursor:pointer}.wy-switch:before{left:0;top:0;width:36px;height:12px;background:#ccc}.wy-switch:after,.wy-switch:before{position:absolute;content:"";display:block;border-radius:4px;-webkit-transition:all .2s ease-in-out;-moz-transition:all .2s ease-in-out;transition:all .2s ease-in-out}.wy-switch:after{width:18px;height:18px;background:#999;left:-3px;top:-3px}.wy-switch span{position:absolute;left:48px;display:block;font-size:12px;color:#ccc;line-height:1}.wy-switch.active:before{background:#1e8449}.wy-switch.active:after{left:24px;background:#27ae60}.wy-switch.disabled{cursor:not-allowed;opacity:.8}.wy-control-group.wy-control-group-error .wy-form-message,.wy-control-group.wy-control-group-error>label{color:#e74c3c}.wy-control-group.wy-control-group-error input[type=color],.wy-control-group.wy-control-group-error input[type=date],.wy-control-group.wy-control-group-error input[type=datetime-local],.wy-control-group.wy-control-group-error input[type=datetime],.wy-control-group.wy-control-group-error input[type=email],.wy-control-group.wy-control-group-error input[type=month],.wy-control-group.wy-control-group-error input[type=number],.wy-control-group.wy-control-group-error input[type=password],.wy-control-group.wy-control-group-error input[type=search],.wy-control-group.wy-control-group-error input[type=tel],.wy-control-group.wy-control-group-error input[type=text],.wy-control-group.wy-control-group-error input[type=time],.wy-control-group.wy-control-group-error input[type=url],.wy-control-group.wy-control-group-error input[type=week],.wy-control-group.wy-control-group-error textarea{border:1px solid #e74c3c}.wy-inline-validate{white-space:nowrap}.wy-inline-validate .wy-input-context{padding:.5em .625em;display:inline-block;font-size:80%}.wy-inline-validate.wy-inline-validate-success .wy-input-context{color:#27ae60}.wy-inline-validate.wy-inline-validate-danger .wy-input-context{color:#e74c3c}.wy-inline-validate.wy-inline-validate-warning .wy-input-context{color:#e67e22}.wy-inline-validate.wy-inline-validate-info .wy-input-context{color:#2980b9}.rotate-90{-webkit-transform:rotate(90deg);-moz-transform:rotate(90deg);-ms-transform:rotate(90deg);-o-transform:rotate(90deg);transform:rotate(90deg)}.rotate-180{-webkit-transform:rotate(180deg);-moz-transform:rotate(180deg);-ms-transform:rotate(180deg);-o-transform:rotate(180deg);transform:rotate(180deg)}.rotate-270{-webkit-transform:rotate(270deg);-moz-transform:rotate(270deg);-ms-transform:rotate(270deg);-o-transform:rotate(270deg);transform:rotate(270deg)}.mirror{-webkit-transform:scaleX(-1);-moz-transform:scaleX(-1);-ms-transform:scaleX(-1);-o-transform:scaleX(-1);transform:scaleX(-1)}.mirror.rotate-90{-webkit-transform:scaleX(-1) rotate(90deg);-moz-transform:scaleX(-1) rotate(90deg);-ms-transform:scaleX(-1) rotate(90deg);-o-transform:scaleX(-1) rotate(90deg);transform:scaleX(-1) rotate(90deg)}.mirror.rotate-180{-webkit-transform:scaleX(-1) rotate(180deg);-moz-transform:scaleX(-1) rotate(180deg);-ms-transform:scaleX(-1) rotate(180deg);-o-transform:scaleX(-1) rotate(180deg);transform:scaleX(-1) rotate(180deg)}.mirror.rotate-270{-webkit-transform:scaleX(-1) rotate(270deg);-moz-transform:scaleX(-1) rotate(270deg);-ms-transform:scaleX(-1) rotate(270deg);-o-transform:scaleX(-1) rotate(270deg);transform:scaleX(-1) rotate(270deg)}@media only screen and (max-width:480px){.wy-form button[type=submit]{margin:.7em 0 0}.wy-form input[type=color],.wy-form input[type=date],.wy-form input[type=datetime-local],.wy-form input[type=datetime],.wy-form input[type=email],.wy-form input[type=month],.wy-form input[type=number],.wy-form input[type=password],.wy-form input[type=search],.wy-form input[type=tel],.wy-form input[type=text],.wy-form input[type=time],.wy-form input[type=url],.wy-form input[type=week],.wy-form label{margin-bottom:.3em;display:block}.wy-form input[type=color],.wy-form input[type=date],.wy-form input[type=datetime-local],.wy-form input[type=datetime],.wy-form input[type=email],.wy-form input[type=month],.wy-form input[type=number],.wy-form input[type=password],.wy-form input[type=search],.wy-form input[type=tel],.wy-form input[type=time],.wy-form input[type=url],.wy-form input[type=week]{margin-bottom:0}.wy-form-aligned .wy-control-group label{margin-bottom:.3em;text-align:left;display:block;width:100%}.wy-form-aligned .wy-control{margin:1.5em 0 0}.wy-form-message,.wy-form-message-inline,.wy-form .wy-help-inline{display:block;font-size:80%;padding:6px 0}}@media screen and (max-width:768px){.tablet-hide{display:none}}@media screen and (max-width:480px){.mobile-hide{display:none}}.float-left{float:left}.float-right{float:right}.full-width{width:100%}.rst-content table.docutils,.rst-content table.field-list,.wy-table{border-collapse:collapse;border-spacing:0;empty-cells:show;margin-bottom:24px}.rst-content table.docutils caption,.rst-content table.field-list caption,.wy-table caption{color:#000;font:italic 85%/1 arial,sans-serif;padding:1em 0;text-align:center}.rst-content table.docutils td,.rst-content table.docutils th,.rst-content table.field-list td,.rst-content table.field-list th,.wy-table td,.wy-table th{font-size:90%;margin:0;overflow:visible;padding:8px 16px}.rst-content table.docutils td:first-child,.rst-content table.docutils th:first-child,.rst-content table.field-list td:first-child,.rst-content table.field-list th:first-child,.wy-table td:first-child,.wy-table th:first-child{border-left-width:0}.rst-content table.docutils thead,.rst-content table.field-list thead,.wy-table thead{color:#000;text-align:left;vertical-align:bottom;white-space:nowrap}.rst-content table.docutils thead th,.rst-content table.field-list thead th,.wy-table thead th{font-weight:700;border-bottom:2px solid #e1e4e5}.rst-content table.docutils td,.rst-content table.field-list td,.wy-table td{background-color:transparent;vertical-align:middle}.rst-content table.docutils td p,.rst-content table.field-list td p,.wy-table td p{line-height:18px}.rst-content table.docutils td p:last-child,.rst-content table.field-list td p:last-child,.wy-table td p:last-child{margin-bottom:0}.rst-content table.docutils .wy-table-cell-min,.rst-content table.field-list .wy-table-cell-min,.wy-table .wy-table-cell-min{width:1%;padding-right:0}.rst-content table.docutils .wy-table-cell-min input[type=checkbox],.rst-content table.field-list .wy-table-cell-min input[type=checkbox],.wy-table .wy-table-cell-min input[type=checkbox]{margin:0}.wy-table-secondary{color:grey;font-size:90%}.wy-table-tertiary{color:grey;font-size:80%}.rst-content table.docutils:not(.field-list) tr:nth-child(2n-1) td,.wy-table-backed,.wy-table-odd td,.wy-table-striped tr:nth-child(2n-1) td{background-color:#f3f6f6}.rst-content table.docutils,.wy-table-bordered-all{border:1px solid #e1e4e5}.rst-content table.docutils td,.wy-table-bordered-all td{border-bottom:1px solid #e1e4e5;border-left:1px solid #e1e4e5}.rst-content table.docutils tbody>tr:last-child td,.wy-table-bordered-all tbody>tr:last-child td{border-bottom-width:0}.wy-table-bordered{border:1px solid #e1e4e5}.wy-table-bordered-rows td{border-bottom:1px solid #e1e4e5}.wy-table-bordered-rows tbody>tr:last-child td{border-bottom-width:0}.wy-table-horizontal td,.wy-table-horizontal th{border-width:0 0 1px;border-bottom:1px solid #e1e4e5}.wy-table-horizontal tbody>tr:last-child td{border-bottom-width:0}.wy-table-responsive{margin-bottom:24px;max-width:100%;overflow:auto}.wy-table-responsive table{margin-bottom:0!important}.wy-table-responsive table td,.wy-table-responsive table th{white-space:nowrap}a{color:#2980b9;text-decoration:none;cursor:pointer}a:hover{color:#3091d1}a:visited{color:#9b59b6}html{height:100%}body,html{overflow-x:hidden}body{font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;font-weight:400;color:#404040;min-height:100%;background:#edf0f2}.wy-text-left{text-align:left}.wy-text-center{text-align:center}.wy-text-right{text-align:right}.wy-text-large{font-size:120%}.wy-text-normal{font-size:100%}.wy-text-small,small{font-size:80%}.wy-text-strike{text-decoration:line-through}.wy-text-warning{color:#e67e22!important}a.wy-text-warning:hover{color:#eb9950!important}.wy-text-info{color:#2980b9!important}a.wy-text-info:hover{color:#409ad5!important}.wy-text-success{color:#27ae60!important}a.wy-text-success:hover{color:#36d278!important}.wy-text-danger{color:#e74c3c!important}a.wy-text-danger:hover{color:#ed7669!important}.wy-text-neutral{color:#404040!important}a.wy-text-neutral:hover{color:#595959!important}.rst-content .toctree-wrapper>p.caption,h1,h2,h3,h4,h5,h6,legend{margin-top:0;font-weight:700;font-family:Roboto Slab,ff-tisa-web-pro,Georgia,Arial,sans-serif}p{line-height:24px;font-size:16px;margin:0 0 24px}h1{font-size:175%}.rst-content .toctree-wrapper>p.caption,h2{font-size:150%}h3{font-size:125%}h4{font-size:115%}h5{font-size:110%}h6{font-size:100%}hr{display:block;height:1px;border:0;border-top:1px solid #e1e4e5;margin:24px 0;padding:0}.rst-content code,.rst-content tt,code{white-space:nowrap;max-width:100%;background:#fff;border:1px solid #e1e4e5;font-size:75%;padding:0 5px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;color:#e74c3c;overflow-x:auto}.rst-content tt.code-large,code.code-large{font-size:90%}.rst-content .section ul,.rst-content .toctree-wrapper ul,.rst-content section ul,.wy-plain-list-disc,article ul{list-style:disc;line-height:24px;margin-bottom:24px}.rst-content .section ul li,.rst-content .toctree-wrapper ul li,.rst-content section ul li,.wy-plain-list-disc li,article ul li{list-style:disc;margin-left:24px}.rst-content .section ul li p:last-child,.rst-content .section ul li ul,.rst-content .toctree-wrapper ul li p:last-child,.rst-content .toctree-wrapper ul li ul,.rst-content section ul li p:last-child,.rst-content section ul li ul,.wy-plain-list-disc li p:last-child,.wy-plain-list-disc li ul,article ul li p:last-child,article ul li ul{margin-bottom:0}.rst-content .section ul li li,.rst-content .toctree-wrapper ul li li,.rst-content section ul li li,.wy-plain-list-disc li li,article ul li li{list-style:circle}.rst-content .section ul li li li,.rst-content .toctree-wrapper ul li li li,.rst-content section ul li li li,.wy-plain-list-disc li li li,article ul li li li{list-style:square}.rst-content .section ul li ol li,.rst-content .toctree-wrapper ul li ol li,.rst-content section ul li ol li,.wy-plain-list-disc li ol li,article ul li ol li{list-style:decimal}.rst-content .section ol,.rst-content .section ol.arabic,.rst-content .toctree-wrapper ol,.rst-content .toctree-wrapper ol.arabic,.rst-content section ol,.rst-content section ol.arabic,.wy-plain-list-decimal,article ol{list-style:decimal;line-height:24px;margin-bottom:24px}.rst-content .section ol.arabic li,.rst-content .section ol li,.rst-content .toctree-wrapper ol.arabic li,.rst-content .toctree-wrapper ol li,.rst-content section ol.arabic li,.rst-content section ol li,.wy-plain-list-decimal li,article ol li{list-style:decimal;margin-left:24px}.rst-content .section ol.arabic li ul,.rst-content .section ol li p:last-child,.rst-content .section ol li ul,.rst-content .toctree-wrapper ol.arabic li ul,.rst-content .toctree-wrapper ol li p:last-child,.rst-content .toctree-wrapper ol li ul,.rst-content section ol.arabic li ul,.rst-content section ol li p:last-child,.rst-content section ol li ul,.wy-plain-list-decimal li p:last-child,.wy-plain-list-decimal li ul,article ol li p:last-child,article ol li ul{margin-bottom:0}.rst-content .section ol.arabic li ul li,.rst-content .section ol li ul li,.rst-content .toctree-wrapper ol.arabic li ul li,.rst-content .toctree-wrapper ol li ul li,.rst-content section ol.arabic li ul li,.rst-content section ol li ul li,.wy-plain-list-decimal li ul li,article ol li ul li{list-style:disc}.wy-breadcrumbs{*zoom:1}.wy-breadcrumbs:after,.wy-breadcrumbs:before{display:table;content:""}.wy-breadcrumbs:after{clear:both}.wy-breadcrumbs li{display:inline-block}.wy-breadcrumbs li.wy-breadcrumbs-aside{float:right}.wy-breadcrumbs li a{display:inline-block;padding:5px}.wy-breadcrumbs li a:first-child{padding-left:0}.rst-content .wy-breadcrumbs li tt,.wy-breadcrumbs li .rst-content tt,.wy-breadcrumbs li code{padding:5px;border:none;background:none}.rst-content .wy-breadcrumbs li tt.literal,.wy-breadcrumbs li .rst-content tt.literal,.wy-breadcrumbs li code.literal{color:#404040}.wy-breadcrumbs-extra{margin-bottom:0;color:#b3b3b3;font-size:80%;display:inline-block}@media screen and (max-width:480px){.wy-breadcrumbs-extra,.wy-breadcrumbs li.wy-breadcrumbs-aside{display:none}}@media print{.wy-breadcrumbs li.wy-breadcrumbs-aside{display:none}}html{font-size:16px}.wy-affix{position:fixed;top:1.618em}.wy-menu a:hover{text-decoration:none}.wy-menu-horiz{*zoom:1}.wy-menu-horiz:after,.wy-menu-horiz:before{display:table;content:""}.wy-menu-horiz:after{clear:both}.wy-menu-horiz li,.wy-menu-horiz ul{display:inline-block}.wy-menu-horiz li:hover{background:hsla(0,0%,100%,.1)}.wy-menu-horiz li.divide-left{border-left:1px solid #404040}.wy-menu-horiz li.divide-right{border-right:1px solid #404040}.wy-menu-horiz a{height:32px;display:inline-block;line-height:32px;padding:0 16px}.wy-menu-vertical{width:300px}.wy-menu-vertical header,.wy-menu-vertical p.caption{color:#55a5d9;height:32px;line-height:32px;padding:0 1.618em;margin:12px 0 0;display:block;font-weight:700;text-transform:uppercase;font-size:85%;white-space:nowrap}.wy-menu-vertical ul{margin-bottom:0}.wy-menu-vertical li.divide-top{border-top:1px solid #404040}.wy-menu-vertical li.divide-bottom{border-bottom:1px solid #404040}.wy-menu-vertical li.current{background:#e3e3e3}.wy-menu-vertical li.current a{color:grey;border-right:1px solid #c9c9c9;padding:.4045em 2.427em}.wy-menu-vertical li.current a:hover{background:#d6d6d6}.rst-content .wy-menu-vertical li tt,.wy-menu-vertical li .rst-content tt,.wy-menu-vertical li code{border:none;background:inherit;color:inherit;padding-left:0;padding-right:0}.wy-menu-vertical li button.toctree-expand{display:block;float:left;margin-left:-1.2em;line-height:18px;color:#4d4d4d;border:none;background:none;padding:0}.wy-menu-vertical li.current>a,.wy-menu-vertical li.on a{color:#404040;font-weight:700;position:relative;background:#fcfcfc;border:none;padding:.4045em 1.618em}.wy-menu-vertical li.current>a:hover,.wy-menu-vertical li.on a:hover{background:#fcfcfc}.wy-menu-vertical li.current>a:hover button.toctree-expand,.wy-menu-vertical li.on a:hover button.toctree-expand{color:grey}.wy-menu-vertical li.current>a button.toctree-expand,.wy-menu-vertical li.on a button.toctree-expand{display:block;line-height:18px;color:#333}.wy-menu-vertical li.toctree-l1.current>a{border-bottom:1px solid #c9c9c9;border-top:1px solid #c9c9c9}.wy-menu-vertical .toctree-l1.current .toctree-l2>ul,.wy-menu-vertical .toctree-l2.current .toctree-l3>ul,.wy-menu-vertical .toctree-l3.current .toctree-l4>ul,.wy-menu-vertical .toctree-l4.current .toctree-l5>ul,.wy-menu-vertical .toctree-l5.current .toctree-l6>ul,.wy-menu-vertical .toctree-l6.current .toctree-l7>ul,.wy-menu-vertical .toctree-l7.current .toctree-l8>ul,.wy-menu-vertical .toctree-l8.current .toctree-l9>ul,.wy-menu-vertical .toctree-l9.current .toctree-l10>ul,.wy-menu-vertical .toctree-l10.current .toctree-l11>ul{display:none}.wy-menu-vertical .toctree-l1.current .current.toctree-l2>ul,.wy-menu-vertical .toctree-l2.current .current.toctree-l3>ul,.wy-menu-vertical .toctree-l3.current .current.toctree-l4>ul,.wy-menu-vertical .toctree-l4.current .current.toctree-l5>ul,.wy-menu-vertical .toctree-l5.current .current.toctree-l6>ul,.wy-menu-vertical .toctree-l6.current .current.toctree-l7>ul,.wy-menu-vertical .toctree-l7.current .current.toctree-l8>ul,.wy-menu-vertical .toctree-l8.current .current.toctree-l9>ul,.wy-menu-vertical .toctree-l9.current .current.toctree-l10>ul,.wy-menu-vertical .toctree-l10.current .current.toctree-l11>ul{display:block}.wy-menu-vertical li.toctree-l3,.wy-menu-vertical li.toctree-l4{font-size:.9em}.wy-menu-vertical li.toctree-l2 a,.wy-menu-vertical li.toctree-l3 a,.wy-menu-vertical li.toctree-l4 a,.wy-menu-vertical li.toctree-l5 a,.wy-menu-vertical li.toctree-l6 a,.wy-menu-vertical li.toctree-l7 a,.wy-menu-vertical li.toctree-l8 a,.wy-menu-vertical li.toctree-l9 a,.wy-menu-vertical li.toctree-l10 a{color:#404040}.wy-menu-vertical li.toctree-l2 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l3 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l4 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l5 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l6 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l7 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l8 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l9 a:hover button.toctree-expand,.wy-menu-vertical li.toctree-l10 a:hover button.toctree-expand{color:grey}.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a,.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a,.wy-menu-vertical li.toctree-l4.current li.toctree-l5>a,.wy-menu-vertical li.toctree-l5.current li.toctree-l6>a,.wy-menu-vertical li.toctree-l6.current li.toctree-l7>a,.wy-menu-vertical li.toctree-l7.current li.toctree-l8>a,.wy-menu-vertical li.toctree-l8.current li.toctree-l9>a,.wy-menu-vertical li.toctree-l9.current li.toctree-l10>a,.wy-menu-vertical li.toctree-l10.current li.toctree-l11>a{display:block}.wy-menu-vertical li.toctree-l2.current>a{padding:.4045em 2.427em}.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a{padding:.4045em 1.618em .4045em 4.045em}.wy-menu-vertical li.toctree-l3.current>a{padding:.4045em 4.045em}.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a{padding:.4045em 1.618em .4045em 5.663em}.wy-menu-vertical li.toctree-l4.current>a{padding:.4045em 5.663em}.wy-menu-vertical li.toctree-l4.current li.toctree-l5>a{padding:.4045em 1.618em .4045em 7.281em}.wy-menu-vertical li.toctree-l5.current>a{padding:.4045em 7.281em}.wy-menu-vertical li.toctree-l5.current li.toctree-l6>a{padding:.4045em 1.618em .4045em 8.899em}.wy-menu-vertical li.toctree-l6.current>a{padding:.4045em 8.899em}.wy-menu-vertical li.toctree-l6.current li.toctree-l7>a{padding:.4045em 1.618em .4045em 10.517em}.wy-menu-vertical li.toctree-l7.current>a{padding:.4045em 10.517em}.wy-menu-vertical li.toctree-l7.current li.toctree-l8>a{padding:.4045em 1.618em .4045em 12.135em}.wy-menu-vertical li.toctree-l8.current>a{padding:.4045em 12.135em}.wy-menu-vertical li.toctree-l8.current li.toctree-l9>a{padding:.4045em 1.618em .4045em 13.753em}.wy-menu-vertical li.toctree-l9.current>a{padding:.4045em 13.753em}.wy-menu-vertical li.toctree-l9.current li.toctree-l10>a{padding:.4045em 1.618em .4045em 15.371em}.wy-menu-vertical li.toctree-l10.current>a{padding:.4045em 15.371em}.wy-menu-vertical li.toctree-l10.current li.toctree-l11>a{padding:.4045em 1.618em .4045em 16.989em}.wy-menu-vertical li.toctree-l2.current>a,.wy-menu-vertical li.toctree-l2.current li.toctree-l3>a{background:#c9c9c9}.wy-menu-vertical li.toctree-l2 button.toctree-expand{color:#a3a3a3}.wy-menu-vertical li.toctree-l3.current>a,.wy-menu-vertical li.toctree-l3.current li.toctree-l4>a{background:#bdbdbd}.wy-menu-vertical li.toctree-l3 button.toctree-expand{color:#969696}.wy-menu-vertical li.current ul{display:block}.wy-menu-vertical li ul{margin-bottom:0;display:none}.wy-menu-vertical li ul li a{margin-bottom:0;color:#d9d9d9;font-weight:400}.wy-menu-vertical a{line-height:18px;padding:.4045em 1.618em;display:block;position:relative;font-size:90%;color:#d9d9d9}.wy-menu-vertical a:hover{background-color:#4e4a4a;cursor:pointer}.wy-menu-vertical a:hover button.toctree-expand{color:#d9d9d9}.wy-menu-vertical a:active{background-color:#2980b9;cursor:pointer;color:#fff}.wy-menu-vertical a:active button.toctree-expand{color:#fff}.wy-side-nav-search{display:block;width:300px;padding:.809em;margin-bottom:.809em;z-index:200;background-color:#2980b9;text-align:center;color:#fcfcfc}.wy-side-nav-search input[type=text]{width:100%;border-radius:50px;padding:6px 12px;border-color:#2472a4}.wy-side-nav-search img{display:block;margin:auto auto .809em;height:45px;width:45px;background-color:#2980b9;padding:5px;border-radius:100%}.wy-side-nav-search .wy-dropdown>a,.wy-side-nav-search>a{color:#fcfcfc;font-size:100%;font-weight:700;display:inline-block;padding:4px 6px;margin-bottom:.809em;max-width:100%}.wy-side-nav-search .wy-dropdown>a:hover,.wy-side-nav-search>a:hover{background:hsla(0,0%,100%,.1)}.wy-side-nav-search .wy-dropdown>a img.logo,.wy-side-nav-search>a img.logo{display:block;margin:0 auto;height:auto;width:auto;border-radius:0;max-width:100%;background:transparent}.wy-side-nav-search .wy-dropdown>a.icon img.logo,.wy-side-nav-search>a.icon img.logo{margin-top:.85em}.wy-side-nav-search>div.version{margin-top:-.4045em;margin-bottom:.809em;font-weight:400;color:hsla(0,0%,100%,.3)}.wy-nav .wy-menu-vertical header{color:#2980b9}.wy-nav .wy-menu-vertical a{color:#b3b3b3}.wy-nav .wy-menu-vertical a:hover{background-color:#2980b9;color:#fff}[data-menu-wrap]{-webkit-transition:all .2s ease-in;-moz-transition:all .2s ease-in;transition:all .2s ease-in;position:absolute;opacity:1;width:100%;opacity:0}[data-menu-wrap].move-center{left:0;right:auto;opacity:1}[data-menu-wrap].move-left{right:auto;left:-100%;opacity:0}[data-menu-wrap].move-right{right:-100%;left:auto;opacity:0}.wy-body-for-nav{background:#fcfcfc}.wy-grid-for-nav{position:absolute;width:100%;height:100%}.wy-nav-side{position:fixed;top:0;bottom:0;left:0;padding-bottom:2em;width:300px;overflow-x:hidden;overflow-y:hidden;min-height:100%;color:#9b9b9b;background:#343131;z-index:200}.wy-side-scroll{width:320px;position:relative;overflow-x:hidden;overflow-y:scroll;height:100%}.wy-nav-top{display:none;background:#2980b9;color:#fff;padding:.4045em .809em;position:relative;line-height:50px;text-align:center;font-size:100%;*zoom:1}.wy-nav-top:after,.wy-nav-top:before{display:table;content:""}.wy-nav-top:after{clear:both}.wy-nav-top a{color:#fff;font-weight:700}.wy-nav-top img{margin-right:12px;height:45px;width:45px;background-color:#2980b9;padding:5px;border-radius:100%}.wy-nav-top i{font-size:30px;float:left;cursor:pointer;padding-top:inherit}.wy-nav-content-wrap{margin-left:300px;background:#fcfcfc;min-height:100%}.wy-nav-content{padding:1.618em 3.236em;height:100%;max-width:800px;margin:auto}.wy-body-mask{position:fixed;width:100%;height:100%;background:rgba(0,0,0,.2);display:none;z-index:499}.wy-body-mask.on{display:block}footer{color:grey}footer p{margin-bottom:12px}.rst-content footer span.commit tt,footer span.commit .rst-content tt,footer span.commit code{padding:0;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;font-size:1em;background:none;border:none;color:grey}.rst-footer-buttons{*zoom:1}.rst-footer-buttons:after,.rst-footer-buttons:before{width:100%;display:table;content:""}.rst-footer-buttons:after{clear:both}.rst-breadcrumbs-buttons{margin-top:12px;*zoom:1}.rst-breadcrumbs-buttons:after,.rst-breadcrumbs-buttons:before{display:table;content:""}.rst-breadcrumbs-buttons:after{clear:both}#search-results .search li{margin-bottom:24px;border-bottom:1px solid #e1e4e5;padding-bottom:24px}#search-results .search li:first-child{border-top:1px solid #e1e4e5;padding-top:24px}#search-results .search li a{font-size:120%;margin-bottom:12px;display:inline-block}#search-results .context{color:grey;font-size:90%}.genindextable li>ul{margin-left:24px}@media screen and (max-width:768px){.wy-body-for-nav{background:#fcfcfc}.wy-nav-top{display:block}.wy-nav-side{left:-300px}.wy-nav-side.shift{width:85%;left:0}.wy-menu.wy-menu-vertical,.wy-side-nav-search,.wy-side-scroll{width:auto}.wy-nav-content-wrap{margin-left:0}.wy-nav-content-wrap .wy-nav-content{padding:1.618em}.wy-nav-content-wrap.shift{position:fixed;min-width:100%;left:85%;top:0;height:100%;overflow:hidden}}@media screen and (min-width:1100px){.wy-nav-content-wrap{background:rgba(0,0,0,.05)}.wy-nav-content{margin:0;background:#fcfcfc}}@media print{.rst-versions,.wy-nav-side,footer{display:none}.wy-nav-content-wrap{margin-left:0}}.rst-versions{position:fixed;bottom:0;left:0;width:300px;color:#fcfcfc;background:#1f1d1d;font-family:Lato,proxima-nova,Helvetica Neue,Arial,sans-serif;z-index:400}.rst-versions a{color:#2980b9;text-decoration:none}.rst-versions .rst-badge-small{display:none}.rst-versions .rst-current-version{padding:12px;background-color:#272525;display:block;text-align:right;font-size:90%;cursor:pointer;color:#27ae60;*zoom:1}.rst-versions .rst-current-version:after,.rst-versions .rst-current-version:before{display:table;content:""}.rst-versions .rst-current-version:after{clear:both}.rst-content .code-block-caption .rst-versions .rst-current-version .headerlink,.rst-content .eqno .rst-versions .rst-current-version .headerlink,.rst-content .rst-versions .rst-current-version .admonition-title,.rst-content code.download .rst-versions .rst-current-version span:first-child,.rst-content dl dt .rst-versions .rst-current-version .headerlink,.rst-content h1 .rst-versions .rst-current-version .headerlink,.rst-content h2 .rst-versions .rst-current-version .headerlink,.rst-content h3 .rst-versions .rst-current-version .headerlink,.rst-content h4 .rst-versions .rst-current-version .headerlink,.rst-content h5 .rst-versions .rst-current-version .headerlink,.rst-content h6 .rst-versions .rst-current-version .headerlink,.rst-content p .rst-versions .rst-current-version .headerlink,.rst-content table>caption .rst-versions .rst-current-version .headerlink,.rst-content tt.download .rst-versions .rst-current-version span:first-child,.rst-versions .rst-current-version .fa,.rst-versions .rst-current-version .icon,.rst-versions .rst-current-version .rst-content .admonition-title,.rst-versions .rst-current-version .rst-content .code-block-caption .headerlink,.rst-versions .rst-current-version .rst-content .eqno .headerlink,.rst-versions .rst-current-version .rst-content code.download span:first-child,.rst-versions .rst-current-version .rst-content dl dt .headerlink,.rst-versions .rst-current-version .rst-content h1 .headerlink,.rst-versions .rst-current-version .rst-content h2 .headerlink,.rst-versions .rst-current-version .rst-content h3 .headerlink,.rst-versions .rst-current-version .rst-content h4 .headerlink,.rst-versions .rst-current-version .rst-content h5 .headerlink,.rst-versions .rst-current-version .rst-content h6 .headerlink,.rst-versions .rst-current-version .rst-content p .headerlink,.rst-versions .rst-current-version .rst-content table>caption .headerlink,.rst-versions .rst-current-version .rst-content tt.download span:first-child,.rst-versions .rst-current-version .wy-menu-vertical li button.toctree-expand,.wy-menu-vertical li .rst-versions .rst-current-version button.toctree-expand{color:#fcfcfc}.rst-versions .rst-current-version .fa-book,.rst-versions .rst-current-version .icon-book{float:left}.rst-versions .rst-current-version.rst-out-of-date{background-color:#e74c3c;color:#fff}.rst-versions .rst-current-version.rst-active-old-version{background-color:#f1c40f;color:#000}.rst-versions.shift-up{height:auto;max-height:100%;overflow-y:scroll}.rst-versions.shift-up .rst-other-versions{display:block}.rst-versions .rst-other-versions{font-size:90%;padding:12px;color:grey;display:none}.rst-versions .rst-other-versions hr{display:block;height:1px;border:0;margin:20px 0;padding:0;border-top:1px solid #413d3d}.rst-versions .rst-other-versions dd{display:inline-block;margin:0}.rst-versions .rst-other-versions dd a{display:inline-block;padding:6px;color:#fcfcfc}.rst-versions.rst-badge{width:auto;bottom:20px;right:20px;left:auto;border:none;max-width:300px;max-height:90%}.rst-versions.rst-badge .fa-book,.rst-versions.rst-badge .icon-book{float:none;line-height:30px}.rst-versions.rst-badge.shift-up .rst-current-version{text-align:right}.rst-versions.rst-badge.shift-up .rst-current-version .fa-book,.rst-versions.rst-badge.shift-up .rst-current-version .icon-book{float:left}.rst-versions.rst-badge>.rst-current-version{width:auto;height:30px;line-height:30px;padding:0 6px;display:block;text-align:center}@media screen and (max-width:768px){.rst-versions{width:85%;display:none}.rst-versions.shift{display:block}}.rst-content .toctree-wrapper>p.caption,.rst-content h1,.rst-content h2,.rst-content h3,.rst-content h4,.rst-content h5,.rst-content h6{margin-bottom:24px}.rst-content img{max-width:100%;height:auto}.rst-content div.figure,.rst-content figure{margin-bottom:24px}.rst-content div.figure .caption-text,.rst-content figure .caption-text{font-style:italic}.rst-content div.figure p:last-child.caption,.rst-content figure p:last-child.caption{margin-bottom:0}.rst-content div.figure.align-center,.rst-content figure.align-center{text-align:center}.rst-content .section>a>img,.rst-content .section>img,.rst-content section>a>img,.rst-content section>img{margin-bottom:24px}.rst-content abbr[title]{text-decoration:none}.rst-content.style-external-links a.reference.external:after{font-family:FontAwesome;content:"\f08e";color:#b3b3b3;vertical-align:super;font-size:60%;margin:0 .2em}.rst-content blockquote{margin-left:24px;line-height:24px;margin-bottom:24px}.rst-content pre.literal-block{white-space:pre;margin:0;padding:12px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;display:block;overflow:auto}.rst-content div[class^=highlight],.rst-content pre.literal-block{border:1px solid #e1e4e5;overflow-x:auto;margin:1px 0 24px}.rst-content div[class^=highlight] div[class^=highlight],.rst-content pre.literal-block div[class^=highlight]{padding:0;border:none;margin:0}.rst-content div[class^=highlight] td.code{width:100%}.rst-content .linenodiv pre{border-right:1px solid #e6e9ea;margin:0;padding:12px;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;user-select:none;pointer-events:none}.rst-content div[class^=highlight] pre{white-space:pre;margin:0;padding:12px;display:block;overflow:auto}.rst-content div[class^=highlight] pre .hll{display:block;margin:0 -12px;padding:0 12px}.rst-content .linenodiv pre,.rst-content div[class^=highlight] pre,.rst-content pre.literal-block{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;font-size:12px;line-height:1.4}.rst-content div.highlight .gp,.rst-content div.highlight span.linenos{user-select:none;pointer-events:none}.rst-content div.highlight span.linenos{display:inline-block;padding-left:0;padding-right:12px;margin-right:12px;border-right:1px solid #e6e9ea}.rst-content .code-block-caption{font-style:italic;font-size:85%;line-height:1;padding:1em 0;text-align:center}@media print{.rst-content .codeblock,.rst-content div[class^=highlight],.rst-content div[class^=highlight] pre{white-space:pre-wrap}}.rst-content .admonition,.rst-content .admonition-todo,.rst-content .attention,.rst-content .caution,.rst-content .danger,.rst-content .error,.rst-content .hint,.rst-content .important,.rst-content .note,.rst-content .seealso,.rst-content .tip,.rst-content .warning{clear:both}.rst-content .admonition-todo .last,.rst-content .admonition-todo>:last-child,.rst-content .admonition .last,.rst-content .admonition>:last-child,.rst-content .attention .last,.rst-content .attention>:last-child,.rst-content .caution .last,.rst-content .caution>:last-child,.rst-content .danger .last,.rst-content .danger>:last-child,.rst-content .error .last,.rst-content .error>:last-child,.rst-content .hint .last,.rst-content .hint>:last-child,.rst-content .important .last,.rst-content .important>:last-child,.rst-content .note .last,.rst-content .note>:last-child,.rst-content .seealso .last,.rst-content .seealso>:last-child,.rst-content .tip .last,.rst-content .tip>:last-child,.rst-content .warning .last,.rst-content .warning>:last-child{margin-bottom:0}.rst-content .admonition-title:before{margin-right:4px}.rst-content .admonition table{border-color:rgba(0,0,0,.1)}.rst-content .admonition table td,.rst-content .admonition table th{background:transparent!important;border-color:rgba(0,0,0,.1)!important}.rst-content .section ol.loweralpha,.rst-content .section ol.loweralpha>li,.rst-content .toctree-wrapper ol.loweralpha,.rst-content .toctree-wrapper ol.loweralpha>li,.rst-content section ol.loweralpha,.rst-content section ol.loweralpha>li{list-style:lower-alpha}.rst-content .section ol.upperalpha,.rst-content .section ol.upperalpha>li,.rst-content .toctree-wrapper ol.upperalpha,.rst-content .toctree-wrapper ol.upperalpha>li,.rst-content section ol.upperalpha,.rst-content section ol.upperalpha>li{list-style:upper-alpha}.rst-content .section ol li>*,.rst-content .section ul li>*,.rst-content .toctree-wrapper ol li>*,.rst-content .toctree-wrapper ul li>*,.rst-content section ol li>*,.rst-content section ul li>*{margin-top:12px;margin-bottom:12px}.rst-content .section ol li>:first-child,.rst-content .section ul li>:first-child,.rst-content .toctree-wrapper ol li>:first-child,.rst-content .toctree-wrapper ul li>:first-child,.rst-content section ol li>:first-child,.rst-content section ul li>:first-child{margin-top:0}.rst-content .section ol li>p,.rst-content .section ol li>p:last-child,.rst-content .section ul li>p,.rst-content .section ul li>p:last-child,.rst-content .toctree-wrapper ol li>p,.rst-content .toctree-wrapper ol li>p:last-child,.rst-content .toctree-wrapper ul li>p,.rst-content .toctree-wrapper ul li>p:last-child,.rst-content section ol li>p,.rst-content section ol li>p:last-child,.rst-content section ul li>p,.rst-content section ul li>p:last-child{margin-bottom:12px}.rst-content .section ol li>p:only-child,.rst-content .section ol li>p:only-child:last-child,.rst-content .section ul li>p:only-child,.rst-content .section ul li>p:only-child:last-child,.rst-content .toctree-wrapper ol li>p:only-child,.rst-content .toctree-wrapper ol li>p:only-child:last-child,.rst-content .toctree-wrapper ul li>p:only-child,.rst-content .toctree-wrapper ul li>p:only-child:last-child,.rst-content section ol li>p:only-child,.rst-content section ol li>p:only-child:last-child,.rst-content section ul li>p:only-child,.rst-content section ul li>p:only-child:last-child{margin-bottom:0}.rst-content .section ol li>ol,.rst-content .section ol li>ul,.rst-content .section ul li>ol,.rst-content .section ul li>ul,.rst-content .toctree-wrapper ol li>ol,.rst-content .toctree-wrapper ol li>ul,.rst-content .toctree-wrapper ul li>ol,.rst-content .toctree-wrapper ul li>ul,.rst-content section ol li>ol,.rst-content section ol li>ul,.rst-content section ul li>ol,.rst-content section ul li>ul{margin-bottom:12px}.rst-content .section ol.simple li>*,.rst-content .section ol.simple li ol,.rst-content .section ol.simple li ul,.rst-content .section ul.simple li>*,.rst-content .section ul.simple li ol,.rst-content .section ul.simple li ul,.rst-content .toctree-wrapper ol.simple li>*,.rst-content .toctree-wrapper ol.simple li ol,.rst-content .toctree-wrapper ol.simple li ul,.rst-content .toctree-wrapper ul.simple li>*,.rst-content .toctree-wrapper ul.simple li ol,.rst-content .toctree-wrapper ul.simple li ul,.rst-content section ol.simple li>*,.rst-content section ol.simple li ol,.rst-content section ol.simple li ul,.rst-content section ul.simple li>*,.rst-content section ul.simple li ol,.rst-content section ul.simple li ul{margin-top:0;margin-bottom:0}.rst-content .line-block{margin-left:0;margin-bottom:24px;line-height:24px}.rst-content .line-block .line-block{margin-left:24px;margin-bottom:0}.rst-content .topic-title{font-weight:700;margin-bottom:12px}.rst-content .toc-backref{color:#404040}.rst-content .align-right{float:right;margin:0 0 24px 24px}.rst-content .align-left{float:left;margin:0 24px 24px 0}.rst-content .align-center{margin:auto}.rst-content .align-center:not(table){display:block}.rst-content .code-block-caption .headerlink,.rst-content .eqno .headerlink,.rst-content .toctree-wrapper>p.caption .headerlink,.rst-content dl dt .headerlink,.rst-content h1 .headerlink,.rst-content h2 .headerlink,.rst-content h3 .headerlink,.rst-content h4 .headerlink,.rst-content h5 .headerlink,.rst-content h6 .headerlink,.rst-content p.caption .headerlink,.rst-content p .headerlink,.rst-content table>caption .headerlink{opacity:0;font-size:14px;font-family:FontAwesome;margin-left:.5em}.rst-content .code-block-caption .headerlink:focus,.rst-content .code-block-caption:hover .headerlink,.rst-content .eqno .headerlink:focus,.rst-content .eqno:hover .headerlink,.rst-content .toctree-wrapper>p.caption .headerlink:focus,.rst-content .toctree-wrapper>p.caption:hover .headerlink,.rst-content dl dt .headerlink:focus,.rst-content dl dt:hover .headerlink,.rst-content h1 .headerlink:focus,.rst-content h1:hover .headerlink,.rst-content h2 .headerlink:focus,.rst-content h2:hover .headerlink,.rst-content h3 .headerlink:focus,.rst-content h3:hover .headerlink,.rst-content h4 .headerlink:focus,.rst-content h4:hover .headerlink,.rst-content h5 .headerlink:focus,.rst-content h5:hover .headerlink,.rst-content h6 .headerlink:focus,.rst-content h6:hover .headerlink,.rst-content p.caption .headerlink:focus,.rst-content p.caption:hover .headerlink,.rst-content p .headerlink:focus,.rst-content p:hover .headerlink,.rst-content table>caption .headerlink:focus,.rst-content table>caption:hover .headerlink{opacity:1}.rst-content .btn:focus{outline:2px solid}.rst-content table>caption .headerlink:after{font-size:12px}.rst-content .centered{text-align:center}.rst-content .sidebar{float:right;width:40%;display:block;margin:0 0 24px 24px;padding:24px;background:#f3f6f6;border:1px solid #e1e4e5}.rst-content .sidebar dl,.rst-content .sidebar p,.rst-content .sidebar ul{font-size:90%}.rst-content .sidebar .last,.rst-content .sidebar>:last-child{margin-bottom:0}.rst-content .sidebar .sidebar-title{display:block;font-family:Roboto Slab,ff-tisa-web-pro,Georgia,Arial,sans-serif;font-weight:700;background:#e1e4e5;padding:6px 12px;margin:-24px -24px 24px;font-size:100%}.rst-content .highlighted{background:#f1c40f;box-shadow:0 0 0 2px #f1c40f;display:inline;font-weight:700}.rst-content .citation-reference,.rst-content .footnote-reference{vertical-align:baseline;position:relative;top:-.4em;line-height:0;font-size:90%}.rst-content .hlist{width:100%}.rst-content dl dt span.classifier:before{content:" : "}.rst-content dl dt span.classifier-delimiter{display:none!important}html.writer-html4 .rst-content table.docutils.citation,html.writer-html4 .rst-content table.docutils.footnote{background:none;border:none}html.writer-html4 .rst-content table.docutils.citation td,html.writer-html4 .rst-content table.docutils.citation tr,html.writer-html4 .rst-content table.docutils.footnote td,html.writer-html4 .rst-content table.docutils.footnote tr{border:none;background-color:transparent!important;white-space:normal}html.writer-html4 .rst-content table.docutils.citation td.label,html.writer-html4 .rst-content table.docutils.footnote td.label{padding-left:0;padding-right:0;vertical-align:top}html.writer-html5 .rst-content dl.field-list,html.writer-html5 .rst-content dl.footnote{display:grid;grid-template-columns:max-content auto}html.writer-html5 .rst-content dl.field-list>dt,html.writer-html5 .rst-content dl.footnote>dt{padding-left:1rem}html.writer-html5 .rst-content dl.field-list>dt:after,html.writer-html5 .rst-content dl.footnote>dt:after{content:":"}html.writer-html5 .rst-content dl.field-list>dd,html.writer-html5 .rst-content dl.field-list>dt,html.writer-html5 .rst-content dl.footnote>dd,html.writer-html5 .rst-content dl.footnote>dt{margin-bottom:0}html.writer-html5 .rst-content dl.footnote{font-size:.9rem}html.writer-html5 .rst-content dl.footnote>dt{margin:0 .5rem .5rem 0;line-height:1.2rem;word-break:break-all;font-weight:400}html.writer-html5 .rst-content dl.footnote>dt>span.brackets{margin-right:.5rem}html.writer-html5 .rst-content dl.footnote>dt>span.brackets:before{content:"["}html.writer-html5 .rst-content dl.footnote>dt>span.brackets:after{content:"]"}html.writer-html5 .rst-content dl.footnote>dt>span.fn-backref{font-style:italic}html.writer-html5 .rst-content dl.footnote>dd{margin:0 0 .5rem;line-height:1.2rem}html.writer-html5 .rst-content dl.footnote>dd p,html.writer-html5 .rst-content dl.option-list kbd{font-size:.9rem}.rst-content table.docutils.footnote,html.writer-html4 .rst-content table.docutils.citation,html.writer-html5 .rst-content dl.footnote{color:grey}.rst-content table.docutils.footnote code,.rst-content table.docutils.footnote tt,html.writer-html4 .rst-content table.docutils.citation code,html.writer-html4 .rst-content table.docutils.citation tt,html.writer-html5 .rst-content dl.footnote code,html.writer-html5 .rst-content dl.footnote tt{color:#555}.rst-content .wy-table-responsive.citation,.rst-content .wy-table-responsive.footnote{margin-bottom:0}.rst-content .wy-table-responsive.citation+:not(.citation),.rst-content .wy-table-responsive.footnote+:not(.footnote){margin-top:24px}.rst-content .wy-table-responsive.citation:last-child,.rst-content .wy-table-responsive.footnote:last-child{margin-bottom:24px}.rst-content table.docutils th{border-color:#e1e4e5}html.writer-html5 .rst-content table.docutils th{border:1px solid #e1e4e5}html.writer-html5 .rst-content table.docutils td>p,html.writer-html5 .rst-content table.docutils th>p{line-height:1rem;margin-bottom:0;font-size:.9rem}.rst-content table.docutils td .last,.rst-content table.docutils td .last>:last-child{margin-bottom:0}.rst-content table.field-list,.rst-content table.field-list td{border:none}.rst-content table.field-list td p{font-size:inherit;line-height:inherit}.rst-content table.field-list td>strong{display:inline-block}.rst-content table.field-list .field-name{padding-right:10px;text-align:left;white-space:nowrap}.rst-content table.field-list .field-body{text-align:left}.rst-content code,.rst-content tt{color:#000;font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;padding:2px 5px}.rst-content code big,.rst-content code em,.rst-content tt big,.rst-content tt em{font-size:100%!important;line-height:normal}.rst-content code.literal,.rst-content tt.literal{color:#e74c3c;white-space:normal}.rst-content code.xref,.rst-content tt.xref,a .rst-content code,a .rst-content tt{font-weight:700;color:#404040}.rst-content kbd,.rst-content pre,.rst-content samp{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace}.rst-content a code,.rst-content a tt{color:#2980b9}.rst-content dl{margin-bottom:24px}.rst-content dl dt{font-weight:700;margin-bottom:12px}.rst-content dl ol,.rst-content dl p,.rst-content dl table,.rst-content dl ul{margin-bottom:12px}.rst-content dl dd{margin:0 0 12px 24px;line-height:24px}html.writer-html4 .rst-content dl:not(.docutils),html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple){margin-bottom:24px}html.writer-html4 .rst-content dl:not(.docutils)>dt,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt{display:table;margin:6px 0;font-size:90%;line-height:normal;background:#e7f2fa;color:#2980b9;border-top:3px solid #6ab0de;padding:6px;position:relative}html.writer-html4 .rst-content dl:not(.docutils)>dt:before,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt:before{color:#6ab0de}html.writer-html4 .rst-content dl:not(.docutils)>dt .headerlink,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt .headerlink{color:#404040;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils) dl:not(.field-list)>dt,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) dl:not(.field-list)>dt{margin-bottom:6px;border:none;border-left:3px solid #ccc;background:#f0f0f0;color:#555}html.writer-html4 .rst-content dl:not(.docutils) dl:not(.field-list)>dt .headerlink,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) dl:not(.field-list)>dt .headerlink{color:#404040;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils)>dt:first-child,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple)>dt:first-child{margin-top:0}html.writer-html4 .rst-content dl:not(.docutils) code.descclassname,html.writer-html4 .rst-content dl:not(.docutils) code.descname,html.writer-html4 .rst-content dl:not(.docutils) tt.descclassname,html.writer-html4 .rst-content dl:not(.docutils) tt.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descname{background-color:transparent;border:none;padding:0;font-size:100%!important}html.writer-html4 .rst-content dl:not(.docutils) code.descname,html.writer-html4 .rst-content dl:not(.docutils) tt.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) code.descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) tt.descname{font-weight:700}html.writer-html4 .rst-content dl:not(.docutils) .optional,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .optional{display:inline-block;padding:0 4px;color:#000;font-weight:700}html.writer-html4 .rst-content dl:not(.docutils) .property,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .property{display:inline-block;padding-right:8px;max-width:100%}html.writer-html4 .rst-content dl:not(.docutils) .k,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .k{font-style:italic}html.writer-html4 .rst-content dl:not(.docutils) .descclassname,html.writer-html4 .rst-content dl:not(.docutils) .descname,html.writer-html4 .rst-content dl:not(.docutils) .sig-name,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .descclassname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .descname,html.writer-html5 .rst-content dl[class]:not(.option-list):not(.field-list):not(.footnote):not(.glossary):not(.simple) .sig-name{font-family:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,Courier,monospace;color:#000}.rst-content .viewcode-back,.rst-content .viewcode-link{display:inline-block;color:#27ae60;font-size:80%;padding-left:24px}.rst-content .viewcode-back{display:block;float:right}.rst-content p.rubric{margin-bottom:12px;font-weight:700}.rst-content code.download,.rst-content tt.download{background:inherit;padding:inherit;font-weight:400;font-family:inherit;font-size:inherit;color:inherit;border:inherit;white-space:inherit}.rst-content code.download span:first-child,.rst-content tt.download span:first-child{-webkit-font-smoothing:subpixel-antialiased}.rst-content code.download span:first-child:before,.rst-content tt.download span:first-child:before{margin-right:4px}.rst-content .guilabel{border:1px solid #7fbbe3;background:#e7f2fa;font-size:80%;font-weight:700;border-radius:4px;padding:2.4px 6px;margin:auto 2px}.rst-content .versionmodified{font-style:italic}@media screen and (max-width:480px){.rst-content .sidebar{width:100%}}span[id*=MathJax-Span]{color:#404040}.math{text-align:center}@font-face{font-family:Lato;src:url(fonts/lato-normal.woff2?bd03a2cc277bbbc338d464e679fe9942) format("woff2"),url(fonts/lato-normal.woff?27bd77b9162d388cb8d4c4217c7c5e2a) format("woff");font-weight:400;font-style:normal;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-bold.woff2?cccb897485813c7c256901dbca54ecf2) format("woff2"),url(fonts/lato-bold.woff?d878b6c29b10beca227e9eef4246111b) format("woff");font-weight:700;font-style:normal;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-bold-italic.woff2?0b6bb6725576b072c5d0b02ecdd1900d) format("woff2"),url(fonts/lato-bold-italic.woff?9c7e4e9eb485b4a121c760e61bc3707c) format("woff");font-weight:700;font-style:italic;font-display:block}@font-face{font-family:Lato;src:url(fonts/lato-normal-italic.woff2?4eb103b4d12be57cb1d040ed5e162e9d) format("woff2"),url(fonts/lato-normal-italic.woff?f28f2d6482446544ef1ea1ccc6dd5892) format("woff");font-weight:400;font-style:italic;font-display:block}@font-face{font-family:Roboto Slab;font-style:normal;font-weight:400;src:url(fonts/Roboto-Slab-Regular.woff2?7abf5b8d04d26a2cafea937019bca958) format("woff2"),url(fonts/Roboto-Slab-Regular.woff?c1be9284088d487c5e3ff0a10a92e58c) format("woff");font-display:block}@font-face{font-family:Roboto Slab;font-style:normal;font-weight:700;src:url(fonts/Roboto-Slab-Bold.woff2?9984f4a9bda09be08e83f2506954adbe) format("woff2"),url(fonts/Roboto-Slab-Bold.woff?bed5564a116b05148e3b3bea6fb1162a) format("woff");font-display:block} \ No newline at end of file diff --git a/docsrc/_build/html/_static/doctools.js b/docsrc/_build/html/_static/doctools.js index daccd20..8cbf1b1 100644 --- a/docsrc/_build/html/_static/doctools.js +++ b/docsrc/_build/html/_static/doctools.js @@ -4,7 +4,7 @@ * * Sphinx JavaScript utilities for all documentation. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ @@ -29,9 +29,14 @@ if (!window.console || !console.firebug) { /** * small helper function to urldecode strings + * + * See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/decodeURIComponent#Decoding_query_parameters_from_a_URL */ jQuery.urldecode = function(x) { - return decodeURIComponent(x).replace(/\+/g, ' '); + if (!x) { + return x + } + return decodeURIComponent(x.replace(/\+/g, ' ')); }; /** @@ -285,9 +290,10 @@ var Documentation = { initOnKeyListeners: function() { $(document).keydown(function(event) { var activeElementType = document.activeElement.tagName; - // don't navigate when in search box or textarea + // don't navigate when in search box, textarea, dropdown or button if (activeElementType !== 'TEXTAREA' && activeElementType !== 'INPUT' && activeElementType !== 'SELECT' - && !event.altKey && !event.ctrlKey && !event.metaKey && !event.shiftKey) { + && activeElementType !== 'BUTTON' && !event.altKey && !event.ctrlKey && !event.metaKey + && !event.shiftKey) { switch (event.keyCode) { case 37: // left var prevHref = $('link[rel="prev"]').prop('href'); @@ -295,12 +301,14 @@ var Documentation = { window.location.href = prevHref; return false; } + break; case 39: // right var nextHref = $('link[rel="next"]').prop('href'); if (nextHref) { window.location.href = nextHref; return false; } + break; } } }); diff --git a/docsrc/_build/html/_static/documentation_options.js b/docsrc/_build/html/_static/documentation_options.js index 9bdd13b..2f08d25 100644 --- a/docsrc/_build/html/_static/documentation_options.js +++ b/docsrc/_build/html/_static/documentation_options.js @@ -1,6 +1,6 @@ var DOCUMENTATION_OPTIONS = { URL_ROOT: document.getElementById("documentation_options").getAttribute('data-url_root'), - VERSION: '0.7.0', + VERSION: '1.0.0', LANGUAGE: 'None', COLLAPSE_INDEX: false, BUILDER: 'html', diff --git a/docsrc/_build/html/_static/graphviz.css b/docsrc/_build/html/_static/graphviz.css index 8ab69e0..b340734 100644 --- a/docsrc/_build/html/_static/graphviz.css +++ b/docsrc/_build/html/_static/graphviz.css @@ -4,7 +4,7 @@ * * Sphinx stylesheet -- graphviz extension. * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. + * :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. * :license: BSD, see LICENSE for details. * */ diff --git a/docsrc/_build/html/_static/js/badge_only.js b/docsrc/_build/html/_static/js/badge_only.js new file mode 100644 index 0000000..526d723 --- /dev/null +++ b/docsrc/_build/html/_static/js/badge_only.js @@ -0,0 +1 @@ +!function(e){var t={};function r(n){if(t[n])return t[n].exports;var o=t[n]={i:n,l:!1,exports:{}};return e[n].call(o.exports,o,o.exports,r),o.l=!0,o.exports}r.m=e,r.c=t,r.d=function(e,t,n){r.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:n})},r.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},r.t=function(e,t){if(1&t&&(e=r(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(r.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)r.d(n,o,function(t){return e[t]}.bind(null,o));return n},r.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return r.d(t,"a",t),t},r.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},r.p="",r(r.s=4)}({4:function(e,t,r){}}); \ No newline at end of file diff --git a/docsrc/_build/html/_static/js/html5shiv-printshiv.min.js b/docsrc/_build/html/_static/js/html5shiv-printshiv.min.js new file mode 100644 index 0000000..2b43bd0 --- /dev/null +++ b/docsrc/_build/html/_static/js/html5shiv-printshiv.min.js @@ -0,0 +1,4 @@ +/** +* @preserve HTML5 Shiv 3.7.3-pre | @afarkas @jdalton @jon_neal @rem | MIT/GPL2 Licensed +*/ +!function(a,b){function c(a,b){var c=a.createElement("p"),d=a.getElementsByTagName("head")[0]||a.documentElement;return c.innerHTML="x",d.insertBefore(c.lastChild,d.firstChild)}function d(){var a=y.elements;return"string"==typeof a?a.split(" "):a}function e(a,b){var c=y.elements;"string"!=typeof c&&(c=c.join(" ")),"string"!=typeof a&&(a=a.join(" ")),y.elements=c+" "+a,j(b)}function f(a){var b=x[a[v]];return b||(b={},w++,a[v]=w,x[w]=b),b}function g(a,c,d){if(c||(c=b),q)return c.createElement(a);d||(d=f(c));var e;return e=d.cache[a]?d.cache[a].cloneNode():u.test(a)?(d.cache[a]=d.createElem(a)).cloneNode():d.createElem(a),!e.canHaveChildren||t.test(a)||e.tagUrn?e:d.frag.appendChild(e)}function h(a,c){if(a||(a=b),q)return a.createDocumentFragment();c=c||f(a);for(var e=c.frag.cloneNode(),g=0,h=d(),i=h.length;i>g;g++)e.createElement(h[g]);return e}function i(a,b){b.cache||(b.cache={},b.createElem=a.createElement,b.createFrag=a.createDocumentFragment,b.frag=b.createFrag()),a.createElement=function(c){return y.shivMethods?g(c,a,b):b.createElem(c)},a.createDocumentFragment=Function("h,f","return function(){var n=f.cloneNode(),c=n.createElement;h.shivMethods&&("+d().join().replace(/[\w\-:]+/g,function(a){return b.createElem(a),b.frag.createElement(a),'c("'+a+'")'})+");return n}")(y,b.frag)}function j(a){a||(a=b);var d=f(a);return!y.shivCSS||p||d.hasCSS||(d.hasCSS=!!c(a,"article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}mark{background:#FF0;color:#000}template{display:none}")),q||i(a,d),a}function k(a){for(var b,c=a.getElementsByTagName("*"),e=c.length,f=RegExp("^(?:"+d().join("|")+")$","i"),g=[];e--;)b=c[e],f.test(b.nodeName)&&g.push(b.applyElement(l(b)));return g}function l(a){for(var b,c=a.attributes,d=c.length,e=a.ownerDocument.createElement(A+":"+a.nodeName);d--;)b=c[d],b.specified&&e.setAttribute(b.nodeName,b.nodeValue);return e.style.cssText=a.style.cssText,e}function m(a){for(var b,c=a.split("{"),e=c.length,f=RegExp("(^|[\\s,>+~])("+d().join("|")+")(?=[[\\s,>+~#.:]|$)","gi"),g="$1"+A+"\\:$2";e--;)b=c[e]=c[e].split("}"),b[b.length-1]=b[b.length-1].replace(f,g),c[e]=b.join("}");return c.join("{")}function n(a){for(var b=a.length;b--;)a[b].removeNode()}function o(a){function b(){clearTimeout(g._removeSheetTimer),d&&d.removeNode(!0),d=null}var d,e,g=f(a),h=a.namespaces,i=a.parentWindow;return!B||a.printShived?a:("undefined"==typeof h[A]&&h.add(A),i.attachEvent("onbeforeprint",function(){b();for(var f,g,h,i=a.styleSheets,j=[],l=i.length,n=Array(l);l--;)n[l]=i[l];for(;h=n.pop();)if(!h.disabled&&z.test(h.media)){try{f=h.imports,g=f.length}catch(o){g=0}for(l=0;g>l;l++)n.push(f[l]);try{j.push(h.cssText)}catch(o){}}j=m(j.reverse().join("")),e=k(a),d=c(a,j)}),i.attachEvent("onafterprint",function(){n(e),clearTimeout(g._removeSheetTimer),g._removeSheetTimer=setTimeout(b,500)}),a.printShived=!0,a)}var p,q,r="3.7.3",s=a.html5||{},t=/^<|^(?:button|map|select|textarea|object|iframe|option|optgroup)$/i,u=/^(?:a|b|code|div|fieldset|h1|h2|h3|h4|h5|h6|i|label|li|ol|p|q|span|strong|style|table|tbody|td|th|tr|ul)$/i,v="_html5shiv",w=0,x={};!function(){try{var a=b.createElement("a");a.innerHTML="",p="hidden"in a,q=1==a.childNodes.length||function(){b.createElement("a");var a=b.createDocumentFragment();return"undefined"==typeof a.cloneNode||"undefined"==typeof a.createDocumentFragment||"undefined"==typeof a.createElement}()}catch(c){p=!0,q=!0}}();var y={elements:s.elements||"abbr article aside audio bdi canvas data datalist details dialog figcaption figure footer header hgroup main mark meter nav output picture progress section summary template time video",version:r,shivCSS:s.shivCSS!==!1,supportsUnknownElements:q,shivMethods:s.shivMethods!==!1,type:"default",shivDocument:j,createElement:g,createDocumentFragment:h,addElements:e};a.html5=y,j(b);var z=/^$|\b(?:all|print)\b/,A="html5shiv",B=!q&&function(){var c=b.documentElement;return!("undefined"==typeof b.namespaces||"undefined"==typeof b.parentWindow||"undefined"==typeof c.applyElement||"undefined"==typeof c.removeNode||"undefined"==typeof a.attachEvent)}();y.type+=" print",y.shivPrint=o,o(b),"object"==typeof module&&module.exports&&(module.exports=y)}("undefined"!=typeof window?window:this,document); \ No newline at end of file diff --git a/docsrc/_build/html/_static/js/html5shiv.min.js b/docsrc/_build/html/_static/js/html5shiv.min.js new file mode 100644 index 0000000..cd1c674 --- /dev/null +++ b/docsrc/_build/html/_static/js/html5shiv.min.js @@ -0,0 +1,4 @@ +/** +* @preserve HTML5 Shiv 3.7.3 | @afarkas @jdalton @jon_neal @rem | MIT/GPL2 Licensed +*/ +!function(a,b){function c(a,b){var c=a.createElement("p"),d=a.getElementsByTagName("head")[0]||a.documentElement;return c.innerHTML="x",d.insertBefore(c.lastChild,d.firstChild)}function d(){var a=t.elements;return"string"==typeof a?a.split(" "):a}function e(a,b){var c=t.elements;"string"!=typeof c&&(c=c.join(" ")),"string"!=typeof a&&(a=a.join(" ")),t.elements=c+" "+a,j(b)}function f(a){var b=s[a[q]];return b||(b={},r++,a[q]=r,s[r]=b),b}function g(a,c,d){if(c||(c=b),l)return c.createElement(a);d||(d=f(c));var e;return e=d.cache[a]?d.cache[a].cloneNode():p.test(a)?(d.cache[a]=d.createElem(a)).cloneNode():d.createElem(a),!e.canHaveChildren||o.test(a)||e.tagUrn?e:d.frag.appendChild(e)}function h(a,c){if(a||(a=b),l)return a.createDocumentFragment();c=c||f(a);for(var e=c.frag.cloneNode(),g=0,h=d(),i=h.length;i>g;g++)e.createElement(h[g]);return e}function i(a,b){b.cache||(b.cache={},b.createElem=a.createElement,b.createFrag=a.createDocumentFragment,b.frag=b.createFrag()),a.createElement=function(c){return t.shivMethods?g(c,a,b):b.createElem(c)},a.createDocumentFragment=Function("h,f","return function(){var n=f.cloneNode(),c=n.createElement;h.shivMethods&&("+d().join().replace(/[\w\-:]+/g,function(a){return b.createElem(a),b.frag.createElement(a),'c("'+a+'")'})+");return n}")(t,b.frag)}function j(a){a||(a=b);var d=f(a);return!t.shivCSS||k||d.hasCSS||(d.hasCSS=!!c(a,"article,aside,dialog,figcaption,figure,footer,header,hgroup,main,nav,section{display:block}mark{background:#FF0;color:#000}template{display:none}")),l||i(a,d),a}var k,l,m="3.7.3-pre",n=a.html5||{},o=/^<|^(?:button|map|select|textarea|object|iframe|option|optgroup)$/i,p=/^(?:a|b|code|div|fieldset|h1|h2|h3|h4|h5|h6|i|label|li|ol|p|q|span|strong|style|table|tbody|td|th|tr|ul)$/i,q="_html5shiv",r=0,s={};!function(){try{var a=b.createElement("a");a.innerHTML="",k="hidden"in a,l=1==a.childNodes.length||function(){b.createElement("a");var a=b.createDocumentFragment();return"undefined"==typeof a.cloneNode||"undefined"==typeof a.createDocumentFragment||"undefined"==typeof a.createElement}()}catch(c){k=!0,l=!0}}();var t={elements:n.elements||"abbr article aside audio bdi canvas data datalist details dialog figcaption figure footer header hgroup main mark meter nav output picture progress section summary template time video",version:m,shivCSS:n.shivCSS!==!1,supportsUnknownElements:l,shivMethods:n.shivMethods!==!1,type:"default",shivDocument:j,createElement:g,createDocumentFragment:h,addElements:e};a.html5=t,j(b),"object"==typeof module&&module.exports&&(module.exports=t)}("undefined"!=typeof window?window:this,document); \ No newline at end of file diff --git a/docsrc/_build/html/_static/js/theme.js b/docsrc/_build/html/_static/js/theme.js new file mode 100644 index 0000000..1fddb6e --- /dev/null +++ b/docsrc/_build/html/_static/js/theme.js @@ -0,0 +1 @@ +!function(n){var e={};function t(i){if(e[i])return e[i].exports;var o=e[i]={i:i,l:!1,exports:{}};return n[i].call(o.exports,o,o.exports,t),o.l=!0,o.exports}t.m=n,t.c=e,t.d=function(n,e,i){t.o(n,e)||Object.defineProperty(n,e,{enumerable:!0,get:i})},t.r=function(n){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(n,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(n,"__esModule",{value:!0})},t.t=function(n,e){if(1&e&&(n=t(n)),8&e)return n;if(4&e&&"object"==typeof n&&n&&n.__esModule)return n;var i=Object.create(null);if(t.r(i),Object.defineProperty(i,"default",{enumerable:!0,value:n}),2&e&&"string"!=typeof n)for(var o in n)t.d(i,o,function(e){return n[e]}.bind(null,o));return i},t.n=function(n){var e=n&&n.__esModule?function(){return n.default}:function(){return n};return t.d(e,"a",e),e},t.o=function(n,e){return Object.prototype.hasOwnProperty.call(n,e)},t.p="",t(t.s=0)}([function(n,e,t){t(1),n.exports=t(3)},function(n,e,t){(function(){var e="undefined"!=typeof window?window.jQuery:t(2);n.exports.ThemeNav={navBar:null,win:null,winScroll:!1,winResize:!1,linkScroll:!1,winPosition:0,winHeight:null,docHeight:null,isRunning:!1,enable:function(n){var t=this;void 0===n&&(n=!0),t.isRunning||(t.isRunning=!0,e((function(e){t.init(e),t.reset(),t.win.on("hashchange",t.reset),n&&t.win.on("scroll",(function(){t.linkScroll||t.winScroll||(t.winScroll=!0,requestAnimationFrame((function(){t.onScroll()})))})),t.win.on("resize",(function(){t.winResize||(t.winResize=!0,requestAnimationFrame((function(){t.onResize()})))})),t.onResize()})))},enableSticky:function(){this.enable(!0)},init:function(n){n(document);var e=this;this.navBar=n("div.wy-side-scroll:first"),this.win=n(window),n(document).on("click","[data-toggle='wy-nav-top']",(function(){n("[data-toggle='wy-nav-shift']").toggleClass("shift"),n("[data-toggle='rst-versions']").toggleClass("shift")})).on("click",".wy-menu-vertical .current ul li a",(function(){var t=n(this);n("[data-toggle='wy-nav-shift']").removeClass("shift"),n("[data-toggle='rst-versions']").toggleClass("shift"),e.toggleCurrent(t),e.hashChange()})).on("click","[data-toggle='rst-current-version']",(function(){n("[data-toggle='rst-versions']").toggleClass("shift-up")})),n("table.docutils:not(.field-list,.footnote,.citation)").wrap("
    "),n("table.docutils.footnote").wrap("
    "),n("table.docutils.citation").wrap("
    "),n(".wy-menu-vertical ul").not(".simple").siblings("a").each((function(){var t=n(this);expand=n(''),expand.on("click",(function(n){return e.toggleCurrent(t),n.stopPropagation(),!1})),t.prepend(expand)}))},reset:function(){var n=encodeURI(window.location.hash)||"#";try{var e=$(".wy-menu-vertical"),t=e.find('[href="'+n+'"]');if(0===t.length){var i=$('.document [id="'+n.substring(1)+'"]').closest("div.section");0===(t=e.find('[href="#'+i.attr("id")+'"]')).length&&(t=e.find('[href="#"]'))}if(t.length>0){$(".wy-menu-vertical .current").removeClass("current").attr("aria-expanded","false"),t.addClass("current").attr("aria-expanded","true"),t.closest("li.toctree-l1").parent().addClass("current").attr("aria-expanded","true");for(let n=1;n<=10;n++)t.closest("li.toctree-l"+n).addClass("current").attr("aria-expanded","true");t[0].scrollIntoView()}}catch(n){console.log("Error expanding nav for anchor",n)}},onScroll:function(){this.winScroll=!1;var n=this.win.scrollTop(),e=n+this.winHeight,t=this.navBar.scrollTop()+(n-this.winPosition);n<0||e>this.docHeight||(this.navBar.scrollTop(t),this.winPosition=n)},onResize:function(){this.winResize=!1,this.winHeight=this.win.height(),this.docHeight=$(document).height()},hashChange:function(){this.linkScroll=!0,this.win.one("hashchange",(function(){this.linkScroll=!1}))},toggleCurrent:function(n){var e=n.closest("li");e.siblings("li.current").removeClass("current").attr("aria-expanded","false"),e.siblings().find("li.current").removeClass("current").attr("aria-expanded","false");var t=e.find("> ul li");t.length&&(t.removeClass("current").attr("aria-expanded","false"),e.toggleClass("current").attr("aria-expanded",(function(n,e){return"true"==e?"false":"true"})))}},"undefined"!=typeof window&&(window.SphinxRtdTheme={Navigation:n.exports.ThemeNav,StickyNav:n.exports.ThemeNav}),function(){for(var n=0,e=["ms","moz","webkit","o"],t=0;t'); + var listItem = $('
  • '); var requestUrl = ""; var linkUrl = ""; if (DOCUMENTATION_OPTIONS.BUILDER === 'dirhtml') { @@ -273,28 +273,31 @@ var Search = { if (item[3]) { listItem.append($(' (' + item[3] + ')')); Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); } else if (DOCUMENTATION_OPTIONS.HAS_SOURCE) { $.ajax({url: requestUrl, dataType: "text", complete: function(jqxhr, textstatus) { var data = jqxhr.responseText; if (data !== '' && data !== undefined) { - listItem.append(Search.makeSearchSummary(data, searchterms, hlterms)); + var summary = Search.makeSearchSummary(data, searchterms, hlterms); + if (summary) { + listItem.append(summary); + } } Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); }}); } else { // no source available, just display title Search.output.append(listItem); - listItem.slideDown(5, function() { + setTimeout(function() { displayNextItem(); - }); + }, 5); } } // search finished, update title and status message @@ -379,6 +382,13 @@ var Search = { return results; }, + /** + * See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions + */ + escapeRegExp : function(string) { + return string.replace(/[.*+\-?^${}()|[\]\\]/g, '\\$&'); // $& means the whole matched string + }, + /** * search for full-text terms in the index */ @@ -402,13 +412,14 @@ var Search = { ]; // add support for partial matches if (word.length > 2) { + var word_regex = this.escapeRegExp(word); for (var w in terms) { - if (w.match(word) && !terms[word]) { + if (w.match(word_regex) && !terms[word]) { _o.push({files: terms[w], score: Scorer.partialTerm}) } } for (var w in titleterms) { - if (w.match(word) && !titleterms[word]) { + if (w.match(word_regex) && !titleterms[word]) { _o.push({files: titleterms[w], score: Scorer.partialTitle}) } } @@ -490,6 +501,9 @@ var Search = { */ makeSearchSummary : function(htmlText, keywords, hlwords) { var text = Search.htmlToText(htmlText); + if (text == "") { + return null; + } var textLower = text.toLowerCase(); var start = 0; $.each(keywords, function() { @@ -501,7 +515,7 @@ var Search = { var excerpt = ((start > 0) ? '...' : '') + $.trim(text.substr(start, 240)) + ((start + 240 - text.length) ? '...' : ''); - var rv = $('
    ').text(excerpt); + var rv = $('

    ').text(excerpt); $.each(hlwords, function() { rv = rv.highlightText(this, 'highlighted'); }); diff --git a/docsrc/_build/html/_static/sidebar.js b/docsrc/_build/html/_static/sidebar.js deleted file mode 100644 index 657f8be..0000000 --- a/docsrc/_build/html/_static/sidebar.js +++ /dev/null @@ -1,159 +0,0 @@ -/* - * sidebar.js - * ~~~~~~~~~~ - * - * This script makes the Sphinx sidebar collapsible. - * - * .sphinxsidebar contains .sphinxsidebarwrapper. This script adds - * in .sphixsidebar, after .sphinxsidebarwrapper, the #sidebarbutton - * used to collapse and expand the sidebar. - * - * When the sidebar is collapsed the .sphinxsidebarwrapper is hidden - * and the width of the sidebar and the margin-left of the document - * are decreased. When the sidebar is expanded the opposite happens. - * This script saves a per-browser/per-session cookie used to - * remember the position of the sidebar among the pages. - * Once the browser is closed the cookie is deleted and the position - * reset to the default (expanded). - * - * :copyright: Copyright 2007-2020 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ - -$(function() { - - - - - - - - - // global elements used by the functions. - // the 'sidebarbutton' element is defined as global after its - // creation, in the add_sidebar_button function - var bodywrapper = $('.bodywrapper'); - var sidebar = $('.sphinxsidebar'); - var sidebarwrapper = $('.sphinxsidebarwrapper'); - - // for some reason, the document has no sidebar; do not run into errors - if (!sidebar.length) return; - - // original margin-left of the bodywrapper and width of the sidebar - // with the sidebar expanded - var bw_margin_expanded = bodywrapper.css('margin-left'); - var ssb_width_expanded = sidebar.width(); - - // margin-left of the bodywrapper and width of the sidebar - // with the sidebar collapsed - var bw_margin_collapsed = '.8em'; - var ssb_width_collapsed = '.8em'; - - // colors used by the current theme - var dark_color = $('.related').css('background-color'); - var light_color = $('.document').css('background-color'); - - function sidebar_is_collapsed() { - return sidebarwrapper.is(':not(:visible)'); - } - - function toggle_sidebar() { - if (sidebar_is_collapsed()) - expand_sidebar(); - else - collapse_sidebar(); - } - - function collapse_sidebar() { - sidebarwrapper.hide(); - sidebar.css('width', ssb_width_collapsed); - bodywrapper.css('margin-left', bw_margin_collapsed); - sidebarbutton.css({ - 'margin-left': '0', - 'height': bodywrapper.height() - }); - sidebarbutton.find('span').text('»'); - sidebarbutton.attr('title', _('Expand sidebar')); - document.cookie = 'sidebar=collapsed'; - } - - function expand_sidebar() { - bodywrapper.css('margin-left', bw_margin_expanded); - sidebar.css('width', ssb_width_expanded); - sidebarwrapper.show(); - sidebarbutton.css({ - 'margin-left': ssb_width_expanded-12, - 'height': bodywrapper.height() - }); - sidebarbutton.find('span').text('«'); - sidebarbutton.attr('title', _('Collapse sidebar')); - document.cookie = 'sidebar=expanded'; - } - - function add_sidebar_button() { - sidebarwrapper.css({ - 'float': 'left', - 'margin-right': '0', - 'width': ssb_width_expanded - 28 - }); - // create the button - sidebar.append( - '
    «
    ' - ); - var sidebarbutton = $('#sidebarbutton'); - light_color = sidebarbutton.css('background-color'); - // find the height of the viewport to center the '<<' in the page - var viewport_height; - if (window.innerHeight) - viewport_height = window.innerHeight; - else - viewport_height = $(window).height(); - sidebarbutton.find('span').css({ - 'display': 'block', - 'margin-top': (viewport_height - sidebar.position().top - 20) / 2 - }); - - sidebarbutton.click(toggle_sidebar); - sidebarbutton.attr('title', _('Collapse sidebar')); - sidebarbutton.css({ - 'color': '#FFFFFF', - 'border-left': '1px solid ' + dark_color, - 'font-size': '1.2em', - 'cursor': 'pointer', - 'height': bodywrapper.height(), - 'padding-top': '1px', - 'margin-left': ssb_width_expanded - 12 - }); - - sidebarbutton.hover( - function () { - $(this).css('background-color', dark_color); - }, - function () { - $(this).css('background-color', light_color); - } - ); - } - - function set_position_from_cookie() { - if (!document.cookie) - return; - var items = document.cookie.split(';'); - for(var k=0; k= 0 && sizeProperty <= MAX_ARRAY_INDEX; + } + } + + // Internal helper to generate a function to obtain property `key` from `obj`. + function shallowProperty(key) { + return function(obj) { + return obj == null ? void 0 : obj[key]; + }; + } + + // Internal helper to obtain the `byteLength` property of an object. + var getByteLength = shallowProperty('byteLength'); + + // Internal helper to determine whether we should spend extensive checks against + // `ArrayBuffer` et al. + var isBufferLike = createSizePropertyCheck(getByteLength); + + // Is a given value a typed array? + var typedArrayPattern = /\[object ((I|Ui)nt(8|16|32)|Float(32|64)|Uint8Clamped|Big(I|Ui)nt64)Array\]/; + function isTypedArray(obj) { + // `ArrayBuffer.isView` is the most future-proof, so use it when available. + // Otherwise, fall back on the above regular expression. + return nativeIsView ? (nativeIsView(obj) && !isDataView$1(obj)) : + isBufferLike(obj) && typedArrayPattern.test(toString.call(obj)); + } + + var isTypedArray$1 = supportsArrayBuffer ? isTypedArray : constant(false); + + // Internal helper to obtain the `length` property of an object. + var getLength = shallowProperty('length'); + + // Internal helper to create a simple lookup structure. + // `collectNonEnumProps` used to depend on `_.contains`, but this led to + // circular imports. `emulatedSet` is a one-off solution that only works for + // arrays of strings. + function emulatedSet(keys) { + var hash = {}; + for (var l = keys.length, i = 0; i < l; ++i) hash[keys[i]] = true; + return { + contains: function(key) { return hash[key]; }, + push: function(key) { + hash[key] = true; + return keys.push(key); + } + }; + } + + // Internal helper. Checks `keys` for the presence of keys in IE < 9 that won't + // be iterated by `for key in ...` and thus missed. Extends `keys` in place if + // needed. + function collectNonEnumProps(obj, keys) { + keys = emulatedSet(keys); + var nonEnumIdx = nonEnumerableProps.length; + var constructor = obj.constructor; + var proto = isFunction$1(constructor) && constructor.prototype || ObjProto; + + // Constructor is a special case. + var prop = 'constructor'; + if (has$1(obj, prop) && !keys.contains(prop)) keys.push(prop); + + while (nonEnumIdx--) { + prop = nonEnumerableProps[nonEnumIdx]; + if (prop in obj && obj[prop] !== proto[prop] && !keys.contains(prop)) { + keys.push(prop); + } + } + } + + // Retrieve the names of an object's own properties. + // Delegates to **ECMAScript 5**'s native `Object.keys`. + function keys(obj) { + if (!isObject(obj)) return []; + if (nativeKeys) return nativeKeys(obj); + var keys = []; + for (var key in obj) if (has$1(obj, key)) keys.push(key); + // Ahem, IE < 9. + if (hasEnumBug) collectNonEnumProps(obj, keys); + return keys; + } + + // Is a given array, string, or object empty? + // An "empty" object has no enumerable own-properties. + function isEmpty(obj) { + if (obj == null) return true; + // Skip the more expensive `toString`-based type checks if `obj` has no + // `.length`. + var length = getLength(obj); + if (typeof length == 'number' && ( + isArray(obj) || isString(obj) || isArguments$1(obj) + )) return length === 0; + return getLength(keys(obj)) === 0; + } + + // Returns whether an object has a given set of `key:value` pairs. + function isMatch(object, attrs) { + var _keys = keys(attrs), length = _keys.length; + if (object == null) return !length; + var obj = Object(object); + for (var i = 0; i < length; i++) { + var key = _keys[i]; + if (attrs[key] !== obj[key] || !(key in obj)) return false; + } + return true; + } + + // If Underscore is called as a function, it returns a wrapped object that can + // be used OO-style. This wrapper holds altered versions of all functions added + // through `_.mixin`. Wrapped objects may be chained. + function _$1(obj) { + if (obj instanceof _$1) return obj; + if (!(this instanceof _$1)) return new _$1(obj); + this._wrapped = obj; + } + + _$1.VERSION = VERSION; + + // Extracts the result from a wrapped and chained object. + _$1.prototype.value = function() { + return this._wrapped; + }; + + // Provide unwrapping proxies for some methods used in engine operations + // such as arithmetic and JSON stringification. + _$1.prototype.valueOf = _$1.prototype.toJSON = _$1.prototype.value; + + _$1.prototype.toString = function() { + return String(this._wrapped); + }; + + // Internal function to wrap or shallow-copy an ArrayBuffer, + // typed array or DataView to a new view, reusing the buffer. + function toBufferView(bufferSource) { + return new Uint8Array( + bufferSource.buffer || bufferSource, + bufferSource.byteOffset || 0, + getByteLength(bufferSource) + ); + } + + // We use this string twice, so give it a name for minification. + var tagDataView = '[object DataView]'; + + // Internal recursive comparison function for `_.isEqual`. + function eq(a, b, aStack, bStack) { + // Identical objects are equal. `0 === -0`, but they aren't identical. + // See the [Harmony `egal` proposal](https://wiki.ecmascript.org/doku.php?id=harmony:egal). + if (a === b) return a !== 0 || 1 / a === 1 / b; + // `null` or `undefined` only equal to itself (strict comparison). + if (a == null || b == null) return false; + // `NaN`s are equivalent, but non-reflexive. + if (a !== a) return b !== b; + // Exhaust primitive checks + var type = typeof a; + if (type !== 'function' && type !== 'object' && typeof b != 'object') return false; + return deepEq(a, b, aStack, bStack); + } + + // Internal recursive comparison function for `_.isEqual`. + function deepEq(a, b, aStack, bStack) { + // Unwrap any wrapped objects. + if (a instanceof _$1) a = a._wrapped; + if (b instanceof _$1) b = b._wrapped; + // Compare `[[Class]]` names. + var className = toString.call(a); + if (className !== toString.call(b)) return false; + // Work around a bug in IE 10 - Edge 13. + if (hasStringTagBug && className == '[object Object]' && isDataView$1(a)) { + if (!isDataView$1(b)) return false; + className = tagDataView; + } + switch (className) { + // These types are compared by value. + case '[object RegExp]': + // RegExps are coerced to strings for comparison (Note: '' + /a/i === '/a/i') + case '[object String]': + // Primitives and their corresponding object wrappers are equivalent; thus, `"5"` is + // equivalent to `new String("5")`. + return '' + a === '' + b; + case '[object Number]': + // `NaN`s are equivalent, but non-reflexive. + // Object(NaN) is equivalent to NaN. + if (+a !== +a) return +b !== +b; + // An `egal` comparison is performed for other numeric values. + return +a === 0 ? 1 / +a === 1 / b : +a === +b; + case '[object Date]': + case '[object Boolean]': + // Coerce dates and booleans to numeric primitive values. Dates are compared by their + // millisecond representations. Note that invalid dates with millisecond representations + // of `NaN` are not equivalent. + return +a === +b; + case '[object Symbol]': + return SymbolProto.valueOf.call(a) === SymbolProto.valueOf.call(b); + case '[object ArrayBuffer]': + case tagDataView: + // Coerce to typed array so we can fall through. + return deepEq(toBufferView(a), toBufferView(b), aStack, bStack); + } + + var areArrays = className === '[object Array]'; + if (!areArrays && isTypedArray$1(a)) { + var byteLength = getByteLength(a); + if (byteLength !== getByteLength(b)) return false; + if (a.buffer === b.buffer && a.byteOffset === b.byteOffset) return true; + areArrays = true; + } + if (!areArrays) { + if (typeof a != 'object' || typeof b != 'object') return false; + + // Objects with different constructors are not equivalent, but `Object`s or `Array`s + // from different frames are. + var aCtor = a.constructor, bCtor = b.constructor; + if (aCtor !== bCtor && !(isFunction$1(aCtor) && aCtor instanceof aCtor && + isFunction$1(bCtor) && bCtor instanceof bCtor) + && ('constructor' in a && 'constructor' in b)) { + return false; + } + } + // Assume equality for cyclic structures. The algorithm for detecting cyclic + // structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`. + + // Initializing stack of traversed objects. + // It's done here since we only need them for objects and arrays comparison. + aStack = aStack || []; + bStack = bStack || []; + var length = aStack.length; + while (length--) { + // Linear search. Performance is inversely proportional to the number of + // unique nested structures. + if (aStack[length] === a) return bStack[length] === b; + } + + // Add the first object to the stack of traversed objects. + aStack.push(a); + bStack.push(b); + + // Recursively compare objects and arrays. + if (areArrays) { + // Compare array lengths to determine if a deep comparison is necessary. + length = a.length; + if (length !== b.length) return false; + // Deep compare the contents, ignoring non-numeric properties. + while (length--) { + if (!eq(a[length], b[length], aStack, bStack)) return false; + } + } else { + // Deep compare objects. + var _keys = keys(a), key; + length = _keys.length; + // Ensure that both objects contain the same number of properties before comparing deep equality. + if (keys(b).length !== length) return false; + while (length--) { + // Deep compare each member + key = _keys[length]; + if (!(has$1(b, key) && eq(a[key], b[key], aStack, bStack))) return false; + } + } + // Remove the first object from the stack of traversed objects. + aStack.pop(); + bStack.pop(); + return true; + } + + // Perform a deep comparison to check if two objects are equal. + function isEqual(a, b) { + return eq(a, b); + } + + // Retrieve all the enumerable property names of an object. + function allKeys(obj) { + if (!isObject(obj)) return []; + var keys = []; + for (var key in obj) keys.push(key); + // Ahem, IE < 9. + if (hasEnumBug) collectNonEnumProps(obj, keys); + return keys; + } + + // Since the regular `Object.prototype.toString` type tests don't work for + // some types in IE 11, we use a fingerprinting heuristic instead, based + // on the methods. It's not great, but it's the best we got. + // The fingerprint method lists are defined below. + function ie11fingerprint(methods) { + var length = getLength(methods); + return function(obj) { + if (obj == null) return false; + // `Map`, `WeakMap` and `Set` have no enumerable keys. + var keys = allKeys(obj); + if (getLength(keys)) return false; + for (var i = 0; i < length; i++) { + if (!isFunction$1(obj[methods[i]])) return false; + } + // If we are testing against `WeakMap`, we need to ensure that + // `obj` doesn't have a `forEach` method in order to distinguish + // it from a regular `Map`. + return methods !== weakMapMethods || !isFunction$1(obj[forEachName]); + }; + } + + // In the interest of compact minification, we write + // each string in the fingerprints only once. + var forEachName = 'forEach', + hasName = 'has', + commonInit = ['clear', 'delete'], + mapTail = ['get', hasName, 'set']; + + // `Map`, `WeakMap` and `Set` each have slightly different + // combinations of the above sublists. + var mapMethods = commonInit.concat(forEachName, mapTail), + weakMapMethods = commonInit.concat(mapTail), + setMethods = ['add'].concat(commonInit, forEachName, hasName); + + var isMap = isIE11 ? ie11fingerprint(mapMethods) : tagTester('Map'); + + var isWeakMap = isIE11 ? ie11fingerprint(weakMapMethods) : tagTester('WeakMap'); + + var isSet = isIE11 ? ie11fingerprint(setMethods) : tagTester('Set'); + + var isWeakSet = tagTester('WeakSet'); + + // Retrieve the values of an object's properties. + function values(obj) { + var _keys = keys(obj); + var length = _keys.length; + var values = Array(length); + for (var i = 0; i < length; i++) { + values[i] = obj[_keys[i]]; + } + return values; + } + + // Convert an object into a list of `[key, value]` pairs. + // The opposite of `_.object` with one argument. + function pairs(obj) { + var _keys = keys(obj); + var length = _keys.length; + var pairs = Array(length); + for (var i = 0; i < length; i++) { + pairs[i] = [_keys[i], obj[_keys[i]]]; + } + return pairs; + } + + // Invert the keys and values of an object. The values must be serializable. + function invert(obj) { + var result = {}; + var _keys = keys(obj); + for (var i = 0, length = _keys.length; i < length; i++) { + result[obj[_keys[i]]] = _keys[i]; + } + return result; + } + + // Return a sorted list of the function names available on the object. + function functions(obj) { + var names = []; + for (var key in obj) { + if (isFunction$1(obj[key])) names.push(key); + } + return names.sort(); + } + + // An internal function for creating assigner functions. + function createAssigner(keysFunc, defaults) { + return function(obj) { + var length = arguments.length; + if (defaults) obj = Object(obj); + if (length < 2 || obj == null) return obj; + for (var index = 1; index < length; index++) { + var source = arguments[index], + keys = keysFunc(source), + l = keys.length; + for (var i = 0; i < l; i++) { + var key = keys[i]; + if (!defaults || obj[key] === void 0) obj[key] = source[key]; + } + } + return obj; + }; + } + + // Extend a given object with all the properties in passed-in object(s). + var extend = createAssigner(allKeys); + + // Assigns a given object with all the own properties in the passed-in + // object(s). + // (https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Object/assign) + var extendOwn = createAssigner(keys); + + // Fill in a given object with default properties. + var defaults = createAssigner(allKeys, true); + + // Create a naked function reference for surrogate-prototype-swapping. + function ctor() { + return function(){}; + } + + // An internal function for creating a new object that inherits from another. + function baseCreate(prototype) { + if (!isObject(prototype)) return {}; + if (nativeCreate) return nativeCreate(prototype); + var Ctor = ctor(); + Ctor.prototype = prototype; + var result = new Ctor; + Ctor.prototype = null; + return result; + } + + // Creates an object that inherits from the given prototype object. + // If additional properties are provided then they will be added to the + // created object. + function create(prototype, props) { + var result = baseCreate(prototype); + if (props) extendOwn(result, props); + return result; + } + + // Create a (shallow-cloned) duplicate of an object. + function clone(obj) { + if (!isObject(obj)) return obj; + return isArray(obj) ? obj.slice() : extend({}, obj); + } + + // Invokes `interceptor` with the `obj` and then returns `obj`. + // The primary purpose of this method is to "tap into" a method chain, in + // order to perform operations on intermediate results within the chain. + function tap(obj, interceptor) { + interceptor(obj); + return obj; + } + + // Normalize a (deep) property `path` to array. + // Like `_.iteratee`, this function can be customized. + function toPath$1(path) { + return isArray(path) ? path : [path]; + } + _$1.toPath = toPath$1; + + // Internal wrapper for `_.toPath` to enable minification. + // Similar to `cb` for `_.iteratee`. + function toPath(path) { + return _$1.toPath(path); + } + + // Internal function to obtain a nested property in `obj` along `path`. + function deepGet(obj, path) { + var length = path.length; + for (var i = 0; i < length; i++) { + if (obj == null) return void 0; + obj = obj[path[i]]; + } + return length ? obj : void 0; + } + + // Get the value of the (deep) property on `path` from `object`. + // If any property in `path` does not exist or if the value is + // `undefined`, return `defaultValue` instead. + // The `path` is normalized through `_.toPath`. + function get(object, path, defaultValue) { + var value = deepGet(object, toPath(path)); + return isUndefined(value) ? defaultValue : value; + } + + // Shortcut function for checking if an object has a given property directly on + // itself (in other words, not on a prototype). Unlike the internal `has` + // function, this public version can also traverse nested properties. + function has(obj, path) { + path = toPath(path); + var length = path.length; + for (var i = 0; i < length; i++) { + var key = path[i]; + if (!has$1(obj, key)) return false; + obj = obj[key]; + } + return !!length; + } + + // Keep the identity function around for default iteratees. + function identity(value) { + return value; + } + + // Returns a predicate for checking whether an object has a given set of + // `key:value` pairs. + function matcher(attrs) { + attrs = extendOwn({}, attrs); + return function(obj) { + return isMatch(obj, attrs); + }; + } + + // Creates a function that, when passed an object, will traverse that object’s + // properties down the given `path`, specified as an array of keys or indices. + function property(path) { + path = toPath(path); + return function(obj) { + return deepGet(obj, path); + }; + } + + // Internal function that returns an efficient (for current engines) version + // of the passed-in callback, to be repeatedly applied in other Underscore + // functions. + function optimizeCb(func, context, argCount) { + if (context === void 0) return func; + switch (argCount == null ? 3 : argCount) { + case 1: return function(value) { + return func.call(context, value); + }; + // The 2-argument case is omitted because we’re not using it. + case 3: return function(value, index, collection) { + return func.call(context, value, index, collection); + }; + case 4: return function(accumulator, value, index, collection) { + return func.call(context, accumulator, value, index, collection); + }; + } + return function() { + return func.apply(context, arguments); + }; + } + + // An internal function to generate callbacks that can be applied to each + // element in a collection, returning the desired result — either `_.identity`, + // an arbitrary callback, a property matcher, or a property accessor. + function baseIteratee(value, context, argCount) { + if (value == null) return identity; + if (isFunction$1(value)) return optimizeCb(value, context, argCount); + if (isObject(value) && !isArray(value)) return matcher(value); + return property(value); + } + + // External wrapper for our callback generator. Users may customize + // `_.iteratee` if they want additional predicate/iteratee shorthand styles. + // This abstraction hides the internal-only `argCount` argument. + function iteratee(value, context) { + return baseIteratee(value, context, Infinity); + } + _$1.iteratee = iteratee; + + // The function we call internally to generate a callback. It invokes + // `_.iteratee` if overridden, otherwise `baseIteratee`. + function cb(value, context, argCount) { + if (_$1.iteratee !== iteratee) return _$1.iteratee(value, context); + return baseIteratee(value, context, argCount); + } + + // Returns the results of applying the `iteratee` to each element of `obj`. + // In contrast to `_.map` it returns an object. + function mapObject(obj, iteratee, context) { + iteratee = cb(iteratee, context); + var _keys = keys(obj), + length = _keys.length, + results = {}; + for (var index = 0; index < length; index++) { + var currentKey = _keys[index]; + results[currentKey] = iteratee(obj[currentKey], currentKey, obj); + } + return results; + } + + // Predicate-generating function. Often useful outside of Underscore. + function noop(){} + + // Generates a function for a given object that returns a given property. + function propertyOf(obj) { + if (obj == null) return noop; + return function(path) { + return get(obj, path); + }; + } + + // Run a function **n** times. + function times(n, iteratee, context) { + var accum = Array(Math.max(0, n)); + iteratee = optimizeCb(iteratee, context, 1); + for (var i = 0; i < n; i++) accum[i] = iteratee(i); + return accum; + } + + // Return a random integer between `min` and `max` (inclusive). + function random(min, max) { + if (max == null) { + max = min; + min = 0; + } + return min + Math.floor(Math.random() * (max - min + 1)); + } + + // A (possibly faster) way to get the current timestamp as an integer. + var now = Date.now || function() { + return new Date().getTime(); + }; + + // Internal helper to generate functions for escaping and unescaping strings + // to/from HTML interpolation. + function createEscaper(map) { + var escaper = function(match) { + return map[match]; + }; + // Regexes for identifying a key that needs to be escaped. + var source = '(?:' + keys(map).join('|') + ')'; + var testRegexp = RegExp(source); + var replaceRegexp = RegExp(source, 'g'); + return function(string) { + string = string == null ? '' : '' + string; + return testRegexp.test(string) ? string.replace(replaceRegexp, escaper) : string; + }; + } + + // Internal list of HTML entities for escaping. + var escapeMap = { + '&': '&', + '<': '<', + '>': '>', + '"': '"', + "'": ''', + '`': '`' + }; + + // Function for escaping strings to HTML interpolation. + var _escape = createEscaper(escapeMap); + + // Internal list of HTML entities for unescaping. + var unescapeMap = invert(escapeMap); + + // Function for unescaping strings from HTML interpolation. + var _unescape = createEscaper(unescapeMap); + + // By default, Underscore uses ERB-style template delimiters. Change the + // following template settings to use alternative delimiters. + var templateSettings = _$1.templateSettings = { + evaluate: /<%([\s\S]+?)%>/g, + interpolate: /<%=([\s\S]+?)%>/g, + escape: /<%-([\s\S]+?)%>/g + }; + + // When customizing `_.templateSettings`, if you don't want to define an + // interpolation, evaluation or escaping regex, we need one that is + // guaranteed not to match. + var noMatch = /(.)^/; + + // Certain characters need to be escaped so that they can be put into a + // string literal. + var escapes = { + "'": "'", + '\\': '\\', + '\r': 'r', + '\n': 'n', + '\u2028': 'u2028', + '\u2029': 'u2029' + }; + + var escapeRegExp = /\\|'|\r|\n|\u2028|\u2029/g; + + function escapeChar(match) { + return '\\' + escapes[match]; + } + + // In order to prevent third-party code injection through + // `_.templateSettings.variable`, we test it against the following regular + // expression. It is intentionally a bit more liberal than just matching valid + // identifiers, but still prevents possible loopholes through defaults or + // destructuring assignment. + var bareIdentifier = /^\s*(\w|\$)+\s*$/; + + // JavaScript micro-templating, similar to John Resig's implementation. + // Underscore templating handles arbitrary delimiters, preserves whitespace, + // and correctly escapes quotes within interpolated code. + // NB: `oldSettings` only exists for backwards compatibility. + function template(text, settings, oldSettings) { + if (!settings && oldSettings) settings = oldSettings; + settings = defaults({}, settings, _$1.templateSettings); + + // Combine delimiters into one regular expression via alternation. + var matcher = RegExp([ + (settings.escape || noMatch).source, + (settings.interpolate || noMatch).source, + (settings.evaluate || noMatch).source + ].join('|') + '|$', 'g'); + + // Compile the template source, escaping string literals appropriately. + var index = 0; + var source = "__p+='"; + text.replace(matcher, function(match, escape, interpolate, evaluate, offset) { + source += text.slice(index, offset).replace(escapeRegExp, escapeChar); + index = offset + match.length; + + if (escape) { + source += "'+\n((__t=(" + escape + "))==null?'':_.escape(__t))+\n'"; + } else if (interpolate) { + source += "'+\n((__t=(" + interpolate + "))==null?'':__t)+\n'"; + } else if (evaluate) { + source += "';\n" + evaluate + "\n__p+='"; + } + + // Adobe VMs need the match returned to produce the correct offset. + return match; + }); + source += "';\n"; + + var argument = settings.variable; + if (argument) { + // Insure against third-party code injection. (CVE-2021-23358) + if (!bareIdentifier.test(argument)) throw new Error( + 'variable is not a bare identifier: ' + argument + ); + } else { + // If a variable is not specified, place data values in local scope. + source = 'with(obj||{}){\n' + source + '}\n'; + argument = 'obj'; + } + + source = "var __t,__p='',__j=Array.prototype.join," + + "print=function(){__p+=__j.call(arguments,'');};\n" + + source + 'return __p;\n'; + + var render; + try { + render = new Function(argument, '_', source); + } catch (e) { + e.source = source; + throw e; + } + + var template = function(data) { + return render.call(this, data, _$1); + }; + + // Provide the compiled source as a convenience for precompilation. + template.source = 'function(' + argument + '){\n' + source + '}'; + + return template; + } + + // Traverses the children of `obj` along `path`. If a child is a function, it + // is invoked with its parent as context. Returns the value of the final + // child, or `fallback` if any child is undefined. + function result(obj, path, fallback) { + path = toPath(path); + var length = path.length; + if (!length) { + return isFunction$1(fallback) ? fallback.call(obj) : fallback; + } + for (var i = 0; i < length; i++) { + var prop = obj == null ? void 0 : obj[path[i]]; + if (prop === void 0) { + prop = fallback; + i = length; // Ensure we don't continue iterating. + } + obj = isFunction$1(prop) ? prop.call(obj) : prop; + } + return obj; + } + + // Generate a unique integer id (unique within the entire client session). + // Useful for temporary DOM ids. + var idCounter = 0; + function uniqueId(prefix) { + var id = ++idCounter + ''; + return prefix ? prefix + id : id; + } + + // Start chaining a wrapped Underscore object. + function chain(obj) { + var instance = _$1(obj); + instance._chain = true; + return instance; + } + + // Internal function to execute `sourceFunc` bound to `context` with optional + // `args`. Determines whether to execute a function as a constructor or as a + // normal function. + function executeBound(sourceFunc, boundFunc, context, callingContext, args) { + if (!(callingContext instanceof boundFunc)) return sourceFunc.apply(context, args); + var self = baseCreate(sourceFunc.prototype); + var result = sourceFunc.apply(self, args); + if (isObject(result)) return result; + return self; + } + + // Partially apply a function by creating a version that has had some of its + // arguments pre-filled, without changing its dynamic `this` context. `_` acts + // as a placeholder by default, allowing any combination of arguments to be + // pre-filled. Set `_.partial.placeholder` for a custom placeholder argument. + var partial = restArguments(function(func, boundArgs) { + var placeholder = partial.placeholder; + var bound = function() { + var position = 0, length = boundArgs.length; + var args = Array(length); + for (var i = 0; i < length; i++) { + args[i] = boundArgs[i] === placeholder ? arguments[position++] : boundArgs[i]; + } + while (position < arguments.length) args.push(arguments[position++]); + return executeBound(func, bound, this, this, args); + }; + return bound; + }); + + partial.placeholder = _$1; + + // Create a function bound to a given object (assigning `this`, and arguments, + // optionally). + var bind = restArguments(function(func, context, args) { + if (!isFunction$1(func)) throw new TypeError('Bind must be called on a function'); + var bound = restArguments(function(callArgs) { + return executeBound(func, bound, context, this, args.concat(callArgs)); + }); + return bound; + }); + + // Internal helper for collection methods to determine whether a collection + // should be iterated as an array or as an object. + // Related: https://people.mozilla.org/~jorendorff/es6-draft.html#sec-tolength + // Avoids a very nasty iOS 8 JIT bug on ARM-64. #2094 + var isArrayLike = createSizePropertyCheck(getLength); + + // Internal implementation of a recursive `flatten` function. + function flatten$1(input, depth, strict, output) { + output = output || []; + if (!depth && depth !== 0) { + depth = Infinity; + } else if (depth <= 0) { + return output.concat(input); + } + var idx = output.length; + for (var i = 0, length = getLength(input); i < length; i++) { + var value = input[i]; + if (isArrayLike(value) && (isArray(value) || isArguments$1(value))) { + // Flatten current level of array or arguments object. + if (depth > 1) { + flatten$1(value, depth - 1, strict, output); + idx = output.length; + } else { + var j = 0, len = value.length; + while (j < len) output[idx++] = value[j++]; + } + } else if (!strict) { + output[idx++] = value; + } + } + return output; + } + + // Bind a number of an object's methods to that object. Remaining arguments + // are the method names to be bound. Useful for ensuring that all callbacks + // defined on an object belong to it. + var bindAll = restArguments(function(obj, keys) { + keys = flatten$1(keys, false, false); + var index = keys.length; + if (index < 1) throw new Error('bindAll must be passed function names'); + while (index--) { + var key = keys[index]; + obj[key] = bind(obj[key], obj); + } + return obj; + }); + + // Memoize an expensive function by storing its results. + function memoize(func, hasher) { + var memoize = function(key) { + var cache = memoize.cache; + var address = '' + (hasher ? hasher.apply(this, arguments) : key); + if (!has$1(cache, address)) cache[address] = func.apply(this, arguments); + return cache[address]; + }; + memoize.cache = {}; + return memoize; + } + + // Delays a function for the given number of milliseconds, and then calls + // it with the arguments supplied. + var delay = restArguments(function(func, wait, args) { + return setTimeout(function() { + return func.apply(null, args); + }, wait); + }); + + // Defers a function, scheduling it to run after the current call stack has + // cleared. + var defer = partial(delay, _$1, 1); + + // Returns a function, that, when invoked, will only be triggered at most once + // during a given window of time. Normally, the throttled function will run + // as much as it can, without ever going more than once per `wait` duration; + // but if you'd like to disable the execution on the leading edge, pass + // `{leading: false}`. To disable execution on the trailing edge, ditto. + function throttle(func, wait, options) { + var timeout, context, args, result; + var previous = 0; + if (!options) options = {}; + + var later = function() { + previous = options.leading === false ? 0 : now(); + timeout = null; + result = func.apply(context, args); + if (!timeout) context = args = null; + }; + + var throttled = function() { + var _now = now(); + if (!previous && options.leading === false) previous = _now; + var remaining = wait - (_now - previous); + context = this; + args = arguments; + if (remaining <= 0 || remaining > wait) { + if (timeout) { + clearTimeout(timeout); + timeout = null; + } + previous = _now; + result = func.apply(context, args); + if (!timeout) context = args = null; + } else if (!timeout && options.trailing !== false) { + timeout = setTimeout(later, remaining); + } + return result; + }; + + throttled.cancel = function() { + clearTimeout(timeout); + previous = 0; + timeout = context = args = null; + }; + + return throttled; + } + + // When a sequence of calls of the returned function ends, the argument + // function is triggered. The end of a sequence is defined by the `wait` + // parameter. If `immediate` is passed, the argument function will be + // triggered at the beginning of the sequence instead of at the end. + function debounce(func, wait, immediate) { + var timeout, previous, args, result, context; + + var later = function() { + var passed = now() - previous; + if (wait > passed) { + timeout = setTimeout(later, wait - passed); + } else { + timeout = null; + if (!immediate) result = func.apply(context, args); + // This check is needed because `func` can recursively invoke `debounced`. + if (!timeout) args = context = null; + } + }; + + var debounced = restArguments(function(_args) { + context = this; + args = _args; + previous = now(); + if (!timeout) { + timeout = setTimeout(later, wait); + if (immediate) result = func.apply(context, args); + } + return result; + }); + + debounced.cancel = function() { + clearTimeout(timeout); + timeout = args = context = null; + }; + + return debounced; + } + + // Returns the first function passed as an argument to the second, + // allowing you to adjust arguments, run code before and after, and + // conditionally execute the original function. + function wrap(func, wrapper) { + return partial(wrapper, func); + } + + // Returns a negated version of the passed-in predicate. + function negate(predicate) { + return function() { + return !predicate.apply(this, arguments); + }; + } + + // Returns a function that is the composition of a list of functions, each + // consuming the return value of the function that follows. + function compose() { + var args = arguments; + var start = args.length - 1; + return function() { + var i = start; + var result = args[start].apply(this, arguments); + while (i--) result = args[i].call(this, result); + return result; + }; + } + + // Returns a function that will only be executed on and after the Nth call. + function after(times, func) { + return function() { + if (--times < 1) { + return func.apply(this, arguments); + } + }; + } + + // Returns a function that will only be executed up to (but not including) the + // Nth call. + function before(times, func) { + var memo; + return function() { + if (--times > 0) { + memo = func.apply(this, arguments); + } + if (times <= 1) func = null; + return memo; + }; + } + + // Returns a function that will be executed at most one time, no matter how + // often you call it. Useful for lazy initialization. + var once = partial(before, 2); + + // Returns the first key on an object that passes a truth test. + function findKey(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = keys(obj), key; + for (var i = 0, length = _keys.length; i < length; i++) { + key = _keys[i]; + if (predicate(obj[key], key, obj)) return key; + } + } + + // Internal function to generate `_.findIndex` and `_.findLastIndex`. + function createPredicateIndexFinder(dir) { + return function(array, predicate, context) { + predicate = cb(predicate, context); + var length = getLength(array); + var index = dir > 0 ? 0 : length - 1; + for (; index >= 0 && index < length; index += dir) { + if (predicate(array[index], index, array)) return index; + } + return -1; + }; + } + + // Returns the first index on an array-like that passes a truth test. + var findIndex = createPredicateIndexFinder(1); + + // Returns the last index on an array-like that passes a truth test. + var findLastIndex = createPredicateIndexFinder(-1); + + // Use a comparator function to figure out the smallest index at which + // an object should be inserted so as to maintain order. Uses binary search. + function sortedIndex(array, obj, iteratee, context) { + iteratee = cb(iteratee, context, 1); + var value = iteratee(obj); + var low = 0, high = getLength(array); + while (low < high) { + var mid = Math.floor((low + high) / 2); + if (iteratee(array[mid]) < value) low = mid + 1; else high = mid; + } + return low; + } + + // Internal function to generate the `_.indexOf` and `_.lastIndexOf` functions. + function createIndexFinder(dir, predicateFind, sortedIndex) { + return function(array, item, idx) { + var i = 0, length = getLength(array); + if (typeof idx == 'number') { + if (dir > 0) { + i = idx >= 0 ? idx : Math.max(idx + length, i); + } else { + length = idx >= 0 ? Math.min(idx + 1, length) : idx + length + 1; + } + } else if (sortedIndex && idx && length) { + idx = sortedIndex(array, item); + return array[idx] === item ? idx : -1; + } + if (item !== item) { + idx = predicateFind(slice.call(array, i, length), isNaN$1); + return idx >= 0 ? idx + i : -1; + } + for (idx = dir > 0 ? i : length - 1; idx >= 0 && idx < length; idx += dir) { + if (array[idx] === item) return idx; + } + return -1; + }; + } + + // Return the position of the first occurrence of an item in an array, + // or -1 if the item is not included in the array. + // If the array is large and already in sort order, pass `true` + // for **isSorted** to use binary search. + var indexOf = createIndexFinder(1, findIndex, sortedIndex); + + // Return the position of the last occurrence of an item in an array, + // or -1 if the item is not included in the array. + var lastIndexOf = createIndexFinder(-1, findLastIndex); + + // Return the first value which passes a truth test. + function find(obj, predicate, context) { + var keyFinder = isArrayLike(obj) ? findIndex : findKey; + var key = keyFinder(obj, predicate, context); + if (key !== void 0 && key !== -1) return obj[key]; + } + + // Convenience version of a common use case of `_.find`: getting the first + // object containing specific `key:value` pairs. + function findWhere(obj, attrs) { + return find(obj, matcher(attrs)); + } + + // The cornerstone for collection functions, an `each` + // implementation, aka `forEach`. + // Handles raw objects in addition to array-likes. Treats all + // sparse array-likes as if they were dense. + function each(obj, iteratee, context) { + iteratee = optimizeCb(iteratee, context); + var i, length; + if (isArrayLike(obj)) { + for (i = 0, length = obj.length; i < length; i++) { + iteratee(obj[i], i, obj); + } + } else { + var _keys = keys(obj); + for (i = 0, length = _keys.length; i < length; i++) { + iteratee(obj[_keys[i]], _keys[i], obj); + } + } + return obj; + } + + // Return the results of applying the iteratee to each element. + function map(obj, iteratee, context) { + iteratee = cb(iteratee, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length, + results = Array(length); + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + results[index] = iteratee(obj[currentKey], currentKey, obj); + } + return results; + } + + // Internal helper to create a reducing function, iterating left or right. + function createReduce(dir) { + // Wrap code that reassigns argument variables in a separate function than + // the one that accesses `arguments.length` to avoid a perf hit. (#1991) + var reducer = function(obj, iteratee, memo, initial) { + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length, + index = dir > 0 ? 0 : length - 1; + if (!initial) { + memo = obj[_keys ? _keys[index] : index]; + index += dir; + } + for (; index >= 0 && index < length; index += dir) { + var currentKey = _keys ? _keys[index] : index; + memo = iteratee(memo, obj[currentKey], currentKey, obj); + } + return memo; + }; + + return function(obj, iteratee, memo, context) { + var initial = arguments.length >= 3; + return reducer(obj, optimizeCb(iteratee, context, 4), memo, initial); + }; + } + + // **Reduce** builds up a single result from a list of values, aka `inject`, + // or `foldl`. + var reduce = createReduce(1); + + // The right-associative version of reduce, also known as `foldr`. + var reduceRight = createReduce(-1); + + // Return all the elements that pass a truth test. + function filter(obj, predicate, context) { + var results = []; + predicate = cb(predicate, context); + each(obj, function(value, index, list) { + if (predicate(value, index, list)) results.push(value); + }); + return results; + } + + // Return all the elements for which a truth test fails. + function reject(obj, predicate, context) { + return filter(obj, negate(cb(predicate)), context); + } + + // Determine whether all of the elements pass a truth test. + function every(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length; + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + if (!predicate(obj[currentKey], currentKey, obj)) return false; + } + return true; + } + + // Determine if at least one element in the object passes a truth test. + function some(obj, predicate, context) { + predicate = cb(predicate, context); + var _keys = !isArrayLike(obj) && keys(obj), + length = (_keys || obj).length; + for (var index = 0; index < length; index++) { + var currentKey = _keys ? _keys[index] : index; + if (predicate(obj[currentKey], currentKey, obj)) return true; + } + return false; + } + + // Determine if the array or object contains a given item (using `===`). + function contains(obj, item, fromIndex, guard) { + if (!isArrayLike(obj)) obj = values(obj); + if (typeof fromIndex != 'number' || guard) fromIndex = 0; + return indexOf(obj, item, fromIndex) >= 0; + } + + // Invoke a method (with arguments) on every item in a collection. + var invoke = restArguments(function(obj, path, args) { + var contextPath, func; + if (isFunction$1(path)) { + func = path; + } else { + path = toPath(path); + contextPath = path.slice(0, -1); + path = path[path.length - 1]; + } + return map(obj, function(context) { + var method = func; + if (!method) { + if (contextPath && contextPath.length) { + context = deepGet(context, contextPath); + } + if (context == null) return void 0; + method = context[path]; + } + return method == null ? method : method.apply(context, args); + }); + }); + + // Convenience version of a common use case of `_.map`: fetching a property. + function pluck(obj, key) { + return map(obj, property(key)); + } + + // Convenience version of a common use case of `_.filter`: selecting only + // objects containing specific `key:value` pairs. + function where(obj, attrs) { + return filter(obj, matcher(attrs)); + } + + // Return the maximum element (or element-based computation). + function max(obj, iteratee, context) { + var result = -Infinity, lastComputed = -Infinity, + value, computed; + if (iteratee == null || typeof iteratee == 'number' && typeof obj[0] != 'object' && obj != null) { + obj = isArrayLike(obj) ? obj : values(obj); + for (var i = 0, length = obj.length; i < length; i++) { + value = obj[i]; + if (value != null && value > result) { + result = value; + } + } + } else { + iteratee = cb(iteratee, context); + each(obj, function(v, index, list) { + computed = iteratee(v, index, list); + if (computed > lastComputed || computed === -Infinity && result === -Infinity) { + result = v; + lastComputed = computed; + } + }); + } + return result; + } + + // Return the minimum element (or element-based computation). + function min(obj, iteratee, context) { + var result = Infinity, lastComputed = Infinity, + value, computed; + if (iteratee == null || typeof iteratee == 'number' && typeof obj[0] != 'object' && obj != null) { + obj = isArrayLike(obj) ? obj : values(obj); + for (var i = 0, length = obj.length; i < length; i++) { + value = obj[i]; + if (value != null && value < result) { + result = value; + } + } + } else { + iteratee = cb(iteratee, context); + each(obj, function(v, index, list) { + computed = iteratee(v, index, list); + if (computed < lastComputed || computed === Infinity && result === Infinity) { + result = v; + lastComputed = computed; + } + }); + } + return result; + } + + // Sample **n** random values from a collection using the modern version of the + // [Fisher-Yates shuffle](https://en.wikipedia.org/wiki/Fisher–Yates_shuffle). + // If **n** is not specified, returns a single random element. + // The internal `guard` argument allows it to work with `_.map`. + function sample(obj, n, guard) { + if (n == null || guard) { + if (!isArrayLike(obj)) obj = values(obj); + return obj[random(obj.length - 1)]; + } + var sample = isArrayLike(obj) ? clone(obj) : values(obj); + var length = getLength(sample); + n = Math.max(Math.min(n, length), 0); + var last = length - 1; + for (var index = 0; index < n; index++) { + var rand = random(index, last); + var temp = sample[index]; + sample[index] = sample[rand]; + sample[rand] = temp; + } + return sample.slice(0, n); + } + + // Shuffle a collection. + function shuffle(obj) { + return sample(obj, Infinity); + } + + // Sort the object's values by a criterion produced by an iteratee. + function sortBy(obj, iteratee, context) { + var index = 0; + iteratee = cb(iteratee, context); + return pluck(map(obj, function(value, key, list) { + return { + value: value, + index: index++, + criteria: iteratee(value, key, list) + }; + }).sort(function(left, right) { + var a = left.criteria; + var b = right.criteria; + if (a !== b) { + if (a > b || a === void 0) return 1; + if (a < b || b === void 0) return -1; + } + return left.index - right.index; + }), 'value'); + } + + // An internal function used for aggregate "group by" operations. + function group(behavior, partition) { + return function(obj, iteratee, context) { + var result = partition ? [[], []] : {}; + iteratee = cb(iteratee, context); + each(obj, function(value, index) { + var key = iteratee(value, index, obj); + behavior(result, value, key); + }); + return result; + }; + } + + // Groups the object's values by a criterion. Pass either a string attribute + // to group by, or a function that returns the criterion. + var groupBy = group(function(result, value, key) { + if (has$1(result, key)) result[key].push(value); else result[key] = [value]; + }); + + // Indexes the object's values by a criterion, similar to `_.groupBy`, but for + // when you know that your index values will be unique. + var indexBy = group(function(result, value, key) { + result[key] = value; + }); + + // Counts instances of an object that group by a certain criterion. Pass + // either a string attribute to count by, or a function that returns the + // criterion. + var countBy = group(function(result, value, key) { + if (has$1(result, key)) result[key]++; else result[key] = 1; + }); + + // Split a collection into two arrays: one whose elements all pass the given + // truth test, and one whose elements all do not pass the truth test. + var partition = group(function(result, value, pass) { + result[pass ? 0 : 1].push(value); + }, true); + + // Safely create a real, live array from anything iterable. + var reStrSymbol = /[^\ud800-\udfff]|[\ud800-\udbff][\udc00-\udfff]|[\ud800-\udfff]/g; + function toArray(obj) { + if (!obj) return []; + if (isArray(obj)) return slice.call(obj); + if (isString(obj)) { + // Keep surrogate pair characters together. + return obj.match(reStrSymbol); + } + if (isArrayLike(obj)) return map(obj, identity); + return values(obj); + } + + // Return the number of elements in a collection. + function size(obj) { + if (obj == null) return 0; + return isArrayLike(obj) ? obj.length : keys(obj).length; + } + + // Internal `_.pick` helper function to determine whether `key` is an enumerable + // property name of `obj`. + function keyInObj(value, key, obj) { + return key in obj; + } + + // Return a copy of the object only containing the allowed properties. + var pick = restArguments(function(obj, keys) { + var result = {}, iteratee = keys[0]; + if (obj == null) return result; + if (isFunction$1(iteratee)) { + if (keys.length > 1) iteratee = optimizeCb(iteratee, keys[1]); + keys = allKeys(obj); + } else { + iteratee = keyInObj; + keys = flatten$1(keys, false, false); + obj = Object(obj); + } + for (var i = 0, length = keys.length; i < length; i++) { + var key = keys[i]; + var value = obj[key]; + if (iteratee(value, key, obj)) result[key] = value; + } + return result; + }); + + // Return a copy of the object without the disallowed properties. + var omit = restArguments(function(obj, keys) { + var iteratee = keys[0], context; + if (isFunction$1(iteratee)) { + iteratee = negate(iteratee); + if (keys.length > 1) context = keys[1]; + } else { + keys = map(flatten$1(keys, false, false), String); + iteratee = function(value, key) { + return !contains(keys, key); + }; + } + return pick(obj, iteratee, context); + }); + + // Returns everything but the last entry of the array. Especially useful on + // the arguments object. Passing **n** will return all the values in + // the array, excluding the last N. + function initial(array, n, guard) { + return slice.call(array, 0, Math.max(0, array.length - (n == null || guard ? 1 : n))); + } + + // Get the first element of an array. Passing **n** will return the first N + // values in the array. The **guard** check allows it to work with `_.map`. + function first(array, n, guard) { + if (array == null || array.length < 1) return n == null || guard ? void 0 : []; + if (n == null || guard) return array[0]; + return initial(array, array.length - n); + } + + // Returns everything but the first entry of the `array`. Especially useful on + // the `arguments` object. Passing an **n** will return the rest N values in the + // `array`. + function rest(array, n, guard) { + return slice.call(array, n == null || guard ? 1 : n); + } + + // Get the last element of an array. Passing **n** will return the last N + // values in the array. + function last(array, n, guard) { + if (array == null || array.length < 1) return n == null || guard ? void 0 : []; + if (n == null || guard) return array[array.length - 1]; + return rest(array, Math.max(0, array.length - n)); + } + + // Trim out all falsy values from an array. + function compact(array) { + return filter(array, Boolean); + } + + // Flatten out an array, either recursively (by default), or up to `depth`. + // Passing `true` or `false` as `depth` means `1` or `Infinity`, respectively. + function flatten(array, depth) { + return flatten$1(array, depth, false); + } + + // Take the difference between one array and a number of other arrays. + // Only the elements present in just the first array will remain. + var difference = restArguments(function(array, rest) { + rest = flatten$1(rest, true, true); + return filter(array, function(value){ + return !contains(rest, value); + }); + }); + + // Return a version of the array that does not contain the specified value(s). + var without = restArguments(function(array, otherArrays) { + return difference(array, otherArrays); + }); + + // Produce a duplicate-free version of the array. If the array has already + // been sorted, you have the option of using a faster algorithm. + // The faster algorithm will not work with an iteratee if the iteratee + // is not a one-to-one function, so providing an iteratee will disable + // the faster algorithm. + function uniq(array, isSorted, iteratee, context) { + if (!isBoolean(isSorted)) { + context = iteratee; + iteratee = isSorted; + isSorted = false; + } + if (iteratee != null) iteratee = cb(iteratee, context); + var result = []; + var seen = []; + for (var i = 0, length = getLength(array); i < length; i++) { + var value = array[i], + computed = iteratee ? iteratee(value, i, array) : value; + if (isSorted && !iteratee) { + if (!i || seen !== computed) result.push(value); + seen = computed; + } else if (iteratee) { + if (!contains(seen, computed)) { + seen.push(computed); + result.push(value); + } + } else if (!contains(result, value)) { + result.push(value); + } + } + return result; + } + + // Produce an array that contains the union: each distinct element from all of + // the passed-in arrays. + var union = restArguments(function(arrays) { + return uniq(flatten$1(arrays, true, true)); + }); + + // Produce an array that contains every item shared between all the + // passed-in arrays. + function intersection(array) { + var result = []; + var argsLength = arguments.length; + for (var i = 0, length = getLength(array); i < length; i++) { + var item = array[i]; + if (contains(result, item)) continue; + var j; + for (j = 1; j < argsLength; j++) { + if (!contains(arguments[j], item)) break; + } + if (j === argsLength) result.push(item); + } + return result; + } + + // Complement of zip. Unzip accepts an array of arrays and groups + // each array's elements on shared indices. + function unzip(array) { + var length = array && max(array, getLength).length || 0; + var result = Array(length); + + for (var index = 0; index < length; index++) { + result[index] = pluck(array, index); + } + return result; + } + + // Zip together multiple lists into a single array -- elements that share + // an index go together. + var zip = restArguments(unzip); + + // Converts lists into objects. Pass either a single array of `[key, value]` + // pairs, or two parallel arrays of the same length -- one of keys, and one of + // the corresponding values. Passing by pairs is the reverse of `_.pairs`. + function object(list, values) { + var result = {}; + for (var i = 0, length = getLength(list); i < length; i++) { + if (values) { + result[list[i]] = values[i]; + } else { + result[list[i][0]] = list[i][1]; + } + } + return result; + } + + // Generate an integer Array containing an arithmetic progression. A port of + // the native Python `range()` function. See + // [the Python documentation](https://docs.python.org/library/functions.html#range). + function range(start, stop, step) { + if (stop == null) { + stop = start || 0; + start = 0; + } + if (!step) { + step = stop < start ? -1 : 1; + } + + var length = Math.max(Math.ceil((stop - start) / step), 0); + var range = Array(length); + + for (var idx = 0; idx < length; idx++, start += step) { + range[idx] = start; + } + + return range; + } + + // Chunk a single array into multiple arrays, each containing `count` or fewer + // items. + function chunk(array, count) { + if (count == null || count < 1) return []; + var result = []; + var i = 0, length = array.length; + while (i < length) { + result.push(slice.call(array, i, i += count)); + } + return result; + } + + // Helper function to continue chaining intermediate results. + function chainResult(instance, obj) { + return instance._chain ? _$1(obj).chain() : obj; + } + + // Add your own custom functions to the Underscore object. + function mixin(obj) { + each(functions(obj), function(name) { + var func = _$1[name] = obj[name]; + _$1.prototype[name] = function() { + var args = [this._wrapped]; + push.apply(args, arguments); + return chainResult(this, func.apply(_$1, args)); + }; + }); + return _$1; + } + + // Add all mutator `Array` functions to the wrapper. + each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) { + var method = ArrayProto[name]; + _$1.prototype[name] = function() { + var obj = this._wrapped; + if (obj != null) { + method.apply(obj, arguments); + if ((name === 'shift' || name === 'splice') && obj.length === 0) { + delete obj[0]; + } + } + return chainResult(this, obj); + }; + }); + + // Add all accessor `Array` functions to the wrapper. + each(['concat', 'join', 'slice'], function(name) { + var method = ArrayProto[name]; + _$1.prototype[name] = function() { + var obj = this._wrapped; + if (obj != null) obj = method.apply(obj, arguments); + return chainResult(this, obj); + }; + }); + + // Named Exports + + var allExports = { + __proto__: null, + VERSION: VERSION, + restArguments: restArguments, + isObject: isObject, + isNull: isNull, + isUndefined: isUndefined, + isBoolean: isBoolean, + isElement: isElement, + isString: isString, + isNumber: isNumber, + isDate: isDate, + isRegExp: isRegExp, + isError: isError, + isSymbol: isSymbol, + isArrayBuffer: isArrayBuffer, + isDataView: isDataView$1, + isArray: isArray, + isFunction: isFunction$1, + isArguments: isArguments$1, + isFinite: isFinite$1, + isNaN: isNaN$1, + isTypedArray: isTypedArray$1, + isEmpty: isEmpty, + isMatch: isMatch, + isEqual: isEqual, + isMap: isMap, + isWeakMap: isWeakMap, + isSet: isSet, + isWeakSet: isWeakSet, + keys: keys, + allKeys: allKeys, + values: values, + pairs: pairs, + invert: invert, + functions: functions, + methods: functions, + extend: extend, + extendOwn: extendOwn, + assign: extendOwn, + defaults: defaults, + create: create, + clone: clone, + tap: tap, + get: get, + has: has, + mapObject: mapObject, + identity: identity, + constant: constant, + noop: noop, + toPath: toPath$1, + property: property, + propertyOf: propertyOf, + matcher: matcher, + matches: matcher, + times: times, + random: random, + now: now, + escape: _escape, + unescape: _unescape, + templateSettings: templateSettings, + template: template, + result: result, + uniqueId: uniqueId, + chain: chain, + iteratee: iteratee, + partial: partial, + bind: bind, + bindAll: bindAll, + memoize: memoize, + delay: delay, + defer: defer, + throttle: throttle, + debounce: debounce, + wrap: wrap, + negate: negate, + compose: compose, + after: after, + before: before, + once: once, + findKey: findKey, + findIndex: findIndex, + findLastIndex: findLastIndex, + sortedIndex: sortedIndex, + indexOf: indexOf, + lastIndexOf: lastIndexOf, + find: find, + detect: find, + findWhere: findWhere, + each: each, + forEach: each, + map: map, + collect: map, + reduce: reduce, + foldl: reduce, + inject: reduce, + reduceRight: reduceRight, + foldr: reduceRight, + filter: filter, + select: filter, + reject: reject, + every: every, + all: every, + some: some, + any: some, + contains: contains, + includes: contains, + include: contains, + invoke: invoke, + pluck: pluck, + where: where, + max: max, + min: min, + shuffle: shuffle, + sample: sample, + sortBy: sortBy, + groupBy: groupBy, + indexBy: indexBy, + countBy: countBy, + partition: partition, + toArray: toArray, + size: size, + pick: pick, + omit: omit, + first: first, + head: first, + take: first, + initial: initial, + last: last, + rest: rest, + tail: rest, + drop: rest, + compact: compact, + flatten: flatten, + without: without, + uniq: uniq, + unique: uniq, + union: union, + intersection: intersection, + difference: difference, + unzip: unzip, + transpose: unzip, + zip: zip, + object: object, + range: range, + chunk: chunk, + mixin: mixin, + 'default': _$1 + }; + + // Default Export + + // Add all of the Underscore functions to the wrapper object. + var _ = mixin(allExports); + // Legacy Node.js API. + _._ = _; + + return _; + +}))); +//# sourceMappingURL=underscore-umd.js.map diff --git a/docsrc/_build/html/_static/underscore-1.3.1.js b/docsrc/_build/html/_static/underscore-1.3.1.js deleted file mode 100644 index 208d4cd..0000000 --- a/docsrc/_build/html/_static/underscore-1.3.1.js +++ /dev/null @@ -1,999 +0,0 @@ -// Underscore.js 1.3.1 -// (c) 2009-2012 Jeremy Ashkenas, DocumentCloud Inc. -// Underscore is freely distributable under the MIT license. -// Portions of Underscore are inspired or borrowed from Prototype, -// Oliver Steele's Functional, and John Resig's Micro-Templating. -// For all details and documentation: -// http://documentcloud.github.com/underscore - -(function() { - - // Baseline setup - // -------------- - - // Establish the root object, `window` in the browser, or `global` on the server. - var root = this; - - // Save the previous value of the `_` variable. - var previousUnderscore = root._; - - // Establish the object that gets returned to break out of a loop iteration. - var breaker = {}; - - // Save bytes in the minified (but not gzipped) version: - var ArrayProto = Array.prototype, ObjProto = Object.prototype, FuncProto = Function.prototype; - - // Create quick reference variables for speed access to core prototypes. - var slice = ArrayProto.slice, - unshift = ArrayProto.unshift, - toString = ObjProto.toString, - hasOwnProperty = ObjProto.hasOwnProperty; - - // All **ECMAScript 5** native function implementations that we hope to use - // are declared here. - var - nativeForEach = ArrayProto.forEach, - nativeMap = ArrayProto.map, - nativeReduce = ArrayProto.reduce, - nativeReduceRight = ArrayProto.reduceRight, - nativeFilter = ArrayProto.filter, - nativeEvery = ArrayProto.every, - nativeSome = ArrayProto.some, - nativeIndexOf = ArrayProto.indexOf, - nativeLastIndexOf = ArrayProto.lastIndexOf, - nativeIsArray = Array.isArray, - nativeKeys = Object.keys, - nativeBind = FuncProto.bind; - - // Create a safe reference to the Underscore object for use below. - var _ = function(obj) { return new wrapper(obj); }; - - // Export the Underscore object for **Node.js**, with - // backwards-compatibility for the old `require()` API. If we're in - // the browser, add `_` as a global object via a string identifier, - // for Closure Compiler "advanced" mode. - if (typeof exports !== 'undefined') { - if (typeof module !== 'undefined' && module.exports) { - exports = module.exports = _; - } - exports._ = _; - } else { - root['_'] = _; - } - - // Current version. - _.VERSION = '1.3.1'; - - // Collection Functions - // -------------------- - - // The cornerstone, an `each` implementation, aka `forEach`. - // Handles objects with the built-in `forEach`, arrays, and raw objects. - // Delegates to **ECMAScript 5**'s native `forEach` if available. - var each = _.each = _.forEach = function(obj, iterator, context) { - if (obj == null) return; - if (nativeForEach && obj.forEach === nativeForEach) { - obj.forEach(iterator, context); - } else if (obj.length === +obj.length) { - for (var i = 0, l = obj.length; i < l; i++) { - if (i in obj && iterator.call(context, obj[i], i, obj) === breaker) return; - } - } else { - for (var key in obj) { - if (_.has(obj, key)) { - if (iterator.call(context, obj[key], key, obj) === breaker) return; - } - } - } - }; - - // Return the results of applying the iterator to each element. - // Delegates to **ECMAScript 5**'s native `map` if available. - _.map = _.collect = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - if (nativeMap && obj.map === nativeMap) return obj.map(iterator, context); - each(obj, function(value, index, list) { - results[results.length] = iterator.call(context, value, index, list); - }); - if (obj.length === +obj.length) results.length = obj.length; - return results; - }; - - // **Reduce** builds up a single result from a list of values, aka `inject`, - // or `foldl`. Delegates to **ECMAScript 5**'s native `reduce` if available. - _.reduce = _.foldl = _.inject = function(obj, iterator, memo, context) { - var initial = arguments.length > 2; - if (obj == null) obj = []; - if (nativeReduce && obj.reduce === nativeReduce) { - if (context) iterator = _.bind(iterator, context); - return initial ? obj.reduce(iterator, memo) : obj.reduce(iterator); - } - each(obj, function(value, index, list) { - if (!initial) { - memo = value; - initial = true; - } else { - memo = iterator.call(context, memo, value, index, list); - } - }); - if (!initial) throw new TypeError('Reduce of empty array with no initial value'); - return memo; - }; - - // The right-associative version of reduce, also known as `foldr`. - // Delegates to **ECMAScript 5**'s native `reduceRight` if available. - _.reduceRight = _.foldr = function(obj, iterator, memo, context) { - var initial = arguments.length > 2; - if (obj == null) obj = []; - if (nativeReduceRight && obj.reduceRight === nativeReduceRight) { - if (context) iterator = _.bind(iterator, context); - return initial ? obj.reduceRight(iterator, memo) : obj.reduceRight(iterator); - } - var reversed = _.toArray(obj).reverse(); - if (context && !initial) iterator = _.bind(iterator, context); - return initial ? _.reduce(reversed, iterator, memo, context) : _.reduce(reversed, iterator); - }; - - // Return the first value which passes a truth test. Aliased as `detect`. - _.find = _.detect = function(obj, iterator, context) { - var result; - any(obj, function(value, index, list) { - if (iterator.call(context, value, index, list)) { - result = value; - return true; - } - }); - return result; - }; - - // Return all the elements that pass a truth test. - // Delegates to **ECMAScript 5**'s native `filter` if available. - // Aliased as `select`. - _.filter = _.select = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - if (nativeFilter && obj.filter === nativeFilter) return obj.filter(iterator, context); - each(obj, function(value, index, list) { - if (iterator.call(context, value, index, list)) results[results.length] = value; - }); - return results; - }; - - // Return all the elements for which a truth test fails. - _.reject = function(obj, iterator, context) { - var results = []; - if (obj == null) return results; - each(obj, function(value, index, list) { - if (!iterator.call(context, value, index, list)) results[results.length] = value; - }); - return results; - }; - - // Determine whether all of the elements match a truth test. - // Delegates to **ECMAScript 5**'s native `every` if available. - // Aliased as `all`. - _.every = _.all = function(obj, iterator, context) { - var result = true; - if (obj == null) return result; - if (nativeEvery && obj.every === nativeEvery) return obj.every(iterator, context); - each(obj, function(value, index, list) { - if (!(result = result && iterator.call(context, value, index, list))) return breaker; - }); - return result; - }; - - // Determine if at least one element in the object matches a truth test. - // Delegates to **ECMAScript 5**'s native `some` if available. - // Aliased as `any`. - var any = _.some = _.any = function(obj, iterator, context) { - iterator || (iterator = _.identity); - var result = false; - if (obj == null) return result; - if (nativeSome && obj.some === nativeSome) return obj.some(iterator, context); - each(obj, function(value, index, list) { - if (result || (result = iterator.call(context, value, index, list))) return breaker; - }); - return !!result; - }; - - // Determine if a given value is included in the array or object using `===`. - // Aliased as `contains`. - _.include = _.contains = function(obj, target) { - var found = false; - if (obj == null) return found; - if (nativeIndexOf && obj.indexOf === nativeIndexOf) return obj.indexOf(target) != -1; - found = any(obj, function(value) { - return value === target; - }); - return found; - }; - - // Invoke a method (with arguments) on every item in a collection. - _.invoke = function(obj, method) { - var args = slice.call(arguments, 2); - return _.map(obj, function(value) { - return (_.isFunction(method) ? method || value : value[method]).apply(value, args); - }); - }; - - // Convenience version of a common use case of `map`: fetching a property. - _.pluck = function(obj, key) { - return _.map(obj, function(value){ return value[key]; }); - }; - - // Return the maximum element or (element-based computation). - _.max = function(obj, iterator, context) { - if (!iterator && _.isArray(obj)) return Math.max.apply(Math, obj); - if (!iterator && _.isEmpty(obj)) return -Infinity; - var result = {computed : -Infinity}; - each(obj, function(value, index, list) { - var computed = iterator ? iterator.call(context, value, index, list) : value; - computed >= result.computed && (result = {value : value, computed : computed}); - }); - return result.value; - }; - - // Return the minimum element (or element-based computation). - _.min = function(obj, iterator, context) { - if (!iterator && _.isArray(obj)) return Math.min.apply(Math, obj); - if (!iterator && _.isEmpty(obj)) return Infinity; - var result = {computed : Infinity}; - each(obj, function(value, index, list) { - var computed = iterator ? iterator.call(context, value, index, list) : value; - computed < result.computed && (result = {value : value, computed : computed}); - }); - return result.value; - }; - - // Shuffle an array. - _.shuffle = function(obj) { - var shuffled = [], rand; - each(obj, function(value, index, list) { - if (index == 0) { - shuffled[0] = value; - } else { - rand = Math.floor(Math.random() * (index + 1)); - shuffled[index] = shuffled[rand]; - shuffled[rand] = value; - } - }); - return shuffled; - }; - - // Sort the object's values by a criterion produced by an iterator. - _.sortBy = function(obj, iterator, context) { - return _.pluck(_.map(obj, function(value, index, list) { - return { - value : value, - criteria : iterator.call(context, value, index, list) - }; - }).sort(function(left, right) { - var a = left.criteria, b = right.criteria; - return a < b ? -1 : a > b ? 1 : 0; - }), 'value'); - }; - - // Groups the object's values by a criterion. Pass either a string attribute - // to group by, or a function that returns the criterion. - _.groupBy = function(obj, val) { - var result = {}; - var iterator = _.isFunction(val) ? val : function(obj) { return obj[val]; }; - each(obj, function(value, index) { - var key = iterator(value, index); - (result[key] || (result[key] = [])).push(value); - }); - return result; - }; - - // Use a comparator function to figure out at what index an object should - // be inserted so as to maintain order. Uses binary search. - _.sortedIndex = function(array, obj, iterator) { - iterator || (iterator = _.identity); - var low = 0, high = array.length; - while (low < high) { - var mid = (low + high) >> 1; - iterator(array[mid]) < iterator(obj) ? low = mid + 1 : high = mid; - } - return low; - }; - - // Safely convert anything iterable into a real, live array. - _.toArray = function(iterable) { - if (!iterable) return []; - if (iterable.toArray) return iterable.toArray(); - if (_.isArray(iterable)) return slice.call(iterable); - if (_.isArguments(iterable)) return slice.call(iterable); - return _.values(iterable); - }; - - // Return the number of elements in an object. - _.size = function(obj) { - return _.toArray(obj).length; - }; - - // Array Functions - // --------------- - - // Get the first element of an array. Passing **n** will return the first N - // values in the array. Aliased as `head`. The **guard** check allows it to work - // with `_.map`. - _.first = _.head = function(array, n, guard) { - return (n != null) && !guard ? slice.call(array, 0, n) : array[0]; - }; - - // Returns everything but the last entry of the array. Especcialy useful on - // the arguments object. Passing **n** will return all the values in - // the array, excluding the last N. The **guard** check allows it to work with - // `_.map`. - _.initial = function(array, n, guard) { - return slice.call(array, 0, array.length - ((n == null) || guard ? 1 : n)); - }; - - // Get the last element of an array. Passing **n** will return the last N - // values in the array. The **guard** check allows it to work with `_.map`. - _.last = function(array, n, guard) { - if ((n != null) && !guard) { - return slice.call(array, Math.max(array.length - n, 0)); - } else { - return array[array.length - 1]; - } - }; - - // Returns everything but the first entry of the array. Aliased as `tail`. - // Especially useful on the arguments object. Passing an **index** will return - // the rest of the values in the array from that index onward. The **guard** - // check allows it to work with `_.map`. - _.rest = _.tail = function(array, index, guard) { - return slice.call(array, (index == null) || guard ? 1 : index); - }; - - // Trim out all falsy values from an array. - _.compact = function(array) { - return _.filter(array, function(value){ return !!value; }); - }; - - // Return a completely flattened version of an array. - _.flatten = function(array, shallow) { - return _.reduce(array, function(memo, value) { - if (_.isArray(value)) return memo.concat(shallow ? value : _.flatten(value)); - memo[memo.length] = value; - return memo; - }, []); - }; - - // Return a version of the array that does not contain the specified value(s). - _.without = function(array) { - return _.difference(array, slice.call(arguments, 1)); - }; - - // Produce a duplicate-free version of the array. If the array has already - // been sorted, you have the option of using a faster algorithm. - // Aliased as `unique`. - _.uniq = _.unique = function(array, isSorted, iterator) { - var initial = iterator ? _.map(array, iterator) : array; - var result = []; - _.reduce(initial, function(memo, el, i) { - if (0 == i || (isSorted === true ? _.last(memo) != el : !_.include(memo, el))) { - memo[memo.length] = el; - result[result.length] = array[i]; - } - return memo; - }, []); - return result; - }; - - // Produce an array that contains the union: each distinct element from all of - // the passed-in arrays. - _.union = function() { - return _.uniq(_.flatten(arguments, true)); - }; - - // Produce an array that contains every item shared between all the - // passed-in arrays. (Aliased as "intersect" for back-compat.) - _.intersection = _.intersect = function(array) { - var rest = slice.call(arguments, 1); - return _.filter(_.uniq(array), function(item) { - return _.every(rest, function(other) { - return _.indexOf(other, item) >= 0; - }); - }); - }; - - // Take the difference between one array and a number of other arrays. - // Only the elements present in just the first array will remain. - _.difference = function(array) { - var rest = _.flatten(slice.call(arguments, 1)); - return _.filter(array, function(value){ return !_.include(rest, value); }); - }; - - // Zip together multiple lists into a single array -- elements that share - // an index go together. - _.zip = function() { - var args = slice.call(arguments); - var length = _.max(_.pluck(args, 'length')); - var results = new Array(length); - for (var i = 0; i < length; i++) results[i] = _.pluck(args, "" + i); - return results; - }; - - // If the browser doesn't supply us with indexOf (I'm looking at you, **MSIE**), - // we need this function. Return the position of the first occurrence of an - // item in an array, or -1 if the item is not included in the array. - // Delegates to **ECMAScript 5**'s native `indexOf` if available. - // If the array is large and already in sort order, pass `true` - // for **isSorted** to use binary search. - _.indexOf = function(array, item, isSorted) { - if (array == null) return -1; - var i, l; - if (isSorted) { - i = _.sortedIndex(array, item); - return array[i] === item ? i : -1; - } - if (nativeIndexOf && array.indexOf === nativeIndexOf) return array.indexOf(item); - for (i = 0, l = array.length; i < l; i++) if (i in array && array[i] === item) return i; - return -1; - }; - - // Delegates to **ECMAScript 5**'s native `lastIndexOf` if available. - _.lastIndexOf = function(array, item) { - if (array == null) return -1; - if (nativeLastIndexOf && array.lastIndexOf === nativeLastIndexOf) return array.lastIndexOf(item); - var i = array.length; - while (i--) if (i in array && array[i] === item) return i; - return -1; - }; - - // Generate an integer Array containing an arithmetic progression. A port of - // the native Python `range()` function. See - // [the Python documentation](http://docs.python.org/library/functions.html#range). - _.range = function(start, stop, step) { - if (arguments.length <= 1) { - stop = start || 0; - start = 0; - } - step = arguments[2] || 1; - - var len = Math.max(Math.ceil((stop - start) / step), 0); - var idx = 0; - var range = new Array(len); - - while(idx < len) { - range[idx++] = start; - start += step; - } - - return range; - }; - - // Function (ahem) Functions - // ------------------ - - // Reusable constructor function for prototype setting. - var ctor = function(){}; - - // Create a function bound to a given object (assigning `this`, and arguments, - // optionally). Binding with arguments is also known as `curry`. - // Delegates to **ECMAScript 5**'s native `Function.bind` if available. - // We check for `func.bind` first, to fail fast when `func` is undefined. - _.bind = function bind(func, context) { - var bound, args; - if (func.bind === nativeBind && nativeBind) return nativeBind.apply(func, slice.call(arguments, 1)); - if (!_.isFunction(func)) throw new TypeError; - args = slice.call(arguments, 2); - return bound = function() { - if (!(this instanceof bound)) return func.apply(context, args.concat(slice.call(arguments))); - ctor.prototype = func.prototype; - var self = new ctor; - var result = func.apply(self, args.concat(slice.call(arguments))); - if (Object(result) === result) return result; - return self; - }; - }; - - // Bind all of an object's methods to that object. Useful for ensuring that - // all callbacks defined on an object belong to it. - _.bindAll = function(obj) { - var funcs = slice.call(arguments, 1); - if (funcs.length == 0) funcs = _.functions(obj); - each(funcs, function(f) { obj[f] = _.bind(obj[f], obj); }); - return obj; - }; - - // Memoize an expensive function by storing its results. - _.memoize = function(func, hasher) { - var memo = {}; - hasher || (hasher = _.identity); - return function() { - var key = hasher.apply(this, arguments); - return _.has(memo, key) ? memo[key] : (memo[key] = func.apply(this, arguments)); - }; - }; - - // Delays a function for the given number of milliseconds, and then calls - // it with the arguments supplied. - _.delay = function(func, wait) { - var args = slice.call(arguments, 2); - return setTimeout(function(){ return func.apply(func, args); }, wait); - }; - - // Defers a function, scheduling it to run after the current call stack has - // cleared. - _.defer = function(func) { - return _.delay.apply(_, [func, 1].concat(slice.call(arguments, 1))); - }; - - // Returns a function, that, when invoked, will only be triggered at most once - // during a given window of time. - _.throttle = function(func, wait) { - var context, args, timeout, throttling, more; - var whenDone = _.debounce(function(){ more = throttling = false; }, wait); - return function() { - context = this; args = arguments; - var later = function() { - timeout = null; - if (more) func.apply(context, args); - whenDone(); - }; - if (!timeout) timeout = setTimeout(later, wait); - if (throttling) { - more = true; - } else { - func.apply(context, args); - } - whenDone(); - throttling = true; - }; - }; - - // Returns a function, that, as long as it continues to be invoked, will not - // be triggered. The function will be called after it stops being called for - // N milliseconds. - _.debounce = function(func, wait) { - var timeout; - return function() { - var context = this, args = arguments; - var later = function() { - timeout = null; - func.apply(context, args); - }; - clearTimeout(timeout); - timeout = setTimeout(later, wait); - }; - }; - - // Returns a function that will be executed at most one time, no matter how - // often you call it. Useful for lazy initialization. - _.once = function(func) { - var ran = false, memo; - return function() { - if (ran) return memo; - ran = true; - return memo = func.apply(this, arguments); - }; - }; - - // Returns the first function passed as an argument to the second, - // allowing you to adjust arguments, run code before and after, and - // conditionally execute the original function. - _.wrap = function(func, wrapper) { - return function() { - var args = [func].concat(slice.call(arguments, 0)); - return wrapper.apply(this, args); - }; - }; - - // Returns a function that is the composition of a list of functions, each - // consuming the return value of the function that follows. - _.compose = function() { - var funcs = arguments; - return function() { - var args = arguments; - for (var i = funcs.length - 1; i >= 0; i--) { - args = [funcs[i].apply(this, args)]; - } - return args[0]; - }; - }; - - // Returns a function that will only be executed after being called N times. - _.after = function(times, func) { - if (times <= 0) return func(); - return function() { - if (--times < 1) { return func.apply(this, arguments); } - }; - }; - - // Object Functions - // ---------------- - - // Retrieve the names of an object's properties. - // Delegates to **ECMAScript 5**'s native `Object.keys` - _.keys = nativeKeys || function(obj) { - if (obj !== Object(obj)) throw new TypeError('Invalid object'); - var keys = []; - for (var key in obj) if (_.has(obj, key)) keys[keys.length] = key; - return keys; - }; - - // Retrieve the values of an object's properties. - _.values = function(obj) { - return _.map(obj, _.identity); - }; - - // Return a sorted list of the function names available on the object. - // Aliased as `methods` - _.functions = _.methods = function(obj) { - var names = []; - for (var key in obj) { - if (_.isFunction(obj[key])) names.push(key); - } - return names.sort(); - }; - - // Extend a given object with all the properties in passed-in object(s). - _.extend = function(obj) { - each(slice.call(arguments, 1), function(source) { - for (var prop in source) { - obj[prop] = source[prop]; - } - }); - return obj; - }; - - // Fill in a given object with default properties. - _.defaults = function(obj) { - each(slice.call(arguments, 1), function(source) { - for (var prop in source) { - if (obj[prop] == null) obj[prop] = source[prop]; - } - }); - return obj; - }; - - // Create a (shallow-cloned) duplicate of an object. - _.clone = function(obj) { - if (!_.isObject(obj)) return obj; - return _.isArray(obj) ? obj.slice() : _.extend({}, obj); - }; - - // Invokes interceptor with the obj, and then returns obj. - // The primary purpose of this method is to "tap into" a method chain, in - // order to perform operations on intermediate results within the chain. - _.tap = function(obj, interceptor) { - interceptor(obj); - return obj; - }; - - // Internal recursive comparison function. - function eq(a, b, stack) { - // Identical objects are equal. `0 === -0`, but they aren't identical. - // See the Harmony `egal` proposal: http://wiki.ecmascript.org/doku.php?id=harmony:egal. - if (a === b) return a !== 0 || 1 / a == 1 / b; - // A strict comparison is necessary because `null == undefined`. - if (a == null || b == null) return a === b; - // Unwrap any wrapped objects. - if (a._chain) a = a._wrapped; - if (b._chain) b = b._wrapped; - // Invoke a custom `isEqual` method if one is provided. - if (a.isEqual && _.isFunction(a.isEqual)) return a.isEqual(b); - if (b.isEqual && _.isFunction(b.isEqual)) return b.isEqual(a); - // Compare `[[Class]]` names. - var className = toString.call(a); - if (className != toString.call(b)) return false; - switch (className) { - // Strings, numbers, dates, and booleans are compared by value. - case '[object String]': - // Primitives and their corresponding object wrappers are equivalent; thus, `"5"` is - // equivalent to `new String("5")`. - return a == String(b); - case '[object Number]': - // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for - // other numeric values. - return a != +a ? b != +b : (a == 0 ? 1 / a == 1 / b : a == +b); - case '[object Date]': - case '[object Boolean]': - // Coerce dates and booleans to numeric primitive values. Dates are compared by their - // millisecond representations. Note that invalid dates with millisecond representations - // of `NaN` are not equivalent. - return +a == +b; - // RegExps are compared by their source patterns and flags. - case '[object RegExp]': - return a.source == b.source && - a.global == b.global && - a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase; - } - if (typeof a != 'object' || typeof b != 'object') return false; - // Assume equality for cyclic structures. The algorithm for detecting cyclic - // structures is adapted from ES 5.1 section 15.12.3, abstract operation `JO`. - var length = stack.length; - while (length--) { - // Linear search. Performance is inversely proportional to the number of - // unique nested structures. - if (stack[length] == a) return true; - } - // Add the first object to the stack of traversed objects. - stack.push(a); - var size = 0, result = true; - // Recursively compare objects and arrays. - if (className == '[object Array]') { - // Compare array lengths to determine if a deep comparison is necessary. - size = a.length; - result = size == b.length; - if (result) { - // Deep compare the contents, ignoring non-numeric properties. - while (size--) { - // Ensure commutative equality for sparse arrays. - if (!(result = size in a == size in b && eq(a[size], b[size], stack))) break; - } - } - } else { - // Objects with different constructors are not equivalent. - if ('constructor' in a != 'constructor' in b || a.constructor != b.constructor) return false; - // Deep compare objects. - for (var key in a) { - if (_.has(a, key)) { - // Count the expected number of properties. - size++; - // Deep compare each member. - if (!(result = _.has(b, key) && eq(a[key], b[key], stack))) break; - } - } - // Ensure that both objects contain the same number of properties. - if (result) { - for (key in b) { - if (_.has(b, key) && !(size--)) break; - } - result = !size; - } - } - // Remove the first object from the stack of traversed objects. - stack.pop(); - return result; - } - - // Perform a deep comparison to check if two objects are equal. - _.isEqual = function(a, b) { - return eq(a, b, []); - }; - - // Is a given array, string, or object empty? - // An "empty" object has no enumerable own-properties. - _.isEmpty = function(obj) { - if (_.isArray(obj) || _.isString(obj)) return obj.length === 0; - for (var key in obj) if (_.has(obj, key)) return false; - return true; - }; - - // Is a given value a DOM element? - _.isElement = function(obj) { - return !!(obj && obj.nodeType == 1); - }; - - // Is a given value an array? - // Delegates to ECMA5's native Array.isArray - _.isArray = nativeIsArray || function(obj) { - return toString.call(obj) == '[object Array]'; - }; - - // Is a given variable an object? - _.isObject = function(obj) { - return obj === Object(obj); - }; - - // Is a given variable an arguments object? - _.isArguments = function(obj) { - return toString.call(obj) == '[object Arguments]'; - }; - if (!_.isArguments(arguments)) { - _.isArguments = function(obj) { - return !!(obj && _.has(obj, 'callee')); - }; - } - - // Is a given value a function? - _.isFunction = function(obj) { - return toString.call(obj) == '[object Function]'; - }; - - // Is a given value a string? - _.isString = function(obj) { - return toString.call(obj) == '[object String]'; - }; - - // Is a given value a number? - _.isNumber = function(obj) { - return toString.call(obj) == '[object Number]'; - }; - - // Is the given value `NaN`? - _.isNaN = function(obj) { - // `NaN` is the only value for which `===` is not reflexive. - return obj !== obj; - }; - - // Is a given value a boolean? - _.isBoolean = function(obj) { - return obj === true || obj === false || toString.call(obj) == '[object Boolean]'; - }; - - // Is a given value a date? - _.isDate = function(obj) { - return toString.call(obj) == '[object Date]'; - }; - - // Is the given value a regular expression? - _.isRegExp = function(obj) { - return toString.call(obj) == '[object RegExp]'; - }; - - // Is a given value equal to null? - _.isNull = function(obj) { - return obj === null; - }; - - // Is a given variable undefined? - _.isUndefined = function(obj) { - return obj === void 0; - }; - - // Has own property? - _.has = function(obj, key) { - return hasOwnProperty.call(obj, key); - }; - - // Utility Functions - // ----------------- - - // Run Underscore.js in *noConflict* mode, returning the `_` variable to its - // previous owner. Returns a reference to the Underscore object. - _.noConflict = function() { - root._ = previousUnderscore; - return this; - }; - - // Keep the identity function around for default iterators. - _.identity = function(value) { - return value; - }; - - // Run a function **n** times. - _.times = function (n, iterator, context) { - for (var i = 0; i < n; i++) iterator.call(context, i); - }; - - // Escape a string for HTML interpolation. - _.escape = function(string) { - return (''+string).replace(/&/g, '&').replace(//g, '>').replace(/"/g, '"').replace(/'/g, ''').replace(/\//g,'/'); - }; - - // Add your own custom functions to the Underscore object, ensuring that - // they're correctly added to the OOP wrapper as well. - _.mixin = function(obj) { - each(_.functions(obj), function(name){ - addToWrapper(name, _[name] = obj[name]); - }); - }; - - // Generate a unique integer id (unique within the entire client session). - // Useful for temporary DOM ids. - var idCounter = 0; - _.uniqueId = function(prefix) { - var id = idCounter++; - return prefix ? prefix + id : id; - }; - - // By default, Underscore uses ERB-style template delimiters, change the - // following template settings to use alternative delimiters. - _.templateSettings = { - evaluate : /<%([\s\S]+?)%>/g, - interpolate : /<%=([\s\S]+?)%>/g, - escape : /<%-([\s\S]+?)%>/g - }; - - // When customizing `templateSettings`, if you don't want to define an - // interpolation, evaluation or escaping regex, we need one that is - // guaranteed not to match. - var noMatch = /.^/; - - // Within an interpolation, evaluation, or escaping, remove HTML escaping - // that had been previously added. - var unescape = function(code) { - return code.replace(/\\\\/g, '\\').replace(/\\'/g, "'"); - }; - - // JavaScript micro-templating, similar to John Resig's implementation. - // Underscore templating handles arbitrary delimiters, preserves whitespace, - // and correctly escapes quotes within interpolated code. - _.template = function(str, data) { - var c = _.templateSettings; - var tmpl = 'var __p=[],print=function(){__p.push.apply(__p,arguments);};' + - 'with(obj||{}){__p.push(\'' + - str.replace(/\\/g, '\\\\') - .replace(/'/g, "\\'") - .replace(c.escape || noMatch, function(match, code) { - return "',_.escape(" + unescape(code) + "),'"; - }) - .replace(c.interpolate || noMatch, function(match, code) { - return "'," + unescape(code) + ",'"; - }) - .replace(c.evaluate || noMatch, function(match, code) { - return "');" + unescape(code).replace(/[\r\n\t]/g, ' ') + ";__p.push('"; - }) - .replace(/\r/g, '\\r') - .replace(/\n/g, '\\n') - .replace(/\t/g, '\\t') - + "');}return __p.join('');"; - var func = new Function('obj', '_', tmpl); - if (data) return func(data, _); - return function(data) { - return func.call(this, data, _); - }; - }; - - // Add a "chain" function, which will delegate to the wrapper. - _.chain = function(obj) { - return _(obj).chain(); - }; - - // The OOP Wrapper - // --------------- - - // If Underscore is called as a function, it returns a wrapped object that - // can be used OO-style. This wrapper holds altered versions of all the - // underscore functions. Wrapped objects may be chained. - var wrapper = function(obj) { this._wrapped = obj; }; - - // Expose `wrapper.prototype` as `_.prototype` - _.prototype = wrapper.prototype; - - // Helper function to continue chaining intermediate results. - var result = function(obj, chain) { - return chain ? _(obj).chain() : obj; - }; - - // A method to easily add functions to the OOP wrapper. - var addToWrapper = function(name, func) { - wrapper.prototype[name] = function() { - var args = slice.call(arguments); - unshift.call(args, this._wrapped); - return result(func.apply(_, args), this._chain); - }; - }; - - // Add all of the Underscore functions to the wrapper object. - _.mixin(_); - - // Add all mutator Array functions to the wrapper. - each(['pop', 'push', 'reverse', 'shift', 'sort', 'splice', 'unshift'], function(name) { - var method = ArrayProto[name]; - wrapper.prototype[name] = function() { - var wrapped = this._wrapped; - method.apply(wrapped, arguments); - var length = wrapped.length; - if ((name == 'shift' || name == 'splice') && length === 0) delete wrapped[0]; - return result(wrapped, this._chain); - }; - }); - - // Add all accessor Array functions to the wrapper. - each(['concat', 'join', 'slice'], function(name) { - var method = ArrayProto[name]; - wrapper.prototype[name] = function() { - return result(method.apply(this._wrapped, arguments), this._chain); - }; - }); - - // Start chaining a wrapped Underscore object. - wrapper.prototype.chain = function() { - this._chain = true; - return this; - }; - - // Extracts the result from a wrapped and chained object. - wrapper.prototype.value = function() { - return this._wrapped; - }; - -}).call(this); diff --git a/docsrc/_build/html/_static/underscore.js b/docsrc/_build/html/_static/underscore.js index 5b55f32..cf177d4 100644 --- a/docsrc/_build/html/_static/underscore.js +++ b/docsrc/_build/html/_static/underscore.js @@ -1,31 +1,6 @@ -// Underscore.js 1.3.1 -// (c) 2009-2012 Jeremy Ashkenas, DocumentCloud Inc. -// Underscore is freely distributable under the MIT license. -// Portions of Underscore are inspired or borrowed from Prototype, -// Oliver Steele's Functional, and John Resig's Micro-Templating. -// For all details and documentation: -// http://documentcloud.github.com/underscore -(function(){function q(a,c,d){if(a===c)return a!==0||1/a==1/c;if(a==null||c==null)return a===c;if(a._chain)a=a._wrapped;if(c._chain)c=c._wrapped;if(a.isEqual&&b.isFunction(a.isEqual))return a.isEqual(c);if(c.isEqual&&b.isFunction(c.isEqual))return c.isEqual(a);var e=l.call(a);if(e!=l.call(c))return false;switch(e){case "[object String]":return a==String(c);case "[object Number]":return a!=+a?c!=+c:a==0?1/a==1/c:a==+c;case "[object Date]":case "[object Boolean]":return+a==+c;case "[object RegExp]":return a.source== -c.source&&a.global==c.global&&a.multiline==c.multiline&&a.ignoreCase==c.ignoreCase}if(typeof a!="object"||typeof c!="object")return false;for(var f=d.length;f--;)if(d[f]==a)return true;d.push(a);var f=0,g=true;if(e=="[object Array]"){if(f=a.length,g=f==c.length)for(;f--;)if(!(g=f in a==f in c&&q(a[f],c[f],d)))break}else{if("constructor"in a!="constructor"in c||a.constructor!=c.constructor)return false;for(var h in a)if(b.has(a,h)&&(f++,!(g=b.has(c,h)&&q(a[h],c[h],d))))break;if(g){for(h in c)if(b.has(c, -h)&&!f--)break;g=!f}}d.pop();return g}var r=this,G=r._,n={},k=Array.prototype,o=Object.prototype,i=k.slice,H=k.unshift,l=o.toString,I=o.hasOwnProperty,w=k.forEach,x=k.map,y=k.reduce,z=k.reduceRight,A=k.filter,B=k.every,C=k.some,p=k.indexOf,D=k.lastIndexOf,o=Array.isArray,J=Object.keys,s=Function.prototype.bind,b=function(a){return new m(a)};if(typeof exports!=="undefined"){if(typeof module!=="undefined"&&module.exports)exports=module.exports=b;exports._=b}else r._=b;b.VERSION="1.3.1";var j=b.each= -b.forEach=function(a,c,d){if(a!=null)if(w&&a.forEach===w)a.forEach(c,d);else if(a.length===+a.length)for(var e=0,f=a.length;e2;a== -null&&(a=[]);if(y&&a.reduce===y)return e&&(c=b.bind(c,e)),f?a.reduce(c,d):a.reduce(c);j(a,function(a,b,i){f?d=c.call(e,d,a,b,i):(d=a,f=true)});if(!f)throw new TypeError("Reduce of empty array with no initial value");return d};b.reduceRight=b.foldr=function(a,c,d,e){var f=arguments.length>2;a==null&&(a=[]);if(z&&a.reduceRight===z)return e&&(c=b.bind(c,e)),f?a.reduceRight(c,d):a.reduceRight(c);var g=b.toArray(a).reverse();e&&!f&&(c=b.bind(c,e));return f?b.reduce(g,c,d,e):b.reduce(g,c)};b.find=b.detect= -function(a,c,b){var e;E(a,function(a,g,h){if(c.call(b,a,g,h))return e=a,true});return e};b.filter=b.select=function(a,c,b){var e=[];if(a==null)return e;if(A&&a.filter===A)return a.filter(c,b);j(a,function(a,g,h){c.call(b,a,g,h)&&(e[e.length]=a)});return e};b.reject=function(a,c,b){var e=[];if(a==null)return e;j(a,function(a,g,h){c.call(b,a,g,h)||(e[e.length]=a)});return e};b.every=b.all=function(a,c,b){var e=true;if(a==null)return e;if(B&&a.every===B)return a.every(c,b);j(a,function(a,g,h){if(!(e= -e&&c.call(b,a,g,h)))return n});return e};var E=b.some=b.any=function(a,c,d){c||(c=b.identity);var e=false;if(a==null)return e;if(C&&a.some===C)return a.some(c,d);j(a,function(a,b,h){if(e||(e=c.call(d,a,b,h)))return n});return!!e};b.include=b.contains=function(a,c){var b=false;if(a==null)return b;return p&&a.indexOf===p?a.indexOf(c)!=-1:b=E(a,function(a){return a===c})};b.invoke=function(a,c){var d=i.call(arguments,2);return b.map(a,function(a){return(b.isFunction(c)?c||a:a[c]).apply(a,d)})};b.pluck= -function(a,c){return b.map(a,function(a){return a[c]})};b.max=function(a,c,d){if(!c&&b.isArray(a))return Math.max.apply(Math,a);if(!c&&b.isEmpty(a))return-Infinity;var e={computed:-Infinity};j(a,function(a,b,h){b=c?c.call(d,a,b,h):a;b>=e.computed&&(e={value:a,computed:b})});return e.value};b.min=function(a,c,d){if(!c&&b.isArray(a))return Math.min.apply(Math,a);if(!c&&b.isEmpty(a))return Infinity;var e={computed:Infinity};j(a,function(a,b,h){b=c?c.call(d,a,b,h):a;bd?1:0}),"value")};b.groupBy=function(a,c){var d={},e=b.isFunction(c)?c:function(a){return a[c]};j(a,function(a,b){var c=e(a,b);(d[c]||(d[c]=[])).push(a)});return d};b.sortedIndex=function(a, -c,d){d||(d=b.identity);for(var e=0,f=a.length;e>1;d(a[g])=0})})};b.difference=function(a){var c=b.flatten(i.call(arguments,1));return b.filter(a,function(a){return!b.include(c,a)})};b.zip=function(){for(var a=i.call(arguments),c=b.max(b.pluck(a,"length")),d=Array(c),e=0;e=0;d--)b=[a[d].apply(this,b)];return b[0]}}; -b.after=function(a,b){return a<=0?b():function(){if(--a<1)return b.apply(this,arguments)}};b.keys=J||function(a){if(a!==Object(a))throw new TypeError("Invalid object");var c=[],d;for(d in a)b.has(a,d)&&(c[c.length]=d);return c};b.values=function(a){return b.map(a,b.identity)};b.functions=b.methods=function(a){var c=[],d;for(d in a)b.isFunction(a[d])&&c.push(d);return c.sort()};b.extend=function(a){j(i.call(arguments,1),function(b){for(var d in b)a[d]=b[d]});return a};b.defaults=function(a){j(i.call(arguments, -1),function(b){for(var d in b)a[d]==null&&(a[d]=b[d])});return a};b.clone=function(a){return!b.isObject(a)?a:b.isArray(a)?a.slice():b.extend({},a)};b.tap=function(a,b){b(a);return a};b.isEqual=function(a,b){return q(a,b,[])};b.isEmpty=function(a){if(b.isArray(a)||b.isString(a))return a.length===0;for(var c in a)if(b.has(a,c))return false;return true};b.isElement=function(a){return!!(a&&a.nodeType==1)};b.isArray=o||function(a){return l.call(a)=="[object Array]"};b.isObject=function(a){return a===Object(a)}; -b.isArguments=function(a){return l.call(a)=="[object Arguments]"};if(!b.isArguments(arguments))b.isArguments=function(a){return!(!a||!b.has(a,"callee"))};b.isFunction=function(a){return l.call(a)=="[object Function]"};b.isString=function(a){return l.call(a)=="[object String]"};b.isNumber=function(a){return l.call(a)=="[object Number]"};b.isNaN=function(a){return a!==a};b.isBoolean=function(a){return a===true||a===false||l.call(a)=="[object Boolean]"};b.isDate=function(a){return l.call(a)=="[object Date]"}; -b.isRegExp=function(a){return l.call(a)=="[object RegExp]"};b.isNull=function(a){return a===null};b.isUndefined=function(a){return a===void 0};b.has=function(a,b){return I.call(a,b)};b.noConflict=function(){r._=G;return this};b.identity=function(a){return a};b.times=function(a,b,d){for(var e=0;e/g,">").replace(/"/g,""").replace(/'/g,"'").replace(/\//g,"/")};b.mixin=function(a){j(b.functions(a), -function(c){K(c,b[c]=a[c])})};var L=0;b.uniqueId=function(a){var b=L++;return a?a+b:b};b.templateSettings={evaluate:/<%([\s\S]+?)%>/g,interpolate:/<%=([\s\S]+?)%>/g,escape:/<%-([\s\S]+?)%>/g};var t=/.^/,u=function(a){return a.replace(/\\\\/g,"\\").replace(/\\'/g,"'")};b.template=function(a,c){var d=b.templateSettings,d="var __p=[],print=function(){__p.push.apply(__p,arguments);};with(obj||{}){__p.push('"+a.replace(/\\/g,"\\\\").replace(/'/g,"\\'").replace(d.escape||t,function(a,b){return"',_.escape("+ -u(b)+"),'"}).replace(d.interpolate||t,function(a,b){return"',"+u(b)+",'"}).replace(d.evaluate||t,function(a,b){return"');"+u(b).replace(/[\r\n\t]/g," ")+";__p.push('"}).replace(/\r/g,"\\r").replace(/\n/g,"\\n").replace(/\t/g,"\\t")+"');}return __p.join('');",e=new Function("obj","_",d);return c?e(c,b):function(a){return e.call(this,a,b)}};b.chain=function(a){return b(a).chain()};var m=function(a){this._wrapped=a};b.prototype=m.prototype;var v=function(a,c){return c?b(a).chain():a},K=function(a,c){m.prototype[a]= -function(){var a=i.call(arguments);H.call(a,this._wrapped);return v(c.apply(b,a),this._chain)}};b.mixin(b);j("pop,push,reverse,shift,sort,splice,unshift".split(","),function(a){var b=k[a];m.prototype[a]=function(){var d=this._wrapped;b.apply(d,arguments);var e=d.length;(a=="shift"||a=="splice")&&e===0&&delete d[0];return v(d,this._chain)}});j(["concat","join","slice"],function(a){var b=k[a];m.prototype[a]=function(){return v(b.apply(this._wrapped,arguments),this._chain)}});m.prototype.chain=function(){this._chain= -true;return this};m.prototype.value=function(){return this._wrapped}}).call(this); +!function(n,r){"object"==typeof exports&&"undefined"!=typeof module?module.exports=r():"function"==typeof define&&define.amd?define("underscore",r):(n="undefined"!=typeof globalThis?globalThis:n||self,function(){var t=n._,e=n._=r();e.noConflict=function(){return n._=t,e}}())}(this,(function(){ +// Underscore.js 1.13.1 +// https://underscorejs.org +// (c) 2009-2021 Jeremy Ashkenas, Julian Gonggrijp, and DocumentCloud and Investigative Reporters & Editors +// Underscore may be freely distributed under the MIT license. +var n="1.13.1",r="object"==typeof self&&self.self===self&&self||"object"==typeof global&&global.global===global&&global||Function("return this")()||{},t=Array.prototype,e=Object.prototype,u="undefined"!=typeof Symbol?Symbol.prototype:null,o=t.push,i=t.slice,a=e.toString,f=e.hasOwnProperty,c="undefined"!=typeof ArrayBuffer,l="undefined"!=typeof DataView,s=Array.isArray,p=Object.keys,v=Object.create,h=c&&ArrayBuffer.isView,y=isNaN,d=isFinite,g=!{toString:null}.propertyIsEnumerable("toString"),b=["valueOf","isPrototypeOf","toString","propertyIsEnumerable","hasOwnProperty","toLocaleString"],m=Math.pow(2,53)-1;function j(n,r){return r=null==r?n.length-1:+r,function(){for(var t=Math.max(arguments.length-r,0),e=Array(t),u=0;u=0&&t<=m}}function J(n){return function(r){return null==r?void 0:r[n]}}var G=J("byteLength"),H=K(G),Q=/\[object ((I|Ui)nt(8|16|32)|Float(32|64)|Uint8Clamped|Big(I|Ui)nt64)Array\]/;var X=c?function(n){return h?h(n)&&!q(n):H(n)&&Q.test(a.call(n))}:C(!1),Y=J("length");function Z(n,r){r=function(n){for(var r={},t=n.length,e=0;e":">",'"':""","'":"'","`":"`"},Cn=Ln($n),Kn=Ln(_n($n)),Jn=tn.templateSettings={evaluate:/<%([\s\S]+?)%>/g,interpolate:/<%=([\s\S]+?)%>/g,escape:/<%-([\s\S]+?)%>/g},Gn=/(.)^/,Hn={"'":"'","\\":"\\","\r":"r","\n":"n","\u2028":"u2028","\u2029":"u2029"},Qn=/\\|'|\r|\n|\u2028|\u2029/g;function Xn(n){return"\\"+Hn[n]}var Yn=/^\s*(\w|\$)+\s*$/;var Zn=0;function nr(n,r,t,e,u){if(!(e instanceof r))return n.apply(t,u);var o=Mn(n.prototype),i=n.apply(o,u);return _(i)?i:o}var rr=j((function(n,r){var t=rr.placeholder,e=function(){for(var u=0,o=r.length,i=Array(o),a=0;a1)ur(a,r-1,t,e),u=e.length;else for(var f=0,c=a.length;f0&&(t=r.apply(this,arguments)),n<=1&&(r=null),t}}var lr=rr(cr,2);function sr(n,r,t){r=qn(r,t);for(var e,u=nn(n),o=0,i=u.length;o0?0:u-1;o>=0&&o0?a=o>=0?o:Math.max(o+f,a):f=o>=0?Math.min(o+1,f):o+f+1;else if(t&&o&&f)return e[o=t(e,u)]===u?o:-1;if(u!=u)return(o=r(i.call(e,a,f),$))>=0?o+a:-1;for(o=n>0?a:f-1;o>=0&&o0?0:i-1;for(u||(e=r[o?o[a]:a],a+=n);a>=0&&a=3;return r(n,Fn(t,u,4),e,o)}}var Ar=wr(1),xr=wr(-1);function Sr(n,r,t){var e=[];return r=qn(r,t),jr(n,(function(n,t,u){r(n,t,u)&&e.push(n)})),e}function Or(n,r,t){r=qn(r,t);for(var e=!er(n)&&nn(n),u=(e||n).length,o=0;o=0}var Br=j((function(n,r,t){var e,u;return D(r)?u=r:(r=Nn(r),e=r.slice(0,-1),r=r[r.length-1]),_r(n,(function(n){var o=u;if(!o){if(e&&e.length&&(n=In(n,e)),null==n)return;o=n[r]}return null==o?o:o.apply(n,t)}))}));function Nr(n,r){return _r(n,Rn(r))}function Ir(n,r,t){var e,u,o=-1/0,i=-1/0;if(null==r||"number"==typeof r&&"object"!=typeof n[0]&&null!=n)for(var a=0,f=(n=er(n)?n:jn(n)).length;ao&&(o=e);else r=qn(r,t),jr(n,(function(n,t,e){((u=r(n,t,e))>i||u===-1/0&&o===-1/0)&&(o=n,i=u)}));return o}function Tr(n,r,t){if(null==r||t)return er(n)||(n=jn(n)),n[Wn(n.length-1)];var e=er(n)?En(n):jn(n),u=Y(e);r=Math.max(Math.min(r,u),0);for(var o=u-1,i=0;i1&&(e=Fn(e,r[1])),r=an(n)):(e=qr,r=ur(r,!1,!1),n=Object(n));for(var u=0,o=r.length;u1&&(t=r[1])):(r=_r(ur(r,!1,!1),String),e=function(n,t){return!Er(r,t)}),Ur(n,e,t)}));function zr(n,r,t){return i.call(n,0,Math.max(0,n.length-(null==r||t?1:r)))}function Lr(n,r,t){return null==n||n.length<1?null==r||t?void 0:[]:null==r||t?n[0]:zr(n,n.length-r)}function $r(n,r,t){return i.call(n,null==r||t?1:r)}var Cr=j((function(n,r){return r=ur(r,!0,!0),Sr(n,(function(n){return!Er(r,n)}))})),Kr=j((function(n,r){return Cr(n,r)}));function Jr(n,r,t,e){A(r)||(e=t,t=r,r=!1),null!=t&&(t=qn(t,e));for(var u=[],o=[],i=0,a=Y(n);ir?(e&&(clearTimeout(e),e=null),a=c,i=n.apply(u,o),e||(u=o=null)):e||!1===t.trailing||(e=setTimeout(f,l)),i};return c.cancel=function(){clearTimeout(e),a=0,e=u=o=null},c},debounce:function(n,r,t){var e,u,o,i,a,f=function(){var c=zn()-u;r>c?e=setTimeout(f,r-c):(e=null,t||(i=n.apply(a,o)),e||(o=a=null))},c=j((function(c){return a=this,o=c,u=zn(),e||(e=setTimeout(f,r),t&&(i=n.apply(a,o))),i}));return c.cancel=function(){clearTimeout(e),e=o=a=null},c},wrap:function(n,r){return rr(r,n)},negate:fr,compose:function(){var n=arguments,r=n.length-1;return function(){for(var t=r,e=n[r].apply(this,arguments);t--;)e=n[t].call(this,e);return e}},after:function(n,r){return function(){if(--n<1)return r.apply(this,arguments)}},before:cr,once:lr,findKey:sr,findIndex:vr,findLastIndex:hr,sortedIndex:yr,indexOf:gr,lastIndexOf:br,find:mr,detect:mr,findWhere:function(n,r){return mr(n,Dn(r))},each:jr,forEach:jr,map:_r,collect:_r,reduce:Ar,foldl:Ar,inject:Ar,reduceRight:xr,foldr:xr,filter:Sr,select:Sr,reject:function(n,r,t){return Sr(n,fr(qn(r)),t)},every:Or,all:Or,some:Mr,any:Mr,contains:Er,includes:Er,include:Er,invoke:Br,pluck:Nr,where:function(n,r){return Sr(n,Dn(r))},max:Ir,min:function(n,r,t){var e,u,o=1/0,i=1/0;if(null==r||"number"==typeof r&&"object"!=typeof n[0]&&null!=n)for(var a=0,f=(n=er(n)?n:jn(n)).length;ae||void 0===t)return 1;if(t + + + - - - - - reactors — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + reactors — python-reactors 1.0.0 documentation + + + + + + + + + + - - - + + -
    -
    -
    -
    - -
    -

    reactors

    + +
    + + +
    + + - - - - +
    +
    + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.agaveutils.html b/docsrc/_build/html/api-ref/reactors.agaveutils.html index c5687a7..16cb489 100644 --- a/docsrc/_build/html/api-ref/reactors.agaveutils.html +++ b/docsrc/_build/html/api-ref/reactors.agaveutils.html @@ -1,64 +1,106 @@ - - - - - - - reactors.agaveutils package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + + reactors.agaveutils package — python-reactors 1.0.0 documentation + + + + + + + + + + - + - - - -
    -
    -
    -
    - -
    -

    reactors.agaveutils package

    -
    -

    Submodules

    + + + +
    + + +
    + +
    +
    +
    + +
    -
    -

    reactors.agaveutils.entity module

    +
    +
    + +
    +

    reactors.agaveutils package

    +
    +

    Submodules

    +
    +
    +

    reactors.agaveutils.entity module

    Functions for working with Agave namespace entities

    -
    -reactors.agaveutils.entity.is_appid(textString, useApi=False, agaveClient=None)
    +
    +reactors.agaveutils.entity.is_appid(textString, useApi=False, agaveClient=None)

    Validate whether textString is an Agave appId

    Positional parameters: textString: str - the candidate text string

    @@ -67,20 +109,20 @@

    Submodules -

    reactors.agaveutils.files module

    +

    +
    +

    reactors.agaveutils.files module

    Helper functions for common filesystem operations with Agave

    -
    -reactors.agaveutils.files.agave_download_file(agaveClient, agaveAbsolutePath, systemId, localFilename='downloaded', sync=True, timeOut=300)
    +
    +reactors.agaveutils.files.agave_download_file(agaveClient, agaveAbsolutePath, systemId, localFilename='downloaded', sync=True, timeOut=300)

    Download an Agave-hosted file to cwd()

    Currently, always a synchronous task.

    -
    -reactors.agaveutils.files.agave_mkdir(agaveClient, dirName, systemId, basePath='/', sync=False, timeOut=300)
    +
    +reactors.agaveutils.files.agave_mkdir(agaveClient, dirName, systemId, basePath='/', sync=False, timeOut=300)

    Creates a directory dirName on a storage system at basePath

    Like mkdir -p this is imdepotent. It will create the child path tree so long as paths are specified correctly, but will do @@ -88,8 +130,8 @@

    Submodules -
    -reactors.agaveutils.files.agave_upload_file(agaveClient, agaveDestPath, systemId, uploadFile, sync=True, timeOut=300)
    +
    +reactors.agaveutils.files.agave_upload_file(agaveClient, agaveDestPath, systemId, uploadFile, sync=True, timeOut=300)

    Upload a file to Agave-managed remote storage.

    If sync is True, the function will wait for the upload to complete before returning. Raises exceptions on importData @@ -97,8 +139,8 @@

    Submodules -
    -reactors.agaveutils.files.get(agaveClient, agaveAbsolutePath, systemId, localFilename, retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.get(agaveClient, agaveAbsolutePath, systemId, localFilename, retries=5, delay=1, multiplier=2)

    files-get with retry and exponential backoff

    Parameters
    @@ -119,8 +161,8 @@

    Submodules -
    -reactors.agaveutils.files.mkdir(agaveClient, dirName, systemId, basePath='/', retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.mkdir(agaveClient, dirName, systemId, basePath='/', retries=5, delay=1, multiplier=2)

    files-mkdir with retry and exponential backoff

    Parameters
    @@ -141,231 +183,187 @@

    Submodules -
    -reactors.agaveutils.files.process_agave_httperror(http_error_object)
    +
    +reactors.agaveutils.files.process_agave_httperror(http_error_object)

    -
    -reactors.agaveutils.files.put(agaveClient, agaveDestPath, systemId, uploadFile, retries=5, delay=1, multiplier=2)
    +
    +reactors.agaveutils.files.put(agaveClient, agaveDestPath, systemId, uploadFile, retries=5, delay=1, multiplier=2)
    -
    -reactors.agaveutils.files.random() → x in the interval [0, 1).
    +
    +reactors.agaveutils.files.random() x in the interval [0, 1).
    -
    -reactors.agaveutils.files.wait_for_file_status(agaveClient, agaveWatchPath, systemId, maxTime=300)
    +
    +reactors.agaveutils.files.wait_for_file_status(agaveClient, agaveWatchPath, systemId, maxTime=300)

    Synchronously wait for a file’s status to reach a terminal state.

    Returns an exception and the final state if it timeout is exceeded. Uses exponential backoff to avoid overloading the files server with poll requests. Returns True on success.

    -

    -
    -

    reactors.agaveutils.reactors module

    +
    +
    +

    reactors.agaveutils.reactors module

    Functions for working with TACC Reactors

    -
    -reactors.agaveutils.reactors.message_reactor(agaveClient, actorId, message, environment={}, ignoreErrors=True, sync=False, senderTags=True, timeOut=300)
    +
    +reactors.agaveutils.reactors.message_reactor(agaveClient, actorId, message, environment={}, ignoreErrors=True, sync=False, senderTags=True, timeOut=300)

    Send a message to an Abaco actor by its ID

    Returns execution ID. If ignoreErrors is True, this is fire-and-forget. Otherwise, failures raise an Exception to handled by the caller.

    -
    -
    -

    reactors.agaveutils.recursive module

    + +
    +

    reactors.agaveutils.recursive module

    Recursively apply permission grants using AgavePy

    -
    -class reactors.agaveutils.recursive.PemAgent(agaveClient, loglevel='INFO')
    +
    +class reactors.agaveutils.recursive.PemAgent(agaveClient, loglevel='INFO')

    Bases: object

    Specialized Agave class for doing recursive pem management

    -
    -enumerate2(sequence)
    +
    +enumerate2(sequence)
    -
    -grant(system, abspath, username='world', pem='READ', recursive=False, permissive=True)
    +
    +grant(system, abspath, username='world', pem='READ', recursive=False, permissive=True)

    Recursively crawl abspath and grant pem

    -
    -listdir(system, fpath)
    +
    +listdir(system, fpath)
    -
    -updatepem(system, fpath, username, pem, rec=False, permissive=True)
    +
    +updatepem(system, fpath, username, pem, rec=False, permissive=True)

    Send an pems update request

    -
    -walk(root, dirs, files, system, username, pem='READ', rec=False)
    +
    +walk(root, dirs, files, system, username, pem='READ', rec=False)
    -
    -reactors.agaveutils.recursive.random() → x in the interval [0, 1).
    +
    +reactors.agaveutils.recursive.random() x in the interval [0, 1).
    -
    -
    -

    reactors.agaveutils.uri module

    + +
    +

    reactors.agaveutils.uri module

    Functions for working with Agave, HTTP, and TACC S3 URIs

    -
    -reactors.agaveutils.uri.agave_uri_from_http(httpURI=None)
    +
    +reactors.agaveutils.uri.agave_uri_from_http(httpURI=None)

    Convert an HTTP(s) URI to its agave:// format * Do not use yet

    -
    -reactors.agaveutils.uri.from_agave_uri(uri=None, Validate=False)
    +
    +reactors.agaveutils.uri.from_agave_uri(uri=None, Validate=False)

    Parse an Agave URI into a tuple (systemId, directoryPath, fileName)

    Validation that it points to a real resource is not implemented. The same caveats about validation apply here as in to_agave_uri()

    -
    -reactors.agaveutils.uri.from_tacc_s3_uri(uri=None, Validate=False)
    +
    +reactors.agaveutils.uri.from_tacc_s3_uri(uri=None, Validate=False)

    Parse a TACC S3 URI into a tuple (systemId, directoryPath, (fileName))

    Validation that it points to a real resource is not implemented. The same caveats about validation apply here as in to_agave_uri()

    -
    -reactors.agaveutils.uri.http_uri_from_agave(agaveURI=None, linkType='media', userName='public')
    +
    +reactors.agaveutils.uri.http_uri_from_agave(agaveURI=None, linkType='media', userName='public')

    Returns an http(s) media URL for data movement or download * Do not use yet.

    -
    -reactors.agaveutils.uri.to_agave_uri(systemId=None, dirPath=None, fileName=None, validate=False)
    +
    +reactors.agaveutils.uri.to_agave_uri(systemId=None, dirPath=None, fileName=None, validate=False)

    Construct an Agave URI for system ID, path, (filename)

    Validation that URI points to a real resource is not implemented. Should we choose to do this, it will be expensive since it will involve at least one API call.

    -
    -
    -

    reactors.agaveutils.utils module

    + +
    +

    reactors.agaveutils.utils module

    Helper functions for working with Agave and Reactors APIs

    `python from agaveutils import * `

    -
    -reactors.agaveutils.utils.get_api_server(ag)
    +
    +reactors.agaveutils.utils.get_api_server(ag)

    Get current API server URI

    -
    -reactors.agaveutils.utils.get_api_token(ag)
    +
    +reactors.agaveutils.utils.get_api_token(ag)

    Get API access_token

    -
    -reactors.agaveutils.utils.get_api_username(ag)
    +
    +reactors.agaveutils.utils.get_api_username(ag)

    Get current API username

    -
    -
    -

    Module contents

    -
    -
    + +
    +

    Module contents

    +
    + -
    +
    -
    -
    - - - - + +
    + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.aliases.agavedb.html b/docsrc/_build/html/api-ref/reactors.aliases.agavedb.html deleted file mode 100644 index 6144337..0000000 --- a/docsrc/_build/html/api-ref/reactors.aliases.agavedb.html +++ /dev/null @@ -1,470 +0,0 @@ - - - - - - - - reactors.aliases.agavedb package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases.agavedb package

    - -
    -

    Submodules

    -
    -
    -

    reactors.aliases.agavedb.keyval module

    -

    AgaveDB is multiuser-aware key/value store built using the Agave metadata web service API.

    -

    The library interface is modeled on pickledb, which is inspired by Redis. Eventually, it will support Agave-based permissions and sharing. If you need a more -document-oriented solution, you can utilize the underlying Agave metadata service.

    -

    Usage: -`python -from agavedb import AgaveKeyValStore -`

    -
    -
    -class reactors.aliases.agavedb.keyval.AgaveKeyValStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: object

    -

    An AgaveKeyValStore instance. Requires an active Agave client

    -
    -
    -classmethod create_key_name()
    -

    Create a unique, human-friendly key name

    -
    - -
    -
    -deldb()
    -

    Delete all user-owned keys

    -
    - -
    -
    -classmethod from_text_pem(pem)
    -
    - -
    -
    -get(key)
    -

    Get the value of a key

    -
    - -
    -
    -getacls(key, user=None)
    -

    Get the ACLs for a given key

    -

    Keywork parameters: -user - str - Return ACL only for this username

    -
    - -
    -
    -getall(sort_aliases=True)
    -

    Return a list of all keys user owns or has access to

    -
    - -
    -
    -rem(key)
    -

    Delete a key (assuming it is owned by the user)

    -
    - -
    -
    -remacl(key, user)
    -

    Remove an ACL on a key for a given user

    -

    Positional parameters: -key - str - Key to manage permissions on -user - str - Username whose ACL should be dropped

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -set(key, value)
    -

    Set the string or numeric value of a key

    -
    - -
    -
    -setacl(key, acl)
    -

    Set an ACL on a given key

    -

    Positional parameters: -key - str - Key to manage permissions on -acl - dict - Valid permissions object

    -

    {‘read’: bool, ‘write’: bool}

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -classmethod to_text_pem(acl)
    -
    - -
    -
    -classmethod validate_acl(acl, permissive=False)
    -

    Validate an ACL object as a dict

    -

    Failure raises Exception unless permissive is True -* Does not validate that username exists

    -
    - -
    - -
    -
    -

    reactors.aliases.agavedb.uniqueid module

    -

    Generate Abaco-style human-readable UUIDs

    -

    Uses the hashids library and strong random -number generator. These UUIDs are nearly as -unique as UUID4 but are much more readable.

    -
    -
    -reactors.aliases.agavedb.uniqueid.get_id()
    -

    Generate a hash id

    -
    - -
    -
    -reactors.aliases.agavedb.uniqueid.is_hashid(identifier)
    -

    Tries to validate a UUID

    -
    - -
    -
    -

    Module contents

    -
    -
    -class reactors.aliases.agavedb.Agave(**kwargs)
    -

    Bases: agavepy.interactive.clients.ClientCommands, agavepy.interactive.tokens.TokenCommands, agavepy.interactive.deprecated.DeprecatedCommands

    -
    -
    -PARAMS = [('username', False, 'username', None), ('password', False, 'password', None), ('token_username', False, 'token_username', None), ('jwt', False, 'jwt', None), ('jwt_header_name', False, 'header_name', None), ('api_server', False, 'api_server', 'https://api.tacc.utexas.edu'), ('tenant_id', False, 'tenant_id', None), ('expires_in', False, 'expires_in', None), ('expires_at', False, 'expires_at', None), ('created_at', False, 'created_at', None), ('client_name', False, 'client_name', None), ('api_key', False, 'api_key', None), ('api_secret', False, 'api_secret', None), ('token', False, '_token', None), ('refresh_token', False, '_refresh_token', None), ('use_nonce', False, 'use_nonce', False), ('resources', False, 'resources', None), ('verify', False, 'verify', True), ('token_callback', False, 'token_callback', None), ('proxies', False, 'proxies', {})]
    -
    - -
    -
    -classmethod agpy_path()
    -

    Return path to an .agpy file

    -
    - -
    -
    -can_refresh = True
    -
    - -
    -
    -clients_ari()
    -
    - -
    -
    -download_uri(uri, local_path)
    -

    Convenience method to download an agave URL or jobs output URL to an -absolute path on the local file system.

    -
    - -
    -
    -full_ari()
    -
    - -
    -
    -geturl(url)
    -

    Make get request to url using the client access token and retry if token has expired. -:param url: str -:return:

    -
    - -
    -
    -jwt_ari()
    -
    - -
    -
    -nonce_ari()
    -
    - -
    -
    -refresh_aris()
    -
    - -
    -
    -resource(auth_type, *args)
    -
    - -
    -
    -classmethod restore(api_key=None, client_name=None, tenant_id=None, token=None, api_server=None, cache_client=True)
    -

    Public API to load an Agave client from an external source

    -
    - -
    -
    -set_client(key, secret)
    -
    -
    Return type
    -

    None

    -
    -
    -
    - -
    -
    -classmethod tapis_cache_path()
    -

    Return the path to the credentials cache directory

    -
    - -
    -
    -classmethod tapis_current_path()
    -

    Return path to the current cached credential

    -
    - -
    -
    -classmethod tapis_sessions_path()
    -

    Return path to the current sessions cache

    -
    - -
    -
    -to_dict()
    -

    Return a dictionary representing this client.

    -
    - -
    - -
    -
    -class reactors.aliases.agavedb.AgaveKeyValStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: object

    -

    An AgaveKeyValStore instance. Requires an active Agave client

    -
    -
    -classmethod create_key_name()
    -

    Create a unique, human-friendly key name

    -
    - -
    -
    -deldb()
    -

    Delete all user-owned keys

    -
    - -
    -
    -classmethod from_text_pem(pem)
    -
    - -
    -
    -get(key)
    -

    Get the value of a key

    -
    - -
    -
    -getacls(key, user=None)
    -

    Get the ACLs for a given key

    -

    Keywork parameters: -user - str - Return ACL only for this username

    -
    - -
    -
    -getall(sort_aliases=True)
    -

    Return a list of all keys user owns or has access to

    -
    - -
    -
    -rem(key)
    -

    Delete a key (assuming it is owned by the user)

    -
    - -
    -
    -remacl(key, user)
    -

    Remove an ACL on a key for a given user

    -

    Positional parameters: -key - str - Key to manage permissions on -user - str - Username whose ACL should be dropped

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -set(key, value)
    -

    Set the string or numeric value of a key

    -
    - -
    -
    -setacl(key, acl)
    -

    Set an ACL on a given key

    -

    Positional parameters: -key - str - Key to manage permissions on -acl - dict - Valid permissions object

    -

    {‘read’: bool, ‘write’: bool}

    -

    Returns: -Boolean True on success, and Exception + False on failure

    -
    - -
    -
    -classmethod to_text_pem(acl)
    -
    - -
    -
    -classmethod validate_acl(acl, permissive=False)
    -

    Validate an ACL object as a dict

    -

    Failure raises Exception unless permissive is True -* Does not validate that username exists

    -
    - -
    - -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.aliases.agavedb.tests.html b/docsrc/_build/html/api-ref/reactors.aliases.agavedb.tests.html deleted file mode 100644 index a806a82..0000000 --- a/docsrc/_build/html/api-ref/reactors.aliases.agavedb.tests.html +++ /dev/null @@ -1,289 +0,0 @@ - - - - - - - - reactors.aliases.agavedb.tests package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases.agavedb.tests package

    -
    -

    Submodules

    -
    -
    -

    reactors.aliases.agavedb.tests.agavefixtures module

    -
    -
    -reactors.aliases.agavedb.tests.agavefixtures.agave(credentials)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.agavefixtures.credentials()
    -

    Load credentials for testing session

    -

    Order: user credential store, test file, env

    -
    - -
    -
    -

    reactors.aliases.agavedb.tests.test_keyval module

    -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_key()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_key_acl()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_user()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.fake_value()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.keyvalstore(agave, prefix)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.prefix()
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_acl_from_world(keyvalstore, fake_key_acl, fake_value, fake_user, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_add_acl(keyvalstore, fake_key_acl, fake_value, fake_user, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_data(credentials)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_get_nonexistent(keyvalstore, credentials)
    -

    test get on a key that doesn’t exist

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_getall(keyvalstore, credentials)
    -

    getall - validate that an array is returned

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_key_valid(keyvalstore, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_list_acl(keyvalstore, fake_key_acl, fake_value, test_data)
    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_fwd(keyvalstore, prefix, credentials)
    -

    _namespace

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_rev_namespace(keyvalstore, credentials, prefix)
    -

    _namespace_rev

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_namespace_rev_wo_namespace(keyvalstore, credentials, prefix)
    -

    _namespace_rev

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_remall(keyvalstore)
    -

    verify that we can delete our session-specific entries

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_set_get_rem(keyvalstore, credentials)
    -

    test key set/get/delete cycle

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_username(keyvalstore, credentials)
    -

    verify that agavedb and test view of username is same

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_validate_acl(keyvalstore, test_data)
    -

    run through various ACL forms

    -
    - -
    -
    -reactors.aliases.agavedb.tests.test_keyval.test_value_valid_type(keyvalstore, credentials)
    -

    valid values for keys

    -
    - -
    -
    -

    reactors.aliases.agavedb.tests.testdata module

    -
    -
    -class reactors.aliases.agavedb.tests.testdata.TestData(credentials)
    -

    Bases: object

    -
    -
    -data(key=None)
    -
    - -
    -
    -file_to_json(filename)
    -
    - -
    - -
    -
    -

    Module contents

    -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.aliases.html b/docsrc/_build/html/api-ref/reactors.aliases.html deleted file mode 100644 index 9073661..0000000 --- a/docsrc/_build/html/api-ref/reactors.aliases.html +++ /dev/null @@ -1,223 +0,0 @@ - - - - - - - - reactors.aliases package — reactors_sdk 0.7.0 documentation - - - - - - - - - - - - - - - - - -
    -
    -
    -
    - -
    -

    reactors.aliases package

    - -
    -

    Submodules

    -
    -
    -

    reactors.aliases.store module

    -

    Manage and retrieve alias-to-actor_id mappings

    -

    Built on AgaveDB which in turn builds on Agave Metatadata

    -
    -
    -class reactors.aliases.store.AliasStore(agaveClient, keyPrefix='kvs_v3', aliasPrefix='', logLevel='ERROR')
    -

    Bases: agavedb.keyval.AgaveKeyValStore

    -
    -
    -get_alias_acls(alias, username=None)
    -

    List ACLs for an alias, optionally filtering by username

    -
    - -
    -
    -get_aliases(sort_aliases=True)
    -

    Fetch all aliases as a alphabetically-sorted list

    -
    - -
    -
    -get_name(alias)
    -

    Get a speciifc alias => entity mapping

    -

    Implements a ‘me’ alias to return self

    -
    - -
    -
    -put_alias_acl(alias, acl)
    -

    Add ACLs to an alias

    -
    - -
    -
    -rem_alias(alias)
    -

    Delete an alias from the database

    -
    - -
    -
    -rem_alias_acl(alias, username=None)
    -

    Entirely remove a user’s ACL for a given key

    -
    - -
    -
    -rem_all_aliases()
    -

    Removes all aliases owned by current user

    -
    - -
    -
    -set_alias(alias, name)
    -

    Create or update actor => alias mapping

    -
    - -
    - -
    -
    -reactors.aliases.store.to_unicode(input)
    -

    Trivial unicode encoder

    -
    - -
    -
    -

    Module contents

    -
    -
    - - -
    -
    -
    -
    - -
    -
    - - - - \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.cli.html b/docsrc/_build/html/api-ref/reactors.cli.html new file mode 100644 index 0000000..22362b3 --- /dev/null +++ b/docsrc/_build/html/api-ref/reactors.cli.html @@ -0,0 +1,161 @@ + + + + + + + reactors.cli package — python-reactors 1.0.0 documentation + + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.cli package

    +
    +

    Submodules

    +
    +
    +

    reactors.cli.run module

    +
    +
    +reactors.cli.run.docstring(fn)
    +
    + +
    +
    +reactors.cli.run.load_function(module='/reactor.py', function='main')
    +
    + +
    +
    +reactors.cli.run.run(module='/reactor.py', function='main', args=None)
    +

    Load and run a function from a script or module

    +
    + +
    +
    +

    reactors.cli.usage module

    +
    +
    +reactors.cli.usage.usage(args=None)
    +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    + +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.html b/docsrc/_build/html/api-ref/reactors.html index a80bf5b..ed0f0ff 100644 --- a/docsrc/_build/html/api-ref/reactors.html +++ b/docsrc/_build/html/api-ref/reactors.html @@ -1,56 +1,98 @@ - - - - - - - reactors package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + + reactors package — python-reactors 1.0.0 documentation + + + + + + + + + + - - + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors package

    +
    +

    Subpackages

    -
    -
    -

    Submodules

    -
    -
    -

    reactors.jsonmessages module

    -
    -
    -reactors.jsonmessages.validate_message(messagedict, messageschema='/Users/TASethanho/tacc/projects/sd2e/python-reactors/src/reactors/message.jsonschema', permissive=True)
    -

    Validate dictonary derived from JSON string against a schema

    -

    Positional arguments: -messagedict - dict - JSON-derived object

    -

    Keyword arguments: -messageschema - str - path to the requisite JSON schema file -permissive - bool - swallow validation errors [True]

    -
    - -
    -
    -

    reactors.process module

    -

    Run subprocesses from within Python

    -
    -
    -reactors.process.run(command_list=[], permissive=False, shell=False, timeout=None)
    -

    Run a child or subshell process.

    -

    Parameters: -exec_params - list - Parameters in exec form -permissive - bool - Ignore errors -shell - bool - Execute command by way of a shell

    -
    -
    Usage:

    # List system logs directory -params=[‘ls’, ‘-alth’, ‘/var/log’] -process.run(params)

    -
    -
    -

    Returns an AttrDict of response attributes.

    -
    - -
    -
    -

    reactors.runtime module

    +
    +
    +

    Submodules

    +
    +
    +

    reactors.config module

    +

    Manages configuration from environment and files

    -
    -reactors.runtime.random() → x in the interval [0, 1).
    +
    +reactors.config.get_redaction_strings(redactions=None, agave_client=None, namespace=None)
    -
    -
    -

    reactors.storage module

    -

    Utility library for supporting container-local, -global POSIX, and eventually, object and document -storage for TACC Reactors

    -
    -
    -

    reactors.uniqueid module

    -

    Generate an Abaco-style UUID

    -
    -
    -reactors.uniqueid.get_id()
    -

    Generate a hash id

    -
    -
    -
    -reactors.uniqueid.is_hashid(identifier)
    -

    Tries to validate a UUID

    -
    - -
    -
    -

    reactors.utils module

    -
    -
    -class reactors.utils.Reactor(redactions=[])
    -

    Bases: object

    -

    Helper class providing a client-side API for the Actors service

    -
    -
    -add_nonce(permission='READ', maxuses=1, actorId=None)
    -

    Add a new nonce.

    -

    Positional arguments: -None

    -

    Keyword arguments: -username: str - a valid TACC.cloud username or role account -permission: str - a valid Abaco permission level -maxuses: int (-1,inf) - maximum number of uses for a given nonce -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -create_webhook(permission='EXECUTE', maxuses=- 1, actorId=None)
    -

    Create a .actor.messages URI suitable for use in integrations

    -

    Default is to grant EXECUTE with unlimited uses.

    -
    - -
    -
    -delete_all_nonces(actorId=None)
    -

    Delete all nonces from an actor

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -delete_nonce(nonceId, actorId=None)
    -

    Delete an specific nonce by its ID

    -

    Positional arguments: -nonceId: str - a valid TACC.cloud username or role account

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -delete_webhook(webhook, actorId=None)
    -

    ‘Delete’ an actor-specific webhook by deleting its nonce

    -

    A key assumption is that webhook was constructed by create_webhook or -its equivalent, as this method sensitive to case and url structure

    -
    - -
    -
    -elapsed()
    -

    Returns elapsed time in microseconds since Reactor was initialized

    -
    - -
    -
    -get_attr(attribute=None, actorId=None)
    -

    Retrieve dict of attributes for an actor

    -

    Parameters: -attribute - str - Any top-level key in the Actor API model -actorId - str - Which actor (if not self) to fetch. Defaults to

    -
    -

    the actor’s own ID, allowing introspection.

    -
    -
    - -
    -
    -get_nonce(nonceId, actorId=None)
    -

    Get an specific nonce by its ID

    -

    Positional arguments: -nonceId: str - a valid TACC.cloud username or role account

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -list_nonces(actorId=None)
    -

    List all nonces

    -

    Positional arguments: -None

    -

    Keyword arguments: -actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    -
    - -
    -
    -on_failure(failMessage='Failure', exceptionObject=None)
    -

    Log message and exit 0

    -
    - -
    -
    -on_success(successMessage='Success')
    -

    Log message and exit 0

    -
    - -
    -
    -resolve_actor_alias(alias)
    -

    Look up the identifier for a alias string

    -
    -
    Arguments

    alias (str): An alias, actorId, appId, or the me/self shortcut

    -
    -
    Returns:

    str: The resolved identifier

    -
    -
    -

    On error: -Returns value of text

    -
    -
    Note:

    Does basic optimization of returning an app ID or abaco actorId -if they are passed, as we can safely assume those are not aliases.

    -
    -
    -
    - -
    -
    -send_message(actorId, message, environment={}, ignoreErrors=True, senderTags=True, retryMaxAttempts=5, retryDelay=1, sync=False)
    -

    Send a message to an Abaco actor by ID, platform alias, or defined alias

    -
    -
    Arguments:

    actorId (str): An actorId or alias -message (str/dict) : Message to send

    -
    -
    Keyword Arguments:

    ignoreErrors: bool - only mark failures by logging not exception -environment: dict - environment variables to pass as url params -senderTags: bool - send provenance and session vars along -retryDelay: int - seconds between retries on send failure -retryMax: int - number of times (up to global MAX_RETRIES) to retry -sync: bool - not implemented - wait for message to execute

    -
    -
    Returns:

    str: The excecutionId of the resulting execution

    -
    -
    Raises:

    AgaveError: Raised if ignoreErrors is True

    -
    -
    -
    - -
    -
    -validate_message(messagedict, messageschema='/message.jsonschema', permissive=True)
    -

    Validate dictonary derived from JSON against a JSON schema

    -

    Positional arguments: -messagedict - dict - JSON-derived object

    -

    Keyword arguments: -messageschema - str - path to the requisite JSON schema file -permissive - bool - swallow validation errors [True]

    -
    - +
    +reactors.config.parse_boolean(s)
    +

    Parse values of Python basic types into equivalent Boolean.

    -
    -reactors.utils.get_client_with_mock_support()
    -

    Get the current Actor API client

    -

    Returns the Abaco actor’s client if running deployed. Attempts to -bootstrap a client from supplied credentials if running in local or -debug mode.

    +
    +reactors.config.read_config(namespace=None, places_list=None, update=True, env=True)
    +

    Override tacconfig’s broken right-favoring merge

    + +
    +

    reactors.utils module

    -
    -reactors.utils.get_context_with_mock_support(agave_client)
    -

    Return the current Actor context

    -

    Return the Abaco actor’s environment context if running deployed. Creates -a test context based on inferred or mocked values if running in local or -debug mode.

    +
    +reactors.utils.get_host_ip()
    +

    Returns current IP address of host

    -
    -reactors.utils.get_token_with_mock_support(client)
    -

    Find current Oauth2 access token from context or mock

    +
    +reactors.utils.microseconds()
    +

    Returns current time in microseconds

    -
    -reactors.utils.microseconds()
    -
    - -
    -
    -reactors.utils.random() → x in the interval [0, 1).
    -
    - -
    -
    -reactors.utils.read_config(namespace='_REACTOR', places_list=['/Users/TASethanho/tacc/projects/sd2e/python-reactors/src/reactors', '/', '/Users/TASethanho/tacc/projects/sd2e/python-reactors/docsrc'], update=True, env=True)
    -

    Override tacconfig’s broken right-favoring merge

    +
    +reactors.utils.utcnow()
    +

    Returns a text-formatted UTC date

    +

    Example: 2018-01-05T18:40:55.290790+00:00

    -
    -
    -reactors.utils.set_os_environ_from_client(agave_client)
    -

    Set environment vars to client values

    -
    +
    +
    +

    reactors.version module

    +
    +
    +

    Module contents

    +
    + -
    -
    -reactors.utils.set_os_environ_from_mock(context)
    -

    Set environment vars to mocked values

    -
    -
    -
    -reactors.utils.utcnow()
    -

    Return a text-formatted UTC date

    -

    example: 2018-01-05T18:40:55.290790+00:00

    -
    +
    +
    +
    -
    -

    reactors.version module

    -
    -
    -

    Module contents

    -
    -
    +
    +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    -
    -
    -
    -
    - -
    -
    - - - + + + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.logtypes.html b/docsrc/_build/html/api-ref/reactors.logtypes.html index abb062d..7f79828 100644 --- a/docsrc/_build/html/api-ref/reactors.logtypes.html +++ b/docsrc/_build/html/api-ref/reactors.logtypes.html @@ -1,262 +1,333 @@ - + + + - - - - - reactors.logtypes package — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + reactors.logtypes package — python-reactors 1.0.0 documentation + + + + + + + + + + - - - - -
    -
    -
    -
    - -
    -

    reactors.logtypes package

    -
    -

    Submodules

    -
    -
    -

    reactors.logtypes.logstash module

    + + + + + +
    + + +
    + +
    +
    +
    + +
    -
    -

    reactors.logtypes.logstash_futures_session module

    +
    +
    + +
    +

    reactors.logtypes package

    +
    +

    Submodules

    +
    +
    +

    reactors.logtypes.loggly module

    +
    +
    +

    reactors.logtypes.loggly_futures_session module

    -
    -class reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler(config, client_secret)
    +
    +class reactors.logtypes.loggly_futures_session.LogglyHandler(url)
    +

    Bases: logging.Handler

    +

    Send logs to Loggly HTTPS handler

    +
    +
    +emit(record)
    +

    Do whatever it takes to actually log the specified logging record.

    +

    This version is intended to be implemented by subclasses and so +raises a NotImplementedError.

    +
    + +
    +
    +get_full_message(record)
    +
    + +
    + +
    +
    +reactors.logtypes.loggly_futures_session.bg_cb(sess, resp)
    +

    Noop the response so logging is fire-and-forget

    +
    + +
    +
    +reactors.logtypes.loggly_futures_session.response_hook_noop(resp, *args, **kwargs)
    +

    Noop the response so logging is fire-and-forget

    +
    + +
    +
    +

    reactors.logtypes.logstash module

    +
    +
    +

    reactors.logtypes.logstash_futures_session module

    +
    +
    +class reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler(config, client_secret)

    Bases: logging.Handler

    Py2-3.4 compatible method to send logs to LogStash HTTP handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -reactors.logtypes.logstash_futures_session.bg_cb(sess, resp)
    +
    +reactors.logtypes.logstash_futures_session.bg_cb(sess, resp)

    Noop the response so logging is fire-and-forget

    -
    -reactors.logtypes.logstash_futures_session.response_hook_noop(resp, *args, **kwargs)
    +
    +reactors.logtypes.logstash_futures_session.response_hook_noop(resp, *args, **kwargs)

    Noop the response so logging is fire-and-forget

    -
    -
    -

    reactors.logtypes.logstash_sync module

    +
    +
    +

    reactors.logtypes.logstash_sync module

    -
    -class reactors.logtypes.logstash_sync.LogstashPlaintextHandler(config, client_secret)
    +
    +class reactors.logtypes.logstash_sync.LogstashPlaintextHandler(config, client_secret)

    Bases: logging.Handler

    Forwards logs on to LogStash HTTP handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -
    -

    reactors.logtypes.main module

    + +
    +

    reactors.logtypes.main module

    Set up a logger with optional support for a logfile and STDERR reporting

    Usage: logger = get_logger(name, log_level, log_file)

    -
    -class reactors.logtypes.main.RedactingFormatter(orig_formatter, patterns)
    -

    Bases: object

    +
    +class reactors.logtypes.main.RedactingFormatter(*args, patterns=None, **kwargs)
    +

    Bases: logging.Formatter

    Specialized formatter used to sanitize log messages

    -
    -format(record)
    -
    +
    +converter()
    +
    +
    gmtime([seconds]) -> (tm_year, tm_mon, tm_mday, tm_hour, tm_min,

    tm_sec, tm_wday, tm_yday, tm_isdst)

    +
    +
    +

    Convert seconds since the Epoch to a time tuple expressing UTC (a.k.a. +GMT). When ‘seconds’ is not passed in, convert the current time instead.

    +

    If the platform supports the tm_gmtoff and tm_zone, they are available as +attributes only.

    +
    + +
    +
    +format(record)
    +

    Format the specified record as text.

    +

    The record’s attribute dictionary is used as the operand to a +string formatting operation which yields the returned string. +Before formatting the dictionary, a couple of preparatory steps +are carried out. The message attribute of the record is computed +using LogRecord.getMessage(). If the formatting string uses the +time (as determined by a call to usesTime(), formatTime() is +called to format the event time. If there is exception information, +it is formatted using formatException() and appended to the message.

    +
    -
    -reactors.logtypes.main.get_log_file(name)
    +
    +reactors.logtypes.main.get_log_file(name)
    -
    -reactors.logtypes.main.get_log_file_strategy()
    +
    +reactors.logtypes.main.get_log_file_strategy()
    -
    -reactors.logtypes.main.get_logger(name, subname=None, log_level='DEBUG', log_file=None, redactions=[], timestamp=False)
    +
    +reactors.logtypes.main.get_logger(name, subname=None, log_level='DEBUG', log_file=None, redactions=[], timestamp=False)

    Legacy alias to get_stderr_logger

    -
    -reactors.logtypes.main.get_screen_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    +
    +reactors.logtypes.main.get_loggly_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    +

    Returns a logger object that can post to Loggly

    +
    + +
    +
    +reactors.logtypes.main.get_screen_logger(name, subname=None, settings={}, redactions=[], fields={}, timestamp=False)
    -
    -reactors.logtypes.main.get_slack_logger(name, subname, settings={}, redactions=[], timestamp=False)
    +
    +reactors.logtypes.main.get_slack_logger(name, subname, settings={}, redactions=[], timestamp=False)

    Returns a logger object that can post to Slack

    -
    -
    -

    reactors.logtypes.slack module

    + +
    +

    reactors.logtypes.slack module

    -
    -class reactors.logtypes.slack.SlackHandler(config)
    +
    +class reactors.logtypes.slack.SlackHandler(config)

    Bases: logging.Handler

    -
    -emit(record)
    +
    +emit(record)

    Do whatever it takes to actually log the specified logging record.

    This version is intended to be implemented by subclasses and so raises a NotImplementedError.

    -
    -get_full_message(record)
    +
    +get_full_message(record)
    -
    -reactors.logtypes.slack.bg_cb(sess, resp)
    +
    +reactors.logtypes.slack.bg_cb(sess, resp)

    Don’t do anything with the response

    -
    -
    -

    Module contents

    -
    -
    + +
    +

    Module contents

    +
    + -
    +
    -
    -
    - - - - + +
    + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.runtime.html b/docsrc/_build/html/api-ref/reactors.runtime.html new file mode 100644 index 0000000..97f0f68 --- /dev/null +++ b/docsrc/_build/html/api-ref/reactors.runtime.html @@ -0,0 +1,517 @@ + + + + + + + reactors.runtime package — python-reactors 1.0.0 documentation + + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.runtime package

    +
    +

    Submodules

    +
    +
    +

    reactors.runtime.abaco module

    +

    Abaco-related vars and helper functions

    +
    +
    +reactors.runtime.abaco.is_hashid(identifier)
    +

    Validates a string presented as an Abaco identifier

    +
    + +
    +
    +reactors.runtime.abaco.load_client(permissive=False)
    +

    Gets the current Tapis API client

    +

    Returns the Abaco actor’s client if running deployed. Attempts to +bootstrap a client from supplied credentials if running in local or +debug mode.

    +
    + +
    +
    +reactors.runtime.abaco.load_context(enable_mocks=True)
    +
    + +
    +
    +reactors.runtime.abaco.new_hashid()
    +

    Generates a valid Abaco-style hash id

    +
    + +
    +
    +

    reactors.runtime.base module

    +

    Reactor base class

    +
    +
    +class reactors.runtime.base.BaseReactor(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: object

    +
    +
    +CONFIG_NAMESPACE = '_REACTOR'
    +
    + +
    +
    +EXIT_CODE = 1
    +
    + +
    +
    +MOCK_ENABLED = True
    +
    + +
    +
    +NICKNAME_SEP = '-'
    +
    + +
    +
    +NICKNAME_WORDS = 2
    +
    + +
    +
    +TAPIS_OPTIONAL = False
    +
    + +
    +
    +elapsed()
    +

    Returns elapsed time in microseconds since Reactor was initialized

    +
    + +
    +
    +on_failure(failMessage='Failure', exceptionObject=None)
    +

    Log message and exit 0

    +
    + +
    +
    +on_success(successMessage='Success')
    +

    Log message and exit 0

    +
    + +
    + +
    +
    +

    reactors.runtime.messaging module

    +

    Derived Reactor class implementing inter-actor messages

    +
    +
    +class reactors.runtime.messaging.Messaging(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +MAX_ELAPSED = 300
    +
    + +
    +
    +MAX_RETRIES = 5
    +
    + +
    +
    +RETRY_DELAY = 1.0
    +
    + +
    +
    +RETRY_MAX_DELAY = 32.0
    +
    + +
    +
    +actor_property(property=None, actor_id=None)
    +

    Retrieve an actor property from Abaco API

    +

    Parameters: +property - str - Any top-level key in the Actor API model +actorId - str - Which actor (if not self) to fetch. Defaults to

    +
    +

    the actor’s own ID, allowing introspection.

    +
    +
    + +
    +
    +message_provenance(senderTags=True)
    +

    Captures provenance attributes for current execution

    +
    + +
    +
    +message_vars(passed_envs={}, sender_envs={}, senderTags=True)
    +

    Private method to merge user- and platform-specific environments

    +
    + +
    +
    +resolve_alias(alias)
    +

    Look up the identifier for a alias string

    +
    +
    Arguments

    alias (str): An alias, actorId, appId, or the me/self shortcut

    +
    +
    Returns:

    str: The resolved identifier

    +
    +
    +

    On error: +Returns value of text

    +
    +
    Note:

    Does basic optimization of returning an app ID or abaco actorId +if they are passed, as we can safely assume those are not aliases.

    +
    +
    +
    + +
    +
    +send_message(actorId, message, environment={}, ignoreErrors=True, senderTags=True, retryMaxAttempts=None, retryDelay=None, sync=False)
    +

    Send a message to an Abaco actor by ID or alias

    +
    +
    Arguments:

    actorId (str): An actorId or alias +message (str/dict) : Message to send

    +
    +
    Keyword Arguments:

    ignoreErrors: bool - only mark failures by logging not exception +environment: dict - environment variables to pass as url params +senderTags: bool - send provenance and session as urlparams with message +retryDelay: int - seconds between retries on send failure +retryMax: int - number of times (up to global MAX_RETRIES) to retry +sync: bool - not implemented - wait for message to execute

    +
    +
    Returns:

    str: The executionId of the resulting execution

    +
    +
    Raises:

    AgaveError: Raised if ignoreErrors is True

    +
    +
    +
    + +
    + +
    +
    +

    reactors.runtime.reactor module

    +

    Composition of mix-in classes into Reactor class

    +
    +
    +class reactors.runtime.reactor.Reactor(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.messaging.Messaging, reactors.runtime.validating.Validation, reactors.runtime.webhooks.Webhooks

    +
    + +
    +
    +

    reactors.runtime.sessions module

    +

    Code having to do with actor sessions

    +
    +
    +reactors.runtime.sessions.get_session(context, default=None)
    +
    + +
    +
    +

    reactors.runtime.validating module

    +

    Derived Reactor class implementing validations

    +
    +
    +class reactors.runtime.validating.Validation(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +AUTO_VALIDATE_BINARY = False
    +
    + +
    +
    +AUTO_VALIDATE_CONTEXT = True
    +
    + +
    +
    +AUTO_VALIDATE_MESSAGE = True
    +
    + +
    +
    +classify_binary()
    +

    Determine what kind of binary was sent

    +
    + +
    +
    +classify_context()
    +

    Determine which schemas match the current context

    +
    + +
    +
    +classify_message()
    +

    Determine which schemas match the current JSON message

    +
    + +
    +
    +validate(check_context=True, check_message=True, check_binary=False, permissive=True)
    +

    Perform all validations using default settings

    +
    + +
    +
    +validate_binary(validator=None, permissive=True)
    +

    (Stub) Verify Actor binary FIFO contents

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    validator - func - user function for validating a binary [binary.validator_function] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    +
    +validate_context(schema=None, permissive=True)
    +

    Validate Actor context using a JSON schema

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    schema - str - override path to a JSON schema file [/schemas/context.jsonschema] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    +
    +validate_message(message=None, schema=None, permissive=True)
    +

    Validate Actor message against a JSON schema

    +

    Positional arguments:

    +
    +
    Keyword arguments:

    message - dict - representation of a JSON message +schema - str - override path to a JSON schema file [/schemas/message.jsonschema] +permissive - bool - swallow validation errors [True]

    +
    +
    +
    + +
    + +
    +
    +

    reactors.runtime.webhooks module

    +

    Derived Reactor class implementing webhooks and nonces

    +
    +
    +class reactors.runtime.webhooks.Webhooks(redactions=[], namespace='_REACTOR', session=None, tapis_optional=False, **kwargs)
    +

    Bases: reactors.runtime.base.BaseReactor

    +
    +
    +DEFAULT_NONCE_MAX_USES = -1
    +
    + +
    +
    +DEFAULT_NONCE_PERMISSION = 'EXECUTE'
    +
    + +
    +
    +add_nonce(permission='READ', maxuses=1, actorId=None)
    +

    Add a new nonce.

    +
    +
    Positional arguments:

    None

    +
    +
    Keyword arguments:

    username: str - a valid TACC.cloud username or role account +permission: str - a valid Abaco permission level +maxuses: int (-1,inf) - maximum number of uses for a given nonce +actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +create_webhook(permission='EXECUTE', maxuses=- 1, actorId=None)
    +

    Create an actor/messages URI for use with external integrations

    +
    + +
    +
    +delete_all_nonces(actorId=None)
    +

    Delete all nonces from an actor

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +delete_nonce(nonceId, actorId=None)
    +

    Delete an specific nonce by its ID

    +
    +
    Positional arguments:

    nonceId: str - a valid TACC.cloud username or role account

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +delete_webhook(webhook, actorId=None)
    +

    ‘Delete’ an actor-specific webhook by deleting its nonce

    +

    A key assumption is that webhook was constructed by create_webhook or +its equivalent, as this method sensitive to case and url structure

    +
    + +
    +
    +get_nonce(nonceId, actorId=None)
    +

    Get an specific nonce by its ID

    +
    +
    Positional arguments:

    nonceId: str - a valid TACC.cloud username or role account

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    +
    +list_nonces(actorId=None)
    +

    List all nonces

    +
    +
    Positional arguments:

    None

    +
    +
    Keyword arguments:

    actorId: str - an Abaco actor ID. Defaults to self.uid if not set.

    +
    +
    +
    + +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    + +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docsrc/_build/html/api-ref/reactors.validation.html b/docsrc/_build/html/api-ref/reactors.validation.html new file mode 100644 index 0000000..535a060 --- /dev/null +++ b/docsrc/_build/html/api-ref/reactors.validation.html @@ -0,0 +1,332 @@ + + + + + + + reactors.validation package — python-reactors 1.0.0 documentation + + + + + + + + + + + + + + + + +
    + + +
    + +
    +
    +
    + +
    +
    +
    +
    + +
    +

    reactors.validation package

    +
    +

    Submodules

    +
    +
    +

    reactors.validation.binary module

    +

    Implements binary validation

    +
    +
    +reactors.validation.binary.classify_binary(binary, validators=None, permissive=True)
    +
    + +
    +
    +reactors.validation.binary.validate(binary, permissive=True)
    +
    + +
    +
    +reactors.validation.binary.validate_binary(binary, validator, permissive=True)
    +
    + +
    +
    +

    reactors.validation.context module

    +

    Implements context validation

    +
    +
    +reactors.validation.context.classify_context(context, schemas=None, min_allowed=0, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a context matches.

    +
    + +
    +
    +reactors.validation.context.validate(context, permissive=True)
    +

    Verifies that a context is valid

    +
    + +
    +
    +reactors.validation.context.validate_context(context, schema, check_formats=True, permissive=True)
    +

    Validates that a document conforms to the given context JSON schema.

    +
    +
    Arguments

    context (dict): Abaco context loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +

    reactors.validation.jsondoc module

    +

    Classes and functions for working with and validating JSON messages

    +
    +
    +reactors.validation.jsondoc.classify_document(message, schemas=None, min_allowed=1, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a document matches.

    +
    + +
    +
    +reactors.validation.jsondoc.find_schema_files(dirname='schemas', filename_glob='*.jsonschema', static_paths=None)
    +

    Searches defined filesystem locations for JSON schema files

    +
    + +
    +
    +class reactors.validation.jsondoc.formatChecker
    +

    Bases: jsonschema._format.FormatChecker

    +

    Enables python-jsonschema to validate format fields

    +
    + +
    +
    +reactors.validation.jsondoc.id_for_schema(schema_as_dict)
    +

    Generates a hash-based identifier for a schema document

    +
    + +
    +
    +reactors.validation.jsondoc.is_default(schema_as_dict)
    +

    Return true if a JSONschema is the built-in default

    +
    + +
    +
    +reactors.validation.jsondoc.load_schema(schema, inject_id=True, force_additional_properties=False)
    +

    Loads a schema from a URL, file path, or dictionary

    +
    +
    Arguments

    schema (str|dict): Schema reference +inject_id (bool): Whether to force the schema to contain an $id property +force_additional_properties (bool): Whether to force the schema to accept additional properties

    +
    +
    Returns:

    dict: A dictionary containing the JSON schema

    +
    +
    On error:

    Returns value of text

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.load_schemas(schemas, inject_id=True, force_additional_properties=False)
    +

    Loads list of schema URLs, file paths, and dictionaries

    +
    +
    Arguments

    schemas (list): List of schema references +inject_id (bool): Whether to force the schema to contain an $id property +force_additional_properties (bool): Whether to force the schema to accept additional properties

    +
    +
    Returns:

    list: A list of JSON schemas

    +
    +
    On error:

    N/A

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.schema_from_url(url, inject_id=True)
    +

    Fetches a schema document from a URL.

    +
    + +
    +
    +reactors.validation.jsondoc.schema_id(schema)
    +

    Returns the identifier from a JSON schema.

    +
    + +
    +
    +reactors.validation.jsondoc.schema_ids(schemas)
    +

    Returns the identifiers from a list of JSON schemas

    +
    + +
    +
    +reactors.validation.jsondoc.validate_document(message, schema, check_formats=True, permissive=True)
    +

    Validates that a document conforms to the given JSON schema.

    +
    +
    Arguments

    message (dict): JSON document loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +reactors.validation.jsondoc.vars_from_schema(schema, filter_private=False, private_prefix='_')
    +

    Transforms a JSON schema into list of dict representations

    +

    Note: This does not (and cannot) resolve JSON $ref subproperties

    +
    + +
    +
    +

    reactors.validation.message module

    +

    Implements JSON message validation

    +
    +
    +reactors.validation.message.classify_message(message, schemas=None, min_allowed=0, max_allowed=- 1, permissive=True)
    +

    Classifies which (if any) provided JSON schemas a message matches.

    +
    + +
    +
    +reactors.validation.message.find_message_schema_files(dirname='message_schemas', filename_glob='*.jsonschema', static_paths=['/message_schemas/default.jsonschema', '/message_schemas/message.jsonschema', '/schemas/message.jsonschema', '/message.jsonschema', '/Users/eho/tacc/projects/sd2e/python-reactors/src/reactors/validation/message.jsonschema'])
    +

    Searches defined filesystem locations for JSON schema files defining Abaco message formats

    +
    + +
    +
    +reactors.validation.message.validate(message, permissive=True)
    +

    Verifies that a message is valid according to one of the schemas

    +
    + +
    +
    +reactors.validation.message.validate_message(message, schema, check_formats=True, permissive=True)
    +

    Validates that a message conforms to the given message JSON schema.

    +
    +
    Arguments

    message (dict): Abaco message loaded as a dictionary +schema (str|dict): JSON schema as a dictionary +check_formats (bool): Whether to enforce format validation +permissive (bool): Whether to return False rather than raise an Exception on error

    +
    +
    Returns:

    bool: Whether the validation succeeded

    +
    +
    On error:

    Returns jsonschema.ValidationError

    +
    +
    +
    + +
    +
    +

    Module contents

    +
    +
    + + +
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    +
    +
    +
    +
    + + + + \ No newline at end of file diff --git a/docsrc/_build/html/genindex.html b/docsrc/_build/html/genindex.html index cf59969..797e5c5 100644 --- a/docsrc/_build/html/genindex.html +++ b/docsrc/_build/html/genindex.html @@ -1,43 +1,76 @@ - - - - - - - Index — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + Index — python-reactors 1.0.0 documentation + + + + + + + + + + - - - -
    -
    -
    -
    - + + + +
    + + +
    + +
    +
    +
    +
      +
    • »
    • +
    • Index
    • +
    • +
    • +
    +
    +
    +
    +
    +

    Index

    @@ -51,8 +84,6 @@

    Index

    | G | H | I - | J - | K | L | M | N @@ -69,11 +100,9 @@

    Index

    A

    @@ -101,9 +126,13 @@

    A

    B

    + + + + + + + + + + + + + + +
        - reactors.aliases + reactors.cli
        - reactors.aliases.agavedb + reactors.cli.run
        - reactors.aliases.agavedb.keyval + reactors.cli.usage
        - reactors.aliases.agavedb.tests + reactors.config
        - reactors.aliases.agavedb.tests.agavefixtures + reactors.logtypes
        - reactors.aliases.agavedb.tests.test_keyval + reactors.logtypes.loggly
        - reactors.aliases.agavedb.tests.testdata + reactors.logtypes.loggly_futures_session
        - reactors.aliases.agavedb.uniqueid + reactors.logtypes.logstash
        - reactors.aliases.store + reactors.logtypes.logstash_futures_session
        - reactors.jsonmessages + reactors.logtypes.logstash_sync
        - reactors.logtypes + reactors.logtypes.main
        - reactors.logtypes.logstash + reactors.logtypes.slack
        - reactors.logtypes.logstash_futures_session + reactors.runtime
        - reactors.logtypes.logstash_sync + reactors.runtime.abaco
        - reactors.logtypes.main + reactors.runtime.base
        - reactors.logtypes.slack + reactors.runtime.messaging
        - reactors.process + reactors.runtime.reactor
        - reactors.runtime + reactors.runtime.sessions
        - reactors.storage + reactors.runtime.validating
        - reactors.uniqueid + reactors.runtime.webhooks
        reactors.utils
        + reactors.validation +
        + reactors.validation.binary +
        + reactors.validation.context +
        + reactors.validation.jsondoc +
        + reactors.validation.message +
        @@ -206,42 +264,31 @@

    Python Module Index

    -
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    - -
    -
    - - - + +
    + + + \ No newline at end of file diff --git a/docsrc/_build/html/search.html b/docsrc/_build/html/search.html index fea5971..84d51ce 100644 --- a/docsrc/_build/html/search.html +++ b/docsrc/_build/html/search.html @@ -1,96 +1,124 @@ - - - - - - - Search — reactors_sdk 0.7.0 documentation - - - - - - - - - - + + + + + Search — python-reactors 1.0.0 documentation + + + + + + + + + + + - - - + + - - + +
    + + +
    + +
    +
    +
    +
      +
    • »
    • +
    • Search
    • +
    • +
    • +
    +
    +
    +
    +
    + + +
    -
    +
    +
    + +
    + +
    +

    © Copyright 2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan.

    +
    + + Built with Sphinx using a + theme + provided by Read the Docs. + + +
    - -
    -
    - - - + +
    + + + + + + + + \ No newline at end of file diff --git a/docsrc/_build/html/searchindex.js b/docsrc/_build/html/searchindex.js index deff784..d8aace1 100644 --- a/docsrc/_build/html/searchindex.js +++ b/docsrc/_build/html/searchindex.js @@ -1 +1 @@ -Search.setIndex({docnames:["api-ref/modules","api-ref/reactors","api-ref/reactors.agaveutils","api-ref/reactors.aliases","api-ref/reactors.aliases.agavedb","api-ref/reactors.aliases.agavedb.tests","api-ref/reactors.logtypes","index"],envversion:{"sphinx.domains.c":2,"sphinx.domains.changeset":1,"sphinx.domains.citation":1,"sphinx.domains.cpp":3,"sphinx.domains.index":1,"sphinx.domains.javascript":2,"sphinx.domains.math":2,"sphinx.domains.python":2,"sphinx.domains.rst":2,"sphinx.domains.std":1,sphinx:56},filenames:["api-ref/modules.rst","api-ref/reactors.rst","api-ref/reactors.agaveutils.rst","api-ref/reactors.aliases.rst","api-ref/reactors.aliases.agavedb.rst","api-ref/reactors.aliases.agavedb.tests.rst","api-ref/reactors.logtypes.rst","index.rst"],objects:{"":{reactors:[1,0,0,"-"]},"reactors.agaveutils":{entity:[2,0,0,"-"],files:[2,0,0,"-"],reactors:[2,0,0,"-"],recursive:[2,0,0,"-"],uri:[2,0,0,"-"],utils:[2,0,0,"-"]},"reactors.agaveutils.entity":{is_appid:[2,1,1,""]},"reactors.agaveutils.files":{agave_download_file:[2,1,1,""],agave_mkdir:[2,1,1,""],agave_upload_file:[2,1,1,""],get:[2,1,1,""],mkdir:[2,1,1,""],process_agave_httperror:[2,1,1,""],put:[2,1,1,""],random:[2,1,1,""],wait_for_file_status:[2,1,1,""]},"reactors.agaveutils.reactors":{message_reactor:[2,1,1,""]},"reactors.agaveutils.recursive":{PemAgent:[2,2,1,""],random:[2,1,1,""]},"reactors.agaveutils.recursive.PemAgent":{enumerate2:[2,3,1,""],grant:[2,3,1,""],listdir:[2,3,1,""],updatepem:[2,3,1,""],walk:[2,3,1,""]},"reactors.agaveutils.uri":{agave_uri_from_http:[2,1,1,""],from_agave_uri:[2,1,1,""],from_tacc_s3_uri:[2,1,1,""],http_uri_from_agave:[2,1,1,""],to_agave_uri:[2,1,1,""]},"reactors.agaveutils.utils":{get_api_server:[2,1,1,""],get_api_token:[2,1,1,""],get_api_username:[2,1,1,""]},"reactors.aliases":{agavedb:[4,0,0,"-"],store:[3,0,0,"-"]},"reactors.aliases.agavedb":{Agave:[4,2,1,""],AgaveKeyValStore:[4,2,1,""],keyval:[4,0,0,"-"],tests:[5,0,0,"-"],uniqueid:[4,0,0,"-"]},"reactors.aliases.agavedb.Agave":{PARAMS:[4,4,1,""],agpy_path:[4,3,1,""],can_refresh:[4,4,1,""],clients_ari:[4,3,1,""],download_uri:[4,3,1,""],full_ari:[4,3,1,""],geturl:[4,3,1,""],jwt_ari:[4,3,1,""],nonce_ari:[4,3,1,""],refresh_aris:[4,3,1,""],resource:[4,3,1,""],restore:[4,3,1,""],set_client:[4,3,1,""],tapis_cache_path:[4,3,1,""],tapis_current_path:[4,3,1,""],tapis_sessions_path:[4,3,1,""],to_dict:[4,3,1,""]},"reactors.aliases.agavedb.AgaveKeyValStore":{create_key_name:[4,3,1,""],deldb:[4,3,1,""],from_text_pem:[4,3,1,""],get:[4,3,1,""],getacls:[4,3,1,""],getall:[4,3,1,""],rem:[4,3,1,""],remacl:[4,3,1,""],set:[4,3,1,""],setacl:[4,3,1,""],to_text_pem:[4,3,1,""],validate_acl:[4,3,1,""]},"reactors.aliases.agavedb.keyval":{AgaveKeyValStore:[4,2,1,""]},"reactors.aliases.agavedb.keyval.AgaveKeyValStore":{create_key_name:[4,3,1,""],deldb:[4,3,1,""],from_text_pem:[4,3,1,""],get:[4,3,1,""],getacls:[4,3,1,""],getall:[4,3,1,""],rem:[4,3,1,""],remacl:[4,3,1,""],set:[4,3,1,""],setacl:[4,3,1,""],to_text_pem:[4,3,1,""],validate_acl:[4,3,1,""]},"reactors.aliases.agavedb.tests":{agavefixtures:[5,0,0,"-"],test_keyval:[5,0,0,"-"],testdata:[5,0,0,"-"]},"reactors.aliases.agavedb.tests.agavefixtures":{agave:[5,1,1,""],credentials:[5,1,1,""]},"reactors.aliases.agavedb.tests.test_keyval":{fake_key:[5,1,1,""],fake_key_acl:[5,1,1,""],fake_user:[5,1,1,""],fake_value:[5,1,1,""],keyvalstore:[5,1,1,""],prefix:[5,1,1,""],test_acl_from_world:[5,1,1,""],test_add_acl:[5,1,1,""],test_data:[5,1,1,""],test_get_nonexistent:[5,1,1,""],test_getall:[5,1,1,""],test_key_valid:[5,1,1,""],test_list_acl:[5,1,1,""],test_namespace_fwd:[5,1,1,""],test_namespace_rev_namespace:[5,1,1,""],test_namespace_rev_wo_namespace:[5,1,1,""],test_remall:[5,1,1,""],test_set_get_rem:[5,1,1,""],test_username:[5,1,1,""],test_validate_acl:[5,1,1,""],test_value_valid_type:[5,1,1,""]},"reactors.aliases.agavedb.tests.testdata":{TestData:[5,2,1,""]},"reactors.aliases.agavedb.tests.testdata.TestData":{data:[5,3,1,""],file_to_json:[5,3,1,""]},"reactors.aliases.agavedb.uniqueid":{get_id:[4,1,1,""],is_hashid:[4,1,1,""]},"reactors.aliases.store":{AliasStore:[3,2,1,""],to_unicode:[3,1,1,""]},"reactors.aliases.store.AliasStore":{get_alias_acls:[3,3,1,""],get_aliases:[3,3,1,""],get_name:[3,3,1,""],put_alias_acl:[3,3,1,""],rem_alias:[3,3,1,""],rem_alias_acl:[3,3,1,""],rem_all_aliases:[3,3,1,""],set_alias:[3,3,1,""]},"reactors.jsonmessages":{validate_message:[1,1,1,""]},"reactors.logtypes":{logstash:[6,0,0,"-"],logstash_futures_session:[6,0,0,"-"],logstash_sync:[6,0,0,"-"],main:[6,0,0,"-"],slack:[6,0,0,"-"]},"reactors.logtypes.logstash_futures_session":{LogstashPlaintextHandler:[6,2,1,""],bg_cb:[6,1,1,""],response_hook_noop:[6,1,1,""]},"reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.logtypes.logstash_sync":{LogstashPlaintextHandler:[6,2,1,""]},"reactors.logtypes.logstash_sync.LogstashPlaintextHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.logtypes.main":{RedactingFormatter:[6,2,1,""],get_log_file:[6,1,1,""],get_log_file_strategy:[6,1,1,""],get_logger:[6,1,1,""],get_screen_logger:[6,1,1,""],get_slack_logger:[6,1,1,""]},"reactors.logtypes.main.RedactingFormatter":{format:[6,3,1,""]},"reactors.logtypes.slack":{SlackHandler:[6,2,1,""],bg_cb:[6,1,1,""]},"reactors.logtypes.slack.SlackHandler":{emit:[6,3,1,""],get_full_message:[6,3,1,""]},"reactors.process":{run:[1,1,1,""]},"reactors.runtime":{random:[1,1,1,""]},"reactors.uniqueid":{get_id:[1,1,1,""],is_hashid:[1,1,1,""]},"reactors.utils":{Reactor:[1,2,1,""],get_client_with_mock_support:[1,1,1,""],get_context_with_mock_support:[1,1,1,""],get_token_with_mock_support:[1,1,1,""],microseconds:[1,1,1,""],random:[1,1,1,""],read_config:[1,1,1,""],set_os_environ_from_client:[1,1,1,""],set_os_environ_from_mock:[1,1,1,""],utcnow:[1,1,1,""]},"reactors.utils.Reactor":{add_nonce:[1,3,1,""],create_webhook:[1,3,1,""],delete_all_nonces:[1,3,1,""],delete_nonce:[1,3,1,""],delete_webhook:[1,3,1,""],elapsed:[1,3,1,""],get_attr:[1,3,1,""],get_nonce:[1,3,1,""],list_nonces:[1,3,1,""],on_failure:[1,3,1,""],on_success:[1,3,1,""],resolve_actor_alias:[1,3,1,""],send_message:[1,3,1,""],validate_message:[1,3,1,""]},reactors:{agaveutils:[2,0,0,"-"],aliases:[3,0,0,"-"],jsonmessages:[1,0,0,"-"],logtypes:[6,0,0,"-"],process:[1,0,0,"-"],runtime:[1,0,0,"-"],storage:[1,0,0,"-"],uniqueid:[1,0,0,"-"],utils:[1,0,0,"-"],version:[1,0,0,"-"]}},objnames:{"0":["py","module","Python module"],"1":["py","function","Python function"],"2":["py","class","Python class"],"3":["py","method","Python method"],"4":["py","attribute","Python attribute"]},objtypes:{"0":"py:module","1":"py:function","2":"py:class","3":"py:method","4":"py:attribute"},terms:{"05t18":1,"2018":1,"290790":1,"300":2,"boolean":4,"case":1,"class":[1,2,3,4,5,6],"default":1,"final":2,"function":2,"import":[2,4],"int":1,"long":2,"new":[1,2],"public":[2,4],"return":[1,2,3,4,5,6],"true":[1,2,3,4],"try":2,"var":1,Not:2,The:[1,2,4],These:4,Uses:[2,4],_namespac:5,_namespace_rev:5,_reactor:1,_refresh_token:4,_token:4,abaco:[1,2,4],about:2,absolut:[2,4],abspath:2,access:[1,4],access_token:2,account:1,acl:[3,4,5],activ:4,actor:[1,2,3],actor_id:3,actorid:[1,2],actual:6,add:[1,3],add_nonc:1,against:1,agav:[2,3,4,5],agave_cli:1,agave_download_fil:2,agave_mkdir:2,agave_upload_fil:2,agave_uri_from_http:2,agaveabsolutepath:2,agavecli:[2,3,4],agavedb:[1,3],agavedestpath:2,agaveerror:[1,2],agavefixtur:[3,4],agavekeyvalstor:[3,4],agavepi:[2,4],agaveuri:2,agaveutil:[0,1],agavewatchpath:2,agpi:4,agpy_path:4,alia:[1,3,6],alias:[0,1],aliasprefix:[3,4],aliasstor:3,all:[1,2,3,4],allow:1,along:1,alphabet:3,alreadi:2,alth:1,alwai:2,ani:1,anoth:2,anyth:6,api:[1,2,4,7],api_kei:4,api_secret:4,api_serv:4,app:[1,2],appid:[1,2],appli:2,arg:[4,6],argument:1,arrai:5,assum:[1,4],assumpt:1,attempt:[1,2],attrdict:1,attribut:1,auth_typ:4,authent:2,avoid:2,awar:4,backoff:2,base:[1,2,3,4,5,6],basepath:2,basic:1,befor:2,between:1,bg_cb:6,bool:[1,2,4],bootstrap:1,broken:1,build:3,built:[3,4],cach:4,cache_cli:4,call:2,caller:2,can:[1,4,5,6],can_refresh:4,candid:2,caveat:2,child:[1,2],choos:2,classmethod:4,client:[1,2,4],client_nam:4,client_secret:6,clientcommand:4,clients_ari:4,cloud:1,command:1,command_list:1,common:2,compat:6,complet:2,config:6,construct:[1,2],contain:1,content:0,context:1,conveni:4,convert:2,correctli:2,crawl:2,creat:[1,2,3,4],create_key_nam:4,create_webhook:1,created_at:4,creation:2,credenti:[1,4,5],current:[1,2,3,4],cwd:2,cycl:5,data:[2,5],databas:3,date:1,debug:[1,6],defin:1,delai:2,deldb:4,delet:[1,3,4,5],delete_all_nonc:1,delete_nonc:1,delete_webhook:1,deploi:1,deprec:4,deprecatedcommand:4,deriv:1,destin:2,dict:[1,4],dictionari:4,dictonari:1,dir:2,directori:[1,2,4],directorypath:2,dirnam:2,dirpath:2,docsrc:1,document:[1,4],doe:[1,4],doesn:5,doing:2,don:6,download:[2,4],download_uri:4,drop:4,edu:4,elaps:1,emit:6,encod:3,entir:3,entiti:[0,1,3],entri:5,enumerate2:2,env:[1,5],environ:[1,2],equival:1,error:[1,2,3,4],eventu:[1,4],exampl:1,excecutionid:1,exceed:2,except:[1,2,4],exceptionobject:1,exec:1,exec_param:1,execut:[1,2],exist:[4,5],exit:1,expens:2,expir:4,expires_at:4,expires_in:4,exponenti:2,extern:4,failmessag:1,failur:[1,2,4],fake_kei:5,fake_key_acl:5,fake_us:5,fake_valu:5,fals:[1,2,4,6],favor:1,fetch:[1,3],field:6,file:[0,1,4,5],file_to_json:5,filenam:[2,5],filesystem:2,filter:3,find:1,fire:[2,6],forget:[2,6],form:[1,5],format:[1,2,6],formatt:6,forward:6,fpath:2,friendli:4,from:[1,2,3,4],from_agave_uri:2,from_tacc_s3_uri:2,from_text_pem:4,full_ari:4,gener:[1,4],get:[1,2,3,4,5],get_alias:3,get_alias_acl:3,get_api_serv:2,get_api_token:2,get_api_usernam:2,get_attr:1,get_client_with_mock_support:1,get_context_with_mock_support:1,get_full_messag:6,get_id:[1,4],get_log_fil:6,get_log_file_strategi:6,get_logg:6,get_nam:3,get_nonc:1,get_screen_logg:6,get_slack_logg:6,get_stderr_logg:6,get_token_with_mock_support:1,getacl:4,getal:[4,5],geturl:4,given:[1,3,4],global:1,grant:[1,2],handl:2,handler:6,has:4,hash:[1,4],hashid:4,header_nam:4,helper:[1,2],here:2,host:2,http:[2,4,6],http_error_object:2,http_uri_from_agav:2,httperror:2,httpuri:2,human:4,identifi:[1,4],ignor:1,ignoreerror:[1,2],imdepot:2,implement:[1,2,3,6],importdata:2,index:7,inf:1,infer:1,info:2,initi:[1,2],input:3,inspir:4,instanc:4,integr:1,intend:6,interact:4,interfac:4,interv:[1,2],introspect:1,involv:2,is_appid:2,is_hashid:[1,4],its:[1,2],job:4,json:1,jsonmessag:0,jsonschema:1,jwt:4,jwt_ari:4,jwt_header_nam:4,kei:[1,3,4,5],keyprefix:[3,4],keyval:[1,3],keyvalstor:5,keyword:1,keywork:4,kvs_v3:[3,4],kwarg:[4,6],least:2,legaci:6,level:1,librari:[1,4],like:2,linktyp:2,list:[1,3,4],list_nonc:1,listdir:2,load:[4,5],local:[1,4],local_path:4,localfilenam:2,log:[1,6],log_fil:6,log_level:6,logfil:6,logger:6,loglevel:[2,3,4],logstash:[0,1],logstash_asyncio:[0,1],logstash_futures_sess:[0,1],logstash_sync:[0,1],logstashplaintexthandl:6,logtyp:[0,1],look:[1,2],main:[0,1],make:[2,4],manag:[2,3,4],map:3,mark:1,max_retri:1,maximum:1,maxtim:2,maxus:1,media:2,merg:1,messag:[1,2,6],message_reactor:2,messagedict:1,messageschema:1,metadata:4,metatadata:3,method:[1,4,6],microsecond:1,mkdir:2,mock:1,mode:1,model:[1,4],modul:[0,7],more:4,movement:2,much:4,multipli:2,multius:4,name:[2,3,4,6],namespac:[1,2],nearli:4,need:4,nonc:1,nonce_ari:4,nonceid:1,none:[1,2,3,4,5,6],noop:6,note:1,noth:2,notimplementederror:6,number:[1,2,4],numer:4,oauth2:1,object:[1,2,4,5,6],on_failur:1,on_success:1,one:2,onli:[1,4],oper:2,optim:1,option:[3,6],order:5,orient:4,orig_formatt:6,otherwis:2,our:5,output:4,overload:2,overrid:1,own:[1,3,4],packag:[0,7],page:7,param:[1,4],paramet:[1,2,4],parent:2,pars:2,pass:1,password:4,path:[1,2,4],pattern:6,pem:[2,4],pemag:2,permiss:[1,2,4],pickledb:4,place:2,places_list:1,platform:1,point:2,poll:2,posit:[1,2,4],posix:1,post:6,prefix:5,process:0,process_agave_httperror:2,project:1,proven:1,provid:1,proxi:4,put:2,put_alias_acl:3,py2:6,python:[1,2,4],rais:[1,2,4,6],random:[1,2,4],reach:2,read:[1,2,4],read_config:1,readabl:4,real:2,rec:2,record:6,recurs:[0,1],redact:[1,6],redactingformatt:6,redi:4,refer:7,refresh_ari:4,refresh_token:4,rem:4,rem_alia:3,rem_alias_acl:3,rem_all_alias:3,remacl:4,remot:2,remov:[3,4],report:6,repres:4,request:[2,4],requir:[2,4],requisit:1,resid:2,resolv:1,resolve_actor_alia:1,resourc:[2,4],resp:6,respons:[1,6],response_hook_noop:6,restor:4,result:1,retri:[1,2,4],retriev:[1,3],retrydelai:1,retrymax:1,retrymaxattempt:1,right:1,role:1,root:2,run:[1,5],runtim:0,safe:1,same:[2,5],sanit:6,schema:1,sd2e:1,search:7,second:1,secret:4,self:[1,3],send:[1,2,6],send_messag:1,sendertag:[1,2],sensit:1,sequenc:2,server:2,servic:[1,4],sess:6,session:[1,4,5],set:[1,4,5,6],set_alia:3,set_client:4,set_os_environ_from_cli:1,set_os_environ_from_mock:1,setacl:4,share:4,shell:1,shortcut:1,should:[2,4],side:1,sinc:[1,2],slack:[0,1],slackhandl:6,solut:4,sort:3,sort_alias:[3,4],sourc:4,special:[2,6],specif:[1,5],specifi:[2,6],speciifc:3,src:1,state:2,statu:2,stderr:6,storag:[0,2],storagesystem:2,store:[0,1,4,5],str:[1,2,4],string:[1,2,4],strong:4,structur:1,style:[1,4],subclass:6,submodul:0,subnam:6,subpackag:0,subprocess:1,subshel:1,success:[1,2,4],successmessag:1,suitabl:1,suppli:1,support:[1,4,6],swallow:1,sync:[1,2],synchron:2,system:[1,2,4],systemid:2,tacc:[1,2,4],tacconfig:1,take:6,tapis_cache_path:4,tapis_current_path:4,tapis_sessions_path:4,tasethanho:1,task:2,tenant_id:4,termin:2,test:[1,3,4],test_acl_from_world:5,test_add_acl:5,test_data:5,test_get_nonexist:5,test_getal:5,test_key_valid:5,test_keyv:[3,4],test_list_acl:5,test_namespace_fwd:5,test_namespace_rev_namespac:5,test_namespace_rev_wo_namespac:5,test_remal:5,test_set_get_rem:5,test_usernam:5,test_validate_acl:5,test_value_valid_typ:5,testdata:[3,4],text:[1,2],textstr:2,thei:1,thi:[1,2,4,6],those:1,through:5,time:[1,2],timeout:[1,2],timestamp:6,to_agave_uri:2,to_dict:4,to_text_pem:4,to_unicod:3,token:[1,4],token_callback:4,token_usernam:4,tokencommand:4,top:1,tree:2,tri:[1,4],trivial:3,tupl:2,turn:3,type:4,uid:1,underli:4,unicod:3,uniqu:4,uniqueid:[0,3],unless:4,unlimit:1,updat:[1,2,3],updatepem:2,upload:2,uploadfil:2,uri:[0,1,4],url:[1,2,4],usag:[1,4,6],use:[1,2],use_nonc:4,useapi:2,used:6,user:[1,3,4,5],usernam:[1,2,3,4,5],uses:1,using:[2,4],utc:1,utcnow:1,utexa:4,util:[0,4],uuid4:4,uuid:[1,4],valid:[1,2,4,5],validate_acl:4,validate_messag:1,valu:[1,4,5],variabl:1,variou:5,verifi:[4,5],version:[0,6],via:2,view:5,wai:1,wait:[1,2],wait_for_file_statu:2,walk:2,web:4,webhook:1,whatev:6,where:2,whether:2,which:[1,3,4],whose:4,within:1,work:2,world:2,write:4,yet:2,you:4},titles:["reactors","reactors package","reactors.agaveutils package","reactors.aliases package","reactors.aliases.agavedb package","reactors.aliases.agavedb.tests package","reactors.logtypes package","Welcome to Reactors SDK documentation!"],titleterms:{agavedb:[4,5],agavefixtur:5,agaveutil:2,alias:[3,4,5],content:[1,2,3,4,5,6],document:7,entiti:2,file:2,indic:7,jsonmessag:1,keyval:4,logstash:6,logstash_asyncio:6,logstash_futures_sess:6,logstash_sync:6,logtyp:6,main:6,modul:[1,2,3,4,5,6],packag:[1,2,3,4,5,6],process:1,reactor:[0,1,2,3,4,5,6,7],recurs:2,runtim:1,sdk:7,slack:6,storag:1,store:3,submodul:[1,2,3,4,5,6],subpackag:[1,3,4],tabl:7,test:5,test_keyv:5,testdata:5,uniqueid:[1,4],uri:2,util:[1,2],version:1,welcom:7}}) \ No newline at end of file +Search.setIndex({docnames:["api-ref/modules","api-ref/reactors","api-ref/reactors.agaveutils","api-ref/reactors.cli","api-ref/reactors.logtypes","api-ref/reactors.runtime","api-ref/reactors.validation","getting-started/index","index","logging/index"],envversion:{"sphinx.domains.c":2,"sphinx.domains.changeset":1,"sphinx.domains.citation":1,"sphinx.domains.cpp":4,"sphinx.domains.index":1,"sphinx.domains.javascript":2,"sphinx.domains.math":2,"sphinx.domains.python":3,"sphinx.domains.rst":2,"sphinx.domains.std":2,sphinx:56},filenames:["api-ref/modules.rst","api-ref/reactors.rst","api-ref/reactors.agaveutils.rst","api-ref/reactors.cli.rst","api-ref/reactors.logtypes.rst","api-ref/reactors.runtime.rst","api-ref/reactors.validation.rst","getting-started/index.md","index.rst","logging/index.md"],objects:{"":{reactors:[1,0,0,"-"]},"reactors.agaveutils":{entity:[2,0,0,"-"],files:[2,0,0,"-"],reactors:[2,0,0,"-"],recursive:[2,0,0,"-"],uri:[2,0,0,"-"],utils:[2,0,0,"-"]},"reactors.agaveutils.entity":{is_appid:[2,1,1,""]},"reactors.agaveutils.files":{agave_download_file:[2,1,1,""],agave_mkdir:[2,1,1,""],agave_upload_file:[2,1,1,""],get:[2,1,1,""],mkdir:[2,1,1,""],process_agave_httperror:[2,1,1,""],put:[2,1,1,""],random:[2,1,1,""],wait_for_file_status:[2,1,1,""]},"reactors.agaveutils.reactors":{message_reactor:[2,1,1,""]},"reactors.agaveutils.recursive":{PemAgent:[2,2,1,""],random:[2,1,1,""]},"reactors.agaveutils.recursive.PemAgent":{enumerate2:[2,3,1,""],grant:[2,3,1,""],listdir:[2,3,1,""],updatepem:[2,3,1,""],walk:[2,3,1,""]},"reactors.agaveutils.uri":{agave_uri_from_http:[2,1,1,""],from_agave_uri:[2,1,1,""],from_tacc_s3_uri:[2,1,1,""],http_uri_from_agave:[2,1,1,""],to_agave_uri:[2,1,1,""]},"reactors.agaveutils.utils":{get_api_server:[2,1,1,""],get_api_token:[2,1,1,""],get_api_username:[2,1,1,""]},"reactors.cli":{run:[3,0,0,"-"],usage:[3,0,0,"-"]},"reactors.cli.run":{docstring:[3,1,1,""],load_function:[3,1,1,""],run:[3,1,1,""]},"reactors.cli.usage":{usage:[3,1,1,""]},"reactors.config":{get_redaction_strings:[1,1,1,""],parse_boolean:[1,1,1,""],read_config:[1,1,1,""]},"reactors.logtypes":{loggly:[4,0,0,"-"],loggly_futures_session:[4,0,0,"-"],logstash:[4,0,0,"-"],logstash_futures_session:[4,0,0,"-"],logstash_sync:[4,0,0,"-"],main:[4,0,0,"-"],slack:[4,0,0,"-"]},"reactors.logtypes.loggly_futures_session":{LogglyHandler:[4,2,1,""],bg_cb:[4,1,1,""],response_hook_noop:[4,1,1,""]},"reactors.logtypes.loggly_futures_session.LogglyHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.logstash_futures_session":{LogstashPlaintextHandler:[4,2,1,""],bg_cb:[4,1,1,""],response_hook_noop:[4,1,1,""]},"reactors.logtypes.logstash_futures_session.LogstashPlaintextHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.logstash_sync":{LogstashPlaintextHandler:[4,2,1,""]},"reactors.logtypes.logstash_sync.LogstashPlaintextHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.logtypes.main":{RedactingFormatter:[4,2,1,""],get_log_file:[4,1,1,""],get_log_file_strategy:[4,1,1,""],get_logger:[4,1,1,""],get_loggly_logger:[4,1,1,""],get_screen_logger:[4,1,1,""],get_slack_logger:[4,1,1,""]},"reactors.logtypes.main.RedactingFormatter":{converter:[4,3,1,""],format:[4,3,1,""]},"reactors.logtypes.slack":{SlackHandler:[4,2,1,""],bg_cb:[4,1,1,""]},"reactors.logtypes.slack.SlackHandler":{emit:[4,3,1,""],get_full_message:[4,3,1,""]},"reactors.runtime":{abaco:[5,0,0,"-"],base:[5,0,0,"-"],messaging:[5,0,0,"-"],reactor:[5,0,0,"-"],sessions:[5,0,0,"-"],validating:[5,0,0,"-"],webhooks:[5,0,0,"-"]},"reactors.runtime.abaco":{is_hashid:[5,1,1,""],load_client:[5,1,1,""],load_context:[5,1,1,""],new_hashid:[5,1,1,""]},"reactors.runtime.base":{BaseReactor:[5,2,1,""]},"reactors.runtime.base.BaseReactor":{CONFIG_NAMESPACE:[5,4,1,""],EXIT_CODE:[5,4,1,""],MOCK_ENABLED:[5,4,1,""],NICKNAME_SEP:[5,4,1,""],NICKNAME_WORDS:[5,4,1,""],TAPIS_OPTIONAL:[5,4,1,""],elapsed:[5,3,1,""],on_failure:[5,3,1,""],on_success:[5,3,1,""]},"reactors.runtime.messaging":{Messaging:[5,2,1,""]},"reactors.runtime.messaging.Messaging":{MAX_ELAPSED:[5,4,1,""],MAX_RETRIES:[5,4,1,""],RETRY_DELAY:[5,4,1,""],RETRY_MAX_DELAY:[5,4,1,""],actor_property:[5,3,1,""],message_provenance:[5,3,1,""],message_vars:[5,3,1,""],resolve_alias:[5,3,1,""],send_message:[5,3,1,""]},"reactors.runtime.reactor":{Reactor:[5,2,1,""]},"reactors.runtime.sessions":{get_session:[5,1,1,""]},"reactors.runtime.validating":{Validation:[5,2,1,""]},"reactors.runtime.validating.Validation":{AUTO_VALIDATE_BINARY:[5,4,1,""],AUTO_VALIDATE_CONTEXT:[5,4,1,""],AUTO_VALIDATE_MESSAGE:[5,4,1,""],classify_binary:[5,3,1,""],classify_context:[5,3,1,""],classify_message:[5,3,1,""],validate:[5,3,1,""],validate_binary:[5,3,1,""],validate_context:[5,3,1,""],validate_message:[5,3,1,""]},"reactors.runtime.webhooks":{Webhooks:[5,2,1,""]},"reactors.runtime.webhooks.Webhooks":{DEFAULT_NONCE_MAX_USES:[5,4,1,""],DEFAULT_NONCE_PERMISSION:[5,4,1,""],add_nonce:[5,3,1,""],create_webhook:[5,3,1,""],delete_all_nonces:[5,3,1,""],delete_nonce:[5,3,1,""],delete_webhook:[5,3,1,""],get_nonce:[5,3,1,""],list_nonces:[5,3,1,""]},"reactors.utils":{get_host_ip:[1,1,1,""],microseconds:[1,1,1,""],utcnow:[1,1,1,""]},"reactors.validation":{binary:[6,0,0,"-"],context:[6,0,0,"-"],jsondoc:[6,0,0,"-"],message:[6,0,0,"-"]},"reactors.validation.binary":{classify_binary:[6,1,1,""],validate:[6,1,1,""],validate_binary:[6,1,1,""]},"reactors.validation.context":{classify_context:[6,1,1,""],validate:[6,1,1,""],validate_context:[6,1,1,""]},"reactors.validation.jsondoc":{classify_document:[6,1,1,""],find_schema_files:[6,1,1,""],formatChecker:[6,2,1,""],id_for_schema:[6,1,1,""],is_default:[6,1,1,""],load_schema:[6,1,1,""],load_schemas:[6,1,1,""],schema_from_url:[6,1,1,""],schema_id:[6,1,1,""],schema_ids:[6,1,1,""],validate_document:[6,1,1,""],vars_from_schema:[6,1,1,""]},"reactors.validation.message":{classify_message:[6,1,1,""],find_message_schema_files:[6,1,1,""],validate:[6,1,1,""],validate_message:[6,1,1,""]},reactors:{agaveutils:[2,0,0,"-"],cli:[3,0,0,"-"],config:[1,0,0,"-"],logtypes:[4,0,0,"-"],runtime:[5,0,0,"-"],utils:[1,0,0,"-"],validation:[6,0,0,"-"],version:[1,0,0,"-"]}},objnames:{"0":["py","module","Python module"],"1":["py","function","Python function"],"2":["py","class","Python class"],"3":["py","method","Python method"],"4":["py","attribute","Python attribute"]},objtypes:{"0":"py:module","1":"py:function","2":"py:class","3":"py:method","4":"py:attribute"},terms:{"0":[2,5,6],"00":1,"01":1,"05t18":1,"1":[2,5,6],"2":[2,5],"2018":1,"290790":1,"3":4,"300":[2,5],"32":5,"3rd":9,"4":4,"40":1,"5":[2,5],"55":1,"boolean":1,"case":5,"class":[2,4,5,6],"default":[5,6],"do":[2,4,5],"final":2,"function":[2,3,5,6],"import":2,"int":5,"long":2,"new":[2,5],"public":2,"return":[1,2,4,5,6],"true":[1,2,5,6],"try":2,"var":5,A:[5,6],If:[2,4],In:9,It:2,Not:2,On:[5,6],The:[2,4,5],_:6,_format:6,_reactor:5,abaco:[0,1,2,6],about:2,absolut:2,abspath:2,accept:6,access_token:2,accord:6,account:5,actor:[2,5],actor_id:5,actor_properti:5,actorid:[2,5],actual:4,add:5,add_nonc:5,addit:6,address:1,ag:2,against:5,agav:2,agave_cli:1,agave_download_fil:2,agave_mkdir:2,agave_upload_fil:2,agave_uri_from_http:2,agaveabsolutepath:2,agavecli:2,agavedestpath:2,agaveerror:[2,5],agavepi:2,agaveuri:2,agaveutil:[0,1],agavewatchpath:2,alia:[4,5],alias:5,all:[2,5],allow:5,alreadi:2,alwai:2,an:[2,5,6],ani:[5,6],anoth:2,anyth:4,api:[2,5],app:[2,5],append:4,appid:[2,5],appli:2,ar:[2,4,5],arg:[3,4],argument:[5,6],assum:5,assumpt:5,attempt:[2,5],attribut:[4,5],authent:2,auto_validate_binari:5,auto_validate_context:5,auto_validate_messag:5,avail:4,avoid:2,backoff:2,base:[0,1,2,4,6],basepath:2,basereactor:5,basic:[1,5],befor:[2,4],between:5,bg_cb:4,binari:[0,1,5],bool:[2,5,6],bootstrap:5,broken:1,built:6,call:[2,4],caller:2,can:[4,5],candid:2,cannot:6,captur:5,carri:4,caveat:2,check_binari:5,check_context:5,check_format:6,check_messag:5,child:2,choos:2,classifi:6,classify_binari:[5,6],classify_context:[5,6],classify_docu:6,classify_messag:[5,6],cli:[0,1],client:[2,5],client_secret:4,cloud:5,code:5,common:2,compat:4,complet:2,composit:5,comput:4,config:[0,4],config_namespac:5,configur:1,conform:6,construct:[2,5],contain:6,content:0,context:[0,1,5],convert:[2,4],correctli:2,coupl:4,crawl:2,creat:[2,5],create_webhook:5,creation:2,credenti:5,current:[1,2,4,5],cwd:2,data:2,date:1,debug:[4,5],default_nonce_max_us:5,default_nonce_permiss:5,defin:6,delai:2,delet:5,delete_all_nonc:5,delete_nonc:5,delete_webhook:5,deploi:5,deriv:5,destin:2,determin:[4,5],dict:[5,6],dictionari:[4,6],dir:2,directori:2,directorypath:2,dirnam:[2,6],dirpath:2,docstr:3,document:6,doe:[5,6],don:4,download:2,eho:6,elaps:5,emit:4,enabl:6,enable_mock:5,enforc:6,entiti:[0,1],enumerate2:2,env:1,environ:[1,2,5],epoch:4,equival:[1,5],error:[2,5,6],event:4,exampl:1,exceed:2,except:[2,4,5,6],exceptionobject:5,execut:[2,5],executionid:5,exit:5,exit_cod:5,expens:2,exponenti:2,express:4,extern:5,failmessag:5,failur:[2,5],fals:[2,4,5,6],favor:1,fetch:[5,6],field:[4,6],fifo:5,file:[0,1,5,6],filenam:2,filename_glob:6,filesystem:[2,6],filter_priv:6,find_message_schema_fil:6,find_schema_fil:6,fire:[2,4],fn:3,forc:6,force_additional_properti:6,forget:[2,4],format:[1,2,4,6],formatcheck:6,formatexcept:4,formatt:4,formattim:4,forward:4,fpath:2,from:[1,2,3,5,6],from_agave_uri:2,from_tacc_s3_uri:2,func:5,gener:[5,6],get:[2,5,8],get_api_serv:2,get_api_token:2,get_api_usernam:2,get_full_messag:4,get_host_ip:1,get_log_fil:4,get_log_file_strategi:4,get_logg:4,get_loggly_logg:4,get_nonc:5,get_redaction_str:1,get_screen_logg:4,get_sess:5,get_slack_logg:4,get_stderr_logg:4,getmessag:4,given:[5,6],global:5,gmt:4,gmtime:4,grant:2,handl:2,handler:4,hash:[5,6],have:5,helper:[2,5],here:2,host:[1,2],http:[2,4],http_error_object:2,http_uri_from_agav:2,httperror:2,httpuri:2,id:[2,5,6],id_for_schema:6,identifi:[5,6],ignoreerror:[2,5],imdepot:2,implement:[2,4,5,6],importdata:2,includ:9,index:8,inf:5,info:2,inform:4,initi:[2,5],inject_id:6,instead:4,integr:5,intend:4,inter:5,interv:2,introspect:5,involv:2,ip:1,is_appid:2,is_default:6,is_hashid:5,its:[2,5],json:[5,6],jsondoc:[0,1],jsonschema:[5,6],k:4,kei:5,keyword:5,kind:5,kwarg:[4,5],least:2,legaci:4,level:5,like:2,linktyp:2,list:[5,6],list_nonc:5,listdir:2,load:[3,6],load_client:5,load_context:5,load_funct:3,load_schema:6,local:5,localfilenam:2,locat:6,log:[4,5,8],log_fil:4,log_level:4,logfil:4,logger:4,loggli:[0,1,9],loggly_futures_sess:[0,1],logglyhandl:4,loglevel:2,logrecord:4,logstash:[0,1],logstash_futures_sess:[0,1],logstash_sync:[0,1],logstashplaintexthandl:4,logtyp:[0,1],look:[2,5],main:[0,1,3],make:2,manag:[1,2],mark:5,match:[5,6],max_allow:6,max_elaps:5,max_retri:5,maximum:5,maxtim:2,maxus:5,me:5,media:2,merg:[1,5],messag:[0,1,2,4],message_proven:5,message_reactor:2,message_schema:6,message_var:5,method:[4,5],microsecond:[1,5],min_allow:6,mix:5,mkdir:2,mock_en:5,mode:5,model:5,modul:[0,8],movement:2,multipli:2,n:6,name:[2,4],namespac:[1,2,5],new_hashid:5,nickname_sep:5,nickname_word:5,nonc:5,nonceid:5,none:[1,2,3,4,5,6],noop:4,note:[5,6],noth:2,notimplementederror:4,number:[2,5],object:[2,4,5],on_failur:5,on_success:5,one:[2,6],onli:[4,5],oper:[2,4],operand:4,optim:5,option:4,otherwis:2,out:4,overload:2,overrid:[1,5],own:5,p:2,packag:[0,7,8],page:8,param:5,paramet:[2,5],parent:2,pars:[1,2],parse_boolean:1,parti:9,pass:[4,5],passed_env:5,path:[2,5,6],pattern:4,pem:2,pemag:2,perform:5,permiss:[2,5,6],place:2,places_list:1,platform:[4,5],point:2,poll:2,posit:[2,5],post:4,preparatori:4,present:5,privat:5,private_prefix:6,process_agave_httperror:2,project:6,properti:[5,6],proven:5,provid:[6,7],put:2,py2:4,py:3,python:[1,2,6,7],quick:7,rais:[2,4,5,6],random:2,rather:6,reach:2,reactor:7,read:[2,5],read_config:1,real:2,rec:2,record:4,recurs:[0,1],redact:[1,4,5],redactingformatt:4,ref:6,refer:6,relat:5,remot:2,report:4,represent:[5,6],request:2,requir:2,resid:2,resolv:[5,6],resolve_alia:5,resourc:2,resp:4,respons:4,response_hook_noop:4,result:5,retri:[2,5],retriev:5,retry_delai:5,retry_max_delai:5,retrydelai:5,retrymax:5,retrymaxattempt:5,review:9,right:1,role:5,root:2,run:[0,1,5],runtim:[0,1],s3:2,s:[1,2,4,5],safe:5,same:2,sanit:4,schema:[5,6],schema_as_dict:6,schema_from_url:6,schema_id:6,script:3,sd2e:6,search:[6,8],second:[4,5],section:9,self:5,send:[2,4,5],send_messag:5,sender_env:5,sendertag:[2,5],sensit:5,sent:5,sequenc:2,server:2,servic:9,sess:4,session:[0,1],set:[4,5],shortcut:5,should:2,sinc:[2,4,5],slack:[0,1,9],slackhandl:4,so:[2,4],special:[2,4],specif:5,specifi:[2,4],src:6,start:8,state:2,static_path:6,statu:2,stderr:4,step:4,storag:2,storagesystem:2,str:[2,5,6],string:[2,4,5],structur:5,stub:5,style:5,subclass:4,submodul:0,subnam:4,subpackag:0,subproperti:6,succeed:6,success:[2,5],successmessag:5,suppli:5,support:4,swallow:5,sync:[2,5],synchron:2,system:2,systemid:2,t:4,tacc:[2,5,6],tacconfig:1,take:4,tapi:5,tapis_opt:5,task:2,termin:2,text:[1,2,4,5,6],textstr:2,than:6,thei:[4,5],thi:[2,4,5,6,7,9],those:5,time:[1,2,4,5],timeout:2,timestamp:4,tm_gmtoff:4,tm_hour:4,tm_isdst:4,tm_mdai:4,tm_min:4,tm_mon:4,tm_sec:4,tm_wdai:4,tm_ydai:4,tm_year:4,tm_zone:4,to_agave_uri:2,top:5,transform:6,tree:2,tupl:[2,4],tutori:7,type:1,uid:5,up:[2,4,5],updat:[1,2],updatepem:2,upload:2,uploadfil:2,uri:[0,1,5],url:[2,4,5,6],urlparam:5,us:[2,4,5],usag:[0,1,4,7],useapi:2,user:[5,6],usernam:[2,5],usestim:4,utc:[1,4],utcnow:1,util:0,valid:[0,1,2],validate_binari:[5,6],validate_context:[5,6],validate_docu:6,validate_messag:[5,6],validationerror:6,validator_funct:5,valu:[1,5,6],variabl:5,vars_from_schema:6,verifi:[5,6],version:[0,4],via:2,wa:5,wait:[2,5],wait_for_file_statu:2,walk:2,we:[2,5,9],webhook:[0,1],what:5,whatev:4,when:4,where:2,whether:[2,6],which:[4,5,6],work:[2,6],world:2,x:2,yet:2,yield:4},titles:["reactors","reactors package","reactors.agaveutils package","reactors.cli package","reactors.logtypes package","reactors.runtime package","reactors.validation package","Getting Started","Welcome to Reactors SDK documentation!","Logging with Reactors"],titleterms:{abaco:5,agaveutil:2,api:8,base:5,binari:6,cli:3,config:1,content:[1,2,3,4,5,6],context:6,document:8,entiti:2,file:2,get:7,indic:8,jsondoc:6,log:9,loggli:4,loggly_futures_sess:4,logstash:4,logstash_futures_sess:4,logstash_sync:4,logtyp:4,main:4,messag:[5,6],modul:[1,2,3,4,5,6],packag:[1,2,3,4,5,6],reactor:[0,1,2,3,4,5,6,8,9],recurs:2,refer:8,run:3,runtim:5,sdk:8,session:5,slack:4,start:7,submodul:[1,2,3,4,5,6],subpackag:1,tabl:8,uri:2,usag:3,util:[1,2],valid:[5,6],version:1,webhook:5,welcom:8}}) \ No newline at end of file diff --git a/docsrc/api-ref/reactors.aliases.agavedb.rst b/docsrc/api-ref/reactors.aliases.agavedb.rst deleted file mode 100644 index 71f303d..0000000 --- a/docsrc/api-ref/reactors.aliases.agavedb.rst +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb package -================================ - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb.tests - -Submodules ----------- - -reactors.aliases.agavedb.keyval module --------------------------------------- - -.. automodule:: reactors.aliases.agavedb.keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.uniqueid module ----------------------------------------- - -.. automodule:: reactors.aliases.agavedb.uniqueid - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/api-ref/reactors.aliases.agavedb.tests.rst b/docsrc/api-ref/reactors.aliases.agavedb.tests.rst deleted file mode 100644 index 6bf5367..0000000 --- a/docsrc/api-ref/reactors.aliases.agavedb.tests.rst +++ /dev/null @@ -1,37 +0,0 @@ -reactors.aliases.agavedb.tests package -====================================== - -Submodules ----------- - -reactors.aliases.agavedb.tests.agavefixtures module ---------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.agavefixtures - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.test\_keyval module --------------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.test_keyval - :members: - :undoc-members: - :show-inheritance: - -reactors.aliases.agavedb.tests.testdata module ----------------------------------------------- - -.. automodule:: reactors.aliases.agavedb.tests.testdata - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases.agavedb.tests - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/api-ref/reactors.aliases.rst b/docsrc/api-ref/reactors.aliases.rst deleted file mode 100644 index db80925..0000000 --- a/docsrc/api-ref/reactors.aliases.rst +++ /dev/null @@ -1,29 +0,0 @@ -reactors.aliases package -======================== - -Subpackages ------------ - -.. toctree:: - :maxdepth: 4 - - reactors.aliases.agavedb - -Submodules ----------- - -reactors.aliases.store module ------------------------------ - -.. automodule:: reactors.aliases.store - :members: - :undoc-members: - :show-inheritance: - -Module contents ---------------- - -.. automodule:: reactors.aliases - :members: - :undoc-members: - :show-inheritance: diff --git a/docsrc/api-ref/reactors.cli.rst b/docsrc/api-ref/reactors.cli.rst new file mode 100644 index 0000000..b669b8c --- /dev/null +++ b/docsrc/api-ref/reactors.cli.rst @@ -0,0 +1,29 @@ +reactors.cli package +==================== + +Submodules +---------- + +reactors.cli.run module +----------------------- + +.. automodule:: reactors.cli.run + :members: + :undoc-members: + :show-inheritance: + +reactors.cli.usage module +------------------------- + +.. automodule:: reactors.cli.usage + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.cli + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/api-ref/reactors.logtypes.rst b/docsrc/api-ref/reactors.logtypes.rst index e9aaf9f..d00a94f 100644 --- a/docsrc/api-ref/reactors.logtypes.rst +++ b/docsrc/api-ref/reactors.logtypes.rst @@ -4,18 +4,26 @@ reactors.logtypes package Submodules ---------- -reactors.logtypes.logstash module ---------------------------------- +reactors.logtypes.loggly module +------------------------------- -.. automodule:: reactors.logtypes.logstash +.. automodule:: reactors.logtypes.loggly :members: :undoc-members: :show-inheritance: -reactors.logtypes.logstash\_asyncio module ------------------------------------------- +reactors.logtypes.loggly\_futures\_session module +------------------------------------------------- -.. automodule:: reactors.logtypes.logstash_asyncio +.. automodule:: reactors.logtypes.loggly_futures_session + :members: + :undoc-members: + :show-inheritance: + +reactors.logtypes.logstash module +--------------------------------- + +.. automodule:: reactors.logtypes.logstash :members: :undoc-members: :show-inheritance: diff --git a/docsrc/api-ref/reactors.rst b/docsrc/api-ref/reactors.rst index aba558d..f5c0b2e 100644 --- a/docsrc/api-ref/reactors.rst +++ b/docsrc/api-ref/reactors.rst @@ -8,48 +8,18 @@ Subpackages :maxdepth: 4 reactors.agaveutils - reactors.aliases + reactors.cli reactors.logtypes + reactors.runtime + reactors.validation Submodules ---------- -reactors.jsonmessages module ----------------------------- +reactors.config module +---------------------- -.. automodule:: reactors.jsonmessages - :members: - :undoc-members: - :show-inheritance: - -reactors.process module ------------------------ - -.. automodule:: reactors.process - :members: - :undoc-members: - :show-inheritance: - -reactors.runtime module ------------------------ - -.. automodule:: reactors.runtime - :members: - :undoc-members: - :show-inheritance: - -reactors.storage module ------------------------ - -.. automodule:: reactors.storage - :members: - :undoc-members: - :show-inheritance: - -reactors.uniqueid module ------------------------- - -.. automodule:: reactors.uniqueid +.. automodule:: reactors.config :members: :undoc-members: :show-inheritance: diff --git a/docsrc/api-ref/reactors.runtime.rst b/docsrc/api-ref/reactors.runtime.rst new file mode 100644 index 0000000..853efa1 --- /dev/null +++ b/docsrc/api-ref/reactors.runtime.rst @@ -0,0 +1,69 @@ +reactors.runtime package +======================== + +Submodules +---------- + +reactors.runtime.abaco module +----------------------------- + +.. automodule:: reactors.runtime.abaco + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.base module +---------------------------- + +.. automodule:: reactors.runtime.base + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.messaging module +--------------------------------- + +.. automodule:: reactors.runtime.messaging + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.reactor module +------------------------------- + +.. automodule:: reactors.runtime.reactor + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.sessions module +-------------------------------- + +.. automodule:: reactors.runtime.sessions + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.validating module +---------------------------------- + +.. automodule:: reactors.runtime.validating + :members: + :undoc-members: + :show-inheritance: + +reactors.runtime.webhooks module +-------------------------------- + +.. automodule:: reactors.runtime.webhooks + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.runtime + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/api-ref/reactors.validation.rst b/docsrc/api-ref/reactors.validation.rst new file mode 100644 index 0000000..0225729 --- /dev/null +++ b/docsrc/api-ref/reactors.validation.rst @@ -0,0 +1,45 @@ +reactors.validation package +=========================== + +Submodules +---------- + +reactors.validation.binary module +--------------------------------- + +.. automodule:: reactors.validation.binary + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.context module +---------------------------------- + +.. automodule:: reactors.validation.context + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.jsondoc module +---------------------------------- + +.. automodule:: reactors.validation.jsondoc + :members: + :undoc-members: + :show-inheritance: + +reactors.validation.message module +---------------------------------- + +.. automodule:: reactors.validation.message + :members: + :undoc-members: + :show-inheritance: + +Module contents +--------------- + +.. automodule:: reactors.validation + :members: + :undoc-members: + :show-inheritance: diff --git a/docsrc/conf.py b/docsrc/conf.py index 67c0b99..a32178c 100644 --- a/docsrc/conf.py +++ b/docsrc/conf.py @@ -19,12 +19,13 @@ # -- Project information ----------------------------------------------------- -project = 'reactors_sdk' -copyright = '2020, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan' +project = 'python-reactors' +copyright = '2021, Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan' author = 'Matthew Vaughn, Ethan Ho, Shweta Gopaulakrishnan' +version = '1.0.0' # The full version, including alpha/beta/rc tags -release = '0.7.0' +release = '1.0.0' # -- General configuration --------------------------------------------------- @@ -36,17 +37,32 @@ # Add any paths that contain templates here, relative to this directory. templates_path = ['_templates'] +source_suffix = ['.rst', '.md'] +# source_suffix = '.rst' + +# The master toctree document. +master_doc = 'index' + +# 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 pattern also affects 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 = None + # -- 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 = 'classic' +html_theme = 'sphinx_rtd_theme' # 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, diff --git a/docsrc/getting-started/index.md b/docsrc/getting-started/index.md new file mode 100644 index 0000000..9b7c248 --- /dev/null +++ b/docsrc/getting-started/index.md @@ -0,0 +1,3 @@ +# Getting Started + +This tutorial will provide a quick tutorial for usage of the `python-reactors` package. \ No newline at end of file diff --git a/docsrc/index.rst b/docsrc/index.rst index 5e7fc37..ed81c70 100644 --- a/docsrc/index.rst +++ b/docsrc/index.rst @@ -8,7 +8,15 @@ Welcome to Reactors SDK documentation! .. toctree:: :maxdepth: 2 - :caption: API Reference: + :caption: Reactors SDK + + getting-started/index.md + logging/index.md + + +.. toctree:: + :maxdepth: 2 + :caption: API Reference api-ref/modules.rst diff --git a/docsrc/logging/index.md b/docsrc/logging/index.md new file mode 100644 index 0000000..9f0f036 --- /dev/null +++ b/docsrc/logging/index.md @@ -0,0 +1,3 @@ +# Logging with Reactors + +In this section, we will review logging with Reactors, including logging to 3rd party services such as Slack and Loggly. \ No newline at end of file diff --git a/poetry.lock b/poetry.lock index 4667a89..cd2ba2c 100644 --- a/poetry.lock +++ b/poetry.lock @@ -5,7 +5,6 @@ description = "SDK for TACC Tapis (formerly Agave)" category = "main" optional = false python-versions = "*" -develop = false [package.dependencies] arrow = ">=0.15.5" @@ -23,12 +22,6 @@ requests-toolbelt = ">=0.9.1" six = ">=1.12.0" websocket-client = ">=0.57.0" -[package.source] -type = "git" -url = "https://github.com/TACC/agavepy" -reference = "master" -resolved_reference = "bd948d6da9be7e84b5330aa4d5fe1e07d82ad34c" - [[package]] name = "arrow" version = "1.1.1" @@ -84,7 +77,7 @@ python-versions = "*" [[package]] name = "charset-normalizer" -version = "2.0.4" +version = "2.0.6" description = "The Real First Universal Charset Detector. Open, modern and actively maintained alternative to Chardet." category = "main" optional = false @@ -95,11 +88,11 @@ unicode_backport = ["unicodedata2"] [[package]] name = "cloudpickle" -version = "1.6.0" +version = "2.0.0" description = "Extended pickling support for Python objects" category = "main" optional = false -python-versions = ">=3.5" +python-versions = ">=3.6" [[package]] name = "colorama" @@ -133,7 +126,7 @@ requests = "*" [[package]] name = "decorator" -version = "5.0.9" +version = "5.1.0" description = "Decorators for Humans" category = "main" optional = false @@ -160,7 +153,7 @@ test = ["pytest (>=2.1.0)"] [[package]] name = "hypothesis" -version = "6.17.4" +version = "6.23.1" description = "A library for property-based testing" category = "dev" optional = false @@ -235,7 +228,7 @@ i18n = ["Babel (>=2.7)"] [[package]] name = "jsonschema" -version = "3.2.0" +version = "4.0.0" description = "An implementation of JSON Schema validation for Python" category = "main" optional = false @@ -244,12 +237,11 @@ python-versions = "*" [package.dependencies] attrs = ">=17.4.0" importlib-metadata = {version = "*", markers = "python_version < \"3.8\""} -pyrsistent = ">=0.14.0" -six = ">=1.11.0" +pyrsistent = ">=0.14.0,<0.17.0 || >0.17.0,<0.17.1 || >0.17.1,<0.17.2 || >0.17.2" [package.extras] -format = ["idna", "jsonpointer (>1.13)", "rfc3987", "strict-rfc3339", "webcolors"] -format_nongpl = ["idna", "jsonpointer (>1.13)", "webcolors", "rfc3986-validator (>0.1.0)", "rfc3339-validator"] +format = ["fqdn", "idna", "isoduration", "jsonpointer (>1.13)", "rfc3339-validator", "rfc3987", "uri-template", "webcolors (>=1.11)"] +format_nongpl = ["fqdn", "idna", "isoduration", "jsonpointer (>1.13)", "rfc3339-validator", "rfc3986-validator (>0.1.0)", "uri-template", "webcolors (>=1.11)"] [[package]] name = "markupsafe" @@ -537,7 +529,7 @@ test = ["websockets"] [[package]] name = "zipp" -version = "3.5.0" +version = "3.6.0" description = "Backport of pathlib-compatible object wrapper for zip files" category = "main" optional = false @@ -550,10 +542,13 @@ testing = ["pytest (>=4.6)", "pytest-checkdocs (>=2.4)", "pytest-flake8", "pytes [metadata] lock-version = "1.1" python-versions = ">=3.6" -content-hash = "d29bc31b783af0253a7256bbc78033b9da3e2bc290d9060bfbb24248a4f90158" +content-hash = "db679c27c1a599cf3e9a0c198951cca0a2e0edfd56850145c6cea4270ee49300" [metadata.files] -agavepy = [] +agavepy = [ + {file = "agavepy-1.0.0a11-py2.py3-none-any.whl", hash = "sha256:343c66c0ef7c83023cf70f122b8d55f36a1aadb93a9f5c469fa7e4900e00be64"}, + {file = "agavepy-1.0.0a11.tar.gz", hash = "sha256:0a8643031c5d86cdee30d94f9b3ab5be7093761176cd53d37048545c30750f27"}, +] arrow = [ {file = "arrow-1.1.1-py3-none-any.whl", hash = "sha256:77a60a4db5766d900a2085ce9074c5c7b8e2c99afeaa98ad627637ff6f292510"}, {file = "arrow-1.1.1.tar.gz", hash = "sha256:dee7602f6c60e3ec510095b5e301441bc56288cb8f51def14dcb3079f623823a"}, @@ -575,12 +570,12 @@ certifi = [ {file = "certifi-2021.5.30.tar.gz", hash = "sha256:2bbf76fd432960138b3ef6dda3dde0544f27cbf8546c458e60baf371917ba9ee"}, ] charset-normalizer = [ - {file = "charset-normalizer-2.0.4.tar.gz", hash = "sha256:f23667ebe1084be45f6ae0538e4a5a865206544097e4e8bbcacf42cd02a348f3"}, - {file = "charset_normalizer-2.0.4-py3-none-any.whl", hash = "sha256:0c8911edd15d19223366a194a513099a302055a962bca2cec0f54b8b63175d8b"}, + {file = "charset-normalizer-2.0.6.tar.gz", hash = "sha256:5ec46d183433dcbd0ab716f2d7f29d8dee50505b3fdb40c6b985c7c4f5a3591f"}, + {file = "charset_normalizer-2.0.6-py3-none-any.whl", hash = "sha256:5d209c0a931f215cee683b6445e2d77677e7e75e159f78def0db09d68fafcaa6"}, ] cloudpickle = [ - {file = "cloudpickle-1.6.0-py3-none-any.whl", hash = "sha256:3a32d0eb0bc6f4d0c57fbc4f3e3780f7a81e6fee0fa935072884d58ae8e1cc7c"}, - {file = "cloudpickle-1.6.0.tar.gz", hash = "sha256:9bc994f9e9447593bd0a45371f0e7ac7333710fcf64a4eb9834bf149f4ef2f32"}, + {file = "cloudpickle-2.0.0-py3-none-any.whl", hash = "sha256:6b2df9741d06f43839a3275c4e6632f7df6487a1f181f5f46a052d3c917c3d11"}, + {file = "cloudpickle-2.0.0.tar.gz", hash = "sha256:5cd02f3b417a783ba84a4ec3e290ff7929009fe51f6405423cfccfadd43ba4a4"}, ] colorama = [ {file = "colorama-0.4.4-py2.py3-none-any.whl", hash = "sha256:9f47eda37229f68eee03b24b9748937c7dc3868f906e8ba69fbcbdd3bc5dc3e2"}, @@ -644,8 +639,8 @@ curlify = [ {file = "curlify-2.2.1.tar.gz", hash = "sha256:0d3f02e7235faf952de8ef45ef469845196d30632d5838bcd5aee217726ddd6d"}, ] decorator = [ - {file = "decorator-5.0.9-py3-none-any.whl", hash = "sha256:6e5c199c16f7a9f0e3a61a4a54b3d27e7dad0dbdde92b944426cb20914376323"}, - {file = "decorator-5.0.9.tar.gz", hash = "sha256:72ecfba4320a893c53f9706bebb2d55c270c1e51a28789361aa93e4a21319ed5"}, + {file = "decorator-5.1.0-py3-none-any.whl", hash = "sha256:7b12e7c3c6ab203a29e157335e9122cb03de9ab7264b137594103fd4a683b374"}, + {file = "decorator-5.1.0.tar.gz", hash = "sha256:e59913af105b9860aa2c8d3272d9de5a56a4e608db9a2f167a8480b323d529a7"}, ] future = [ {file = "future-0.18.2.tar.gz", hash = "sha256:b1bead90b70cf6ec3f0710ae53a525360fa360d306a86583adc6bf83a4db537d"}, @@ -655,8 +650,8 @@ hashids = [ {file = "hashids-1.3.1.tar.gz", hash = "sha256:6c3dc775e65efc2ce2c157a65acb776d634cb814598f406469abef00ae3f635c"}, ] hypothesis = [ - {file = "hypothesis-6.17.4-py3-none-any.whl", hash = "sha256:47b86bda10dba94bb9e5733dcb4df27fca8b421ebe81aad2516441272c374c10"}, - {file = "hypothesis-6.17.4.tar.gz", hash = "sha256:fd5a2207aaaaea430fe1dd0fc4392edb1c95cb21034fdf69231113cc1ab86fa0"}, + {file = "hypothesis-6.23.1-py3-none-any.whl", hash = "sha256:e1c5c4a7e1f9a1a1da03cf6a148703333c468fb036f3cd785da1210c23648a4f"}, + {file = "hypothesis-6.23.1.tar.gz", hash = "sha256:23a1b0488aec5719e2f9e399342e10f30d497cbb9fd39470ef0975c1b502ae35"}, ] idna = [ {file = "idna-3.2-py3-none-any.whl", hash = "sha256:14475042e284991034cb48e06f6851428fb14c4dc953acd9be9a5e95c7b6dd7a"}, @@ -675,8 +670,8 @@ jinja2 = [ {file = "Jinja2-3.0.1.tar.gz", hash = "sha256:703f484b47a6af502e743c9122595cc812b0271f661722403114f71a79d0f5a4"}, ] jsonschema = [ - {file = "jsonschema-3.2.0-py2.py3-none-any.whl", hash = "sha256:4e5b3cf8216f577bee9ce139cbe72eca3ea4f292ec60928ff24758ce626cd163"}, - {file = "jsonschema-3.2.0.tar.gz", hash = "sha256:c8a85b28d377cc7737e46e2d9f2b4f44ee3c0e1deac6bf46ddefc7187d30797a"}, + {file = "jsonschema-4.0.0-py3-none-any.whl", hash = "sha256:c773028c649441ab980015b5b622f4cd5134cf563daaf0235ca4b73cc3734f20"}, + {file = "jsonschema-4.0.0.tar.gz", hash = "sha256:bc51325b929171791c42ebc1c70b9713eb134d3bb8ebd5474c8b659b15be6d86"}, ] markupsafe = [ {file = "MarkupSafe-2.0.1-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:f9081981fe268bd86831e5c75f7de206ef275defcb82bc70740ae6dc507aee51"}, @@ -859,6 +854,6 @@ websocket-client = [ {file = "websocket_client-1.2.1-py2.py3-none-any.whl", hash = "sha256:0133d2f784858e59959ce82ddac316634229da55b498aac311f1620567a710ec"}, ] zipp = [ - {file = "zipp-3.5.0-py3-none-any.whl", hash = "sha256:957cfda87797e389580cb8b9e3870841ca991e2125350677b2ca83a0e99390a3"}, - {file = "zipp-3.5.0.tar.gz", hash = "sha256:f5812b1e007e48cff63449a5e9f4e7ebea716b4111f9c4f9a645f91d579bf0c4"}, + {file = "zipp-3.6.0-py3-none-any.whl", hash = "sha256:9fe5ea21568a0a70e50f273397638d39b03353731e6cbbb3fd8502a33fec40bc"}, + {file = "zipp-3.6.0.tar.gz", hash = "sha256:71c644c5369f4a6e07636f0aa966270449561fcea2e3d6747b8d23efaa9d7832"}, ] diff --git a/pyproject.toml b/pyproject.toml index f5deb29..b37bfb7 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,7 +1,7 @@ [tool.poetry] name = "reactors" -version = "0.8.0" -description = "Software development kit for Tapis actors" +version = "1.0.0" +description = "Software development kit for Tapis Actors" authors = ["Matthew W Vaughn", "Shweta Gopaulakrishnan", "Ethan Ho "] license = "bsd-2-clause" include = ["src/**/*.yml", "src/**/*.jsonschema", "src/**/*.j2"] @@ -9,7 +9,7 @@ include = ["src/**/*.yml", "src/**/*.jsonschema", "src/**/*.j2"] [tool.poetry.dependencies] python = ">=3.6" -agavepy = {git = "https://github.com/TACC/agavepy", rev = "master"} +agavepy = {version = "^1.*", allow-prereleases = true} requests_futures = ">=0.9.7" pytz = "^2021.1" petname = ">=2.2" diff --git a/src/reactors/logglytoken.py b/src/reactors/logglytoken.py deleted file mode 100644 index cf02570..0000000 --- a/src/reactors/logglytoken.py +++ /dev/null @@ -1,21 +0,0 @@ -"""Get LOGGLY CUSTOMER_TOKEN from Github Secrets and pass it to config.yml""" - -import os -import agavepy -import validators -import yaml - -def parse_token(): - customer_token = os.environ.get("CUSTOMER_TOKEN_LOGGLY") - - with open('src/reactors/config.yml', 'r') as yamlfile: - cur_yaml = yaml.safe_load(yamlfile) - cur_yaml['loggly']['customer_token'] = customer_token - - if cur_yaml: - with open('src/reactors/config.yml', 'w') as yamlfile: - yaml.safe_dump(cur_yaml, yamlfile) - - print("parsed") - -parse_token() diff --git a/src/reactors/logtypes/logstash_asyncio.py b/src/reactors/logtypes/logstash_asyncio.py deleted file mode 100644 index 64c53ea..0000000 --- a/src/reactors/logtypes/logstash_asyncio.py +++ /dev/null @@ -1,7 +0,0 @@ -import json -import requests -import logging -import logging.handlers -import traceback -import asyncio -import aiohttp diff --git a/src/reactors/process.py b/src/reactors/process.py deleted file mode 100644 index 8db45d5..0000000 --- a/src/reactors/process.py +++ /dev/null @@ -1,56 +0,0 @@ -"""Run subprocesses from within Python""" -import subprocess -import warnings -from datetime import datetime - -from attrdict import AttrDict - -DEFAULT_TIMEOUT = 60 # 1 minute - - -def run(command_list=[], permissive=False, shell=False, timeout=None): - """ - Run a child or subshell process. - - Parameters: - exec_params - list - Parameters in exec form - permissive - bool - Ignore errors - shell - bool - Execute command by way of a shell - - Usage: - # List system logs directory - params=['ls', '-alth', '/var/log'] - process.run(params) - - Returns an AttrDict of response attributes. - - """ - - # timeout remains unimplemented pending Py3-nativity - if timeout is not None: - warnings.warn('timeout parameter for run is not implemented') - - response = AttrDict( - {'cmdline': None, - 'return_code': None, - 'output': None, - 'elapsed_msec': None}) - - t1 = datetime.now() - try: - response.cmdline = subprocess.list2cmdline(command_list) - out_bytes = subprocess.check_output( - command_list, shell=shell, stderr=subprocess.STDOUT) - response.output = out_bytes.decode() - response.return_code = 0 - t2 = datetime.now() - delta = t2 - t1 - response.elapsed_msec = int(delta.total_seconds() * 1000) - except subprocess.CalledProcessError as e: - if permissive is True: - response.output = e.output - response.return_code = e.returncode - else: - raise OSError(e) - - return response diff --git a/src/reactors/runtime/base.py b/src/reactors/runtime/base.py index 4f20d7b..e64b0be 100644 --- a/src/reactors/runtime/base.py +++ b/src/reactors/runtime/base.py @@ -5,10 +5,9 @@ import petname from attrdict import AttrDict -from reactors import agaveutils, logtypes -from reactors.config import get_redaction_strings, parse_boolean, read_config -from reactors.utils import get_host_ip, microseconds - +from .. import agaveutils, logtypes +from ..config import get_redaction_strings, parse_boolean, read_config +from ..utils import get_host_ip, microseconds from . import abaco, sessions diff --git a/src/reactors/runtime/messaging.py b/src/reactors/runtime/messaging.py index 49acc78..d8e6077 100644 --- a/src/reactors/runtime/messaging.py +++ b/src/reactors/runtime/messaging.py @@ -2,11 +2,13 @@ """ import os import sys +from time import sleep from agavepy.agave import Agave, AgaveError from requests.exceptions import HTTPError from . import abaco, sessions from .base import BaseReactor +from .. import agaveutils class Messaging(BaseReactor): @@ -202,13 +204,11 @@ def send_message(self, actorId, message, self.logger.error(exception_err.format(resolved_actor_id)) attempts = attempts + 1 - # random-skew exponential backoff with limit if attempts <= retryMaxAttempts: self.logger.debug('pause {} sec then try again'.format(retry)) sleep(retry) - retry = retry * (1.0 + random()) - if retry > RETRY_MAX_DELAY: - retry = RETRY_MAX_DELAY + if retry > self.RETRY_MAX_DELAY: + retry = self.RETRY_MAX_DELAY # Maximum attempts have passed and execution_id was not returned if ignoreErrors: diff --git a/src/reactors/version.py b/src/reactors/version.py index 81e3dc5..1e83699 100644 --- a/src/reactors/version.py +++ b/src/reactors/version.py @@ -1,2 +1 @@ -# THIS FILE IS GENERATED FROM SETUP.PY -version = '0.8.0' \ No newline at end of file +version = '1.0.0' \ No newline at end of file diff --git a/tests/test_jsonmessage.py b/tests/test_jsonmessage.py index 8cf01fd..cdb60e1 100644 --- a/tests/test_jsonmessage.py +++ b/tests/test_jsonmessage.py @@ -110,7 +110,7 @@ def test_classify_simple_json_message(change_test_dir, tests_data_dir): message = json.loads('{"aljsydgflajsgd": "FKJHFKJLJHGL345678"}') matches = message_module.classify_message(message, permissive=True) logging.debug(f"matches: {pf(matches)}") - assert len(matches) == 1 + assert len(matches) >= 1 assert 'Default' in [m['$id'] for m in matches]