From 83f1a486f82a54e97bf3ba01f011d171c353d13a Mon Sep 17 00:00:00 2001 From: Shyue Ping Ong Date: Tue, 1 Aug 2023 14:09:49 -0700 Subject: [PATCH] Update docs. --- .github/workflows/test.yml | 4 + README.rst => README.md | 13 +- docs/.nojekyll | 0 docs/Gemfile | 35 + docs/Gemfile.lock | 266 + {docs_rst => docs}/Makefile | 0 docs/_config.yml | 21 + docs/_includes/footer_custom.html | 1 + docs/_includes/nav_footer_custom.html | 1 + docs/_modules/index.html | 102 - docs/_modules/monty/bisect.html | 141 - docs/_modules/monty/collections.html | 299 - docs/_modules/monty/design_patterns.html | 204 - docs/_modules/monty/dev.html | 326 - docs/_modules/monty/fnmatch.html | 140 - docs/_modules/monty/fractions.html | 145 - docs/_modules/monty/functools.html | 501 - docs/_modules/monty/inspect.html | 181 - docs/_modules/monty/io.html | 344 - docs/_modules/monty/itertools.html | 174 - docs/_modules/monty/json.html | 698 - docs/_modules/monty/logging.html | 161 - docs/_modules/monty/math.html | 114 - docs/_modules/monty/msgpack.html | 102 - docs/_modules/monty/multiprocessing.html | 117 - docs/_modules/monty/operator.html | 112 - docs/_modules/monty/os.html | 134 - docs/_modules/monty/os/path.html | 206 - docs/_modules/monty/pprint.html | 206 - docs/_modules/monty/re.html | 128 - docs/_modules/monty/serialization.html | 204 - docs/_modules/monty/shutil.html | 227 - docs/_modules/monty/string.html | 220 - docs/_modules/monty/subprocess.html | 181 - docs/_modules/monty/tempfile.html | 205 - docs/_modules/monty/termcolor.html | 285 - .../_sphinx_javascript_frameworks_compat.js | 134 - docs/_static/ajax-loader.gif | Bin 673 -> 0 bytes docs/_static/basic.css | 903 -- docs/_static/comment-bright.png | Bin 756 -> 0 bytes docs/_static/comment-close.png | Bin 829 -> 0 bytes docs/_static/comment.png | Bin 641 -> 0 bytes docs/_static/doctools.js | 156 - docs/_static/documentation_options.js | 14 - docs/_static/down-pressed.png | Bin 222 -> 0 bytes docs/_static/down.png | Bin 202 -> 0 bytes docs/_static/file.png | Bin 286 -> 0 bytes docs/_static/flasky.css | 445 - docs/_static/jquery-3.1.0.js | 10074 -------------- docs/_static/jquery-3.2.1.js | 10253 --------------- docs/_static/jquery-3.4.1.js | 10598 --------------- docs/_static/jquery-3.5.1.js | 10872 --------------- docs/_static/jquery-3.6.0.js | 10881 ---------------- docs/_static/jquery.js | 2 - docs/_static/language_data.js | 199 - docs/_static/minus.png | Bin 90 -> 0 bytes docs/_static/plus.png | Bin 90 -> 0 bytes docs/_static/pygments.css | 74 - docs/_static/searchtools.js | 566 - docs/_static/small_flask.css | 90 - docs/_static/sphinx_highlight.js | 144 - docs/_static/underscore-1.12.0.js | 2027 --- docs/_static/underscore-1.13.1.js | 2042 --- docs/_static/underscore-1.3.1.js | 999 -- docs/_static/underscore.js | 6 - docs/_static/up-pressed.png | Bin 214 -> 0 bytes docs/_static/up.png | Bin 203 -> 0 bytes docs/_static/websupport.js | 808 -- docs/_themes/README.html | 108 - docs/changelog.html | 714 - docs_rst/changelog.rst => docs/changelog.md | 265 +- docs/conf.py | 60 + docs/genindex.html | 760 -- docs/index.html | 489 - docs/index.md | 35 + {docs_rst => docs}/make.bat | 0 docs/modules.html | 327 - docs/monty.bisect.html | 149 - docs/monty.bisect.md | 34 + docs/monty.collections.html | 313 - docs/monty.collections.md | 197 + docs/monty.design_patterns.html | 169 - docs/monty.design_patterns.md | 59 + docs/monty.dev.html | 201 - docs/monty.dev.md | 102 + docs/monty.fnmatch.html | 153 - docs/monty.fnmatch.md | 48 + docs/monty.fractions.html | 158 - docs/monty.fractions.md | 61 + docs/monty.functools.html | 270 - docs/monty.functools.md | 159 + docs/monty.html | 356 - docs/monty.inspect.html | 157 - docs/monty.inspect.md | 49 + docs/monty.io.html | 248 - docs/monty.io.md | 147 + docs/monty.itertools.html | 180 - docs/monty.itertools.md | 77 + docs/monty.json.html | 375 - docs/monty.json.md | 270 + docs/monty.logging.html | 138 - docs/monty.logging.md | 33 + docs/monty.math.html | 145 - docs/monty.math.md | 48 + docs/monty.md | 441 + docs/monty.msgpack.html | 127 - docs/monty.msgpack.md | 21 + docs/monty.multiprocessing.html | 131 - docs/monty.multiprocessing.md | 38 + docs/monty.operator.html | 121 - docs/monty.operator.md | 18 + docs/monty.os.html | 165 - docs/monty.os.md | 51 + docs/monty.os.path.html | 172 - docs/monty.os.path.md | 82 + docs/monty.pprint.html | 207 - docs/monty.pprint.md | 110 + docs/monty.re.html | 146 - docs/monty.re.md | 55 + docs/monty.serialization.html | 166 - docs/monty.serialization.md | 77 + docs/monty.shutil.html | 229 - docs/monty.shutil.md | 121 + docs/monty.string.html | 248 - docs/monty.string.md | 154 + docs/monty.subprocess.html | 171 - docs/monty.subprocess.md | 58 + docs/monty.tempfile.html | 181 - docs/monty.tempfile.md | 97 + docs/monty.termcolor.html | 150 - docs/monty.termcolor.md | 58 + docs/objects.inv | Bin 1915 -> 0 bytes docs/py-modindex.html | 226 - docs/search.html | 100 - docs/searchindex.js | 1 - docs_rst/_templates/layout.html | 10 - docs_rst/_themes/LICENSE | 45 - docs_rst/_themes/README.rst | 25 - docs_rst/_themes/flask_theme_support.py | 87 - docs_rst/_themes/kr/layout.html | 16 - docs_rst/_themes/kr/relations.html | 19 - docs_rst/_themes/kr/static/flasky.css_t | 445 - docs_rst/_themes/kr/static/small_flask.css | 90 - docs_rst/_themes/kr/theme.conf | 7 - docs_rst/_themes/kr_small/layout.html | 22 - docs_rst/_themes/kr_small/static/flasky.css_t | 287 - docs_rst/_themes/kr_small/theme.conf | 10 - docs_rst/conf.py | 296 - docs_rst/index.rst | 144 - docs_rst/modules.rst | 7 - docs_rst/monty.bisect.rst | 7 - docs_rst/monty.collections.rst | 7 - docs_rst/monty.design_patterns.rst | 7 - docs_rst/monty.dev.rst | 7 - docs_rst/monty.fnmatch.rst | 7 - docs_rst/monty.fractions.rst | 7 - docs_rst/monty.functools.rst | 7 - docs_rst/monty.inspect.rst | 7 - docs_rst/monty.io.rst | 7 - docs_rst/monty.itertools.rst | 7 - docs_rst/monty.json.rst | 7 - docs_rst/monty.logging.rst | 7 - docs_rst/monty.math.rst | 7 - docs_rst/monty.msgpack.rst | 7 - docs_rst/monty.multiprocessing.rst | 7 - docs_rst/monty.operator.rst | 7 - docs_rst/monty.os.path.rst | 7 - docs_rst/monty.os.rst | 18 - docs_rst/monty.pprint.rst | 7 - docs_rst/monty.re.rst | 7 - docs_rst/monty.rst | 49 - docs_rst/monty.serialization.rst | 7 - docs_rst/monty.shutil.rst | 7 - docs_rst/monty.string.rst | 7 - docs_rst/monty.subprocess.rst | 7 - docs_rst/monty.tempfile.rst | 7 - docs_rst/monty.termcolor.rst | 7 - tasks.py | 72 +- 178 files changed, 3220 insertions(+), 77065 deletions(-) rename README.rst => README.md (55%) delete mode 100644 docs/.nojekyll create mode 100644 docs/Gemfile create mode 100644 docs/Gemfile.lock rename {docs_rst => docs}/Makefile (100%) create mode 100644 docs/_config.yml create mode 100644 docs/_includes/footer_custom.html create mode 100644 docs/_includes/nav_footer_custom.html delete mode 100644 docs/_modules/index.html delete mode 100644 docs/_modules/monty/bisect.html delete mode 100644 docs/_modules/monty/collections.html delete mode 100644 docs/_modules/monty/design_patterns.html delete mode 100644 docs/_modules/monty/dev.html delete mode 100644 docs/_modules/monty/fnmatch.html delete mode 100644 docs/_modules/monty/fractions.html delete mode 100644 docs/_modules/monty/functools.html delete mode 100644 docs/_modules/monty/inspect.html delete mode 100644 docs/_modules/monty/io.html delete mode 100644 docs/_modules/monty/itertools.html delete mode 100644 docs/_modules/monty/json.html delete mode 100644 docs/_modules/monty/logging.html delete mode 100644 docs/_modules/monty/math.html delete mode 100644 docs/_modules/monty/msgpack.html delete mode 100644 docs/_modules/monty/multiprocessing.html delete mode 100644 docs/_modules/monty/operator.html delete mode 100644 docs/_modules/monty/os.html delete mode 100644 docs/_modules/monty/os/path.html delete mode 100644 docs/_modules/monty/pprint.html delete mode 100644 docs/_modules/monty/re.html delete mode 100644 docs/_modules/monty/serialization.html delete mode 100644 docs/_modules/monty/shutil.html delete mode 100644 docs/_modules/monty/string.html delete mode 100644 docs/_modules/monty/subprocess.html delete mode 100644 docs/_modules/monty/tempfile.html delete mode 100644 docs/_modules/monty/termcolor.html delete mode 100644 docs/_static/_sphinx_javascript_frameworks_compat.js delete mode 100644 docs/_static/ajax-loader.gif delete mode 100644 docs/_static/basic.css delete mode 100644 docs/_static/comment-bright.png delete mode 100644 docs/_static/comment-close.png delete mode 100644 docs/_static/comment.png delete mode 100644 docs/_static/doctools.js delete mode 100644 docs/_static/documentation_options.js delete mode 100644 docs/_static/down-pressed.png delete mode 100644 docs/_static/down.png delete mode 100644 docs/_static/file.png delete mode 100644 docs/_static/flasky.css delete mode 100644 docs/_static/jquery-3.1.0.js delete mode 100644 docs/_static/jquery-3.2.1.js delete mode 100644 docs/_static/jquery-3.4.1.js delete mode 100644 docs/_static/jquery-3.5.1.js delete mode 100644 docs/_static/jquery-3.6.0.js delete mode 100644 docs/_static/jquery.js delete mode 100644 docs/_static/language_data.js delete mode 100644 docs/_static/minus.png delete mode 100644 docs/_static/plus.png delete mode 100644 docs/_static/pygments.css delete mode 100644 docs/_static/searchtools.js delete mode 100644 docs/_static/small_flask.css delete mode 100644 docs/_static/sphinx_highlight.js delete mode 100644 docs/_static/underscore-1.12.0.js delete mode 100644 docs/_static/underscore-1.13.1.js delete mode 100644 docs/_static/underscore-1.3.1.js delete mode 100644 docs/_static/underscore.js delete mode 100644 docs/_static/up-pressed.png delete mode 100644 docs/_static/up.png delete mode 100644 docs/_static/websupport.js delete mode 100644 docs/_themes/README.html delete mode 100644 docs/changelog.html rename docs_rst/changelog.rst => docs/changelog.md (78%) create mode 100644 docs/conf.py delete mode 100644 docs/genindex.html delete mode 100644 docs/index.html create mode 100644 docs/index.md rename {docs_rst => docs}/make.bat (100%) delete mode 100644 docs/modules.html delete mode 100644 docs/monty.bisect.html create mode 100644 docs/monty.bisect.md delete mode 100644 docs/monty.collections.html create mode 100644 docs/monty.collections.md delete mode 100644 docs/monty.design_patterns.html create mode 100644 docs/monty.design_patterns.md delete mode 100644 docs/monty.dev.html create mode 100644 docs/monty.dev.md delete mode 100644 docs/monty.fnmatch.html create mode 100644 docs/monty.fnmatch.md delete mode 100644 docs/monty.fractions.html create mode 100644 docs/monty.fractions.md delete mode 100644 docs/monty.functools.html create mode 100644 docs/monty.functools.md delete mode 100644 docs/monty.html delete mode 100644 docs/monty.inspect.html create mode 100644 docs/monty.inspect.md delete mode 100644 docs/monty.io.html create mode 100644 docs/monty.io.md delete mode 100644 docs/monty.itertools.html create mode 100644 docs/monty.itertools.md delete mode 100644 docs/monty.json.html create mode 100644 docs/monty.json.md delete mode 100644 docs/monty.logging.html create mode 100644 docs/monty.logging.md delete mode 100644 docs/monty.math.html create mode 100644 docs/monty.math.md create mode 100644 docs/monty.md delete mode 100644 docs/monty.msgpack.html create mode 100644 docs/monty.msgpack.md delete mode 100644 docs/monty.multiprocessing.html create mode 100644 docs/monty.multiprocessing.md delete mode 100644 docs/monty.operator.html create mode 100644 docs/monty.operator.md delete mode 100644 docs/monty.os.html create mode 100644 docs/monty.os.md delete mode 100644 docs/monty.os.path.html create mode 100644 docs/monty.os.path.md delete mode 100644 docs/monty.pprint.html create mode 100644 docs/monty.pprint.md delete mode 100644 docs/monty.re.html create mode 100644 docs/monty.re.md delete mode 100644 docs/monty.serialization.html create mode 100644 docs/monty.serialization.md delete mode 100644 docs/monty.shutil.html create mode 100644 docs/monty.shutil.md delete mode 100644 docs/monty.string.html create mode 100644 docs/monty.string.md delete mode 100644 docs/monty.subprocess.html create mode 100644 docs/monty.subprocess.md delete mode 100644 docs/monty.tempfile.html create mode 100644 docs/monty.tempfile.md delete mode 100644 docs/monty.termcolor.html create mode 100644 docs/monty.termcolor.md delete mode 100644 docs/objects.inv delete mode 100644 docs/py-modindex.html delete mode 100644 docs/search.html delete mode 100644 docs/searchindex.js delete mode 100644 docs_rst/_templates/layout.html delete mode 100755 docs_rst/_themes/LICENSE delete mode 100755 docs_rst/_themes/README.rst delete mode 100755 docs_rst/_themes/flask_theme_support.py delete mode 100755 docs_rst/_themes/kr/layout.html delete mode 100755 docs_rst/_themes/kr/relations.html delete mode 100755 docs_rst/_themes/kr/static/flasky.css_t delete mode 100755 docs_rst/_themes/kr/static/small_flask.css delete mode 100755 docs_rst/_themes/kr/theme.conf delete mode 100755 docs_rst/_themes/kr_small/layout.html delete mode 100755 docs_rst/_themes/kr_small/static/flasky.css_t delete mode 100755 docs_rst/_themes/kr_small/theme.conf delete mode 100644 docs_rst/conf.py delete mode 100644 docs_rst/index.rst delete mode 100644 docs_rst/modules.rst delete mode 100644 docs_rst/monty.bisect.rst delete mode 100644 docs_rst/monty.collections.rst delete mode 100644 docs_rst/monty.design_patterns.rst delete mode 100644 docs_rst/monty.dev.rst delete mode 100644 docs_rst/monty.fnmatch.rst delete mode 100644 docs_rst/monty.fractions.rst delete mode 100644 docs_rst/monty.functools.rst delete mode 100644 docs_rst/monty.inspect.rst delete mode 100644 docs_rst/monty.io.rst delete mode 100644 docs_rst/monty.itertools.rst delete mode 100644 docs_rst/monty.json.rst delete mode 100644 docs_rst/monty.logging.rst delete mode 100644 docs_rst/monty.math.rst delete mode 100644 docs_rst/monty.msgpack.rst delete mode 100644 docs_rst/monty.multiprocessing.rst delete mode 100644 docs_rst/monty.operator.rst delete mode 100644 docs_rst/monty.os.path.rst delete mode 100644 docs_rst/monty.os.rst delete mode 100644 docs_rst/monty.pprint.rst delete mode 100644 docs_rst/monty.re.rst delete mode 100644 docs_rst/monty.rst delete mode 100644 docs_rst/monty.serialization.rst delete mode 100644 docs_rst/monty.shutil.rst delete mode 100644 docs_rst/monty.string.rst delete mode 100644 docs_rst/monty.subprocess.rst delete mode 100644 docs_rst/monty.tempfile.rst delete mode 100644 docs_rst/monty.termcolor.rst diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 52460d47c..95aff67b3 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -27,3 +27,7 @@ jobs: - name: pytest run: | pytest --cov=monty --cov-report html:coverage_reports monty tests + - name: Upload coverage reports to Codecov + uses: codecov/codecov-action@v3 + env: + CODECOV_TOKEN: ${{ secrets.CODECOV_TOKEN }} \ No newline at end of file diff --git a/README.rst b/README.md similarity index 55% rename from README.rst rename to README.md index 988a1f8b0..52cf835f2 100644 --- a/README.rst +++ b/README.md @@ -1,9 +1,10 @@ -Monty: Python Made Even Easier -============================== +[![GitHub license](https://img.shields.io/github/license/materialsvirtuallab/monty)](https://github.com/materialsvirtuallab/monty/blob/main/LICENSE) +[![Linting](https://github.com/materialsvirtuallab/monty/workflows/Linting/badge.svg)](https://github.com/materialsvirtuallab/monty/workflows/Linting/badge.svg) +[![Testing](https://github.com/materialsvirtuallab/monty/workflows/Testing/badge.svg)](https://github.com/materialsvirtuallab/monty/workflows/Testing/badge.svg) +[![Downloads](https://pepy.tech/badge/monty)](https://pepy.tech/project/monty) +[![codecov](https://codecov.io/gh/materialsvirtuallab/monty/branch/main/graph/badge.svg?token=3V3O79GODQ)](https://codecov.io/gh/materialsvirtuallab/monty) -.. image:: https://travis-ci.org/materialsvirtuallab/monty.png?branch=master -.. image:: https://coveralls.io/repos/github/materialsvirtuallab/monty/badge.svg?branch=master -.. image:: https://anaconda.org/conda-forge/monty/badges/downloads.svg +# Monty: Python Made Even Easier Monty is the missing complement to Python. Monty implements supplementary useful functions for Python that are not part of the standard library. @@ -25,4 +26,4 @@ be a resource to collect the best solutions. Monty supports Python 3.x. -Please visit the `official docs `_ for more information. +Please visit the [official docs](https://materialsvirtuallab.github.io/monty) for more information. diff --git a/docs/.nojekyll b/docs/.nojekyll deleted file mode 100644 index e69de29bb..000000000 diff --git a/docs/Gemfile b/docs/Gemfile new file mode 100644 index 000000000..68a681b41 --- /dev/null +++ b/docs/Gemfile @@ -0,0 +1,35 @@ +source "https://rubygems.org" +# Hello! This is where you manage which Jekyll version is used to run. +# When you want to use a different version, change it below, save the +# file and run `bundle install`. Run Jekyll with `bundle exec`, like so: +# +# bundle exec jekyll serve +# +# This will help ensure the proper Jekyll version is running. +# Happy Jekylling! +# gem "jekyll", "~> 4.3.2" +# This is the default theme for new Jekyll sites. You may change this to anything you like. +gem "minima", "~> 2.5" +# If you want to use GitHub Pages, remove the "gem "jekyll"" above and +# uncomment the line below. To upgrade, run `bundle update github-pages`. +gem "github-pages", group: :jekyll_plugins +# If you have any plugins, put them here! +group :jekyll_plugins do + gem "jekyll-feed", "~> 0.12" +end + +# Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem +# and associated library. +platforms :mingw, :x64_mingw, :mswin, :jruby do + gem "tzinfo", ">= 1", "< 3" + gem "tzinfo-data" +end + +# Performance-booster for watching directories on Windows +gem "wdm", "~> 0.1.1", :platforms => [:mingw, :x64_mingw, :mswin] + +# Lock `http_parser.rb` gem to `v0.6.x` on JRuby builds since newer versions of the gem +# do not have a Java counterpart. +gem "http_parser.rb", "~> 0.6.0", :platforms => [:jruby] + +gem "webrick", "~> 1.8" diff --git a/docs/Gemfile.lock b/docs/Gemfile.lock new file mode 100644 index 000000000..2763cfeb1 --- /dev/null +++ b/docs/Gemfile.lock @@ -0,0 +1,266 @@ +GEM + remote: https://rubygems.org/ + specs: + activesupport (7.0.6) + concurrent-ruby (~> 1.0, >= 1.0.2) + i18n (>= 1.6, < 2) + minitest (>= 5.1) + tzinfo (~> 2.0) + addressable (2.8.4) + public_suffix (>= 2.0.2, < 6.0) + coffee-script (2.4.1) + coffee-script-source + execjs + coffee-script-source (1.11.1) + colorator (1.1.0) + commonmarker (0.23.10) + concurrent-ruby (1.2.2) + dnsruby (1.70.0) + simpleidn (~> 0.2.1) + em-websocket (0.5.3) + eventmachine (>= 0.12.9) + http_parser.rb (~> 0) + ethon (0.16.0) + ffi (>= 1.15.0) + eventmachine (1.2.7) + execjs (2.8.1) + faraday (2.7.10) + faraday-net_http (>= 2.0, < 3.1) + ruby2_keywords (>= 0.0.4) + faraday-net_http (3.0.2) + ffi (1.15.5) + forwardable-extended (2.6.0) + gemoji (3.0.1) + github-pages (228) + github-pages-health-check (= 1.17.9) + jekyll (= 3.9.3) + jekyll-avatar (= 0.7.0) + jekyll-coffeescript (= 1.1.1) + jekyll-commonmark-ghpages (= 0.4.0) + jekyll-default-layout (= 0.1.4) + jekyll-feed (= 0.15.1) + jekyll-gist (= 1.5.0) + jekyll-github-metadata (= 2.13.0) + jekyll-include-cache (= 0.2.1) + jekyll-mentions (= 1.6.0) + jekyll-optional-front-matter (= 0.3.2) + jekyll-paginate (= 1.1.0) + jekyll-readme-index (= 0.3.0) + jekyll-redirect-from (= 0.16.0) + jekyll-relative-links (= 0.6.1) + jekyll-remote-theme (= 0.4.3) + jekyll-sass-converter (= 1.5.2) + jekyll-seo-tag (= 2.8.0) + jekyll-sitemap (= 1.4.0) + jekyll-swiss (= 1.0.0) + jekyll-theme-architect (= 0.2.0) + jekyll-theme-cayman (= 0.2.0) + jekyll-theme-dinky (= 0.2.0) + jekyll-theme-hacker (= 0.2.0) + jekyll-theme-leap-day (= 0.2.0) + jekyll-theme-merlot (= 0.2.0) + jekyll-theme-midnight (= 0.2.0) + jekyll-theme-minimal (= 0.2.0) + jekyll-theme-modernist (= 0.2.0) + jekyll-theme-primer (= 0.6.0) + jekyll-theme-slate (= 0.2.0) + jekyll-theme-tactile (= 0.2.0) + jekyll-theme-time-machine (= 0.2.0) + jekyll-titles-from-headings (= 0.5.3) + jemoji (= 0.12.0) + kramdown (= 2.3.2) + kramdown-parser-gfm (= 1.1.0) + liquid (= 4.0.4) + mercenary (~> 0.3) + minima (= 2.5.1) + nokogiri (>= 1.13.6, < 2.0) + rouge (= 3.26.0) + terminal-table (~> 1.4) + github-pages-health-check (1.17.9) + addressable (~> 2.3) + dnsruby (~> 1.60) + octokit (~> 4.0) + public_suffix (>= 3.0, < 5.0) + typhoeus (~> 1.3) + html-pipeline (2.14.3) + activesupport (>= 2) + nokogiri (>= 1.4) + http_parser.rb (0.8.0) + i18n (1.14.1) + concurrent-ruby (~> 1.0) + jekyll (3.9.3) + addressable (~> 2.4) + colorator (~> 1.0) + em-websocket (~> 0.5) + i18n (>= 0.7, < 2) + jekyll-sass-converter (~> 1.0) + jekyll-watch (~> 2.0) + kramdown (>= 1.17, < 3) + liquid (~> 4.0) + mercenary (~> 0.3.3) + pathutil (~> 0.9) + rouge (>= 1.7, < 4) + safe_yaml (~> 1.0) + jekyll-avatar (0.7.0) + jekyll (>= 3.0, < 5.0) + jekyll-coffeescript (1.1.1) + coffee-script (~> 2.2) + coffee-script-source (~> 1.11.1) + jekyll-commonmark (1.4.0) + commonmarker (~> 0.22) + jekyll-commonmark-ghpages (0.4.0) + commonmarker (~> 0.23.7) + jekyll (~> 3.9.0) + jekyll-commonmark (~> 1.4.0) + rouge (>= 2.0, < 5.0) + jekyll-default-layout (0.1.4) + jekyll (~> 3.0) + jekyll-feed (0.15.1) + jekyll (>= 3.7, < 5.0) + jekyll-gist (1.5.0) + octokit (~> 4.2) + jekyll-github-metadata (2.13.0) + jekyll (>= 3.4, < 5.0) + octokit (~> 4.0, != 4.4.0) + jekyll-include-cache (0.2.1) + jekyll (>= 3.7, < 5.0) + jekyll-mentions (1.6.0) + html-pipeline (~> 2.3) + jekyll (>= 3.7, < 5.0) + jekyll-optional-front-matter (0.3.2) + jekyll (>= 3.0, < 5.0) + jekyll-paginate (1.1.0) + jekyll-readme-index (0.3.0) + jekyll (>= 3.0, < 5.0) + jekyll-redirect-from (0.16.0) + jekyll (>= 3.3, < 5.0) + jekyll-relative-links (0.6.1) + jekyll (>= 3.3, < 5.0) + jekyll-remote-theme (0.4.3) + addressable (~> 2.0) + jekyll (>= 3.5, < 5.0) + jekyll-sass-converter (>= 1.0, <= 3.0.0, != 2.0.0) + rubyzip (>= 1.3.0, < 3.0) + jekyll-sass-converter (1.5.2) + sass (~> 3.4) + jekyll-seo-tag (2.8.0) + jekyll (>= 3.8, < 5.0) + jekyll-sitemap (1.4.0) + jekyll (>= 3.7, < 5.0) + jekyll-swiss (1.0.0) + jekyll-theme-architect (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-cayman (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-dinky (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-hacker (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-leap-day (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-merlot (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-midnight (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-minimal (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-modernist (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-primer (0.6.0) + jekyll (> 3.5, < 5.0) + jekyll-github-metadata (~> 2.9) + jekyll-seo-tag (~> 2.0) + jekyll-theme-slate (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-tactile (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-theme-time-machine (0.2.0) + jekyll (> 3.5, < 5.0) + jekyll-seo-tag (~> 2.0) + jekyll-titles-from-headings (0.5.3) + jekyll (>= 3.3, < 5.0) + jekyll-watch (2.2.1) + listen (~> 3.0) + jemoji (0.12.0) + gemoji (~> 3.0) + html-pipeline (~> 2.2) + jekyll (>= 3.0, < 5.0) + kramdown (2.3.2) + rexml + kramdown-parser-gfm (1.1.0) + kramdown (~> 2.0) + liquid (4.0.4) + listen (3.8.0) + rb-fsevent (~> 0.10, >= 0.10.3) + rb-inotify (~> 0.9, >= 0.9.10) + mercenary (0.3.6) + minima (2.5.1) + jekyll (>= 3.5, < 5.0) + jekyll-feed (~> 0.9) + jekyll-seo-tag (~> 2.1) + minitest (5.16.3) + nokogiri (1.15.3-arm64-darwin) + racc (~> 1.4) + octokit (4.25.1) + faraday (>= 1, < 3) + sawyer (~> 0.9) + pathutil (0.16.2) + forwardable-extended (~> 2.6) + public_suffix (4.0.7) + racc (1.6.2) + rb-fsevent (0.11.2) + rb-inotify (0.10.1) + ffi (~> 1.0) + rexml (3.2.5) + rouge (3.26.0) + ruby2_keywords (0.0.5) + rubyzip (2.3.2) + safe_yaml (1.0.5) + sass (3.7.4) + sass-listen (~> 4.0.0) + sass-listen (4.0.0) + rb-fsevent (~> 0.9, >= 0.9.4) + rb-inotify (~> 0.9, >= 0.9.7) + sawyer (0.9.2) + addressable (>= 2.3.5) + faraday (>= 0.17.3, < 3) + simpleidn (0.2.1) + unf (~> 0.1.4) + terminal-table (1.8.0) + unicode-display_width (~> 1.1, >= 1.1.1) + typhoeus (1.4.0) + ethon (>= 0.9.0) + tzinfo (2.0.6) + concurrent-ruby (~> 1.0) + unf (0.1.4) + unf_ext + unf_ext (0.0.8.2) + unicode-display_width (1.8.0) + webrick (1.8.1) + +PLATFORMS + arm64-darwin-22 + +DEPENDENCIES + github-pages + http_parser.rb (~> 0.6.0) + jekyll-feed (~> 0.12) + minima (~> 2.5) + tzinfo (>= 1, < 3) + tzinfo-data + wdm (~> 0.1.1) + webrick (~> 1.8) + +BUNDLED WITH + 2.4.17 diff --git a/docs_rst/Makefile b/docs/Makefile similarity index 100% rename from docs_rst/Makefile rename to docs/Makefile diff --git a/docs/_config.yml b/docs/_config.yml new file mode 100644 index 000000000..581d848ab --- /dev/null +++ b/docs/_config.yml @@ -0,0 +1,21 @@ +title: monty +email: ongsp@ucsd.edu +description: >- # this means to ignore newlines until "baseurl:" + A graph deep learning library for materials science. +# twitter_username: jekyllrb +github_username: materialsvirtuallab + +# Build settings +remote_theme: just-the-docs/just-the-docs +plugins: + - jekyll-feed + +# favicon_ico: "/assets/favicon.ico" + +nav_external_links: + - title: "monty on GitHub" + url: "https://github.com/materialsvirtuallab/monty" + +aux_links: + "Materials Virtual Lab": + - "https://materialsvirtuallab.org" \ No newline at end of file diff --git a/docs/_includes/footer_custom.html b/docs/_includes/footer_custom.html new file mode 100644 index 000000000..773d554f1 --- /dev/null +++ b/docs/_includes/footer_custom.html @@ -0,0 +1 @@ +© Copyright 2022, Materials Virtual Lab \ No newline at end of file diff --git a/docs/_includes/nav_footer_custom.html b/docs/_includes/nav_footer_custom.html new file mode 100644 index 000000000..177a82bc4 --- /dev/null +++ b/docs/_includes/nav_footer_custom.html @@ -0,0 +1 @@ +© Copyright 2022, Materials Virtual Lab \ No newline at end of file diff --git a/docs/_modules/index.html b/docs/_modules/index.html deleted file mode 100644 index e8a69b7b1..000000000 --- a/docs/_modules/index.html +++ /dev/null @@ -1,102 +0,0 @@ - - - - - - - Overview: module code — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/bisect.html b/docs/_modules/monty/bisect.html deleted file mode 100644 index 41e2e3ab9..000000000 --- a/docs/_modules/monty/bisect.html +++ /dev/null @@ -1,141 +0,0 @@ - - - - - - - monty.bisect — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.bisect

-"""
-Additional bisect functions. Taken from
-https://docs.python.org/2/library/bisect.html
-The above bisect() functions are useful for finding insertion points but can be
-tricky or awkward to use for common searching tasks.
-The functions show how to transform them into the standard lookups for sorted
-lists.
-"""
-
-import bisect as bs
-
-__author__ = "Matteo Giantomassi"
-__copyright__ = "Copyright 2013, The Materials Virtual Lab"
-__version__ = "0.1"
-__maintainer__ = "Matteo Giantomass"
-__email__ = "gmatteo@gmail.com"
-__date__ = "11/09/14"
-
-
-
[docs]def index(a, x, atol=None): - """Locate the leftmost value exactly equal to x.""" - i = bs.bisect_left(a, x) - if i != len(a): - if atol is None: - if a[i] == x: - return i - else: - if abs(a[i] - x) < atol: - return i - raise ValueError
- - -
[docs]def find_lt(a, x): - """Find rightmost value less than x.""" - i = bs.bisect_left(a, x) - if i: - return i - 1 - raise ValueError
- - -
[docs]def find_le(a, x): - """Find rightmost value less than or equal to x.""" - i = bs.bisect_right(a, x) - if i: - return i - 1 - raise ValueError
- - -
[docs]def find_gt(a, x): - """Find leftmost value greater than x.""" - i = bs.bisect_right(a, x) - if i != len(a): - return i - raise ValueError
- - -
[docs]def find_ge(a, x): - """Find leftmost item greater than or equal to x.""" - i = bs.bisect_left(a, x) - if i != len(a): - return i - raise ValueError
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/collections.html b/docs/_modules/monty/collections.html deleted file mode 100644 index daae99fc6..000000000 --- a/docs/_modules/monty/collections.html +++ /dev/null @@ -1,299 +0,0 @@ - - - - - - - monty.collections — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.collections

-"""
-Useful collection classes, e.g., tree, frozendict, etc.
-"""
-
-import collections
-
-
-
[docs]def tree(): - """ - A tree object, which is effectively a recursive defaultdict that - adds tree as members. - - Usage: - x = tree() - x['a']['b']['c'] = 1 - - Returns: - A tree. - """ - return collections.defaultdict(tree)
- - -
[docs]class frozendict(dict): - """ - A dictionary that does not permit changes. The naming - violates PEP8 to be consistent with standard Python's "frozenset" naming. - """ - - def __init__(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - dict.__init__(self, *args, **kwargs) - - def __setitem__(self, key, val): - raise KeyError(f"Cannot overwrite existing key: {str(key)}") - -
[docs] def update(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - raise KeyError(f"Cannot update a {self.__class__.__name__}")
- - -
[docs]class Namespace(dict): - """A dictionary that does not permit to redefine its keys.""" - - def __init__(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - self.update(*args, **kwargs) - - def __setitem__(self, key, val): - if key in self: - raise KeyError(f"Cannot overwrite existent key: {str(key)}") - - dict.__setitem__(self, key, val) - -
[docs] def update(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - for k, v in dict(*args, **kwargs).items(): - self[k] = v
- - -
[docs]class AttrDict(dict): - """ - Allows to access dict keys as obj.foo in addition - to the traditional way obj['foo']" - - Example: - >>> d = AttrDict(foo=1, bar=2) - >>> assert d["foo"] == d.foo - >>> d.bar = "hello" - >>> assert d.bar == "hello" - """ - - def __init__(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - super().__init__(*args, **kwargs) - self.__dict__ = self - -
[docs] def copy(self): - """ - :return: Copy of AttrDict - """ - newd = super().copy() - return self.__class__(**newd)
- - -
[docs]class FrozenAttrDict(frozendict): - """ - A dictionary that: - * does not permit changes. - * Allows to access dict keys as obj.foo in addition - to the traditional way obj['foo'] - """ - - def __init__(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - super().__init__(*args, **kwargs) - - def __getattribute__(self, name): - try: - return super().__getattribute__(name) - except AttributeError: - try: - return self[name] - except KeyError as exc: - raise AttributeError(str(exc)) - - def __setattr__(self, name, value): - raise KeyError(f"You cannot modify attribute {name} of {self.__class__.__name__}")
- - -
[docs]class MongoDict: - """ - This dict-like object allows one to access the entries in a nested dict as - attributes. - Entries (attributes) cannot be modified. It also provides Ipython tab - completion hence this object is particularly useful if you need to analyze - a nested dict interactively (e.g. documents extracted from a MongoDB - database). - - >>> m = MongoDict({'a': {'b': 1}, 'x': 2}) - >>> assert m.a.b == 1 and m.x == 2 - >>> assert "a" in m and "b" in m.a - >>> m["a"] - {'b': 1} - - .. note:: - - Cannot inherit from ABC collections.Mapping because otherwise - dict.keys and dict.items will pollute the namespace. - e.g MongoDict({"keys": 1}).keys would be the ABC dict method. - """ - - def __init__(self, *args, **kwargs): - """ - :param args: Passthrough arguments for standard dict. - :param kwargs: Passthrough keyword arguments for standard dict. - """ - self.__dict__["_mongo_dict_"] = dict(*args, **kwargs) - - def __repr__(self): - return str(self) - - def __str__(self): - return str(self._mongo_dict_) - - def __setattr__(self, name, value): - raise NotImplementedError(f"You cannot modify attribute {name} of {self.__class__.__name__}") - - def __getattribute__(self, name): - try: - return super().__getattribute__(name) - except AttributeError: - # raise - try: - a = self._mongo_dict_[name] - if isinstance(a, collections.abc.Mapping): - a = self.__class__(a) - return a - except Exception as exc: - raise AttributeError(str(exc)) - - def __getitem__(self, slice_): - return self._mongo_dict_.__getitem__(slice_) - - def __iter__(self): - return iter(self._mongo_dict_) - - def __len__(self): - return len(self._mongo_dict_) - - def __dir__(self): - """ - For Ipython tab completion. - See http://ipython.org/ipython-doc/dev/config/integrating.html - """ - return sorted(list(k for k in self._mongo_dict_ if not callable(k)))
- - -
[docs]def dict2namedtuple(*args, **kwargs): - """ - Helper function to create a :class:`namedtuple` from a dictionary. - - Example: - - >>> t = dict2namedtuple(foo=1, bar="hello") - >>> assert t.foo == 1 and t.bar == "hello" - - >>> t = dict2namedtuple([("foo", 1), ("bar", "hello")]) - >>> assert t[0] == t.foo and t[1] == t.bar - - .. warning:: - - - The order of the items in the namedtuple is not deterministic if - kwargs are used. - namedtuples, however, should always be accessed by attribute hence - this behaviour should not represent a serious problem. - - - Don't use this function in code in which memory and performance are - crucial since a dict is needed to instantiate the tuple! - """ - d = collections.OrderedDict(*args) - d.update(**kwargs) - return collections.namedtuple(typename="dict2namedtuple", field_names=list(d.keys()))(**d)
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/design_patterns.html b/docs/_modules/monty/design_patterns.html deleted file mode 100644 index 009797f77..000000000 --- a/docs/_modules/monty/design_patterns.html +++ /dev/null @@ -1,204 +0,0 @@ - - - - - - - monty.design_patterns — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.design_patterns

-"""
-Some common design patterns such as singleton and cached classes.
-"""
-
-from __future__ import annotations
-
-import os
-from functools import wraps
-from typing import Hashable, TypeVar
-
-
-
[docs]def singleton(cls): - """ - This decorator can be used to create a singleton out of a class. - - Usage:: - - @singleton - class MySingleton(): - - def __init__(): - pass - """ - - instances = {} - - def getinstance(): - if cls not in instances: - instances[cls] = cls() - return instances[cls] - - return getinstance
- - -# https://github.com/microsoft/pylance-release/issues/3478 -Klass = TypeVar("Klass") - - -
[docs]def cached_class(klass: type[Klass]) -> type[Klass]: - """ - Decorator to cache class instances by constructor arguments. - This results in a class that behaves like a singleton for each - set of constructor arguments, ensuring efficiency. - - Note that this should be used for *immutable classes only*. Having - a cached mutable class makes very little sense. For efficiency, - avoid using this decorator for situations where there are many - constructor arguments permutations. - - The keywords argument dictionary is converted to a tuple because - dicts are mutable; keywords themselves are strings and - so are always hashable, but if any arguments (keyword - or positional) are non-hashable, that set of arguments - is not cached. - """ - cache: dict[tuple[Hashable, ...], type[Klass]] = {} - - @wraps(klass, assigned=("__name__", "__module__"), updated=()) - class _decorated(klass): # type: ignore - # The wraps decorator can't do this because __doc__ - # isn't writable once the class is created - __doc__ = klass.__doc__ - - def __new__(cls, *args, **kwargs): - """ - Pass through... - :param args: - :param kwargs: - :return: - """ - key = (cls,) + args + tuple(kwargs.items()) - try: - inst = cache.get(key, None) - except TypeError: - # Can't cache this set of arguments - inst = key = None - if inst is None: - # Technically this is cheating, but it works, - # and takes care of initializing the instance - # (so we can override __init__ below safely); - # calling up to klass.__new__ would be the - # "official" way to create the instance, but - # that raises DeprecationWarning if there are - # args or kwargs and klass does not override - # __new__ (which most classes don't), because - # object.__new__ takes no parameters (and in - # Python 3 the warning will become an error) - inst = klass(*args, **kwargs) - # This makes isinstance and issubclass work - # properly - inst.__class__ = cls - if key is not None: - cache[key] = inst - return inst - - def __init__(self, *args, **kwargs): - # This will be called every time __new__ is - # called, so we skip initializing here and do - # it only when the instance is created above - pass - - return _decorated
- - -
[docs]class NullFile: - """A file object that is associated to /dev/null.""" - - def __new__(cls): - """ - Pass through - """ - return open(os.devnull, "w") # pylint: disable=R1732 - - def __init__(self): - """no-op"""
- - -
[docs]class NullStream: - """A fake stream with a no-op write.""" - -
[docs] def write(self, *args): # pylint: disable=E0211 - """ - Does nothing... - :param args: - """
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/dev.html b/docs/_modules/monty/dev.html deleted file mode 100644 index f6bc5569c..000000000 --- a/docs/_modules/monty/dev.html +++ /dev/null @@ -1,326 +0,0 @@ - - - - - - - monty.dev — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.dev

-"""
-This module implements several useful functions and decorators that can be
-particularly useful for developers. E.g., deprecating methods / classes, etc.
-"""
-
-import functools
-import inspect
-import logging
-import multiprocessing
-import os
-import re
-import subprocess
-import sys
-import warnings
-
-logger = logging.getLogger(__name__)
-
-
-
[docs]def deprecated(replacement=None, message=None, category=FutureWarning): - """ - Decorator to mark classes or functions as deprecated, - with a possible replacement. - - Args: - replacement (callable): A replacement class or method. - message (str): A warning message to be displayed. - category (Warning): Choose the category of the warning to issue. Defaults - to FutureWarning. Another choice can be DeprecationWarning. NOte that - FutureWarning is meant for end users and is always shown unless silenced. - DeprecationWarning is meant for developers and is never shown unless - python is run in developmental mode or the filter is changed. Make - the choice accordingly. - - Returns: - Original function, but with a warning to use the updated class. - """ - - def craft_message(old, replacement, message): - msg = f"{old.__name__} is deprecated" - if replacement is not None: - if isinstance(replacement, property): - r = replacement.fget - elif isinstance(replacement, (classmethod, staticmethod)): - r = replacement.__func__ - else: - r = replacement - msg += f"; use {r.__name__} in {r.__module__} instead." - if message is not None: - msg += "\n" + message - return msg - - def deprecated_decorator(old): - if inspect.isclass(old): - - class _DecoratedClass(old): - def __init__(self, *args, **kwargs): - msg = craft_message(old, replacement, message) - warnings.warn(msg, category=category, stacklevel=2) - super().__init__(*args, **kwargs) - - return _DecoratedClass - else: - - def wrapped(*args, **kwargs): - msg = craft_message(old, replacement, message) - warnings.warn(msg, category=category, stacklevel=2) - return old(*args, **kwargs) - - return wrapped - - return deprecated_decorator
- - -
[docs]class requires: - """ - Decorator to mark classes or functions as requiring a specified condition - to be true. This can be used to present useful error messages for - optional dependencies. For example, decorating the following code will - check if scipy is present and if not, a runtime error will be raised if - someone attempts to call the use_scipy function:: - - try: - import scipy - except ImportError: - scipy = None - - @requires(scipy is not None, "scipy is not present.") - def use_scipy(): - print(scipy.majver) - - Args: - condition: Condition necessary to use the class or function. - message: A message to be displayed if the condition is not True. - """ - - def __init__(self, condition, message): - """ - :param condition: A expression returning a bool. - :param message: Message to display if condition is False. - """ - self.condition = condition - self.message = message - - def __call__(self, _callable): - """ - :param _callable: Callable function. - """ - - @functools.wraps(_callable) - def decorated(*args, **kwargs): - if not self.condition: - raise RuntimeError(self.message) - return _callable(*args, **kwargs) - - return decorated
- - -
[docs]def get_ncpus(): - """ - .. note:: - - If you are using Python >= 2.7, multiprocessing.cpu_count() already - provides the number of CPUs. In fact, this is the first method tried. - The purpose of this function is to cater to old Python versions that - still exist on many Linux style clusters. - - Number of virtual or physical CPUs on this system, i.e. - user/real as output by time(1) when called with an optimally scaling - userspace-only program. Return -1 if ncpus cannot be detected. Taken from: - http://stackoverflow.com/questions/1006289/how-to-find-out-the-number-of- - cpus-in-python - """ - # Python 2.6+ - # May raise NonImplementedError - try: - return multiprocessing.cpu_count() - except (ImportError, NotImplementedError): - pass - - # POSIX - try: - res = int(os.sysconf("SC_NPROCESSORS_ONLN")) - if res > 0: - return res - except (AttributeError, ValueError): - pass - - # Windows - try: - res = int(os.environ["NUMBER_OF_PROCESSORS"]) - if res > 0: - return res - except (KeyError, ValueError): - pass - - # jython - try: - from java.lang import Runtime # pylint: disable=import-outside-toplevel - - runtime = Runtime.getRuntime() - res = runtime.availableProcessors() - if res > 0: - return res - except ImportError: - pass - - # BSD - try: - with subprocess.Popen(["sysctl", "-n", "hw.ncpu"], stdout=subprocess.PIPE) as sysctl: - scstdout = sysctl.communicate()[0] - res = int(scstdout) - if res > 0: - return res - except (OSError, ValueError): - pass - - # Linux - try: - res = open("/proc/cpuinfo").read().count("processor\t:") # pylint: disable=R1732 - if res > 0: - return res - except OSError: - pass - - # Solaris - try: - pseudo_devices = os.listdir("/devices/pseudo/") - expr = re.compile("^cpuid@[0-9]+$") - res = 0 - for pd in pseudo_devices: - if expr.match(pd) is not None: - res += 1 - if res > 0: - return res - except OSError: - pass - - # Other UNIXes (heuristic) - try: - try: - with open("/var/run/dmesg.boot") as f: - dmesg = f.read() - except OSError: - with subprocess.Popen(["dmesg"], stdout=subprocess.PIPE) as dmesg_process: - dmesg = dmesg_process.communicate()[0] - - res = 0 - while "\ncpu" + str(res) + ":" in dmesg: - res += 1 - - if res > 0: - return res - except OSError: - pass - - logger.warning("Cannot determine number of CPUs on this system!") - return -1
- - -
[docs]def install_excepthook(hook_type="color", **kwargs): - """ - This function replaces the original python traceback with an improved - version from Ipython. Use `color` for colourful traceback formatting, - `verbose` for Ka-Ping Yee's "cgitb.py" version kwargs are the keyword - arguments passed to the constructor. See IPython.core.ultratb.py for more - info. - - Return: - 0 if hook is installed successfully. - """ - try: - from IPython.core import ultratb # pylint: disable=import-outside-toplevel - except ImportError: - warnings.warn("Cannot install excepthook, IPyhon.core.ultratb not available") - return 1 - - # Select the hook. - hook = dict( - color=ultratb.ColorTB, - verbose=ultratb.VerboseTB, - ).get(hook_type.lower(), None) - - if hook is None: - return 2 - - sys.excepthook = hook(**kwargs) - return 0
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/fnmatch.html b/docs/_modules/monty/fnmatch.html deleted file mode 100644 index 7c0d68c91..000000000 --- a/docs/_modules/monty/fnmatch.html +++ /dev/null @@ -1,140 +0,0 @@ - - - - - - - monty.fnmatch — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.fnmatch

-"""
-This module provides support for Unix shell-style wildcards
-"""
-
-import fnmatch
-
-from monty.string import list_strings
-
-
-
[docs]class WildCard: - """ - This object provides an easy-to-use interface for filename matching with - shell patterns (fnmatch). - - >>> w = WildCard("*.nc|*.pdf") - >>> w.filter(["foo.nc", "bar.pdf", "hello.txt"]) - ['foo.nc', 'bar.pdf'] - - >>> w.filter("foo.nc") - ['foo.nc'] - """ - - def __init__(self, wildcard, sep="|"): - """ - Initializes a WildCard. - - Args: - wildcard (str): String of tokens separated by sep. Each token - represents a pattern. - sep (str): Separator for shell patterns. - """ - self.pats = ["*"] - if wildcard: - self.pats = wildcard.split(sep) - - def __str__(self): - return f"<{self.__class__.__name__}, patterns = {self.pats}>" - -
[docs] def filter(self, names): - """ - Returns a list with the names matching the pattern. - """ - names = list_strings(names) - - fnames = [] - for f in names: - for pat in self.pats: - if fnmatch.fnmatch(f, pat): - fnames.append(f) - - return fnames
- -
[docs] def match(self, name): - """ - Returns True if name matches one of the patterns. - """ - for pat in self.pats: - if fnmatch.fnmatch(name, pat): - return True - - return False
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/fractions.html b/docs/_modules/monty/fractions.html deleted file mode 100644 index c396ec386..000000000 --- a/docs/_modules/monty/fractions.html +++ /dev/null @@ -1,145 +0,0 @@ - - - - - - - monty.fractions — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.fractions

-"""
-Math functions.
-"""
-
-import math
-
-
-
[docs]def gcd(*numbers): - r""" - Returns the greatest common divisor for a sequence of numbers. - - Args: - *numbers: Sequence of numbers. - - Returns: - (int) Greatest common divisor of numbers. - """ - n = numbers[0] - for i in numbers: - n = math.gcd(n, i) - return n
- - -
[docs]def lcm(*numbers): - r""" - Return lowest common multiple of a sequence of numbers. - - Args: - *numbers: Sequence of numbers. - - Returns: - (int) Lowest common multiple of numbers. - """ - n = 1 - for i in numbers: - n = (i * n) // gcd(i, n) - return n
- - -
[docs]def gcd_float(numbers, tol=1e-8): - """ - Returns the greatest common divisor for a sequence of numbers. - Uses a numerical tolerance, so can be used on floats - - Args: - numbers: Sequence of numbers. - tol: Numerical tolerance - - Returns: - (int) Greatest common divisor of numbers. - """ - - def pair_gcd_tol(a, b): - """Calculate the Greatest Common Divisor of a and b. - - Unless b==0, the result will have the same sign as b (so that when - b is divided by it, the result comes out positive). - """ - while b > tol: - a, b = b, a % b - return a - - n = numbers[0] - for i in numbers: - n = pair_gcd_tol(n, i) - return n
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/functools.html b/docs/_modules/monty/functools.html deleted file mode 100644 index 329b1efb5..000000000 --- a/docs/_modules/monty/functools.html +++ /dev/null @@ -1,501 +0,0 @@ - - - - - - - monty.functools — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.functools

-"""
-functools, especially backported from Python 3.
-"""
-
-import cProfile
-import pstats
-import signal
-import sys
-import tempfile
-from collections import namedtuple
-from functools import partial, update_wrapper, wraps
-from threading import RLock
-
-_CacheInfo = namedtuple("_CacheInfo", ["hits", "misses", "maxsize", "currsize"])
-
-
-class _HashedSeq(list):  # pylint: disable=C0205
-    """
-    This class guarantees that hash() will be called no more than once
-    per element.  This is important because the lru_cache() will hash
-    the key multiple times on a cache miss.
-    """
-
-    __slots__ = "hashvalue"
-
-    def __init__(self, tup, hashfunc=hash):
-        """
-        :param tup: Tuple.
-        :param hashfunc: Hash function.
-        """
-        self[:] = tup
-        self.hashvalue = hashfunc(tup)
-
-    def __hash__(self):
-        return self.hashvalue
-
-
-def _make_key(args, kwds, typed, kwd_mark=(object(),), fasttypes={int, str, frozenset, type(None)}):
-    """
-    Make a cache key from optionally typed positional and keyword arguments
-
-    The key is constructed in a way that is flat as possible rather than
-    as a nested structure that would take more memory.
-
-    If there is only a single argument and its data type is known to cache
-    its hash value, then that argument is returned without a wrapper.  This
-    saves space and improves lookup speed.
-
-    """
-    key = args
-    if kwds:
-        sorted_items = sorted(kwds.items())
-        key += kwd_mark
-        for item in sorted_items:
-            key += item
-    if typed:
-        key += tuple(type(v) for v in args)
-        if kwds:
-            key += tuple(type(v) for k, v in sorted_items)
-    elif len(key) == 1 and isinstance(key[0], fasttypes):
-        return key[0]
-    return _HashedSeq(key)
-
-
-
[docs]def lru_cache(maxsize=128, typed=False): - """ - Least-recently-used cache decorator, which is a backport of the same - function in Python >= 3.2. - - If *maxsize* is set to None, the LRU features are disabled and the cache - can grow without bound. - - If *typed* is True, arguments of different types will be cached separately. - For example, f(3.0) and f(3) will be treated as distinct calls with - distinct results. - - Arguments to the cached function must be hashable. - - View the cache statistics named tuple (hits, misses, maxsize, currsize) - with f.cache_info(). Clear the cache and statistics with f.cache_clear(). - Access the underlying function with f.__wrapped__. - - See: http://en.wikipedia.org/wiki/Cache_algorithms#Least_Recently_Used - """ - - # Users should only access the lru_cache through its public API: - # cache_info, cache_clear, and f.__wrapped__ - # The internals of the lru_cache are encapsulated for thread safety and - # to allow the implementation to change (including a possible C version). - - # Early detection of an erroneous call to @lru_cache without any arguments - # resulting in the inner function being passed to maxsize instead of an - # integer or None. - if maxsize is not None and not isinstance(maxsize, int): - raise TypeError("Expected maxsize to be an integer or None") - - # Constants shared by all lru cache instances: - sentinel = object() # unique object used to signal cache misses - make_key = _make_key # build a key from the function arguments - PREV, NEXT, KEY, RESULT = 0, 1, 2, 3 # names for the link fields - - def decorating_function(user_function): - cache = {} - hits = [0] - misses = [0] - full = [False] - cache_get = cache.get # bound method to lookup a key or return None - lock = RLock() # because linkedlist updates aren't threadsafe - root = [] # root of the circular doubly linked list - root[:] = [root, root, None, None] # initialize by pointing to self - r = [root] - - if maxsize == 0: - - def wrapper(*args, **kwds): - # No caching - just a statistics update after a successful call - result = user_function(*args, **kwds) - misses[0] += 1 - return result - - elif maxsize is None: - - def wrapper(*args, **kwds): - # Simple caching without ordering or size limit - key = make_key(args, kwds, typed) - result = cache_get(key, sentinel) - if result is not sentinel: - hits[0] += 1 - return result - result = user_function(*args, **kwds) - cache[key] = result - misses[0] += 1 - return result - - else: - - def wrapper(*args, **kwds): - # Size limited caching that tracks accesses by recency - key = make_key(args, kwds, typed) - with lock: - link = cache_get(key) - if link is not None: - # Move the link to the front of the circular queue - link_prev, link_next, _key, result = link - link_prev[NEXT] = link_next - link_next[PREV] = link_prev - last = r[0][PREV] - last[NEXT] = r[0][PREV] = link - link[PREV] = last - link[NEXT] = r[0] - hits[0] += 1 - return result - result = user_function(*args, **kwds) - with lock: - if key in cache: - # Getting here means that this same key was added to - # cache while the lock was released. Since the link - # update is already done, we need only return the - # computed result and update the count of misses. - pass - elif full[0]: - # Use the old root to store the new key and result. - oldroot = r[0] - oldroot[KEY] = key - oldroot[RESULT] = result - # Empty the oldest link and make it the new root. - # Keep a reference to the old key and old result to - # prevent their ref counts from going to zero during - # update. That will prevent arbitrary object - # clean-up code (i.e. __del__) from running while we're - # still adjusting the links. - r[0] = oldroot[NEXT] - oldkey = r[0][KEY] - r[0][KEY] = r[0][RESULT] = None - # Now update the cache dictionary. - del cache[oldkey] - # Save the potentially reentrant cache[key] assignment - # for last, after the root and links have been put in - # a consistent state. - cache[key] = oldroot - else: - # Put result in a new link at the front of the queue. - last = r[0][PREV] - link = [last, r[0], key, result] - last[NEXT] = r[0][PREV] = cache[key] = link - full[0] = len(cache) >= maxsize - misses[0] += 1 - return result - - def cache_info(): - """Report cache statistics""" - with lock: - return _CacheInfo(hits[0], misses[0], maxsize, len(cache)) - - def cache_clear(): - """Clear the cache and cache statistics""" - with lock: - cache.clear() - root[:] = [root, root, None, None] - r[0] = root - hits[0] = 0 - misses[0] = 0 - full[0] = False - - wrapper.cache_info = cache_info - wrapper.cache_clear = cache_clear - return update_wrapper(wrapper, user_function) - - return decorating_function
- - -
[docs]class lazy_property: - """ - lazy_property descriptor - - Used as a decorator to create lazy attributes. Lazy attributes - are evaluated on first use. - """ - - def __init__(self, func): - """ - :param func: Function to decorate. - """ - self.__func = func - wraps(self.__func)(self) - - def __get__(self, inst, inst_cls): - if inst is None: - return self - - if not hasattr(inst, "__dict__"): - raise AttributeError(f"'{inst_cls.__name__}' object has no attribute '__dict__'") - - name = self.__name__ # pylint: disable=E1101 - if name.startswith("__") and not name.endswith("__"): - name = f"_{inst_cls.__name__}{name}" - - value = self.__func(inst) - inst.__dict__[name] = value - return value - -
[docs] @classmethod - def invalidate(cls, inst, name): - """Invalidate a lazy attribute. - - This obviously violates the lazy contract. A subclass of lazy - may however have a contract where invalidation is appropriate. - """ - inst_cls = inst.__class__ - - if not hasattr(inst, "__dict__"): - raise AttributeError(f"'{inst_cls.__name__}' object has no attribute '__dict__'") - - if name.startswith("__") and not name.endswith("__"): - name = f"_{inst_cls.__name__}{name}" - - if not isinstance(getattr(inst_cls, name), cls): - raise AttributeError(f"'{inst_cls.__name__}.{name}' is not a {cls.__name__} attribute") - - if name in inst.__dict__: - del inst.__dict__[name]
- - -
[docs]def return_if_raise(exception_tuple, retval_if_exc, disabled=False): - """ - Decorator for functions, methods or properties. Execute the callable in a - try block, and return retval_if_exc if one of the exceptions listed in - exception_tuple is raised (se also ``return_node_if_raise``). - - Setting disabled to True disables the try except block (useful for - debugging purposes). One can use this decorator to define properties. - - Example:: - - @return_if_raise(ValueError, None) - def return_none_if_value_error(self): - pass - - @return_if_raise((ValueError, KeyError), "hello") - def another_method(self): - pass - - @property - @return_if_raise(AttributeError, None) - def name(self): - "Name of the object, None if not set." - return self._name - - """ - # we need a tuple of exceptions. - if isinstance(exception_tuple, list): - exception_tuple = tuple(exception_tuple) - elif not isinstance(exception_tuple, tuple): - exception_tuple = (exception_tuple,) - else: - raise TypeError(f"Wrong exception_tuple {type(exception_tuple)}") - - def decorator(func): - @wraps(func) - def wrapper(*args, **kwargs): - if disabled: - return func(*args, **kwargs) - try: - return func(*args, **kwargs) - except exception_tuple: # pylint: disable=E0712 - return retval_if_exc - - return wrapper - - return decorator
- - -# One could use None as default value in return_if_raise but this one is -# explicit and more readable -return_none_if_raise = partial(return_if_raise, retval_if_exc=None) -""" -This decorator returns None if one of the exceptions is raised. - - @return_none_if_raise(ValueError) - def method(self): -""" - - -
[docs]class timeout: - """ - Timeout function. Use to limit matching to a certain time limit. Note that - this works only on Unix-based systems as it uses signal. Usage: - - try: - with timeout(3): - do_stuff() - except TimeoutError: - do_something_else() - """ - - def __init__(self, seconds=1, error_message="Timeout"): - """ - Args: - seconds (int): Allowed time for function in seconds. - error_message (str): An error message. - - """ - self.seconds = seconds - self.error_message = error_message - -
[docs] def handle_timeout(self, signum, frame): - """ - :param signum: Return signal from call. - :param frame: - """ - raise TimeoutError(self.error_message)
- - def __enter__(self): - signal.signal(signal.SIGALRM, self.handle_timeout) - signal.alarm(self.seconds) - - def __exit__(self, type, value, traceback): - signal.alarm(0)
- - -
[docs]class TimeoutError(Exception): - """ - Exception class for timeouts. - """ - - def __init__(self, message): - """ - :param message: Error message - """ - self.message = message
- - -
[docs]def prof_main(main): - """ - Decorator for profiling main programs. - - Profiling is activated by prepending the command line options - supported by the original main program with the keyword `prof`. - Example: - - $ script.py arg --foo=1 - - becomes - - $ script.py prof arg --foo=1 - - The decorated main accepts two new arguments: - - prof_file: Name of the output file with profiling data - If not given, a temporary file is created. - sortby: Profiling data are sorted according to this value. - default is "time". See sort_stats. - """ - - @wraps(main) - def wrapper(*args, **kwargs): - try: - do_prof = sys.argv[1] == "prof" - if do_prof: - sys.argv.pop(1) - except Exception: - do_prof = False - - if not do_prof: - sys.exit(main()) - else: - print("Entering profiling mode...") - prof_file = kwargs.get("prof_file", None) - if prof_file is None: - _, prof_file = tempfile.mkstemp() - print(f"Profiling data stored in {prof_file}") - - sortby = kwargs.get("sortby", "time") - cProfile.runctx("main()", globals(), locals(), prof_file) - s = pstats.Stats(prof_file) - s.strip_dirs().sort_stats(sortby).print_stats() - if "retval" not in kwargs: - sys.exit(0) - else: - return kwargs["retval"] - - return wrapper
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/inspect.html b/docs/_modules/monty/inspect.html deleted file mode 100644 index 868d90986..000000000 --- a/docs/_modules/monty/inspect.html +++ /dev/null @@ -1,181 +0,0 @@ - - - - - - - monty.inspect — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.inspect

-"""
-Useful additional functions to help get information about live objects
-"""
-
-import inspect
-import os
-from functools import wraps
-from inspect import currentframe, getframeinfo, getfullargspec
-
-
-
[docs]def all_subclasses(cls): - """ - Given a class `cls`, this recursive function returns a list with - all subclasses, subclasses of subclasses, and so on. - """ - subclasses = cls.__subclasses__() - return subclasses + [g for s in subclasses for g in all_subclasses(s)]
- - -
[docs]def find_top_pyfile(): - """ - This function inspects the Cpython frame to find the path of the script. - """ - frame = currentframe() - while True: - if frame.f_back is None: - finfo = getframeinfo(frame) - return os.path.abspath(finfo.filename) - - frame = frame.f_back
- - -
[docs]def caller_name(skip=2): - """ - Get a name of a caller in the format module.class.method - - `skip` specifies how many levels of stack to skip while getting caller - name. skip=1 means "who calls me", skip=2 "who calls my caller" etc. - - An empty string is returned if skipped levels exceed stack height - - Taken from: - - https://gist.github.com/techtonik/2151727 - - Public Domain, i.e. feel free to copy/paste - """ - stack = inspect.stack() - start = 0 + skip - if len(stack) < start + 1: - return "" - parentframe = stack[start][0] - - name = [] - module = inspect.getmodule(parentframe) - # `modname` can be None when frame is executed directly in console - # TODO(techtonik): consider using __main__ - if module: - name.append(module.__name__) - # detect classname - if "self" in parentframe.f_locals: - # I don't know any way to detect call from the object method - # XXX: there seems to be no way to detect static method call - it will - # be just a function call - name.append(parentframe.f_locals["self"].__class__.__name__) - codename = parentframe.f_code.co_name - if codename != "<module>": # top level usually - name.append(codename) # function or a method - del parentframe - return ".".join(name)
- - -
[docs]def initializer(func): - """ - Automatically assigns the parameters. - http://stackoverflow.com/questions/1389180/python-automatically-initialize - -instance-variables - - >>> class process: - ... @initializer - ... def __init__(self, cmd, reachable=False, user='root'): - ... pass - >>> p = process('halt', True) - >>> p.cmd, p.reachable, p.user - ('halt', True, 'root') - """ - names, varargs, keywords, defaults = getfullargspec(func) # type: ignore - - @wraps(func) - def wrapper(self, *args, **kargs): - for name, arg in list(zip(names[1:], args)) + list(kargs.items()): - setattr(self, name, arg) - - # Avoid TypeError: argument to reversed() must be a sequence - if defaults is not None: - for name, default in zip(reversed(names), reversed(defaults)): - if not hasattr(self, name): - setattr(self, name, default) - - return func(self, *args, **kargs) - - return wrapper
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/io.html b/docs/_modules/monty/io.html deleted file mode 100644 index c41b6b6cc..000000000 --- a/docs/_modules/monty/io.html +++ /dev/null @@ -1,344 +0,0 @@ - - - - - - - monty.io — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.io

-"""
-Augments Python's suite of IO functions with useful transparent support for
-compressed files.
-"""
-
-import bz2
-import errno
-import gzip
-import io
-import lzma
-import mmap
-import os
-import subprocess
-import time
-from pathlib import Path
-from typing import IO, Generator, Union
-
-
-
[docs]def zopen(filename: Union[str, Path], *args, **kwargs) -> IO: - r""" - This function wraps around the bz2, gzip, lzma, xz and standard python's open - function to deal intelligently with bzipped, gzipped or standard text - files. - - Args: - filename (str/Path): filename or pathlib.Path. - *args: Standard args for python open(..). E.g., 'r' for read, 'w' for - write. - **kwargs: Standard kwargs for python open(..). - - Returns: - File-like object. Supports with context. - """ - if Path is not None and isinstance(filename, Path): - filename = str(filename) - - name, ext = os.path.splitext(filename) - ext = ext.upper() - if ext == ".BZ2": - return bz2.open(filename, *args, **kwargs) - if ext in (".GZ", ".Z"): - return gzip.open(filename, *args, **kwargs) - if ext in (".XZ", ".LZMA"): - return lzma.open(filename, *args, **kwargs) - return open(filename, *args, **kwargs) # pylint: disable=R1732
- - -
[docs]def reverse_readfile(filename: Union[str, Path]) -> Generator[str, str, None]: - """ - A much faster reverse read of file by using Python's mmap to generate a - memory-mapped file. It is slower for very small files than - reverse_readline, but at least 2x faster for large files (the primary use - of such a method). - - Args: - filename (str): - Name of file to read. - - Yields: - Lines from the file in reverse order. - """ - try: - with zopen(filename, "rb") as f: - if isinstance(f, (gzip.GzipFile, bz2.BZ2File)): - for line in reversed(f.readlines()): - yield line.decode("utf-8").rstrip() - else: - fm = mmap.mmap(f.fileno(), 0, access=mmap.ACCESS_READ) - n = len(fm) - while n > 0: - i = fm.rfind(b"\n", 0, n) - yield fm[i + 1 : n].decode("utf-8").strip("\n") - n = i - except ValueError: - return
- - -
[docs]def reverse_readline(m_file, blk_size=4096, max_mem=4000000) -> Generator[str, str, None]: - """ - Generator method to read a file line-by-line, but backwards. This allows - one to efficiently get data at the end of a file. - - Based on code by Peter Astrand <astrand@cendio.se>, using modifications by - Raymond Hettinger and Kevin German. - http://code.activestate.com/recipes/439045-read-a-text-file-backwards - -yet-another-implementat/ - - Reads file forwards and reverses in memory for files smaller than the - max_mem parameter, or for gzip files where reverse seeks are not supported. - - Files larger than max_mem are dynamically read backwards. - - Args: - m_file (File): File stream to read (backwards) - blk_size (int): The buffer size. Defaults to 4096. - max_mem (int): The maximum amount of memory to involve in this - operation. This is used to determine when to reverse a file - in-memory versus seeking portions of a file. For bz2 files, - this sets the maximum block size. - - Returns: - Generator that returns lines from the file. Similar behavior to the - file.readline() method, except the lines are returned from the back - of the file. - """ - # Check if the file stream is a bit stream or not - is_text = isinstance(m_file, io.TextIOWrapper) - - try: - file_size = os.path.getsize(m_file.name) - except AttributeError: - # Bz2 files do not have name attribute. Just set file_size to above - # max_mem for now. - file_size = max_mem + 1 - - # If the file size is within our desired RAM use, just reverse it in memory - # GZip files must use this method because there is no way to negative seek - # For windows, we also read the whole file. - if file_size < max_mem or isinstance(m_file, gzip.GzipFile) or os.name == "nt": - for line in reversed(m_file.readlines()): - yield line.rstrip() - else: - if isinstance(m_file, bz2.BZ2File): - # for bz2 files, seeks are expensive. It is therefore in our best - # interest to maximize the blk_size within limits of desired RAM - # use. - blk_size = min(max_mem, file_size) - - buf = "" - m_file.seek(0, 2) - if is_text: - lastchar = m_file.read(1) - else: - lastchar = m_file.read(1).decode("utf-8") - - trailing_newline = lastchar == "\n" - - while 1: - newline_pos = buf.rfind("\n") - pos = m_file.tell() - if newline_pos != -1: - # Found a newline - line = buf[newline_pos + 1 :] - buf = buf[:newline_pos] - if pos or newline_pos or trailing_newline: - line += "\n" - yield line - elif pos: - # Need to fill buffer - toread = min(blk_size, pos) - m_file.seek(pos - toread, 0) - if is_text: - buf = m_file.read(toread) + buf - else: - buf = m_file.read(toread).decode("utf-8") + buf - m_file.seek(pos - toread, 0) - if pos == toread: - buf = "\n" + buf - else: - # Start-of-file - return
- - -
[docs]class FileLockException(Exception): - """Exception raised by FileLock."""
- - -
[docs]class FileLock: - """ - A file locking mechanism that has context-manager support so you can use - it in a with statement. This should be relatively cross-compatible as it - doesn't rely on msvcrt or fcntl for the locking. - Taken from http://www.evanfosmark.com/2009/01/cross-platform-file-locking - -support-in-python/ - """ - - Error = FileLockException - - def __init__(self, file_name, timeout=10, delay=0.05): - """ - Prepare the file locker. Specify the file to lock and optionally - the maximum timeout and the delay between each attempt to lock. - - Args: - file_name: Name of file to lock. - timeout: Maximum timeout for locking. Defaults to 10. - delay: Delay between each attempt to lock. Defaults to 0.05. - """ - self.file_name = os.path.abspath(file_name) - self.lockfile = os.path.abspath(file_name) + ".lock" - self.timeout = float(timeout) - self.delay = float(delay) - self.is_locked = False - - if self.delay > self.timeout or self.delay <= 0 or self.timeout <= 0: - raise ValueError("delay and timeout must be positive with delay " "<= timeout") - -
[docs] def acquire(self): - """ - Acquire the lock, if possible. If the lock is in use, it check again - every `delay` seconds. It does this until it either gets the lock or - exceeds `timeout` number of seconds, in which case it throws - an exception. - """ - start_time = time.time() - while True: - try: - self.fd = os.open(self.lockfile, os.O_CREAT | os.O_EXCL | os.O_RDWR) - break - except (OSError,) as e: - if e.errno != errno.EEXIST: - raise - if (time.time() - start_time) >= self.timeout: - raise FileLockException(f"{self.lockfile}: Timeout occurred.") - time.sleep(self.delay) - - self.is_locked = True
- -
[docs] def release(self): - """ - Get rid of the lock by deleting the lockfile. - When working in a `with` statement, this gets automatically - called at the end. - """ - if self.is_locked: - os.close(self.fd) - os.unlink(self.lockfile) - self.is_locked = False
- - def __enter__(self): - """ - Activated when used in the with statement. Should automatically - acquire a lock to be used in the with block. - """ - if not self.is_locked: - self.acquire() - return self - - def __exit__(self, type_, value, traceback): - """ - Activated at the end of the with statement. It automatically releases - the lock if it isn't locked. - """ - if self.is_locked: - self.release() - - def __del__(self): - """ - Make sure that the FileLock instance doesn't leave a lockfile - lying around. - """ - self.release()
- - -
[docs]def get_open_fds(): - """ - Return the number of open file descriptors for current process - - .. warning: will only work on UNIX-like OS-es. - """ - pid = os.getpid() - procs = subprocess.check_output(["lsof", "-w", "-Ff", "-p", str(pid)]) - procs = procs.decode("utf-8") - - return len([s for s in procs.split("\n") if s and s[0] == "f" and s[1:].isdigit()])
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/itertools.html b/docs/_modules/monty/itertools.html deleted file mode 100644 index c4f46bc97..000000000 --- a/docs/_modules/monty/itertools.html +++ /dev/null @@ -1,174 +0,0 @@ - - - - - - - monty.itertools — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.itertools

-"""
-Additional tools for iteration.
-"""
-import itertools
-
-try:
-    import numpy as np
-except ImportError:
-    np = None  # type: ignore
-
-
-
[docs]def chunks(items, n): - """ - Yield successive n-sized chunks from a list-like object. - - >>> import pprint - >>> pprint.pprint(list(chunks(range(1, 25), 10))) - [(1, 2, 3, 4, 5, 6, 7, 8, 9, 10), - (11, 12, 13, 14, 15, 16, 17, 18, 19, 20), - (21, 22, 23, 24)] - """ - it = iter(items) - chunk = tuple(itertools.islice(it, n)) - while chunk: - yield chunk - chunk = tuple(itertools.islice(it, n))
- - -
[docs]def iterator_from_slice(s): - """ - Constructs an iterator given a slice object s. - - .. note:: - - The function returns an infinite iterator if s.stop is None - """ - start = s.start if s.start is not None else 0 - step = s.step if s.step is not None else 1 - - if s.stop is None: - # Infinite iterator. - return itertools.count(start=start, step=step) - - # xrange-like iterator that supports float. - return iter(np.arange(start, s.stop, step))
- - -
[docs]def iuptri(items, diago=True, with_inds=False): - """ - A generator that yields the upper triangle of the matrix (items x items) - - Args: - items: Iterable object with elements [e0, e1, ...] - diago: False if diagonal matrix elements should be excluded - with_inds: If True, (i,j) (e_i, e_j) is returned else (e_i, e_j) - - >>> for (ij, mate) in iuptri([0,1], with_inds=True): - ... print("ij:", ij, "mate:", mate) - ij: (0, 0) mate: (0, 0) - ij: (0, 1) mate: (0, 1) - ij: (1, 1) mate: (1, 1) - """ - for ii, item1 in enumerate(items): - for jj, item2 in enumerate(items): - do_yield = (jj >= ii) if diago else (jj > ii) - if do_yield: - if with_inds: - yield (ii, jj), (item1, item2) - else: - yield item1, item2
- - -
[docs]def ilotri(items, diago=True, with_inds=False): - """ - A generator that yields the lower triangle of the matrix (items x items) - - Args: - items: Iterable object with elements [e0, e1, ...] - diago: False if diagonal matrix elements should be excluded - with_inds: If True, (i,j) (e_i, e_j) is returned else (e_i, e_j) - - >>> for (ij, mate) in ilotri([0,1], with_inds=True): - ... print("ij:", ij, "mate:", mate) - ij: (0, 0) mate: (0, 0) - ij: (1, 0) mate: (1, 0) - ij: (1, 1) mate: (1, 1) - """ - for ii, item1 in enumerate(items): - for jj, item2 in enumerate(items): - do_yield = (jj <= ii) if diago else (jj < ii) - if do_yield: - if with_inds: - yield (ii, jj), (item1, item2) - else: - yield item1, item2
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/json.html b/docs/_modules/monty/json.html deleted file mode 100644 index 3e512d9d6..000000000 --- a/docs/_modules/monty/json.html +++ /dev/null @@ -1,698 +0,0 @@ - - - - - - - monty.json — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.json

-"""
-JSON serialization and deserialization utilities.
-"""
-
-import datetime
-import json
-import os
-import pathlib
-import types
-from collections import OrderedDict, defaultdict
-from enum import Enum
-from hashlib import sha1
-from importlib import import_module
-from inspect import getfullargspec
-from uuid import UUID
-
-try:
-    import numpy as np
-except ImportError:
-    np = None  # type: ignore
-
-try:
-    import pandas as pd
-except ImportError:
-    pd = None  # type: ignore
-
-try:
-    import pydantic
-except ImportError:
-    pydantic = None  # type: ignore
-
-try:
-    import bson
-except ImportError:
-    bson = None  # type: ignore
-
-try:
-    from ruamel.yaml import YAML
-except ImportError:
-    YAML = None  # type: ignore
-
-try:
-    import orjson
-except ImportError:
-    orjson = None  # type: ignore
-
-try:
-    import dataclasses
-except ImportError:
-    dataclasses = None  # type: ignore
-
-try:
-    import torch
-except ImportError:
-    torch = None  # type: ignore
-
-__version__ = "3.0.0"
-
-
-def _load_redirect(redirect_file):
-    try:
-        with open(redirect_file) as f:
-            yaml = YAML()
-            d = yaml.load(f)
-    except OSError:
-        # If we can't find the file
-        # Just use an empty redirect dict
-        return {}
-
-    # Convert the full paths to module/class
-    redirect_dict = defaultdict(dict)
-    for old_path, new_path in d.items():
-        old_class = old_path.split(".")[-1]
-        old_module = ".".join(old_path.split(".")[:-1])
-
-        new_class = new_path.split(".")[-1]
-        new_module = ".".join(new_path.split(".")[:-1])
-
-        redirect_dict[old_module][old_class] = {
-            "@module": new_module,
-            "@class": new_class,
-        }
-
-    return dict(redirect_dict)
-
-
-
[docs]class MSONable: - """ - This is a mix-in base class specifying an API for msonable objects. MSON - is Monty JSON. Essentially, MSONable objects must implement an as_dict - method, which must return a json serializable dict and must also support - no arguments (though optional arguments to finetune the output is ok), - and a from_dict class method that regenerates the object from the dict - generated by the as_dict method. The as_dict method should contain the - "@module" and "@class" keys which will allow the MontyEncoder to - dynamically deserialize the class. E.g.:: - - d["@module"] = self.__class__.__module__ - d["@class"] = self.__class__.__name__ - - A default implementation is provided in MSONable, which automatically - determines if the class already contains self.argname or self._argname - attributes for every arg. If so, these will be used for serialization in - the dict format. Similarly, the default from_dict will deserialization - classes of such form. An example is given below:: - - class MSONClass(MSONable): - - def __init__(self, a, b, c, d=1, **kwargs): - self.a = a - self.b = b - self._c = c - self._d = d - self.kwargs = kwargs - - For such classes, you merely need to inherit from MSONable and you do not - need to implement your own as_dict or from_dict protocol. - - New to Monty V2.0.6.... - Classes can be redirected to moved implementations by putting in the old - fully qualified path and new fully qualified path into .monty.yaml in the - home folder - - Example: - old_module.old_class: new_module.new_class - """ - - REDIRECT = _load_redirect(os.path.join(os.path.expanduser("~"), ".monty.yaml")) - -
[docs] def as_dict(self) -> dict: - """ - A JSON serializable dict representation of an object. - """ - d = {"@module": self.__class__.__module__, "@class": self.__class__.__name__} - - try: - parent_module = self.__class__.__module__.split(".", maxsplit=1)[0] - module_version = import_module(parent_module).__version__ # type: ignore - d["@version"] = str(module_version) - except (AttributeError, ImportError): - d["@version"] = None # type: ignore - - spec = getfullargspec(self.__class__.__init__) - args = spec.args - - def recursive_as_dict(obj): - if isinstance(obj, (list, tuple)): - return [recursive_as_dict(it) for it in obj] - if isinstance(obj, dict): - return {kk: recursive_as_dict(vv) for kk, vv in obj.items()} - if hasattr(obj, "as_dict"): - return obj.as_dict() - if dataclasses is not None and dataclasses.is_dataclass(obj): - d = dataclasses.asdict(obj) - d.update({"@module": obj.__class__.__module__, "@class": obj.__class__.__name__}) - return d - return obj - - for c in args: - if c != "self": - try: - a = getattr(self, c) - except AttributeError: - try: - a = getattr(self, "_" + c) - except AttributeError: - raise NotImplementedError( - "Unable to automatically determine as_dict " - "format from class. MSONAble requires all " - "args to be present as either self.argname or " - "self._argname, and kwargs to be present under " - "a self.kwargs variable to automatically " - "determine the dict format. Alternatively, " - "you can implement both as_dict and from_dict." - ) - d[c] = recursive_as_dict(a) - if hasattr(self, "kwargs"): - # type: ignore - d.update(**getattr(self, "kwargs")) # pylint: disable=E1101 - if spec.varargs is not None and getattr(self, spec.varargs, None) is not None: - d.update({spec.varargs: getattr(self, spec.varargs)}) - if hasattr(self, "_kwargs"): - d.update(**getattr(self, "_kwargs")) # pylint: disable=E1101 - if isinstance(self, Enum): - d.update({"value": self.value}) # pylint: disable=E1101 - return d
- -
[docs] @classmethod - def from_dict(cls, d): - """ - :param d: Dict representation. - :return: MSONable class. - """ - decoded = {k: MontyDecoder().process_decoded(v) for k, v in d.items() if not k.startswith("@")} - return cls(**decoded)
- -
[docs] def to_json(self) -> str: - """ - Returns a json string representation of the MSONable object. - """ - return json.dumps(self, cls=MontyEncoder)
- -
[docs] def unsafe_hash(self): - """ - Returns an hash of the current object. This uses a generic but low - performance method of converting the object to a dictionary, flattening - any nested keys, and then performing a hash on the resulting object - """ - - def flatten(obj, separator="."): - # Flattens a dictionary - - flat_dict = {} - for key, value in obj.items(): - if isinstance(value, dict): - flat_dict.update({separator.join([key, _key]): _value for _key, _value in flatten(value).items()}) - elif isinstance(value, list): - list_dict = {f"{key}{separator}{num}": item for num, item in enumerate(value)} - flat_dict.update(flatten(list_dict)) - else: - flat_dict[key] = value - - return flat_dict - - ordered_keys = sorted(flatten(jsanitize(self.as_dict())).items(), key=lambda x: x[0]) - ordered_keys = [item for item in ordered_keys if "@" not in item[0]] - return sha1(json.dumps(OrderedDict(ordered_keys)).encode("utf-8"))
- - @classmethod - def __get_validators__(cls): - """Return validators for use in pydantic""" - yield cls.validate_monty - -
[docs] @classmethod - def validate_monty(cls, v): - """ - pydantic Validator for MSONable pattern - """ - if isinstance(v, cls): - return v - if isinstance(v, dict): - new_obj = MontyDecoder().process_decoded(v) - if isinstance(new_obj, cls): - return new_obj - - new_obj = cls(**v) - return new_obj - - raise ValueError(f"Must provide {cls.__name__}, the as_dict form, or the proper")
- - @classmethod - def __modify_schema__(cls, field_schema): - """JSON schema for MSONable pattern""" - field_schema.update( - { - "type": "object", - "properties": { - "@class": {"enum": [cls.__name__], "type": "string"}, - "@module": {"enum": [cls.__module__], "type": "string"}, - "@version": {"type": "string"}, - }, - "required": ["@class", "@module"], - } - )
- - -
[docs]class MontyEncoder(json.JSONEncoder): - """ - A Json Encoder which supports the MSONable API, plus adds support for - numpy arrays, datetime objects, bson ObjectIds (requires bson). - Usage:: - # Add it as a *cls* keyword when using json.dump - json.dumps(object, cls=MontyEncoder) - """ - -
[docs] def default(self, o) -> dict: # pylint: disable=E0202 - """ - Overriding default method for JSON encoding. This method does two - things: (a) If an object has a to_dict property, return the to_dict - output. (b) If the @module and @class keys are not in the to_dict, - add them to the output automatically. If the object has no to_dict - property, the default Python json encoder default method is called. - Args: - o: Python object. - Return: - Python dict representation. - """ - if isinstance(o, datetime.datetime): - return {"@module": "datetime", "@class": "datetime", "string": str(o)} - if isinstance(o, UUID): - return {"@module": "uuid", "@class": "UUID", "string": str(o)} - - if torch is not None and isinstance(o, torch.Tensor): - # Support for Pytorch Tensors. - d = { - "@module": "torch", - "@class": "Tensor", - "dtype": o.type(), - } - if "Complex" in o.type(): - d["data"] = [o.real.tolist(), o.imag.tolist()] # type: ignore - else: - d["data"] = o.numpy().tolist() - return d - - if np is not None: - if isinstance(o, np.ndarray): - if str(o.dtype).startswith("complex"): - return { - "@module": "numpy", - "@class": "array", - "dtype": str(o.dtype), - "data": [o.real.tolist(), o.imag.tolist()], - } - return { - "@module": "numpy", - "@class": "array", - "dtype": str(o.dtype), - "data": o.tolist(), - } - if isinstance(o, np.generic): - return o.item() - - if pd is not None: - if isinstance(o, pd.DataFrame): - return { - "@module": "pandas", - "@class": "DataFrame", - "data": o.to_json(default_handler=MontyEncoder().encode), - } - if isinstance(o, pd.Series): - return { - "@module": "pandas", - "@class": "Series", - "data": o.to_json(default_handler=MontyEncoder().encode), - } - - if bson is not None: - if isinstance(o, bson.objectid.ObjectId): - return {"@module": "bson.objectid", "@class": "ObjectId", "oid": str(o)} - - if callable(o) and not isinstance(o, MSONable): - return _serialize_callable(o) - - try: - if pydantic is not None and isinstance(o, pydantic.BaseModel): - d = o.dict() - elif dataclasses is not None and (not issubclass(o.__class__, MSONable)) and dataclasses.is_dataclass(o): - # This handles dataclasses that are not subclasses of MSONAble. - d = dataclasses.asdict(o) - else: - d = o.as_dict() - - if "@module" not in d: - d["@module"] = str(o.__class__.__module__) - if "@class" not in d: - d["@class"] = str(o.__class__.__name__) - if "@version" not in d: - try: - parent_module = o.__class__.__module__.split(".")[0] - module_version = import_module(parent_module).__version__ # type: ignore - d["@version"] = str(module_version) - except (AttributeError, ImportError): - d["@version"] = None # type: ignore - return d - except AttributeError: - return json.JSONEncoder.default(self, o)
- - -
[docs]class MontyDecoder(json.JSONDecoder): - """ - A Json Decoder which supports the MSONable API. By default, the - decoder attempts to find a module and name associated with a dict. If - found, the decoder will generate a Pymatgen as a priority. If that fails, - the original decoded dictionary from the string is returned. Note that - nested lists and dicts containing pymatgen object will be decoded correctly - as well. - - Usage: - - # Add it as a *cls* keyword when using json.load - json.loads(json_string, cls=MontyDecoder) - """ - -
[docs] def process_decoded(self, d): - """ - Recursive method to support decoding dicts and lists containing - pymatgen objects. - """ - if isinstance(d, dict): - if "@module" in d and "@class" in d: - modname = d["@module"] - classname = d["@class"] - if classname in MSONable.REDIRECT.get(modname, {}): - modname = MSONable.REDIRECT[modname][classname]["@module"] - classname = MSONable.REDIRECT[modname][classname]["@class"] - elif "@module" in d and "@callable" in d: - modname = d["@module"] - objname = d["@callable"] - classname = None - if d.get("@bound", None) is not None: - # if the function is bound to an instance or class, first - # deserialize the bound object and then remove the object name - # from the function name. - obj = self.process_decoded(d["@bound"]) - objname = objname.split(".")[1:] - else: - # if the function is not bound to an object, import the - # function from the module name - obj = __import__(modname, globals(), locals(), [objname], 0) - objname = objname.split(".") - try: - # the function could be nested. e.g., MyClass.NestedClass.function - # so iteratively access the nesting - for attr in objname: - obj = getattr(obj, attr) - - return obj - - except AttributeError: - pass - else: - modname = None - classname = None - - if classname: - if modname and modname not in ["bson.objectid", "numpy", "pandas", "torch"]: - if modname == "datetime" and classname == "datetime": - try: - dt = datetime.datetime.strptime(d["string"], "%Y-%m-%d %H:%M:%S.%f") - except ValueError: - dt = datetime.datetime.strptime(d["string"], "%Y-%m-%d %H:%M:%S") - return dt - - if modname == "uuid" and classname == "UUID": - return UUID(d["string"]) - - mod = __import__(modname, globals(), locals(), [classname], 0) - if hasattr(mod, classname): - cls_ = getattr(mod, classname) - data = {k: v for k, v in d.items() if not k.startswith("@")} - if hasattr(cls_, "from_dict"): - return cls_.from_dict(data) - if pydantic is not None and issubclass(cls_, pydantic.BaseModel): # pylint: disable=E1101 - return cls_(**data) - if ( - dataclasses is not None - and (not issubclass(cls_, MSONable)) - and dataclasses.is_dataclass(cls_) - ): - d = {k: self.process_decoded(v) for k, v in data.items()} - return cls_(**d) - elif torch is not None and modname == "torch" and classname == "Tensor": - if "Complex" in d["dtype"]: - return torch.tensor( # pylint: disable=E1101 - [np.array(r) + np.array(i) * 1j for r, i in zip(*d["data"])], - ).type(d["dtype"]) - return torch.tensor(d["data"]).type(d["dtype"]) # pylint: disable=E1101 - elif np is not None and modname == "numpy" and classname == "array": - if d["dtype"].startswith("complex"): - return np.array( - [np.array(r) + np.array(i) * 1j for r, i in zip(*d["data"])], - dtype=d["dtype"], - ) - return np.array(d["data"], dtype=d["dtype"]) - elif pd is not None and modname == "pandas": - if classname == "DataFrame": - decoded_data = MontyDecoder().decode(d["data"]) - return pd.DataFrame(decoded_data) - if classname == "Series": - decoded_data = MontyDecoder().decode(d["data"]) - return pd.Series(decoded_data) - elif (bson is not None) and modname == "bson.objectid" and classname == "ObjectId": - return bson.objectid.ObjectId(d["oid"]) - - return {self.process_decoded(k): self.process_decoded(v) for k, v in d.items()} - - if isinstance(d, list): - return [self.process_decoded(x) for x in d] - - return d
- -
[docs] def decode(self, s): - """ - Overrides decode from JSONDecoder. - - :param s: string - :return: Object. - """ - if orjson is not None: - try: - d = orjson.loads(s) # pylint: disable=E1101 - except orjson.JSONDecodeError: # pylint: disable=E1101 - d = json.loads(s) - else: - d = json.loads(s) - return self.process_decoded(d)
- - -
[docs]class MSONError(Exception): - """ - Exception class for serialization errors. - """
- - -
[docs]def jsanitize(obj, strict=False, allow_bson=False, enum_values=False, recursive_msonable=False): - """ - This method cleans an input json-like object, either a list or a dict or - some sequence, nested or otherwise, by converting all non-string - dictionary keys (such as int and float) to strings, and also recursively - encodes all objects using Monty's as_dict() protocol. - - Args: - obj: input json-like object. - strict (bool): This parameters sets the behavior when jsanitize - encounters an object it does not understand. If strict is True, - jsanitize will try to get the as_dict() attribute of the object. If - no such attribute is found, an attribute error will be thrown. If - strict is False, jsanitize will simply call str(object) to convert - the object to a string representation. - allow_bson (bool): This parameters sets the behavior when jsanitize - encounters a bson supported type such as objectid and datetime. If - True, such bson types will be ignored, allowing for proper - insertion into MongoDB databases. - enum_values (bool): Convert Enums to their values. - recursive_msonable (bool): If True, uses .as_dict() for MSONables regardless - of the value of strict. - - Returns: - Sanitized dict that can be json serialized. - """ - if isinstance(obj, Enum) and enum_values: - return obj.value - - if allow_bson and ( - isinstance(obj, (datetime.datetime, bytes)) or (bson is not None and isinstance(obj, bson.objectid.ObjectId)) - ): - return obj - if isinstance(obj, (list, tuple)): - return [jsanitize(i, strict=strict, allow_bson=allow_bson, enum_values=enum_values) for i in obj] - if np is not None and isinstance(obj, np.ndarray): - return [jsanitize(i, strict=strict, allow_bson=allow_bson, enum_values=enum_values) for i in obj.tolist()] - if np is not None and isinstance(obj, np.generic): - return obj.item() - if pd is not None and isinstance(obj, (pd.Series, pd.DataFrame)): - return obj.to_dict() - if isinstance(obj, dict): - return { - str(k): jsanitize( - v, - strict=strict, - allow_bson=allow_bson, - enum_values=enum_values, - recursive_msonable=recursive_msonable, - ) - for k, v in obj.items() - } - if isinstance(obj, (int, float)): - return obj - if obj is None: - return None - if isinstance(obj, pathlib.Path) or isinstance(obj, datetime.datetime): - return str(obj) - - if callable(obj) and not isinstance(obj, MSONable): - try: - return _serialize_callable(obj) - except TypeError: - pass - - if recursive_msonable and isinstance(obj, MSONable): - return obj.as_dict() - - if not strict: - return str(obj) - - if isinstance(obj, str): - return obj - - if pydantic is not None and isinstance(obj, pydantic.BaseModel): # pylint: disable=E1101 - return jsanitize( - MontyEncoder().default(obj), - strict=strict, - allow_bson=allow_bson, - enum_values=enum_values, - recursive_msonable=recursive_msonable, - ) - - return jsanitize( - obj.as_dict(), - strict=strict, - allow_bson=allow_bson, - enum_values=enum_values, - recursive_msonable=recursive_msonable, - )
- - -def _serialize_callable(o): - if isinstance(o, types.BuiltinFunctionType): - # don't care about what builtin functions (sum, open, etc) are bound to - bound = None - else: - # bound methods (i.e., instance methods) have a __self__ attribute - # that points to the class/module/instance - bound = getattr(o, "__self__", None) - - # we are only able to serialize bound methods if the object the method is - # bound to is itself serializable - if bound is not None: - try: - bound = MontyEncoder().default(bound) - except TypeError: - raise TypeError("Only bound methods of classes or MSONable instances are supported.") - - return { - "@module": o.__module__, - "@callable": getattr(o, "__qualname__", o.__name__), - "@bound": bound, - } -
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/logging.html b/docs/_modules/monty/logging.html deleted file mode 100644 index 78cb0f90b..000000000 --- a/docs/_modules/monty/logging.html +++ /dev/null @@ -1,161 +0,0 @@ - - - - - - - monty.logging — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.logging

-#!/usr/bin/env python
-
-"""
-Logging tools
-"""
-
-import argparse
-import datetime
-import functools
-import logging
-
-logger = logging.getLogger(__name__)
-
-
-
[docs]def logged(level=logging.DEBUG): - """ - Useful logging decorator. If a method is logged, the beginning and end of - the method call will be logged at a pre-specified level. - - Args: - level: Level to log method at. Defaults to DEBUG. - """ - - def wrap(f): - _logger = logging.getLogger(f"{f.__module__}.{f.__name__}") - - def wrapped_f(*args, **kwargs): - _logger.log( - level, - f"Called at {datetime.datetime.now()} with args = {args} and kwargs = {kwargs}", - ) - data = f(*args, **kwargs) - _logger.log( - level, - f"Done at {datetime.datetime.now()} with args = {args} and kwargs = {kwargs}", - ) - return data - - return wrapped_f - - return wrap
- - -
[docs]def enable_logging(main): - """ - This decorator is used to decorate main functions. - It adds the initialization of the logger and an argument parser that allows - one to select the loglevel. - Useful if we are writing simple main functions that call libraries where - the logging module is used - - Args: - main: - main function. - """ - - @functools.wraps(main) - def wrapper(*args, **kwargs): - parser = argparse.ArgumentParser() - - parser.add_argument( - "--loglevel", - default="ERROR", - type=str, - help="Set the loglevel. Possible values: CRITICAL, ERROR (default)," "WARNING, INFO, DEBUG", - ) - - options = parser.parse_args() - - # loglevel is bound to the string value obtained from the command line - # argument. - # Convert to upper case to allow the user to specify --loglevel=DEBUG - # or --loglevel=debug - numeric_level = getattr(logging, options.loglevel.upper(), None) - if not isinstance(numeric_level, int): - raise ValueError(f"Invalid log level: {options.loglevel}") - logging.basicConfig(level=numeric_level) - - retcode = main(*args, **kwargs) - return retcode - - return wrapper
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/math.html b/docs/_modules/monty/math.html deleted file mode 100644 index 8d05d1aff..000000000 --- a/docs/_modules/monty/math.html +++ /dev/null @@ -1,114 +0,0 @@ - - - - - - - monty.math — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.math

-"""
-Addition math functions.
-"""
-
-import math
-
-
-
[docs]def nCr(n, r): - """ - Calculates nCr. - - Args: - n (int): total number of items. - r (int): items to choose - - Returns: - nCr. - """ - f = math.factorial - return int(f(n) / f(r) / f(n - r))
- - -
[docs]def nPr(n, r): - """ - Calculates nPr. - - Args: - n (int): total number of items. - r (int): items to permute - - Returns: - nPr. - """ - f = math.factorial - return int(f(n) / f(n - r))
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/msgpack.html b/docs/_modules/monty/msgpack.html deleted file mode 100644 index 709cbbe21..000000000 --- a/docs/_modules/monty/msgpack.html +++ /dev/null @@ -1,102 +0,0 @@ - - - - - - - monty.msgpack — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.msgpack

-"""
-msgpack serialization and deserialization utilities. Right now, this is a stub
-using monty.json encoder and decoders. The naming is just for clearer usage with
-msgpack's default and object_hook naming.
-"""
-
-from monty.json import MontyDecoder, MontyEncoder
-
-
-
[docs]def default(obj): - """ - For use with msgpack.packb(obj, default=default). Supports Monty's as_dict - protocol, numpy arrays and datetime. - """ - return MontyEncoder().default(obj)
- - -
[docs]def object_hook(d): - """ - For use with msgpack.unpackb(dict, object_hook=object_hook.). Supports - Monty's as_dict protocol, numpy arrays and datetime. - """ - return MontyDecoder().process_decoded(d)
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/multiprocessing.html b/docs/_modules/monty/multiprocessing.html deleted file mode 100644 index d5a6ac2a9..000000000 --- a/docs/_modules/monty/multiprocessing.html +++ /dev/null @@ -1,117 +0,0 @@ - - - - - - - monty.multiprocessing — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.multiprocessing

-"""
-Multiprocessing utilities.
-"""
-
-from multiprocessing import Pool
-from typing import Callable, Iterable
-
-try:
-    from tqdm.autonotebook import tqdm
-except ImportError:
-    tqdm = None
-
-
-
[docs]def imap_tqdm(nprocs: int, func: Callable, iterable: Iterable, *args, **kwargs): - """ - A wrapper around Pool.imap. Creates a Pool with nprocs and then runs a f - unction over an iterable with progress bar. - - :param nprocs: Number of processes - :param func: Callable - :param iterable: Iterable of arguments. - :param args: Passthrough to Pool.imap - :param kwargs: Passthrough to Pool.imap - :return: Results of Pool.imap. - """ - if tqdm is None: - raise ImportError("tqdm must be installed for this function.") - data = [] - with Pool(nprocs) as pool: - try: - n = len(iterable) # type: ignore - except TypeError: - n = None # type: ignore - with tqdm(total=n) as pbar: - for i, d in enumerate(pool.imap(func, iterable, *args, **kwargs)): - pbar.update() - data.append(d) - return data
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/operator.html b/docs/_modules/monty/operator.html deleted file mode 100644 index a8a2c90d9..000000000 --- a/docs/_modules/monty/operator.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - monty.operator — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.operator

-"""
-Useful additional functions for operators
-"""
-import operator
-
-
-
[docs]def operator_from_str(op): - """ - Return the operator associated to the given string `op`. - - raises: - `KeyError` if invalid string. - """ - d = { - "==": operator.eq, - "!=": operator.ne, - ">": operator.gt, - ">=": operator.ge, - "<": operator.lt, - "<=": operator.le, - "+": operator.add, - "-": operator.sub, - "*": operator.mul, - "%": operator.mod, - "^": operator.xor, - } - - try: - d["/"] = operator.truediv - except AttributeError: - pass - - return d[op]
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/os.html b/docs/_modules/monty/os.html deleted file mode 100644 index f38b2cee6..000000000 --- a/docs/_modules/monty/os.html +++ /dev/null @@ -1,134 +0,0 @@ - - - - - - - monty.os — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.os

-"""
-Os functions, e.g., cd, makedirs_p.
-"""
-
-import errno
-import os
-from contextlib import contextmanager
-
-__author__ = "Shyue Ping Ong"
-__copyright__ = "Copyright 2013, The Materials Project"
-__version__ = "0.1"
-__maintainer__ = "Shyue Ping Ong"
-__email__ = "ongsp@ucsd.edu"
-__date__ = "1/24/14"
-
-
-
[docs]@contextmanager -def cd(path): - """ - A Fabric-inspired cd context that temporarily changes directory for - performing some tasks, and returns to the original working directory - afterwards. E.g., - - with cd("/my/path/"): - do_something() - - Args: - path: Path to cd to. - """ - cwd = os.getcwd() - os.chdir(path) - try: - yield - finally: - os.chdir(cwd)
- - -
[docs]def makedirs_p(path, **kwargs): - """ - Wrapper for os.makedirs that does not raise an exception if the directory - already exists, in the fashion of "mkdir -p" command. The check is - performed in a thread-safe way - - Args: - path: path of the directory to create - kwargs: standard kwargs for os.makedirs - """ - - try: - os.makedirs(path, **kwargs) - except OSError as exc: - if exc.errno == errno.EEXIST and os.path.isdir(path): - pass - else: - raise
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/os/path.html b/docs/_modules/monty/os/path.html deleted file mode 100644 index abcd9552f..000000000 --- a/docs/_modules/monty/os/path.html +++ /dev/null @@ -1,206 +0,0 @@ - - - - - - - monty.os.path — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.os.path

-"""
-Path based methods, e.g., which, zpath, etc.
-"""
-import os
-import shutil
-
-from monty.dev import deprecated
-from monty.fnmatch import WildCard
-from monty.string import list_strings
-
-
-@deprecated(shutil.which, message="shutil.which has been available since Python 3.3. This will be removed in v2023.")
-def which(cmd):
-    """
-    Returns full path to a executable.
-
-    Args:
-        cmd (str): Executable command to search for.
-
-    Returns:
-        (str) Full path to command. None if it is not found.
-
-    Example::
-
-        full_path_to_python = which("python")
-    """
-
-    def is_exe(fp):
-        return os.path.isfile(fp) and os.access(fp, os.X_OK)
-
-    fpath, fname = os.path.split(cmd)
-    if fpath:
-        if is_exe(cmd):
-            return cmd
-    else:
-        for path in os.environ["PATH"].split(os.pathsep):
-            exe_file = os.path.join(path, cmd)
-            if is_exe(exe_file):
-                return exe_file
-    return None
-
-
-
[docs]def zpath(filename): - """ - Returns an existing (zipped or unzipped) file path given the unzipped - version. If no path exists, returns the filename unmodified. - - Args: - filename: filename without zip extension - - Returns: - filename with a zip extension (unless an unzipped version - exists). If filename is not found, the same filename is returned - unchanged. - """ - for ext in ["", ".gz", ".GZ", ".bz2", ".BZ2", ".z", ".Z"]: - zfilename = f"{filename}{ext}" - if os.path.exists(zfilename): - return zfilename - return filename
- - -
[docs]def find_exts(top, exts, exclude_dirs=None, include_dirs=None, match_mode="basename"): - """ - Find all files with the extension listed in `exts` that are located within - the directory tree rooted at `top` (including top itself, but excluding - '.' and '..') - - Args: - top (str): Root directory - exts (str or list of strings): List of extensions. - exclude_dirs (str): Wildcards used to exclude particular directories. - Can be concatenated via `|` - include_dirs (str): Wildcards used to select particular directories. - `include_dirs` and `exclude_dirs` are mutually exclusive - match_mode (str): "basename" if match should be done on the basename. - "abspath" for absolute path. - - Returns: - (list of str): Absolute paths of the files. - - Examples:: - - # Find all pdf and ps files starting from the current directory. - find_exts(".", ("pdf", "ps")) - - # Find all pdf files, exclude hidden directories and dirs whose name - # starts with `_` - find_exts(".", "pdf", exclude_dirs="_*|.*") - - # Find all ps files, in the directories whose basename starts with - # output. - find_exts(".", "ps", include_dirs="output*")) - """ - exts = list_strings(exts) - - # Handle file! - if os.path.isfile(top): - return [os.path.abspath(top)] if any(top.endswith(ext) for ext in exts) else [] - - # Build shell-style wildcards. - if exclude_dirs is not None: - exclude_dirs = WildCard(exclude_dirs) - - if include_dirs is not None: - include_dirs = WildCard(include_dirs) - - mangle = dict(basename=os.path.basename, abspath=os.path.abspath)[match_mode] - - # Assume directory - paths = [] - for dirpath, dirnames, filenames in os.walk(top): - dirpath = os.path.abspath(dirpath) - - if exclude_dirs and exclude_dirs.match(mangle(dirpath)): - continue - if include_dirs and not include_dirs.match(mangle(dirpath)): - continue - - for filename in filenames: - if any(filename.endswith(ext) for ext in exts): - paths.append(os.path.join(dirpath, filename)) - - return paths
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/pprint.html b/docs/_modules/monty/pprint.html deleted file mode 100644 index 69defc30f..000000000 --- a/docs/_modules/monty/pprint.html +++ /dev/null @@ -1,206 +0,0 @@ - - - - - - - monty.pprint — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.pprint

-"""
-Pretty printing functions.
-"""
-
-import sys
-from io import StringIO
-from json import JSONEncoder, loads
-
-
-
[docs]def pprint_table(table, out=sys.stdout, rstrip=False): - """ - Prints out a table of data, padded for alignment - Each row must have the same number of columns. - - Args: - table: The table to print. A list of lists. - out: Output stream (file-like object) - rstrip: if True, trailing withespaces are removed from the entries. - """ - - def max_width_col(table, col_idx): - """ - Get the maximum width of the given column index - """ - return max(len(row[col_idx]) for row in table) - - if rstrip: - for row_idx, row in enumerate(table): - table[row_idx] = [c.rstrip() for c in row] - - col_paddings = [] - ncols = len(table[0]) - for i in range(ncols): - col_paddings.append(max_width_col(table, i)) - - for row in table: - # left col - out.write(row[0].ljust(col_paddings[0] + 1)) - # rest of the cols - for i in range(1, len(row)): - col = row[i].rjust(col_paddings[i] + 2) - out.write(col) - out.write("\n")
- - -
[docs]def draw_tree(node, child_iter=lambda n: n.children, text_str=lambda n: str(n)): - """ - Args: - node: the root of the tree to be drawn, - child_iter: function that when called with a node, returns an iterable - over all its children - text_str: turns a node into the text to be displayed in the tree. - - The default implementations of these two arguments retrieve the children - by accessing node.children and simply use str(node) to convert a node to a - string. The resulting tree is drawn into a buffer and returned as a string. - - Based on https://pypi.python.org/pypi/asciitree/ - """ - return _draw_tree(node, "", child_iter, text_str)
- - -def _draw_tree(node, prefix, child_iter, text_str): - buf = StringIO() - - children = list(child_iter(node)) - - # check if root node - if prefix: - buf.write(prefix[:-3]) - buf.write(" +--") - buf.write(text_str(node)) - buf.write("\n") - - for index, child in enumerate(children): - if index + 1 == len(children): - sub_prefix = prefix + " " - else: - sub_prefix = prefix + " |" - - buf.write(_draw_tree(child, sub_prefix, child_iter, text_str)) - - return buf.getvalue() - - -
[docs]class DisplayEcoder(JSONEncoder): - """ - Help convert dicts and objects to a format that can be displayed in notebooks - """ - -
[docs] def default(self, o): - """ - Try diffent ways of converting the present object for displaying - """ - try: - return o.as_dict() - except Exception: - pass - - try: - return o.__dict__ - except Exception: - pass - - try: - return str(o) - except Exception: - pass - - return None
- - -
[docs]def pprint_json(data): - """ - Display a tree-like object in a jupyter notebook. - Allows for collapsible interactive interaction with data. - - Args: - data: a dictionary or object - - Based on: - https://gist.github.com/jmmshn/d37d5a1be80a6da11f901675f195ca22 - - """ - from IPython.display import JSON, display # pylint: disable=C0415 - - display(JSON(loads(DisplayEcoder().encode(data))))
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/re.html b/docs/_modules/monty/re.html deleted file mode 100644 index f3661b002..000000000 --- a/docs/_modules/monty/re.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - monty.re — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.re

-"""
-Helpful regex based functions. E.g., grepping.
-"""
-
-import collections
-import re
-
-from monty.io import reverse_readfile, zopen
-
-
-
[docs]def regrep(filename, patterns, reverse=False, terminate_on_match=False, postprocess=str): - r""" - A powerful regular expression version of grep. - - Args: - filename (str): Filename to grep. - patterns (dict): A dict of patterns, e.g., - {"energy": r"energy\\(sigma->0\\)\\s+=\\s+([\\d\\-\\.]+)"}. - reverse (bool): Read files in reverse. Defaults to false. Useful for - large files, especially when used with terminate_on_match. - terminate_on_match (bool): Whether to terminate when there is at - least one match in each key in pattern. - postprocess (callable): A post processing function to convert all - matches. Defaults to str, i.e., no change. - - Returns: - A dict of the following form: - {key1: [[[matches...], lineno], [[matches...], lineno], - [[matches...], lineno], ...], - key2: ...} - For reverse reads, the lineno is given as a -ve number. Please note - that 0-based indexing is used. - """ - compiled = {k: re.compile(v) for k, v in patterns.items()} - matches = collections.defaultdict(list) - gen = reverse_readfile(filename) if reverse else zopen(filename, "rt") - for i, l in enumerate(gen): - for k, p in compiled.items(): - m = p.search(l) - if m: - matches[k].append([[postprocess(g) for g in m.groups()], -i if reverse else i]) - if terminate_on_match and all(len(matches.get(k, [])) for k in compiled.keys()): - break - try: - # Try to close open file handle. Pass if it is a generator. - gen.close() - except Exception: - pass - return matches
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/serialization.html b/docs/_modules/monty/serialization.html deleted file mode 100644 index 48aa123dd..000000000 --- a/docs/_modules/monty/serialization.html +++ /dev/null @@ -1,204 +0,0 @@ - - - - - - - monty.serialization — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.serialization

-"""
-This module implements serialization support for common formats such as json
-and yaml.
-"""
-import json
-import os
-
-try:
-    from ruamel.yaml import YAML
-except ImportError:
-    YAML = None  # type: ignore
-
-from monty.io import zopen
-from monty.json import MontyDecoder, MontyEncoder
-from monty.msgpack import default, object_hook
-
-try:
-    import msgpack
-except ImportError:
-    msgpack = None
-
-
-
[docs]def loadfn(fn, *args, fmt=None, **kwargs): - r""" - Loads json/yaml/msgpack directly from a filename instead of a - File-like object. File may also be a BZ2 (".BZ2") or GZIP (".GZ", ".Z") - compressed file. - For YAML, ruamel.yaml must be installed. The file type is automatically - detected from the file extension (case insensitive). - YAML is assumed if the filename contains ".yaml" or ".yml". - Msgpack is assumed if the filename contains ".mpk". - JSON is otherwise assumed. - - Args: - fn (str/Path): filename or pathlib.Path. - *args: Any of the args supported by json/yaml.load. - fmt (string): If specified, the fmt specified would be used instead - of autodetection from filename. Supported formats right now are - "json", "yaml" or "mpk". - **kwargs: Any of the kwargs supported by json/yaml.load. - - Returns: - (object) Result of json/yaml/msgpack.load. - """ - - if fmt is None: - basename = os.path.basename(fn).lower() - if ".mpk" in basename: - fmt = "mpk" - elif any(ext in basename for ext in (".yaml", ".yml")): - fmt = "yaml" - else: - fmt = "json" - - if fmt == "mpk": - if msgpack is None: - raise RuntimeError("Loading of message pack files is not possible as msgpack-python is not installed.") - if "object_hook" not in kwargs: - kwargs["object_hook"] = object_hook - with zopen(fn, "rb") as fp: - return msgpack.load(fp, *args, **kwargs) # pylint: disable=E1101 - else: - with zopen(fn, "rt") as fp: - if fmt == "yaml": - if YAML is None: - raise RuntimeError("Loading of YAML files requires ruamel.yaml.") - yaml = YAML() - return yaml.load(fp, *args, **kwargs) - if fmt == "json": - if "cls" not in kwargs: - kwargs["cls"] = MontyDecoder - return json.load(fp, *args, **kwargs) - - raise TypeError(f"Invalid format: {fmt}")
- - -
[docs]def dumpfn(obj, fn, *args, fmt=None, **kwargs): - r""" - Dump to a json/yaml directly by filename instead of a - File-like object. File may also be a BZ2 (".BZ2") or GZIP (".GZ", ".Z") - compressed file. - For YAML, ruamel.yaml must be installed. The file type is automatically - detected from the file extension (case insensitive). YAML is assumed if the - filename contains ".yaml" or ".yml". - Msgpack is assumed if the filename contains ".mpk". - JSON is otherwise assumed. - - Args: - obj (object): Object to dump. - fn (str/Path): filename or pathlib.Path. - *args: Any of the args supported by json/yaml.dump. - **kwargs: Any of the kwargs supported by json/yaml.dump. - - Returns: - (object) Result of json.load. - """ - if fmt is None: - basename = os.path.basename(fn).lower() - if ".mpk" in basename: - fmt = "mpk" - elif any(ext in basename for ext in (".yaml", ".yml")): - fmt = "yaml" - else: - fmt = "json" - - if fmt == "mpk": - if msgpack is None: - raise RuntimeError("Loading of message pack files is not possible as msgpack-python is not installed.") - if "default" not in kwargs: - kwargs["default"] = default - with zopen(fn, "wb") as fp: - msgpack.dump(obj, fp, *args, **kwargs) # pylint: disable=E1101 - else: - with zopen(fn, "wt") as fp: - if fmt == "yaml": - if YAML is None: - raise RuntimeError("Loading of YAML files requires ruamel.yaml.") - yaml = YAML() - yaml.dump(obj, fp, *args, **kwargs) - elif fmt == "json": - if "cls" not in kwargs: - kwargs["cls"] = MontyEncoder - fp.write(json.dumps(obj, *args, **kwargs)) - else: - raise TypeError(f"Invalid format: {fmt}")
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/shutil.html b/docs/_modules/monty/shutil.html deleted file mode 100644 index 1ba6deae0..000000000 --- a/docs/_modules/monty/shutil.html +++ /dev/null @@ -1,227 +0,0 @@ - - - - - - - monty.shutil — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.shutil

-"""
-Copying and zipping utilities. Works on directories mostly.
-"""
-
-import os
-import shutil
-import warnings
-from gzip import GzipFile
-
-from .io import zopen
-
-
-
[docs]def copy_r(src, dst): - """ - Implements a recursive copy function similar to Unix's "cp -r" command. - Surprisingly, python does not have a real equivalent. shutil.copytree - only works if the destination directory is not present. - - Args: - src (str): Source folder to copy. - dst (str): Destination folder. - """ - - abssrc = os.path.abspath(src) - absdst = os.path.abspath(dst) - try: - os.makedirs(absdst) - except OSError: - # If absdst exists, an OSError is raised. We ignore this error. - pass - for f in os.listdir(abssrc): - fpath = os.path.join(abssrc, f) - if os.path.isfile(fpath): - shutil.copy(fpath, absdst) - elif not absdst.startswith(fpath): - copy_r(fpath, os.path.join(absdst, f)) - else: - warnings.warn(f"Cannot copy {fpath} to itself")
- - -
[docs]def gzip_dir(path, compresslevel=6): - """ - Gzips all files in a directory. Note that this is different from - shutil.make_archive, which creates a tar archive. The aim of this method - is to create gzipped files that can still be read using common Unix-style - commands like zless or zcat. - - Args: - path (str): Path to directory. - compresslevel (int): Level of compression, 1-9. 9 is default for - GzipFile, 6 is default for gzip. - """ - for root, _, files in os.walk(path): - for f in files: - full_f = os.path.abspath(os.path.join(root, f)) - if not f.lower().endswith("gz") and not os.path.isdir(full_f): - with open(full_f, "rb") as f_in, GzipFile(f"{full_f}.gz", "wb", compresslevel=compresslevel) as f_out: - shutil.copyfileobj(f_in, f_out) - shutil.copystat(full_f, f"{full_f}.gz") - os.remove(full_f)
- - -
[docs]def compress_file(filepath, compression="gz"): - """ - Compresses a file with the correct extension. Functions like standard - Unix command line gzip and bzip2 in the sense that the original - uncompressed files are not retained. - - Args: - filepath (str): Path to file. - compression (str): A compression mode. Valid options are "gz" or - "bz2". Defaults to "gz". - """ - if compression not in ["gz", "bz2"]: - raise ValueError("Supported compression formats are 'gz' and 'bz2'.") - if not filepath.lower().endswith(f".{compression}"): - with open(filepath, "rb") as f_in, zopen(f"{filepath}.{compression}", "wb") as f_out: - f_out.writelines(f_in) - os.remove(filepath)
- - -
[docs]def compress_dir(path, compression="gz"): - """ - Recursively compresses all files in a directory. Note that this - compresses all files singly, i.e., it does not create a tar archive. For - that, just use Python tarfile class. - - Args: - path (str): Path to parent directory. - compression (str): A compression mode. Valid options are "gz" or - "bz2". Defaults to gz. - """ - for parent, subdirs, files in os.walk(path): - for f in files: - compress_file(os.path.join(parent, f), compression=compression)
- - -
[docs]def decompress_file(filepath): - """ - Decompresses a file with the correct extension. Automatically detects - gz, bz2 or z extension. - - Args: - filepath (str): Path to file. - compression (str): A compression mode. Valid options are "gz" or - "bz2". Defaults to "gz". - """ - toks = filepath.split(".") - file_ext = toks[-1].upper() - if file_ext in ["BZ2", "GZ", "Z"]: - with open(".".join(toks[0:-1]), "wb") as f_out, zopen(filepath, "rb") as f_in: - f_out.writelines(f_in) - os.remove(filepath)
- - -
[docs]def decompress_dir(path): - """ - Recursively decompresses all files in a directory. - - Args: - path (str): Path to parent directory. - """ - for parent, subdirs, files in os.walk(path): - for f in files: - decompress_file(os.path.join(parent, f))
- - -
[docs]def remove(path, follow_symlink=False): - """ - Implements a remove function that will delete files, folder trees and - symlink trees - - 1.) Remove a file - 2.) Remove a symlink and follow into with a recursive rm if follow_symlink - 3.) Remove directory with rmtree - - Args: - path (str): path to remove - follow_symlink(bool): follow symlinks and removes whatever is in them - """ - if os.path.isfile(path): - os.remove(path) - elif os.path.islink(path): - if follow_symlink: - remove(os.readlink(path)) - os.unlink(path) - else: - shutil.rmtree(path)
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/string.html b/docs/_modules/monty/string.html deleted file mode 100644 index 33a88f396..000000000 --- a/docs/_modules/monty/string.html +++ /dev/null @@ -1,220 +0,0 @@ - - - - - - - monty.string — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.string

-"""
-Useful additional string functions.
-"""
-
-import sys
-
-
-
[docs]def remove_non_ascii(s): - """ - Remove non-ascii characters in a file. Needed when support for non-ASCII - is not available. - - Args: - s (str): Input string - - Returns: - String with all non-ascii characters removed. - """ - return "".join(i for i in s if ord(i) < 128)
- - -
[docs]def unicode2str(s): - """ - Forces a unicode to a string in Python 2, but transparently handles - Python 3. - - Args: - s (str/unicode): Input string / unicode. - - Returns: - str in Python 2. Unchanged otherwise. - """ - return s.encode("utf-8") if sys.version_info.major < 3 else s
- - -
[docs]def is_string(s): - """True if s behaves like a string (duck typing test).""" - try: - s + " " - return True - - except TypeError: - return False
- - -
[docs]def list_strings(arg): - """ - Always return a list of strings, given a string or list of strings as - input. - - :Examples: - - >>> list_strings('A single string') - ['A single string'] - - >>> list_strings(['A single string in a list']) - ['A single string in a list'] - - >>> list_strings(['A','list','of','strings']) - ['A', 'list', 'of', 'strings'] - """ - if is_string(arg): - return [arg] - - return arg
- - -
[docs]def marquee(text="", width=78, mark="*"): - """ - Return the input string centered in a 'marquee'. - - Args: - text (str): Input string - width (int): Width of final output string. - mark (str): Character used to fill string. - - :Examples: - - >>> marquee('A test', width=40) - '**************** A test ****************' - - >>> marquee('A test', width=40, mark='-') - '---------------- A test ----------------' - - marquee('A test',40, ' ') - ' A test ' - """ - if not text: - return (mark * width)[:width] - - nmark = (width - len(text) - 2) // len(mark) // 2 - nmark = max(nmark, 0) - - marks = mark * nmark - return f"{marks} {text} {marks}"
- - -
[docs]def boxed(msg, ch="=", pad=5): - """ - Returns a string in a box - - Args: - msg: Input string. - ch: Character used to form the box. - pad: Number of characters ch added before and after msg. - - >>> print(boxed("hello", ch="*", pad=2)) - *********** - ** hello ** - *********** - """ - if pad > 0: - msg = pad * ch + " " + msg.strip() + " " + pad * ch - - return "\n".join( - [ - len(msg) * ch, - msg, - len(msg) * ch, - ] - )
- - -
[docs]def make_banner(s, width=78, mark="*"): - """ - :param s: String - :param width: Width of banner. Defaults to 78. - :param mark: The mark used to create the banner. - :return: Banner string. - """ - banner = marquee(s, width=width, mark=mark) - return "\n" + len(banner) * mark + "\n" + banner + "\n" + len(banner) * mark
- - -
[docs]def indent(lines, amount, ch=" "): - """ - Indent the lines in a string by padding each one with proper number of pad - characters - """ - padding = amount * ch - return padding + ("\n" + padding).join(lines.split("\n"))
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/subprocess.html b/docs/_modules/monty/subprocess.html deleted file mode 100644 index 6fe15b8f0..000000000 --- a/docs/_modules/monty/subprocess.html +++ /dev/null @@ -1,181 +0,0 @@ - - - - - - - monty.subprocess — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.subprocess

-"""
-Calling shell processes.
-"""
-import shlex
-import threading
-import traceback
-from subprocess import PIPE, Popen
-
-from .string import is_string
-
-__author__ = "Matteo Giantomass"
-__copyright__ = "Copyright 2014, The Materials Virtual Lab"
-__version__ = "0.1"
-__maintainer__ = "Matteo Giantomassi"
-__email__ = "gmatteo@gmail.com"
-__date__ = "10/26/14"
-
-
-
[docs]class Command: - """ - Enables to run subprocess commands in a different thread with TIMEOUT - option. - - Based on jcollado's solution: - http://stackoverflow.com/questions/1191374/subprocess-with-timeout/4825933#4825933 - and - https://gist.github.com/kirpit/1306188 - - .. attribute:: retcode - - Return code of the subprocess - - .. attribute:: killed - - True if subprocess has been killed due to the timeout - - .. attribute:: output - - stdout of the subprocess - - .. attribute:: error - - stderr of the subprocess - - Example: - com = Command("sleep 1").run(timeout=2) - print(com.retcode, com.killed, com.output, com.output) - """ - - def __init__(self, command): - """ - :param command: Command to execute - """ - if is_string(command): - command = shlex.split(command) - self.command = command - self.process = None - self.retcode = None - self.output, self.error = "", "" - self.killed = False - - def __str__(self): - return f"command: {self.command}, retcode: {self.retcode}" - -
[docs] def run(self, timeout=None, **kwargs): - """ - Run a command in a separated thread and wait timeout seconds. - kwargs are keyword arguments passed to Popen. - - Return: self - """ - - def target(**kw): - try: - # print('Thread started') - with Popen(self.command, **kw) as self.process: - self.output, self.error = self.process.communicate() - self.retcode = self.process.returncode - # print('Thread stopped') - except Exception: - self.error = traceback.format_exc() - self.retcode = -1 - - # default stdout and stderr - if "stdout" not in kwargs: - kwargs["stdout"] = PIPE - - if "stderr" not in kwargs: - kwargs["stderr"] = PIPE - - # thread - thread = threading.Thread(target=target, kwargs=kwargs) - thread.start() - thread.join(timeout) - - if thread.is_alive(): - # print("Terminating process") - self.process.terminate() - self.killed = True - thread.join() - - return self
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/tempfile.html b/docs/_modules/monty/tempfile.html deleted file mode 100644 index 0081421cb..000000000 --- a/docs/_modules/monty/tempfile.html +++ /dev/null @@ -1,205 +0,0 @@ - - - - - - - monty.tempfile — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.tempfile

-"""
-Temporary directory and file creation utilities.
-"""
-
-import os
-import tempfile
-from pathlib import Path
-
-from monty.shutil import copy_r, gzip_dir, remove
-
-
-
[docs]class ScratchDir: - """ - .. note:: - - With effect from Python 3.2, tempfile.TemporaryDirectory already - implements much of the functionality of ScratchDir. However, it does - not provide options for copying of files to and from (though it is - possible to do this with other methods provided by shutil). - - Creates a "with" context manager that automatically handles creation of - temporary directories (utilizing Python's build in temp directory - functions) and cleanup when done. This improves on Python's built in - functions by allowing for truly temporary workspace that are deleted - when it is done. The way it works is as follows: - - 1. Create a temp dir in specified root path. - 2. Optionally copy input files from current directory to temp dir. - 3. Change to temp dir. - 4. User performs specified operations. - 5. Optionally copy generated output files back to original directory. - 6. Change back to original directory. - 7. Delete temp dir. - """ - - SCR_LINK = "scratch_link" - - def __init__( - self, - rootpath, - create_symbolic_link=False, - copy_from_current_on_enter=False, - copy_to_current_on_exit=False, - gzip_on_exit=False, - delete_removed_files=True, - ): - """ - Initializes scratch directory given a **root** path. There is no need - to try to create unique directory names. The code will generate a - temporary sub directory in the rootpath. The way to use this is using a - with context manager. Example:: - - with ScratchDir("/scratch"): - do_something() - - If the root path does not exist or is None, this will function as a - simple pass through, i.e., nothing happens. - - Args: - rootpath (str/Path): Path in which to create temp subdirectories. - If this is None, no temp directories will be created and - this will just be a simple pass through. - create_symbolic_link (bool): Whether to create a symbolic link in - the current working directory to the scratch directory - created. - copy_from_current_on_enter (bool): Whether to copy all files from - the current directory (recursively) to the temp dir at the - start, e.g., if input files are needed for performing some - actions. Defaults to False. - copy_to_current_on_exit (bool): Whether to copy files from the - scratch to the current directory (recursively) at the end. E - .g., if output files are generated during the operation. - Defaults to False. - gzip_on_exit (bool): Whether to gzip the files generated in the - ScratchDir before copying them back. - Defaults to False. - delete_removed_files (bool): Whether to delete files in the cwd - that are removed from the tmp dir. - Defaults to True - """ - if Path is not None and isinstance(rootpath, Path): - rootpath = str(rootpath) - - self.rootpath = os.path.abspath(rootpath) if rootpath is not None else None - self.cwd = os.getcwd() - self.create_symbolic_link = create_symbolic_link - self.start_copy = copy_from_current_on_enter - self.end_copy = copy_to_current_on_exit - self.gzip_on_exit = gzip_on_exit - self.delete_removed_files = delete_removed_files - - def __enter__(self): - tempdir = self.cwd - if self.rootpath is not None and os.path.exists(self.rootpath): - tempdir = tempfile.mkdtemp(dir=self.rootpath) - self.tempdir = os.path.abspath(tempdir) - if self.start_copy: - copy_r(self.cwd, tempdir) - if self.create_symbolic_link: - os.symlink(tempdir, ScratchDir.SCR_LINK) - os.chdir(tempdir) - return tempdir - - def __exit__(self, exc_type, exc_val, exc_tb): - if self.rootpath is not None and os.path.exists(self.rootpath): - if self.end_copy: - files = set(os.listdir(self.tempdir)) - orig_files = set(os.listdir(self.cwd)) - - # gzip files - if self.gzip_on_exit: - gzip_dir(self.tempdir) - - # copy files over - copy_r(self.tempdir, self.cwd) - - # Delete any files that are now gone - if self.delete_removed_files: - for f in orig_files - files: - fpath = os.path.join(self.cwd, f) - remove(fpath) - - os.chdir(self.cwd) - remove(self.tempdir) - if self.create_symbolic_link and os.path.islink(ScratchDir.SCR_LINK): - os.remove(ScratchDir.SCR_LINK)
-
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_modules/monty/termcolor.html b/docs/_modules/monty/termcolor.html deleted file mode 100644 index 894143002..000000000 --- a/docs/_modules/monty/termcolor.html +++ /dev/null @@ -1,285 +0,0 @@ - - - - - - - monty.termcolor — monty 2023.5.8 documentation - - - - - - - - - - - - - - - - - -
-
-
-
- -

Source code for monty.termcolor

-"""
-Copyright (c) 2008-2011 Volvox Development Team
-
-# Permission is hereby granted, free of charge, to any person obtaining a copy
-# of this software and associated documentation files (the "Software"), to deal
-# in the Software without restriction, including without limitation the rights
-# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-# copies of the Software, and to permit persons to whom the Software is
-# furnished to do so, subject to the following conditions:
-#
-# The above copyright notice and this permission notice shall be included in
-# all copies or substantial portions of the Software.
-#
-# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-# THE SOFTWARE.
-#
-# Author: Konstantin Lepa <konstantin.lepa@gmail.com>
-
-ANSII Color formatting for output in terminal.
-"""
-import os
-
-try:
-    import curses
-    import fcntl
-    import struct
-    import termios
-except Exception:
-    pass
-
-__all__ = ["colored", "cprint"]
-
-VERSION = (1, 1, 0)
-
-ATTRIBUTES = dict(bold=1, dark=2, underline=4, blink=5, reverse=7, concealed=8)
-
-HIGHLIGHTS = dict(
-    on_grey=40,
-    on_red=41,
-    on_green=42,
-    on_yellow=43,
-    on_blue=44,
-    on_magenta=45,
-    on_cyan=46,
-    on_white=47,
-)
-
-COLORS = dict(grey=30, red=31, green=32, yellow=33, blue=34, magenta=35, cyan=36, white=37)
-
-RESET = "\033[0m"
-
-__ISON = True
-
-
-def enable(true_false):
-    """Enable/Disable ANSII Color formatting"""
-    global __ISON
-    __ISON = true_false
-
-
-def ison():
-    """True if ANSII Color formatting is activated."""
-    return __ISON
-
-
-def stream_has_colours(stream):
-    """
-    True if stream supports colours. Python cookbook, #475186
-    """
-    if not hasattr(stream, "isatty"):
-        return False
-
-    if not stream.isatty():
-        return False  # auto color only on TTYs
-    try:
-        curses.setupterm()
-        return curses.tigetnum("colors") > 2
-    except Exception:
-        return False  # guess false in case of error
-
-
-
[docs]def colored(text, color=None, on_color=None, attrs=None): - """Colorize text. - - Available text colors: - red, green, yellow, blue, magenta, cyan, white. - - Available text highlights: - on_red, on_green, on_yellow, on_blue, on_magenta, on_cyan, on_white. - - Available attributes: - bold, dark, underline, blink, reverse, concealed. - - Example: - colored('Hello, World!', 'red', 'on_grey', ['blue', 'blink']) - colored('Hello, World!', 'green') - """ - - if __ISON and os.getenv("ANSI_COLORS_DISABLED") is None: - fmt_str = "\033[%dm%s" - if color is not None: - text = fmt_str % (COLORS[color], text) - - if on_color is not None: - text = fmt_str % (HIGHLIGHTS[on_color], text) - - if attrs is not None: - for attr in attrs: - text = fmt_str % (ATTRIBUTES[attr], text) - - text += RESET - return text
- - -
[docs]def cprint(text, color=None, on_color=None, attrs=None, **kwargs): - """Print colorize text. - - It accepts arguments of print function. - """ - try: - print((colored(text, color, on_color, attrs)), **kwargs) - except TypeError: - # flush is not supported by py2.7 - kwargs.pop("flush", None) - print((colored(text, color, on_color, attrs)), **kwargs)
- - -def colored_map(text, cmap): - """ - Return colorized text. cmap is a dict mapping tokens to color options. - - .. Example: - - colored_key("foo bar", {bar: "green"}) - colored_key("foo bar", {bar: {"color": "green", "on_color": "on_red"}}) - """ - if not __ISON: - return text - for key, v in cmap.items(): - if isinstance(v, dict): - text = text.replace(key, colored(key, **v)) - else: - text = text.replace(key, colored(key, color=v)) - return text - - -def cprint_map(text, cmap, **kwargs): - """ - Print colorize text. - cmap is a dict mapping keys to color options. - kwargs are passed to print function - - Example: - cprint_map("Hello world", {"Hello": "red"}) - """ - try: - print(colored_map(text, cmap), **kwargs) - except TypeError: - # flush is not supported by py2.7 - kwargs.pop("flush", None) - print(colored_map(text, cmap), **kwargs) - - -def get_terminal_size(): - """ - Return the size of the terminal as (nrow, ncols) - - Based on: - - http://stackoverflow.com/questions/566746/how-to-get-console-window- - width-in-python - """ - try: - rc = os.popen("stty size", "r").read().split() - return int(rc[0]), int(rc[1]) - except Exception: - pass - - env = os.environ - - def ioctl_GWINSZ(fd): - try: - rc = struct.unpack("hh", fcntl.ioctl(fd, termios.TIOCGWINSZ, "1234")) - return rc - except Exception: - return None - - rc = ioctl_GWINSZ(0) or ioctl_GWINSZ(1) or ioctl_GWINSZ(2) - - if not rc: - try: - fd = os.open(os.ctermid(), os.O_RDONLY) - rc = ioctl_GWINSZ(fd) - os.close(fd) - except Exception: - pass - - if not rc: - rc = (env.get("LINES", 25), env.get("COLUMNS", 80)) - - return int(rc[0]), int(rc[1]) -
- -
-
-
-
- -
-
- - - - - - \ No newline at end of file diff --git a/docs/_static/_sphinx_javascript_frameworks_compat.js b/docs/_static/_sphinx_javascript_frameworks_compat.js deleted file mode 100644 index 8549469dc..000000000 --- a/docs/_static/_sphinx_javascript_frameworks_compat.js +++ /dev/null @@ -1,134 +0,0 @@ -/* - * _sphinx_javascript_frameworks_compat.js - * ~~~~~~~~~~ - * - * Compatability shim for jQuery and underscores.js. - * - * WILL BE REMOVED IN Sphinx 6.0 - * xref RemovedInSphinx60Warning - * - */ - -/** - * select a different prefix for underscore - */ -$u = _.noConflict(); - - -/** - * 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) { - if (!x) { - return x - } - return decodeURIComponent(x.replace(/\+/g, ' ')); -}; - -/** - * small helper function to urlencode strings - */ -jQuery.urlencode = encodeURIComponent; - -/** - * This function returns the parsed url parameters of the - * current request. Multiple values per key are supported, - * it will always return arrays of strings for the value parts. - */ -jQuery.getQueryParameters = function(s) { - if (typeof s === 'undefined') - s = document.location.search; - var parts = s.substr(s.indexOf('?') + 1).split('&'); - var result = {}; - for (var i = 0; i < parts.length; i++) { - var tmp = parts[i].split('=', 2); - var key = jQuery.urldecode(tmp[0]); - var value = jQuery.urldecode(tmp[1]); - if (key in result) - result[key].push(value); - else - result[key] = [value]; - } - return result; -}; - -/** - * highlight a given string on a jquery object by wrapping it in - * span elements with the given class name. - */ -jQuery.fn.highlightText = function(text, className) { - function highlight(node, addItems) { - if (node.nodeType === 3) { - var val = node.nodeValue; - var pos = val.toLowerCase().indexOf(text); - if (pos >= 0 && - !jQuery(node.parentNode).hasClass(className) && - !jQuery(node.parentNode).hasClass("nohighlight")) { - var span; - var isInSVG = jQuery(node).closest("body, svg, foreignObject").is("svg"); - if (isInSVG) { - span = document.createElementNS("http://www.w3.org/2000/svg", "tspan"); - } else { - span = document.createElement("span"); - span.className = className; - } - span.appendChild(document.createTextNode(val.substr(pos, text.length))); - node.parentNode.insertBefore(span, node.parentNode.insertBefore( - document.createTextNode(val.substr(pos + text.length)), - node.nextSibling)); - node.nodeValue = val.substr(0, pos); - if (isInSVG) { - var rect = document.createElementNS("http://www.w3.org/2000/svg", "rect"); - var bbox = node.parentElement.getBBox(); - rect.x.baseVal.value = bbox.x; - rect.y.baseVal.value = bbox.y; - rect.width.baseVal.value = bbox.width; - rect.height.baseVal.value = bbox.height; - rect.setAttribute('class', className); - addItems.push({ - "parent": node.parentNode, - "target": rect}); - } - } - } - else if (!jQuery(node).is("button, select, textarea")) { - jQuery.each(node.childNodes, function() { - highlight(this, addItems); - }); - } - } - var addItems = []; - var result = this.each(function() { - highlight(this, addItems); - }); - for (var i = 0; i < addItems.length; ++i) { - jQuery(addItems[i].parent).before(addItems[i].target); - } - return result; -}; - -/* - * backward compatibility for jQuery.browser - * This will be supported until firefox bug is fixed. - */ -if (!jQuery.browser) { - jQuery.uaMatch = function(ua) { - ua = ua.toLowerCase(); - - var match = /(chrome)[ \/]([\w.]+)/.exec(ua) || - /(webkit)[ \/]([\w.]+)/.exec(ua) || - /(opera)(?:.*version|)[ \/]([\w.]+)/.exec(ua) || - /(msie) ([\w.]+)/.exec(ua) || - ua.indexOf("compatible") < 0 && /(mozilla)(?:.*? rv:([\w.]+)|)/.exec(ua) || - []; - - return { - browser: match[ 1 ] || "", - version: match[ 2 ] || "0" - }; - }; - jQuery.browser = {}; - jQuery.browser[jQuery.uaMatch(navigator.userAgent).browser] = true; -} diff --git a/docs/_static/ajax-loader.gif b/docs/_static/ajax-loader.gif deleted file mode 100644 index 61faf8cab23993bd3e1560bff0668bd628642330..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 673 zcmZ?wbhEHb6krfw_{6~Q|Nno%(3)e{?)x>&1u}A`t?OF7Z|1gRivOgXi&7IyQd1Pl zGfOfQ60;I3a`F>X^fL3(@);C=vM_KlFfb_o=k{|A33hf2a5d61U}gjg=>Rd%XaNQW zW@Cw{|b%Y*pl8F?4B9 zlo4Fz*0kZGJabY|>}Okf0}CCg{u4`zEPY^pV?j2@h+|igy0+Kz6p;@SpM4s6)XEMg z#3Y4GX>Hjlml5ftdH$4x0JGdn8~MX(U~_^d!Hi)=HU{V%g+mi8#UGbE-*ao8f#h+S z2a0-5+vc7MU$e-NhmBjLIC1v|)9+Im8x1yacJ7{^tLX(ZhYi^rpmXm0`@ku9b53aN zEXH@Y3JaztblgpxbJt{AtE1ad1Ca>{v$rwwvK(>{m~Gf_=-Ro7Fk{#;i~+{{>QtvI yb2P8Zac~?~=sRA>$6{!(^3;ZP0TPFR(G_-UDU(8Jl0?(IXu$~#4A!880|o%~Al1tN diff --git a/docs/_static/basic.css b/docs/_static/basic.css deleted file mode 100644 index 7577acb1a..000000000 --- a/docs/_static/basic.css +++ /dev/null @@ -1,903 +0,0 @@ -/* - * basic.css - * ~~~~~~~~~ - * - * Sphinx stylesheet -- basic theme. - * - * :copyright: Copyright 2007-2023 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ - -/* -- main layout ----------------------------------------------------------- */ - -div.clearer { - clear: both; -} - -div.section::after { - display: block; - content: ''; - clear: left; -} - -/* -- relbar ---------------------------------------------------------------- */ - -div.related { - width: 100%; - font-size: 90%; -} - -div.related h3 { - display: none; -} - -div.related ul { - margin: 0; - padding: 0 0 0 10px; - list-style: none; -} - -div.related li { - display: inline; -} - -div.related li.right { - float: right; - margin-right: 5px; -} - -/* -- sidebar --------------------------------------------------------------- */ - -div.sphinxsidebarwrapper { - padding: 10px 5px 0 10px; -} - -div.sphinxsidebar { - float: left; - width: 230px; - margin-left: -100%; - font-size: 90%; - word-wrap: break-word; - overflow-wrap : break-word; -} - -div.sphinxsidebar ul { - list-style: none; -} - -div.sphinxsidebar ul ul, -div.sphinxsidebar ul.want-points { - margin-left: 20px; - list-style: square; -} - -div.sphinxsidebar ul ul { - margin-top: 0; - margin-bottom: 0; -} - -div.sphinxsidebar form { - margin-top: 10px; -} - -div.sphinxsidebar input { - border: 1px solid #98dbcc; - font-family: sans-serif; - font-size: 1em; -} - -div.sphinxsidebar #searchbox form.search { - overflow: hidden; -} - -div.sphinxsidebar #searchbox input[type="text"] { - float: left; - width: 80%; - padding: 0.25em; - box-sizing: border-box; -} - -div.sphinxsidebar #searchbox input[type="submit"] { - float: left; - width: 20%; - border-left: none; - padding: 0.25em; - box-sizing: border-box; -} - - -img { - border: 0; - max-width: 100%; -} - -/* -- search page ----------------------------------------------------------- */ - -ul.search { - margin: 10px 0 0 20px; - padding: 0; -} - -ul.search li { - padding: 5px 0 5px 20px; - background-image: url(file.png); - background-repeat: no-repeat; - background-position: 0 7px; -} - -ul.search li a { - font-weight: bold; -} - -ul.search li p.context { - color: #888; - margin: 2px 0 0 30px; - text-align: left; -} - -ul.keywordmatches li.goodmatch a { - font-weight: bold; -} - -/* -- index page ------------------------------------------------------------ */ - -table.contentstable { - width: 90%; - margin-left: auto; - margin-right: auto; -} - -table.contentstable p.biglink { - line-height: 150%; -} - -a.biglink { - font-size: 1.3em; -} - -span.linkdescr { - font-style: italic; - padding-top: 5px; - font-size: 90%; -} - -/* -- general index --------------------------------------------------------- */ - -table.indextable { - width: 100%; -} - -table.indextable td { - text-align: left; - vertical-align: top; -} - -table.indextable ul { - margin-top: 0; - margin-bottom: 0; - list-style-type: none; -} - -table.indextable > tbody > tr > td > ul { - padding-left: 0em; -} - -table.indextable tr.pcap { - height: 10px; -} - -table.indextable tr.cap { - margin-top: 10px; - background-color: #f2f2f2; -} - -img.toggler { - margin-right: 3px; - margin-top: 3px; - cursor: pointer; -} - -div.modindex-jumpbox { - border-top: 1px solid #ddd; - border-bottom: 1px solid #ddd; - margin: 1em 0 1em 0; - padding: 0.4em; -} - -div.genindex-jumpbox { - border-top: 1px solid #ddd; - border-bottom: 1px solid #ddd; - margin: 1em 0 1em 0; - padding: 0.4em; -} - -/* -- domain module index --------------------------------------------------- */ - -table.modindextable td { - padding: 2px; - border-collapse: collapse; -} - -/* -- general body styles --------------------------------------------------- */ - -div.body { - min-width: 360px; - max-width: 800px; -} - -div.body p, div.body dd, div.body li, div.body blockquote { - -moz-hyphens: auto; - -ms-hyphens: auto; - -webkit-hyphens: auto; - hyphens: auto; -} - -a.headerlink { - visibility: hidden; -} - -h1:hover > a.headerlink, -h2:hover > a.headerlink, -h3:hover > a.headerlink, -h4:hover > a.headerlink, -h5:hover > a.headerlink, -h6:hover > a.headerlink, -dt:hover > a.headerlink, -caption:hover > a.headerlink, -p.caption:hover > a.headerlink, -div.code-block-caption:hover > a.headerlink { - visibility: visible; -} - -div.body p.caption { - text-align: inherit; -} - -div.body td { - text-align: left; -} - -.first { - margin-top: 0 !important; -} - -p.rubric { - margin-top: 30px; - font-weight: bold; -} - -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, .figure.align-right, object.align-right { - clear: right; - float: right; - margin-left: 1em; -} - -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, .figure.align-default { - display: block; - margin-left: auto; - margin-right: auto; -} - -.align-left { - text-align: left; -} - -.align-center { - text-align: center; -} - -.align-default { - text-align: center; -} - -.align-right { - text-align: right; -} - -/* -- sidebars -------------------------------------------------------------- */ - -div.sidebar, -aside.sidebar { - margin: 0 0 0.5em 1em; - border: 1px solid #ddb; - padding: 7px; - background-color: #ffe; - width: 40%; - float: right; - clear: right; - overflow-x: auto; -} - -p.sidebar-title { - font-weight: bold; -} - -nav.contents, -aside.topic, -div.admonition, div.topic, blockquote { - clear: left; -} - -/* -- topics ---------------------------------------------------------------- */ - -nav.contents, -aside.topic, -div.topic { - border: 1px solid #ccc; - padding: 7px; - margin: 10px 0 10px 0; -} - -p.topic-title { - font-size: 1.1em; - font-weight: bold; - margin-top: 10px; -} - -/* -- admonitions ----------------------------------------------------------- */ - -div.admonition { - margin-top: 10px; - margin-bottom: 10px; - padding: 7px; -} - -div.admonition dt { - font-weight: bold; -} - -p.admonition-title { - margin: 0px 10px 5px 0px; - font-weight: bold; -} - -div.body p.centered { - text-align: center; - margin-top: 25px; -} - -/* -- content of sidebars/topics/admonitions -------------------------------- */ - -div.sidebar > :last-child, -aside.sidebar > :last-child, -nav.contents > :last-child, -aside.topic > :last-child, -div.topic > :last-child, -div.admonition > :last-child { - margin-bottom: 0; -} - -div.sidebar::after, -aside.sidebar::after, -nav.contents::after, -aside.topic::after, -div.topic::after, -div.admonition::after, -blockquote::after { - display: block; - content: ''; - clear: both; -} - -/* -- tables ---------------------------------------------------------------- */ - -table.docutils { - margin-top: 10px; - margin-bottom: 10px; - border: 0; - border-collapse: collapse; -} - -table.align-center { - margin-left: auto; - margin-right: auto; -} - -table.align-default { - margin-left: auto; - margin-right: auto; -} - -table caption span.caption-number { - font-style: italic; -} - -table caption span.caption-text { -} - -table.docutils td, table.docutils th { - padding: 1px 8px 1px 5px; - border-top: 0; - border-left: 0; - border-right: 0; - border-bottom: 1px solid #aaa; -} - -th { - text-align: left; - padding-right: 5px; -} - -table.citation { - border-left: solid 1px gray; - margin-left: 1px; -} - -table.citation td { - border-bottom: none; -} - -th > :first-child, -td > :first-child { - margin-top: 0px; -} - -th > :last-child, -td > :last-child { - margin-bottom: 0px; -} - -/* -- figures --------------------------------------------------------------- */ - -div.figure, figure { - margin: 0.5em; - padding: 0.5em; -} - -div.figure p.caption, figcaption { - padding: 0.3em; -} - -div.figure p.caption span.caption-number, -figcaption span.caption-number { - font-style: italic; -} - -div.figure p.caption span.caption-text, -figcaption span.caption-text { -} - -/* -- field list styles ----------------------------------------------------- */ - -table.field-list td, table.field-list th { - border: 0 !important; -} - -.field-list ul { - margin: 0; - padding-left: 1em; -} - -.field-list p { - margin: 0; -} - -.field-name { - -moz-hyphens: manual; - -ms-hyphens: manual; - -webkit-hyphens: manual; - hyphens: manual; -} - -/* -- hlist styles ---------------------------------------------------------- */ - -table.hlist { - margin: 1em 0; -} - -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 ----------------------------------------------------- */ - -ol.arabic { - list-style: decimal; -} - -ol.loweralpha { - list-style: lower-alpha; -} - -ol.upperalpha { - list-style: upper-alpha; -} - -ol.lowerroman { - list-style: lower-roman; -} - -ol.upperroman { - list-style: upper-roman; -} - -:not(li) > ol > li:first-child > :first-child, -:not(li) > ul > li:first-child > :first-child { - margin-top: 0px; -} - -:not(li) > ol > li:last-child > :last-child, -:not(li) > ul > li:last-child > :last-child { - margin-bottom: 0px; -} - -ol.simple ol p, -ol.simple ul p, -ul.simple ol p, -ul.simple ul p { - margin-top: 0; -} - -ol.simple > li:not(:first-child) > p, -ul.simple > li:not(:first-child) > p { - margin-top: 0; -} - -ol.simple p, -ul.simple p { - margin-bottom: 0; -} - -aside.footnote > span, -div.citation > span { - float: left; -} -aside.footnote > span:last-of-type, -div.citation > span:last-of-type { - padding-right: 0.5em; -} -aside.footnote > p { - margin-left: 2em; -} -div.citation > p { - margin-left: 4em; -} -aside.footnote > p:last-of-type, -div.citation > p:last-of-type { - margin-bottom: 0em; -} -aside.footnote > p:last-of-type:after, -div.citation > p:last-of-type:after { - content: ""; - clear: both; -} - -dl.field-list { - display: grid; - grid-template-columns: fit-content(30%) auto; -} - -dl.field-list > dt { - font-weight: bold; - word-break: break-word; - padding-left: 0.5em; - padding-right: 5px; -} - -dl.field-list > dd { - padding-left: 0.5em; - margin-top: 0em; - margin-left: 0em; - margin-bottom: 0em; -} - -dl { - margin-bottom: 15px; -} - -dd > :first-child { - margin-top: 0px; -} - -dd ul, dd table { - margin-bottom: 10px; -} - -dd { - margin-top: 3px; - margin-bottom: 10px; - margin-left: 30px; -} - -dl > dd:last-child, -dl > dd:last-child > :last-child { - margin-bottom: 0; -} - -dt:target, span.highlighted { - background-color: #fbe54e; -} - -rect.highlighted { - fill: #fbe54e; -} - -dl.glossary dt { - font-weight: bold; - font-size: 1.1em; -} - -.versionmodified { - font-style: italic; -} - -.system-message { - background-color: #fda; - padding: 5px; - border: 3px solid red; -} - -.footnote:target { - background-color: #ffa; -} - -.line-block { - display: block; - margin-top: 1em; - margin-bottom: 1em; -} - -.line-block .line-block { - margin-top: 0; - margin-bottom: 0; - margin-left: 1.5em; -} - -.guilabel, .menuselection { - font-family: sans-serif; -} - -.accelerator { - text-decoration: underline; -} - -.classifier { - font-style: oblique; -} - -.classifier:before { - font-style: normal; - margin: 0 0.5em; - content: ":"; - display: inline-block; -} - -abbr, acronym { - border-bottom: dotted 1px; - cursor: help; -} - -/* -- code displays --------------------------------------------------------- */ - -pre { - overflow: auto; - overflow-y: hidden; /* fixes display issues on Chrome browsers */ -} - -pre, div[class*="highlight-"] { - clear: both; -} - -span.pre { - -moz-hyphens: none; - -ms-hyphens: none; - -webkit-hyphens: none; - hyphens: none; - white-space: nowrap; -} - -div[class*="highlight-"] { - margin: 1em 0; -} - -td.linenos pre { - border: 0; - background-color: transparent; - color: #aaa; -} - -table.highlighttable { - display: block; -} - -table.highlighttable tbody { - display: block; -} - -table.highlighttable tr { - display: flex; -} - -table.highlighttable td { - margin: 0; - padding: 0; -} - -table.highlighttable td.linenos { - padding-right: 0.5em; -} - -table.highlighttable td.code { - flex: 1; - overflow: hidden; -} - -.highlight .hll { - display: block; -} - -div.highlight pre, -table.highlighttable pre { - margin: 0; -} - -div.code-block-caption + div { - margin-top: 0; -} - -div.code-block-caption { - margin-top: 1em; - padding: 2px 5px; - font-size: small; -} - -div.code-block-caption code { - background-color: transparent; -} - -table.highlighttable td.linenos, -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 { - padding: 0.1em 0.3em; - font-style: italic; -} - -div.code-block-caption span.caption-text { -} - -div.literal-block-wrapper { - margin: 1em 0; -} - -code.xref, a code { - background-color: transparent; - font-weight: bold; -} - -h1 code, h2 code, h3 code, h4 code, h5 code, h6 code { - background-color: transparent; -} - -.viewcode-link { - float: right; -} - -.viewcode-back { - float: right; - font-family: sans-serif; -} - -div.viewcode-block:target { - margin: -1px -10px; - padding: 0 10px; -} - -/* -- math display ---------------------------------------------------------- */ - -img.math { - vertical-align: middle; -} - -div.body div.math p { - text-align: center; -} - -span.eqno { - float: right; -} - -span.eqno a.headerlink { - position: absolute; - z-index: 1; -} - -div.math:hover a.headerlink { - visibility: visible; -} - -/* -- printout stylesheet --------------------------------------------------- */ - -@media print { - div.document, - div.documentwrapper, - div.bodywrapper { - margin: 0 !important; - width: 100%; - } - - div.sphinxsidebar, - div.related, - div.footer, - #top-link { - display: none; - } -} \ No newline at end of file diff --git a/docs/_static/comment-bright.png b/docs/_static/comment-bright.png deleted file mode 100644 index 15e27edb12ac25701ac0ac21b97b52bb4e45415e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 756 zcmVgfIX78 z$8Pzv({A~p%??+>KickCb#0FM1rYN=mBmQ&Nwp<#JXUhU;{|)}%&s>suq6lXw*~s{ zvHx}3C%<;wE5CH!BR{p5@ml9ws}y)=QN-kL2?#`S5d*6j zk`h<}j1>tD$b?4D^N9w}-k)bxXxFg>+#kme^xx#qg6FI-%iv2U{0h(Y)cs%5a|m%Pn_K3X_bDJ>EH#(Fb73Z zfUt2Q3B>N+ot3qb*DqbTZpFIn4a!#_R-}{?-~Hs=xSS6p&$sZ-k1zDdtqU`Y@`#qL z&zv-~)Q#JCU(dI)Hf;$CEnK=6CK50}q7~wdbI->?E07bJ0R;!GSQTs5Am`#;*WHjvHRvY?&$Lm-vq1a_BzocI^ULXV!lbMd%|^B#fY;XX)n<&R^L z=84u1e_3ziq;Hz-*k5~zwY3*oDKt0;bM@M@@89;@m*4RFgvvM_4;5LB!@OB@^WbVT zjl{t;a8_>od-~P4 m{5|DvB&z#xT;*OnJqG}gk~_7HcNkCr0000W zanA~u9RIXo;n7c96&U)YLgs-FGlx~*_c{Jgvesu1E5(8YEf&5wF=YFPcRe@1=MJmi zag(L*xc2r0(slpcN!vC5CUju;vHJkHc*&70_n2OZsK%O~A=!+YIw z7zLLl7~Z+~RgWOQ=MI6$#0pvpu$Q43 zP@36QAmu6!_9NPM?o<1_!+stoVRRZbW9#SPe!n;#A_6m8f}|xN1;H{`0RoXQ2LM47 zt(g;iZ6|pCb@h2xk&(}S3=EVBUO0e90m2Lp5CB<(SPIaB;n4))3JB87Or#XPOPcum z?<^(g+m9}VNn4Y&B`g8h{t_$+RB1%HKRY6fjtd-<7&EsU;vs0GM(Lmbhi%Gwcfs0FTF}T zL{_M6Go&E0Eg8FuB*(Yn+Z*RVTBE@10eIOb3El^MhO`GabDll(V0&FlJi2k^;q8af zkENdk2}x2)_KVp`5OAwXZM;dG0?M-S)xE1IKDi6BY@5%Or?#aZ9$gcX)dPZ&wA1a< z$rFXHPn|TBf`e?>Are8sKtKrKcjF$i^lp!zkL?C|y^vlHr1HXeVJd;1I~g&Ob-q)& z(fn7s-KI}G{wnKzg_U5G(V%bX6uk zIa+<@>rdmZYd!9Y=C0cuchrbIjuRB_Wq{-RXlic?flu1*_ux}x%(HDH&nT`k^xCeC ziHi1!ChH*sQ6|UqJpTTzX$aw8e(UfcS^f;6yBWd+(1-70zU(rtxtqR%j z-lsH|CKQJXqD{+F7V0OTv8@{~(wp(`oIP^ZykMWgR>&|RsklFMCnOo&Bd{le} zV5F6424Qzl;o2G%oVvmHgRDP9!=rK8fy^!yV8y*4p=??uIRrrr0?>O!(z*g5AvL2!4z0{sq%vhG*Po}`a<6%kTK5TNhtC8}rXNu&h^QH4A&Sk~Autm*s~45(H7+0bi^MraaRVzr05hQ3iK?j` zR#U@^i0WhkIHTg29u~|ypU?sXCQEQgXfObPW;+0YAF;|5XyaMAEM0sQ@4-xCZe=0e z7r$ofiAxn@O5#RodD8rh5D@nKQ;?lcf@tg4o+Wp44aMl~c47azN_(im0N)7OqdPBC zGw;353_o$DqGRDhuhU$Eaj!@m000000NkvXXu0mjfjZ7Z_ diff --git a/docs/_static/doctools.js b/docs/_static/doctools.js deleted file mode 100644 index d06a71d75..000000000 --- a/docs/_static/doctools.js +++ /dev/null @@ -1,156 +0,0 @@ -/* - * doctools.js - * ~~~~~~~~~~~ - * - * Base JavaScript utilities for all Sphinx HTML documentation. - * - * :copyright: Copyright 2007-2023 by the Sphinx team, see AUTHORS. - * :license: BSD, see LICENSE for details. - * - */ -"use strict"; - -const BLACKLISTED_KEY_CONTROL_ELEMENTS = new Set([ - "TEXTAREA", - "INPUT", - "SELECT", - "BUTTON", -]); - -const _ready = (callback) => { - if (document.readyState !== "loading") { - callback(); - } else { - document.addEventListener("DOMContentLoaded", callback); - } -}; - -/** - * Small JavaScript module for the documentation. - */ -const Documentation = { - init: () => { - Documentation.initDomainIndexTable(); - Documentation.initOnKeyListeners(); - }, - - /** - * i18n support - */ - TRANSLATIONS: {}, - PLURAL_EXPR: (n) => (n === 1 ? 0 : 1), - LOCALE: "unknown", - - // gettext and ngettext don't access this so that the functions - // can safely bound to a different name (_ = Documentation.gettext) - gettext: (string) => { - const translated = Documentation.TRANSLATIONS[string]; - switch (typeof translated) { - case "undefined": - return string; // no translation - case "string": - return translated; // translation exists - default: - return translated[0]; // (singular, plural) translation tuple exists - } - }, - - ngettext: (singular, plural, n) => { - const translated = Documentation.TRANSLATIONS[singular]; - if (typeof translated !== "undefined") - return translated[Documentation.PLURAL_EXPR(n)]; - return n === 1 ? singular : plural; - }, - - addTranslations: (catalog) => { - Object.assign(Documentation.TRANSLATIONS, catalog.messages); - Documentation.PLURAL_EXPR = new Function( - "n", - `return (${catalog.plural_expr})` - ); - Documentation.LOCALE = catalog.locale; - }, - - /** - * helper function to focus on search bar - */ - focusSearchBar: () => { - document.querySelectorAll("input[name=q]")[0]?.focus(); - }, - - /** - * Initialise the domain index toggle buttons - */ - initDomainIndexTable: () => { - const toggler = (el) => { - const idNumber = el.id.substr(7); - const toggledRows = document.querySelectorAll(`tr.cg-${idNumber}`); - if (el.src.substr(-9) === "minus.png") { - el.src = `${el.src.substr(0, el.src.length - 9)}plus.png`; - toggledRows.forEach((el) => (el.style.display = "none")); - } else { - el.src = `${el.src.substr(0, el.src.length - 8)}minus.png`; - toggledRows.forEach((el) => (el.style.display = "")); - } - }; - - const togglerElements = document.querySelectorAll("img.toggler"); - togglerElements.forEach((el) => - el.addEventListener("click", (event) => toggler(event.currentTarget)) - ); - togglerElements.forEach((el) => (el.style.display = "")); - if (DOCUMENTATION_OPTIONS.COLLAPSE_INDEX) togglerElements.forEach(toggler); - }, - - initOnKeyListeners: () => { - // only install a listener if it is really needed - if ( - !DOCUMENTATION_OPTIONS.NAVIGATION_WITH_KEYS && - !DOCUMENTATION_OPTIONS.ENABLE_SEARCH_SHORTCUTS - ) - return; - - document.addEventListener("keydown", (event) => { - // bail for input elements - if (BLACKLISTED_KEY_CONTROL_ELEMENTS.has(document.activeElement.tagName)) return; - // bail with special keys - if (event.altKey || event.ctrlKey || event.metaKey) return; - - if (!event.shiftKey) { - switch (event.key) { - case "ArrowLeft": - if (!DOCUMENTATION_OPTIONS.NAVIGATION_WITH_KEYS) break; - - const prevLink = document.querySelector('link[rel="prev"]'); - if (prevLink && prevLink.href) { - window.location.href = prevLink.href; - event.preventDefault(); - } - break; - case "ArrowRight": - if (!DOCUMENTATION_OPTIONS.NAVIGATION_WITH_KEYS) break; - - const nextLink = document.querySelector('link[rel="next"]'); - if (nextLink && nextLink.href) { - window.location.href = nextLink.href; - event.preventDefault(); - } - break; - } - } - - // some keyboard layouts may need Shift to get / - switch (event.key) { - case "/": - if (!DOCUMENTATION_OPTIONS.ENABLE_SEARCH_SHORTCUTS) break; - Documentation.focusSearchBar(); - event.preventDefault(); - } - }); - }, -}; - -// quick alias for translations -const _ = Documentation.gettext; - -_ready(Documentation.init); diff --git a/docs/_static/documentation_options.js b/docs/_static/documentation_options.js deleted file mode 100644 index 40ea65095..000000000 --- a/docs/_static/documentation_options.js +++ /dev/null @@ -1,14 +0,0 @@ -var DOCUMENTATION_OPTIONS = { - URL_ROOT: document.getElementById("documentation_options").getAttribute('data-url_root'), - VERSION: '2023.5.8', - LANGUAGE: 'en', - COLLAPSE_INDEX: false, - BUILDER: 'html', - FILE_SUFFIX: '.html', - LINK_SUFFIX: '.html', - HAS_SOURCE: true, - SOURCELINK_SUFFIX: '.txt', - NAVIGATION_WITH_KEYS: false, - SHOW_SEARCH_SUMMARY: true, - ENABLE_SEARCH_SHORTCUTS: true, -}; \ No newline at end of file diff --git a/docs/_static/down-pressed.png b/docs/_static/down-pressed.png deleted file mode 100644 index 5756c8cad8854722893dc70b9eb4bb0400343a39..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 222 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`OFdm2Ln;`PZ^+1>KjR?B@S0W7 z%OS_REiHONoJ6{+Ks@6k3590|7k9F+ddB6!zw3#&!aw#S`x}3V3&=A(a#84O-&F7T z^k3tZB;&iR9siw0|F|E|DAL<8r-F4!1H-;1{e*~yAKZN5f0|Ei6yUmR#Is)EM(Po_ zi`qJR6|P<~+)N+kSDgL7AjdIC_!O7Q?eGb+L+qOjm{~LLinM4NHn7U%HcK%uoMYO5 VJ~8zD2B3o(JYD@<);T3K0RV0%P>BEl diff --git a/docs/_static/down.png b/docs/_static/down.png deleted file mode 100644 index 1b3bdad2ceffae91cee61b32f3295f9bbe646e48..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 202 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!60wlNoGJgf6CVIL!hEy=F?b*7pIY7kW{q%Rg zx!yQ<9v8bmJwa`TQk7YSw}WVQ()mRdQ;TC;* diff --git a/docs/_static/file.png b/docs/_static/file.png deleted file mode 100644 index a858a410e4faa62ce324d814e4b816fff83a6fb3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 286 zcmV+(0pb3MP)s`hMrGg#P~ix$^RISR_I47Y|r1 z_CyJOe}D1){SET-^Amu_i71Lt6eYfZjRyw@I6OQAIXXHDfiX^GbOlHe=Ae4>0m)d(f|Me07*qoM6N<$f}vM^LjV8( diff --git a/docs/_static/flasky.css b/docs/_static/flasky.css deleted file mode 100644 index f764eb5ee..000000000 --- a/docs/_static/flasky.css +++ /dev/null @@ -1,445 +0,0 @@ -/* - * flasky.css_t - * ~~~~~~~~~~~~ - * - * :copyright: Copyright 2010 by Armin Ronacher. Modifications by Kenneth Reitz. - * :license: Flask Design License, see LICENSE for details. - */ - - - - -@import url("basic.css"); - -/* -- page layout ----------------------------------------------------------- */ - -body { - font-family: 'goudy old style', 'minion pro', 'bell mt', Georgia, 'Hiragino Mincho Pro'; - font-size: 17px; - background-color: white; - color: #000; - margin: 0; - padding: 0; -} - -div.document { - width: 940px; - margin: 30px auto 0 auto; -} - -div.documentwrapper { - float: left; - width: 100%; -} - -div.bodywrapper { - margin: 0 0 0 220px; -} - -div.sphinxsidebar { - width: 220px; -} - -hr { - border: 1px solid #B1B4B6; -} - -div.body { - background-color: #ffffff; - color: #3E4349; - padding: 0 30px 0 30px; -} - -img.floatingflask { - padding: 0 0 10px 10px; - float: right; -} - -div.footer { - width: 940px; - margin: 20px auto 30px auto; - font-size: 14px; - color: #888; - text-align: right; -} - -div.footer a { - color: #888; -} - -div.related { - display: none; -} - -div.sphinxsidebar a { - color: #444; - text-decoration: none; - border-bottom: 1px dotted #999; -} - -div.sphinxsidebar a:hover { - border-bottom: 1px solid #999; -} - -div.sphinxsidebar { - font-size: 14px; - line-height: 1.5; -} - -div.sphinxsidebarwrapper { - padding: 18px 10px; -} - -div.sphinxsidebarwrapper p.logo { - padding: 0; - margin: -10px 0 0 -20px; - text-align: center; -} - -div.sphinxsidebar h3, -div.sphinxsidebar h4 { - font-family: 'Garamond', 'Georgia', serif; - color: #444; - font-size: 24px; - font-weight: normal; - margin: 0 0 5px 0; - padding: 0; -} - -div.sphinxsidebar h4 { - font-size: 20px; -} - -div.sphinxsidebar h3 a { - color: #444; -} - -div.sphinxsidebar p.logo a, -div.sphinxsidebar h3 a, -div.sphinxsidebar p.logo a:hover, -div.sphinxsidebar h3 a:hover { - border: none; -} - -div.sphinxsidebar p { - color: #555; - margin: 10px 0; -} - -div.sphinxsidebar ul { - margin: 10px 0; - padding: 0; - color: #000; -} - -div.sphinxsidebar input { - border: 1px solid #ccc; - font-family: 'Georgia', serif; - font-size: 1em; -} - -/* -- body styles ----------------------------------------------------------- */ - -a { - color: #004B6B; - text-decoration: underline; -} - -a:hover { - color: #6D4100; - text-decoration: underline; -} - -div.body h1, -div.body h2, -div.body h3, -div.body h4, -div.body h5, -div.body h6 { - font-family: 'Garamond', 'Georgia', serif; - font-weight: normal; - margin: 30px 0px 10px 0px; - padding: 0; -} - -div.body h1 { margin-top: 0; padding-top: 0; font-size: 240%; } -div.body h2 { font-size: 180%; } -div.body h3 { font-size: 150%; } -div.body h4 { font-size: 130%; } -div.body h5 { font-size: 100%; } -div.body h6 { font-size: 100%; } - -a.headerlink { - color: #ddd; - padding: 0 4px; - text-decoration: none; -} - -a.headerlink:hover { - color: #444; - background: #eaeaea; -} - -div.body p, div.body dd, div.body li { - line-height: 1.4em; -} - -div.admonition { - background: #fafafa; - margin: 20px -30px; - padding: 10px 30px; - border-top: 1px solid #ccc; - border-bottom: 1px solid #ccc; -} - -div.admonition tt.xref, div.admonition a tt { - border-bottom: 1px solid #fafafa; -} - -dd div.admonition { - margin-left: -60px; - padding-left: 60px; -} - -div.admonition p.admonition-title { - font-family: 'Garamond', 'Georgia', serif; - font-weight: normal; - font-size: 24px; - margin: 0 0 10px 0; - padding: 0; - line-height: 1; -} - -div.admonition p.last { - margin-bottom: 0; -} - -div.highlight { - background-color: white; -} - -dt:target, .highlight { - background: #FAF3E8; -} - -div.note { - background-color: #eee; - border: 1px solid #ccc; -} - -div.seealso { - background-color: #ffc; - border: 1px solid #ff6; -} - -div.topic { - background-color: #eee; -} - -p.admonition-title { - display: inline; -} - -p.admonition-title:after { - content: ":"; -} - -pre, tt { - font-family: 'Consolas', 'Menlo', 'Deja Vu Sans Mono', 'Bitstream Vera Sans Mono', monospace; - font-size: 0.9em; -} - -img.screenshot { -} - -tt.descname, tt.descclassname { - font-size: 0.95em; -} - -tt.descname { - padding-right: 0.08em; -} - -img.screenshot { - -moz-box-shadow: 2px 2px 4px #eee; - -webkit-box-shadow: 2px 2px 4px #eee; - box-shadow: 2px 2px 4px #eee; -} - -table.docutils { - border: 1px solid #888; - -moz-box-shadow: 2px 2px 4px #eee; - -webkit-box-shadow: 2px 2px 4px #eee; - box-shadow: 2px 2px 4px #eee; -} - -table.docutils td, table.docutils th { - border: 1px solid #888; - padding: 0.25em 0.7em; -} - -table.field-list, table.footnote { - border: none; - -moz-box-shadow: none; - -webkit-box-shadow: none; - box-shadow: none; -} - -table.footnote { - margin: 15px 0; - width: 100%; - border: 1px solid #eee; - background: #fdfdfd; - font-size: 0.9em; -} - -table.footnote + table.footnote { - margin-top: -15px; - border-top: none; -} - -table.field-list th { - padding: 0 0.8em 0 0; -} - -table.field-list td { - padding: 0; -} - -table.footnote td.label { - width: 0px; - padding: 0.3em 0 0.3em 0.5em; -} - -table.footnote td { - padding: 0.3em 0.5em; -} - -dl { - margin: 0; - padding: 0; -} - -dl dd { - margin-left: 30px; -} - -blockquote { - margin: 0 0 0 30px; - padding: 0; -} - -ul, ol { - margin: 10px 0 10px 30px; - padding: 0; -} - -pre { - background: #eee; - padding: 7px 30px; - margin: 15px -30px; - line-height: 1.3em; -} - -dl pre, blockquote pre, li pre { - margin-left: -60px; - padding-left: 60px; -} - -dl dl pre { - margin-left: -90px; - padding-left: 90px; -} - -tt { - background-color: #ecf0f3; - color: #222; - /* padding: 1px 2px; */ -} - -tt.xref, a tt { - background-color: #FBFBFB; - border-bottom: 1px solid white; -} - -a.reference { - text-decoration: none; - border-bottom: 1px dotted #004B6B; -} - -a.reference:hover { - border-bottom: 1px solid #6D4100; -} - -a.footnote-reference { - text-decoration: none; - font-size: 0.7em; - vertical-align: top; - border-bottom: 1px dotted #004B6B; -} - -a.footnote-reference:hover { - border-bottom: 1px solid #6D4100; -} - -a:hover tt { - background: #EEE; -} - - -@media screen and (max-width: 600px) { - - div.sphinxsidebar { - display: none; - } - - div.document { - width: 100%; - - } - - div.documentwrapper { - margin-left: 0; - margin-top: 0; - margin-right: 0; - margin-bottom: 0; - } - - div.bodywrapper { - margin-top: 0; - margin-right: 0; - margin-bottom: 0; - margin-left: 0; - } - - ul { - margin-left: 0; - } - - .document { - width: auto; - } - - .footer { - width: auto; - } - - .bodywrapper { - margin: 0; - } - - .footer { - width: auto; - } - - .github { - display: none; - } - -} - -/* misc. */ - -.revsys-inline { - display: none!important; -} \ No newline at end of file diff --git a/docs/_static/jquery-3.1.0.js b/docs/_static/jquery-3.1.0.js deleted file mode 100644 index f2fc27478..000000000 --- a/docs/_static/jquery-3.1.0.js +++ /dev/null @@ -1,10074 +0,0 @@ -/*eslint-disable no-unused-vars*/ -/*! - * jQuery JavaScript Library v3.1.0 - * https://jquery.com/ - * - * Includes Sizzle.js - * https://sizzlejs.com/ - * - * Copyright jQuery Foundation and other contributors - * Released under the MIT license - * https://jquery.org/license - * - * Date: 2016-07-07T21:44Z - */ -( function( global, factory ) { - - "use strict"; - - if ( typeof module === "object" && typeof module.exports === "object" ) { - - // For CommonJS and CommonJS-like environments where a proper `window` - // is present, execute the factory and get jQuery. - // For environments that do not have a `window` with a `document` - // (such as Node.js), expose a factory as module.exports. - // This accentuates the need for the creation of a real `window`. - // e.g. var jQuery = require("jquery")(window); - // See ticket #14549 for more info. - module.exports = global.document ? - factory( global, true ) : - function( w ) { - if ( !w.document ) { - throw new Error( "jQuery requires a window with a document" ); - } - return factory( w ); - }; - } else { - factory( global ); - } - -// Pass this if window is not defined yet -} )( typeof window !== "undefined" ? window : this, function( window, noGlobal ) { - -// Edge <= 12 - 13+, Firefox <=18 - 45+, IE 10 - 11, Safari 5.1 - 9+, iOS 6 - 9.1 -// throw exceptions when non-strict code (e.g., ASP.NET 4.5) accesses strict mode -// arguments.callee.caller (trac-13335). But as of jQuery 3.0 (2016), strict mode should be common -// enough that all such attempts are guarded in a try block. -"use strict"; - -var arr = []; - -var document = window.document; - -var getProto = Object.getPrototypeOf; - -var slice = arr.slice; - -var concat = arr.concat; - -var push = arr.push; - -var indexOf = arr.indexOf; - -var class2type = {}; - -var toString = class2type.toString; - -var hasOwn = class2type.hasOwnProperty; - -var fnToString = hasOwn.toString; - -var ObjectFunctionString = fnToString.call( Object ); - -var support = {}; - - - - function DOMEval( code, doc ) { - doc = doc || document; - - var script = doc.createElement( "script" ); - - script.text = code; - doc.head.appendChild( script ).parentNode.removeChild( script ); - } -/* global Symbol */ -// Defining this global in .eslintrc would create a danger of using the global -// unguarded in another place, it seems safer to define global only for this module - - - -var - version = "3.1.0", - - // Define a local copy of jQuery - jQuery = function( selector, context ) { - - // The jQuery object is actually just the init constructor 'enhanced' - // Need init if jQuery is called (just allow error to be thrown if not included) - return new jQuery.fn.init( selector, context ); - }, - - // Support: Android <=4.0 only - // Make sure we trim BOM and NBSP - rtrim = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g, - - // Matches dashed string for camelizing - rmsPrefix = /^-ms-/, - rdashAlpha = /-([a-z])/g, - - // Used by jQuery.camelCase as callback to replace() - fcamelCase = function( all, letter ) { - return letter.toUpperCase(); - }; - -jQuery.fn = jQuery.prototype = { - - // The current version of jQuery being used - jquery: version, - - constructor: jQuery, - - // The default length of a jQuery object is 0 - length: 0, - - toArray: function() { - return slice.call( this ); - }, - - // Get the Nth element in the matched element set OR - // Get the whole matched element set as a clean array - get: function( num ) { - return num != null ? - - // Return just the one element from the set - ( num < 0 ? this[ num + this.length ] : this[ num ] ) : - - // Return all the elements in a clean array - slice.call( this ); - }, - - // Take an array of elements and push it onto the stack - // (returning the new matched element set) - pushStack: function( elems ) { - - // Build a new jQuery matched element set - var ret = jQuery.merge( this.constructor(), elems ); - - // Add the old object onto the stack (as a reference) - ret.prevObject = this; - - // Return the newly-formed element set - return ret; - }, - - // Execute a callback for every element in the matched set. - each: function( callback ) { - return jQuery.each( this, callback ); - }, - - map: function( callback ) { - return this.pushStack( jQuery.map( this, function( elem, i ) { - return callback.call( elem, i, elem ); - } ) ); - }, - - slice: function() { - return this.pushStack( slice.apply( this, arguments ) ); - }, - - first: function() { - return this.eq( 0 ); - }, - - last: function() { - return this.eq( -1 ); - }, - - eq: function( i ) { - var len = this.length, - j = +i + ( i < 0 ? len : 0 ); - return this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] ); - }, - - end: function() { - return this.prevObject || this.constructor(); - }, - - // For internal use only. - // Behaves like an Array's method, not like a jQuery method. - push: push, - sort: arr.sort, - splice: arr.splice -}; - -jQuery.extend = jQuery.fn.extend = function() { - var options, name, src, copy, copyIsArray, clone, - target = arguments[ 0 ] || {}, - i = 1, - length = arguments.length, - deep = false; - - // Handle a deep copy situation - if ( typeof target === "boolean" ) { - deep = target; - - // Skip the boolean and the target - target = arguments[ i ] || {}; - i++; - } - - // Handle case when target is a string or something (possible in deep copy) - if ( typeof target !== "object" && !jQuery.isFunction( target ) ) { - target = {}; - } - - // Extend jQuery itself if only one argument is passed - if ( i === length ) { - target = this; - i--; - } - - for ( ; i < length; i++ ) { - - // Only deal with non-null/undefined values - if ( ( options = arguments[ i ] ) != null ) { - - // Extend the base object - for ( name in options ) { - src = target[ name ]; - copy = options[ name ]; - - // Prevent never-ending loop - if ( target === copy ) { - continue; - } - - // Recurse if we're merging plain objects or arrays - if ( deep && copy && ( jQuery.isPlainObject( copy ) || - ( copyIsArray = jQuery.isArray( copy ) ) ) ) { - - if ( copyIsArray ) { - copyIsArray = false; - clone = src && jQuery.isArray( src ) ? src : []; - - } else { - clone = src && jQuery.isPlainObject( src ) ? src : {}; - } - - // Never move original objects, clone them - target[ name ] = jQuery.extend( deep, clone, copy ); - - // Don't bring in undefined values - } else if ( copy !== undefined ) { - target[ name ] = copy; - } - } - } - } - - // Return the modified object - return target; -}; - -jQuery.extend( { - - // Unique for each copy of jQuery on the page - expando: "jQuery" + ( version + Math.random() ).replace( /\D/g, "" ), - - // Assume jQuery is ready without the ready module - isReady: true, - - error: function( msg ) { - throw new Error( msg ); - }, - - noop: function() {}, - - isFunction: function( obj ) { - return jQuery.type( obj ) === "function"; - }, - - isArray: Array.isArray, - - isWindow: function( obj ) { - return obj != null && obj === obj.window; - }, - - isNumeric: function( obj ) { - - // As of jQuery 3.0, isNumeric is limited to - // strings and numbers (primitives or objects) - // that can be coerced to finite numbers (gh-2662) - var type = jQuery.type( obj ); - return ( type === "number" || type === "string" ) && - - // parseFloat NaNs numeric-cast false positives ("") - // ...but misinterprets leading-number strings, particularly hex literals ("0x...") - // subtraction forces infinities to NaN - !isNaN( obj - parseFloat( obj ) ); - }, - - isPlainObject: function( obj ) { - var proto, Ctor; - - // Detect obvious negatives - // Use toString instead of jQuery.type to catch host objects - if ( !obj || toString.call( obj ) !== "[object Object]" ) { - return false; - } - - proto = getProto( obj ); - - // Objects with no prototype (e.g., `Object.create( null )`) are plain - if ( !proto ) { - return true; - } - - // Objects with prototype are plain iff they were constructed by a global Object function - Ctor = hasOwn.call( proto, "constructor" ) && proto.constructor; - return typeof Ctor === "function" && fnToString.call( Ctor ) === ObjectFunctionString; - }, - - isEmptyObject: function( obj ) { - - /* eslint-disable no-unused-vars */ - // See https://github.com/eslint/eslint/issues/6125 - var name; - - for ( name in obj ) { - return false; - } - return true; - }, - - type: function( obj ) { - if ( obj == null ) { - return obj + ""; - } - - // Support: Android <=2.3 only (functionish RegExp) - return typeof obj === "object" || typeof obj === "function" ? - class2type[ toString.call( obj ) ] || "object" : - typeof obj; - }, - - // Evaluates a script in a global context - globalEval: function( code ) { - DOMEval( code ); - }, - - // Convert dashed to camelCase; used by the css and data modules - // Support: IE <=9 - 11, Edge 12 - 13 - // Microsoft forgot to hump their vendor prefix (#9572) - camelCase: function( string ) { - return string.replace( rmsPrefix, "ms-" ).replace( rdashAlpha, fcamelCase ); - }, - - nodeName: function( elem, name ) { - return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase(); - }, - - each: function( obj, callback ) { - var length, i = 0; - - if ( isArrayLike( obj ) ) { - length = obj.length; - for ( ; i < length; i++ ) { - if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) { - break; - } - } - } else { - for ( i in obj ) { - if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) { - break; - } - } - } - - return obj; - }, - - // Support: Android <=4.0 only - trim: function( text ) { - return text == null ? - "" : - ( text + "" ).replace( rtrim, "" ); - }, - - // results is for internal usage only - makeArray: function( arr, results ) { - var ret = results || []; - - if ( arr != null ) { - if ( isArrayLike( Object( arr ) ) ) { - jQuery.merge( ret, - typeof arr === "string" ? - [ arr ] : arr - ); - } else { - push.call( ret, arr ); - } - } - - return ret; - }, - - inArray: function( elem, arr, i ) { - return arr == null ? -1 : indexOf.call( arr, elem, i ); - }, - - // Support: Android <=4.0 only, PhantomJS 1 only - // push.apply(_, arraylike) throws on ancient WebKit - merge: function( first, second ) { - var len = +second.length, - j = 0, - i = first.length; - - for ( ; j < len; j++ ) { - first[ i++ ] = second[ j ]; - } - - first.length = i; - - return first; - }, - - grep: function( elems, callback, invert ) { - var callbackInverse, - matches = [], - i = 0, - length = elems.length, - callbackExpect = !invert; - - // Go through the array, only saving the items - // that pass the validator function - for ( ; i < length; i++ ) { - callbackInverse = !callback( elems[ i ], i ); - if ( callbackInverse !== callbackExpect ) { - matches.push( elems[ i ] ); - } - } - - return matches; - }, - - // arg is for internal usage only - map: function( elems, callback, arg ) { - var length, value, - i = 0, - ret = []; - - // Go through the array, translating each of the items to their new values - if ( isArrayLike( elems ) ) { - length = elems.length; - for ( ; i < length; i++ ) { - value = callback( elems[ i ], i, arg ); - - if ( value != null ) { - ret.push( value ); - } - } - - // Go through every key on the object, - } else { - for ( i in elems ) { - value = callback( elems[ i ], i, arg ); - - if ( value != null ) { - ret.push( value ); - } - } - } - - // Flatten any nested arrays - return concat.apply( [], ret ); - }, - - // A global GUID counter for objects - guid: 1, - - // Bind a function to a context, optionally partially applying any - // arguments. - proxy: function( fn, context ) { - var tmp, args, proxy; - - if ( typeof context === "string" ) { - tmp = fn[ context ]; - context = fn; - fn = tmp; - } - - // Quick check to determine if target is callable, in the spec - // this throws a TypeError, but we will just return undefined. - if ( !jQuery.isFunction( fn ) ) { - return undefined; - } - - // Simulated bind - args = slice.call( arguments, 2 ); - proxy = function() { - return fn.apply( context || this, args.concat( slice.call( arguments ) ) ); - }; - - // Set the guid of unique handler to the same of original handler, so it can be removed - proxy.guid = fn.guid = fn.guid || jQuery.guid++; - - return proxy; - }, - - now: Date.now, - - // jQuery.support is not used in Core but other projects attach their - // properties to it so it needs to exist. - support: support -} ); - -if ( typeof Symbol === "function" ) { - jQuery.fn[ Symbol.iterator ] = arr[ Symbol.iterator ]; -} - -// Populate the class2type map -jQuery.each( "Boolean Number String Function Array Date RegExp Object Error Symbol".split( " " ), -function( i, name ) { - class2type[ "[object " + name + "]" ] = name.toLowerCase(); -} ); - -function isArrayLike( obj ) { - - // Support: real iOS 8.2 only (not reproducible in simulator) - // `in` check used to prevent JIT error (gh-2145) - // hasOwn isn't used here due to false negatives - // regarding Nodelist length in IE - var length = !!obj && "length" in obj && obj.length, - type = jQuery.type( obj ); - - if ( type === "function" || jQuery.isWindow( obj ) ) { - return false; - } - - return type === "array" || length === 0 || - typeof length === "number" && length > 0 && ( length - 1 ) in obj; -} -var Sizzle = -/*! - * Sizzle CSS Selector Engine v2.3.0 - * https://sizzlejs.com/ - * - * Copyright jQuery Foundation and other contributors - * Released under the MIT license - * http://jquery.org/license - * - * Date: 2016-01-04 - */ -(function( window ) { - -var i, - support, - Expr, - getText, - isXML, - tokenize, - compile, - select, - outermostContext, - sortInput, - hasDuplicate, - - // Local document vars - setDocument, - document, - docElem, - documentIsHTML, - rbuggyQSA, - rbuggyMatches, - matches, - contains, - - // Instance-specific data - expando = "sizzle" + 1 * new Date(), - preferredDoc = window.document, - dirruns = 0, - done = 0, - classCache = createCache(), - tokenCache = createCache(), - compilerCache = createCache(), - sortOrder = function( a, b ) { - if ( a === b ) { - hasDuplicate = true; - } - return 0; - }, - - // Instance methods - hasOwn = ({}).hasOwnProperty, - arr = [], - pop = arr.pop, - push_native = arr.push, - push = arr.push, - slice = arr.slice, - // Use a stripped-down indexOf as it's faster than native - // https://jsperf.com/thor-indexof-vs-for/5 - indexOf = function( list, elem ) { - var i = 0, - len = list.length; - for ( ; i < len; i++ ) { - if ( list[i] === elem ) { - return i; - } - } - return -1; - }, - - booleans = "checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped", - - // Regular expressions - - // http://www.w3.org/TR/css3-selectors/#whitespace - whitespace = "[\\x20\\t\\r\\n\\f]", - - // http://www.w3.org/TR/CSS21/syndata.html#value-def-identifier - identifier = "(?:\\\\.|[\\w-]|[^\0-\\xa0])+", - - // Attribute selectors: http://www.w3.org/TR/selectors/#attribute-selectors - attributes = "\\[" + whitespace + "*(" + identifier + ")(?:" + whitespace + - // Operator (capture 2) - "*([*^$|!~]?=)" + whitespace + - // "Attribute values must be CSS identifiers [capture 5] or strings [capture 3 or capture 4]" - "*(?:'((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\"|(" + identifier + "))|)" + whitespace + - "*\\]", - - pseudos = ":(" + identifier + ")(?:\\((" + - // To reduce the number of selectors needing tokenize in the preFilter, prefer arguments: - // 1. quoted (capture 3; capture 4 or capture 5) - "('((?:\\\\.|[^\\\\'])*)'|\"((?:\\\\.|[^\\\\\"])*)\")|" + - // 2. simple (capture 6) - "((?:\\\\.|[^\\\\()[\\]]|" + attributes + ")*)|" + - // 3. anything else (capture 2) - ".*" + - ")\\)|)", - - // Leading and non-escaped trailing whitespace, capturing some non-whitespace characters preceding the latter - rwhitespace = new RegExp( whitespace + "+", "g" ), - rtrim = new RegExp( "^" + whitespace + "+|((?:^|[^\\\\])(?:\\\\.)*)" + whitespace + "+$", "g" ), - - rcomma = new RegExp( "^" + whitespace + "*," + whitespace + "*" ), - rcombinators = new RegExp( "^" + whitespace + "*([>+~]|" + whitespace + ")" + whitespace + "*" ), - - rattributeQuotes = new RegExp( "=" + whitespace + "*([^\\]'\"]*?)" + whitespace + "*\\]", "g" ), - - rpseudo = new RegExp( pseudos ), - ridentifier = new RegExp( "^" + identifier + "$" ), - - matchExpr = { - "ID": new RegExp( "^#(" + identifier + ")" ), - "CLASS": new RegExp( "^\\.(" + identifier + ")" ), - "TAG": new RegExp( "^(" + identifier + "|[*])" ), - "ATTR": new RegExp( "^" + attributes ), - "PSEUDO": new RegExp( "^" + pseudos ), - "CHILD": new RegExp( "^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\(" + whitespace + - "*(even|odd|(([+-]|)(\\d*)n|)" + whitespace + "*(?:([+-]|)" + whitespace + - "*(\\d+)|))" + whitespace + "*\\)|)", "i" ), - "bool": new RegExp( "^(?:" + booleans + ")$", "i" ), - // For use in libraries implementing .is() - // We use this for POS matching in `select` - "needsContext": new RegExp( "^" + whitespace + "*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\(" + - whitespace + "*((?:-\\d)?\\d*)" + whitespace + "*\\)|)(?=[^-]|$)", "i" ) - }, - - rinputs = /^(?:input|select|textarea|button)$/i, - rheader = /^h\d$/i, - - rnative = /^[^{]+\{\s*\[native \w/, - - // Easily-parseable/retrievable ID or TAG or CLASS selectors - rquickExpr = /^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/, - - rsibling = /[+~]/, - - // CSS escapes - // http://www.w3.org/TR/CSS21/syndata.html#escaped-characters - runescape = new RegExp( "\\\\([\\da-f]{1,6}" + whitespace + "?|(" + whitespace + ")|.)", "ig" ), - funescape = function( _, escaped, escapedWhitespace ) { - var high = "0x" + escaped - 0x10000; - // NaN means non-codepoint - // Support: Firefox<24 - // Workaround erroneous numeric interpretation of +"0x" - return high !== high || escapedWhitespace ? - escaped : - high < 0 ? - // BMP codepoint - String.fromCharCode( high + 0x10000 ) : - // Supplemental Plane codepoint (surrogate pair) - String.fromCharCode( high >> 10 | 0xD800, high & 0x3FF | 0xDC00 ); - }, - - // CSS string/identifier serialization - // https://drafts.csswg.org/cssom/#common-serializing-idioms - rcssescape = /([\0-\x1f\x7f]|^-?\d)|^-$|[^\x80-\uFFFF\w-]/g, - fcssescape = function( ch, asCodePoint ) { - if ( asCodePoint ) { - - // U+0000 NULL becomes U+FFFD REPLACEMENT CHARACTER - if ( ch === "\0" ) { - return "\uFFFD"; - } - - // Control characters and (dependent upon position) numbers get escaped as code points - return ch.slice( 0, -1 ) + "\\" + ch.charCodeAt( ch.length - 1 ).toString( 16 ) + " "; - } - - // Other potentially-special ASCII characters get backslash-escaped - return "\\" + ch; - }, - - // Used for iframes - // See setDocument() - // Removing the function wrapper causes a "Permission Denied" - // error in IE - unloadHandler = function() { - setDocument(); - }, - - disabledAncestor = addCombinator( - function( elem ) { - return elem.disabled === true; - }, - { dir: "parentNode", next: "legend" } - ); - -// Optimize for push.apply( _, NodeList ) -try { - push.apply( - (arr = slice.call( preferredDoc.childNodes )), - preferredDoc.childNodes - ); - // Support: Android<4.0 - // Detect silently failing push.apply - arr[ preferredDoc.childNodes.length ].nodeType; -} catch ( e ) { - push = { apply: arr.length ? - - // Leverage slice if possible - function( target, els ) { - push_native.apply( target, slice.call(els) ); - } : - - // Support: IE<9 - // Otherwise append directly - function( target, els ) { - var j = target.length, - i = 0; - // Can't trust NodeList.length - while ( (target[j++] = els[i++]) ) {} - target.length = j - 1; - } - }; -} - -function Sizzle( selector, context, results, seed ) { - var m, i, elem, nid, match, groups, newSelector, - newContext = context && context.ownerDocument, - - // nodeType defaults to 9, since context defaults to document - nodeType = context ? context.nodeType : 9; - - results = results || []; - - // Return early from calls with invalid selector or context - if ( typeof selector !== "string" || !selector || - nodeType !== 1 && nodeType !== 9 && nodeType !== 11 ) { - - return results; - } - - // Try to shortcut find operations (as opposed to filters) in HTML documents - if ( !seed ) { - - if ( ( context ? context.ownerDocument || context : preferredDoc ) !== document ) { - setDocument( context ); - } - context = context || document; - - if ( documentIsHTML ) { - - // If the selector is sufficiently simple, try using a "get*By*" DOM method - // (excepting DocumentFragment context, where the methods don't exist) - if ( nodeType !== 11 && (match = rquickExpr.exec( selector )) ) { - - // ID selector - if ( (m = match[1]) ) { - - // Document context - if ( nodeType === 9 ) { - if ( (elem = context.getElementById( m )) ) { - - // Support: IE, Opera, Webkit - // TODO: identify versions - // getElementById can match elements by name instead of ID - if ( elem.id === m ) { - results.push( elem ); - return results; - } - } else { - return results; - } - - // Element context - } else { - - // Support: IE, Opera, Webkit - // TODO: identify versions - // getElementById can match elements by name instead of ID - if ( newContext && (elem = newContext.getElementById( m )) && - contains( context, elem ) && - elem.id === m ) { - - results.push( elem ); - return results; - } - } - - // Type selector - } else if ( match[2] ) { - push.apply( results, context.getElementsByTagName( selector ) ); - return results; - - // Class selector - } else if ( (m = match[3]) && support.getElementsByClassName && - context.getElementsByClassName ) { - - push.apply( results, context.getElementsByClassName( m ) ); - return results; - } - } - - // Take advantage of querySelectorAll - if ( support.qsa && - !compilerCache[ selector + " " ] && - (!rbuggyQSA || !rbuggyQSA.test( selector )) ) { - - if ( nodeType !== 1 ) { - newContext = context; - newSelector = selector; - - // qSA looks outside Element context, which is not what we want - // Thanks to Andrew Dupont for this workaround technique - // Support: IE <=8 - // Exclude object elements - } else if ( context.nodeName.toLowerCase() !== "object" ) { - - // Capture the context ID, setting it first if necessary - if ( (nid = context.getAttribute( "id" )) ) { - nid = nid.replace( rcssescape, fcssescape ); - } else { - context.setAttribute( "id", (nid = expando) ); - } - - // Prefix every selector in the list - groups = tokenize( selector ); - i = groups.length; - while ( i-- ) { - groups[i] = "#" + nid + " " + toSelector( groups[i] ); - } - newSelector = groups.join( "," ); - - // Expand context for sibling selectors - newContext = rsibling.test( selector ) && testContext( context.parentNode ) || - context; - } - - if ( newSelector ) { - try { - push.apply( results, - newContext.querySelectorAll( newSelector ) - ); - return results; - } catch ( qsaError ) { - } finally { - if ( nid === expando ) { - context.removeAttribute( "id" ); - } - } - } - } - } - } - - // All others - return select( selector.replace( rtrim, "$1" ), context, results, seed ); -} - -/** - * Create key-value caches of limited size - * @returns {function(string, object)} Returns the Object data after storing it on itself with - * property name the (space-suffixed) string and (if the cache is larger than Expr.cacheLength) - * deleting the oldest entry - */ -function createCache() { - var keys = []; - - function cache( key, value ) { - // Use (key + " ") to avoid collision with native prototype properties (see Issue #157) - if ( keys.push( key + " " ) > Expr.cacheLength ) { - // Only keep the most recent entries - delete cache[ keys.shift() ]; - } - return (cache[ key + " " ] = value); - } - return cache; -} - -/** - * Mark a function for special use by Sizzle - * @param {Function} fn The function to mark - */ -function markFunction( fn ) { - fn[ expando ] = true; - return fn; -} - -/** - * Support testing using an element - * @param {Function} fn Passed the created element and returns a boolean result - */ -function assert( fn ) { - var el = document.createElement("fieldset"); - - try { - return !!fn( el ); - } catch (e) { - return false; - } finally { - // Remove from its parent by default - if ( el.parentNode ) { - el.parentNode.removeChild( el ); - } - // release memory in IE - el = null; - } -} - -/** - * Adds the same handler for all of the specified attrs - * @param {String} attrs Pipe-separated list of attributes - * @param {Function} handler The method that will be applied - */ -function addHandle( attrs, handler ) { - var arr = attrs.split("|"), - i = arr.length; - - while ( i-- ) { - Expr.attrHandle[ arr[i] ] = handler; - } -} - -/** - * Checks document order of two siblings - * @param {Element} a - * @param {Element} b - * @returns {Number} Returns less than 0 if a precedes b, greater than 0 if a follows b - */ -function siblingCheck( a, b ) { - var cur = b && a, - diff = cur && a.nodeType === 1 && b.nodeType === 1 && - a.sourceIndex - b.sourceIndex; - - // Use IE sourceIndex if available on both nodes - if ( diff ) { - return diff; - } - - // Check if b follows a - if ( cur ) { - while ( (cur = cur.nextSibling) ) { - if ( cur === b ) { - return -1; - } - } - } - - return a ? 1 : -1; -} - -/** - * Returns a function to use in pseudos for input types - * @param {String} type - */ -function createInputPseudo( type ) { - return function( elem ) { - var name = elem.nodeName.toLowerCase(); - return name === "input" && elem.type === type; - }; -} - -/** - * Returns a function to use in pseudos for buttons - * @param {String} type - */ -function createButtonPseudo( type ) { - return function( elem ) { - var name = elem.nodeName.toLowerCase(); - return (name === "input" || name === "button") && elem.type === type; - }; -} - -/** - * Returns a function to use in pseudos for :enabled/:disabled - * @param {Boolean} disabled true for :disabled; false for :enabled - */ -function createDisabledPseudo( disabled ) { - // Known :disabled false positives: - // IE: *[disabled]:not(button, input, select, textarea, optgroup, option, menuitem, fieldset) - // not IE: fieldset[disabled] > legend:nth-of-type(n+2) :can-disable - return function( elem ) { - - // Check form elements and option elements for explicit disabling - return "label" in elem && elem.disabled === disabled || - "form" in elem && elem.disabled === disabled || - - // Check non-disabled form elements for fieldset[disabled] ancestors - "form" in elem && elem.disabled === false && ( - // Support: IE6-11+ - // Ancestry is covered for us - elem.isDisabled === disabled || - - // Otherwise, assume any non-