diff --git a/.codespellrc b/.codespellrc index ba63319e..98a102d6 100644 --- a/.codespellrc +++ b/.codespellrc @@ -1,6 +1,6 @@ [codespell] # Ref: https://github.com/codespell-project/codespell#using-a-config-file -skip = .git,.codespellrc +skip = .git,.codespellrc,references.bib check-hidden = true # ignore-regex = ignore-words-list = commend,Fuchsia diff --git a/.github/workflows/dependabot.yml b/.github/workflows/dependabot.yml new file mode 100644 index 00000000..9acee99b --- /dev/null +++ b/.github/workflows/dependabot.yml @@ -0,0 +1,9 @@ +version: 2 +updates: + - package-ecosystem: "gitsubmodule" + directory: "/specifications/dev" + schedule: + interval: "daily" + open-pull-requests-limit: 10 + commit-message: + prefix: "chore(deps): " diff --git a/.github/workflows/review.yml b/.github/workflows/review.yml index 0679ea76..0c7042cf 100644 --- a/.github/workflows/review.yml +++ b/.github/workflows/review.yml @@ -1,27 +1,27 @@ ---- -name: Add review url +# --- +# name: Add review url -on: - pull_request_target: +# on: +# pull_request_target: -jobs: - build: - runs-on: ubuntu-latest - steps: - - uses: peter-evans/find-comment@v2 - id: fc - with: - issue-number: ${{ github.event.pull_request.number }} - comment-author: 'github-actions[bot]' - body-includes: Automated Review URLs +# jobs: +# build: +# runs-on: ubuntu-latest +# steps: +# - uses: peter-evans/find-comment@v2 +# id: fc +# with: +# issue-number: ${{ github.event.pull_request.number }} +# comment-author: 'github-actions[bot]' +# body-includes: Automated Review URLs - - uses: peter-evans/create-or-update-comment@v2 - with: - comment-id: ${{ steps.fc.outputs.comment-id }} - issue-number: ${{ github.event.pull_request.number }} - body: | - #### Automated Review URLs - * [Readthedocs](https://ngff--${{ github.event.pull_request.number }}.org.readthedocs.build/) - * [render latest/index.bs](http://api.csswg.org/bikeshed/?url=https://raw.githubusercontent.com/ome/ngff/${{ github.event.pull_request.head.sha }}/latest/index.bs) - * [diff latest modified](https://services.w3.org/htmldiff?doc1=https%3A%2F%2Fngff.openmicroscopy.org%2Flatest%2F&doc2=http%3A%2F%2Fapi.csswg.org%2Fbikeshed%2F%3Furl%3Dhttps%3A%2F%2Fraw.githubusercontent.com%2Fome%2Fngff%2F${{ github.event.pull_request.head.sha }}%2Flatest%2Findex.bs) - edit-mode: replace +# - uses: peter-evans/create-or-update-comment@v2 +# with: +# comment-id: ${{ steps.fc.outputs.comment-id }} +# issue-number: ${{ github.event.pull_request.number }} +# body: | +# #### Automated Review URLs +# * [Readthedocs](https://ngff--${{ github.event.pull_request.number }}.org.readthedocs.build/) +# * [render latest/index.bs](http://api.csswg.org/bikeshed/?url=https://raw.githubusercontent.com/ome/ngff/${{ github.event.pull_request.head.sha }}/latest/index.bs) +# * [diff latest modified](https://services.w3.org/htmldiff?doc1=https%3A%2F%2Fngff.openmicroscopy.org%2Flatest%2F&doc2=http%3A%2F%2Fapi.csswg.org%2Fbikeshed%2F%3Furl%3Dhttps%3A%2F%2Fraw.githubusercontent.com%2Fome%2Fngff%2F${{ github.event.pull_request.head.sha }}%2Flatest%2Findex.bs) +# edit-mode: replace diff --git a/.github/workflows/validation.yml b/.github/workflows/validation.yml index 180bf42c..007642e7 100644 --- a/.github/workflows/validation.yml +++ b/.github/workflows/validation.yml @@ -1,28 +1,28 @@ -name: Validation -on: - push: - pull_request: +# name: Validation +# on: +# push: +# pull_request: -jobs: +# jobs: - validate: - name: Validation - strategy: - matrix: - ngff: - - '0.1' - - '0.2' - - '0.3' - - '0.4' - - '0.5' - - 'latest' - runs-on: ubuntu-24.04 - steps: - - uses: actions/checkout@v4 - with: - submodules: 'true' - - uses: actions/setup-python@v5 - with: - python-version: '3.9' - - run: python -mpip install --upgrade wheel tox - - run: cd ${{matrix.ngff}} && tox +# validate: +# name: Validation +# strategy: +# matrix: +# ngff: +# - '0.1' +# - '0.2' +# - '0.3' +# - '0.4' +# - '0.5' +# - 'latest' +# runs-on: ubuntu-24.04 +# steps: +# - uses: actions/checkout@v4 +# with: +# submodules: 'true' +# - uses: actions/setup-python@v5 +# with: +# python-version: '3.9' +# - run: python -mpip install --upgrade wheel tox +# - run: cd ${{matrix.ngff}} && tox diff --git a/.gitignore b/.gitignore index fc506c7c..798d3b77 100644 --- a/.gitignore +++ b/.gitignore @@ -2,7 +2,7 @@ **/__pycache__/* */index.html _build -_bikeshed +_html_extra .tox .vscode .*plist diff --git a/.gitmodules b/.gitmodules index 88a43580..b0df15ce 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,24 +1,30 @@ -[submodule "0.1"] - path = 0.1 - url = https://github.com/ome/ngff - branch = v0.1 -[submodule "0.2"] - path = 0.2 - url = https://github.com/ome/ngff - branch = v0.2 -[submodule "0.3"] - path = 0.3 - url = https://github.com/ome/ngff - branch = v0.3 -[submodule "0.4"] - path = 0.4 - url = https://github.com/ome/ngff - branch = v0.4 +[submodule "dev"] + path = specifications/dev + url = https://github.com/ome/ngff-spec + branch = main +; [submodule "0.6.dev2"] +; path = specifications/0.6.dev2 +; url = https://github.com/ome/ngff-spec +; branch = 0.6.dev2 [submodule "0.5"] - path = 0.5 - url = https://github.com/ome/ngff - branch = v0.5 -[submodule "latest"] - path = latest - url = https://github.com/ome/ngff - branch = v0.5 + path = specifications/0.5 + url = https://github.com/ome/ngff-spec + branch = 0.5 + +[submodule "0.4"] + path = specifications/0.4 + url = https://github.com/ome/ngff-spec + branch = 0.4 +[submodule "0.3"] + path = specifications/0.3 + url = https://github.com/ome/ngff-spec + branch = 0.3 +[submodule "specifications/0.2"] + path = specifications/0.2 + url = https://github.com/ome/ngff-spec + branch = 0.2 +[submodule "specifications/0.1"] + path = specifications/0.1 + url = https://github.com/ome/ngff-spec + branch = 0.1 + diff --git a/0.1 b/0.1 deleted file mode 160000 index d669ceb9..00000000 --- a/0.1 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit d669ceb90b424638eff0885f29ff588670333caa diff --git a/0.2 b/0.2 deleted file mode 160000 index d2dbd2d1..00000000 --- a/0.2 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit d2dbd2d13d9899e0b012ddaddd629fe39ec134f7 diff --git a/0.3 b/0.3 deleted file mode 160000 index e53257b1..00000000 --- a/0.3 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit e53257b18bac6ba5e86f3e74dc5fc9c3773a5a4e diff --git a/0.4 b/0.4 deleted file mode 160000 index 7ac3430c..00000000 --- a/0.4 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 7ac3430c74a66e5bcf53e41c429143172d68c0a4 diff --git a/0.5 b/0.5 deleted file mode 160000 index 8cbba216..00000000 --- a/0.5 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 8cbba216e37407bd2d4bd5c7128ab13bd0a6404e diff --git a/conf.py b/conf.py index eae698d7..29fcaf35 100644 --- a/conf.py +++ b/conf.py @@ -16,8 +16,9 @@ extensions = [ "myst_parser", "sphinx_reredirects", - "sphinx_design" - ] + "sphinx_design", + "sphinxcontrib.bibtex"] +bibtex_bibfiles = ["references.bib"] source_suffix = [".rst", ".md"] myst_heading_anchors = 5 myst_enable_extensions = [ @@ -38,13 +39,25 @@ "README.md", "LICENSE.md", "CONTRIBUTING.md", + "**/README.md", + "**/LICENSE.md", + "**/CONTRIBUTING.md", ] redirects = { - "tools/index": "../resources/tools/index.html", - "publications/index": "../resources/publications/index.html", - "data/index": "../resources/data/index.html", - "about/index": "../index.html" + "tools/index": "../resources/tools/index.html", + "publications/index": "../resources/publications/index.html", + "data/index": "../resources/data/index.html", + "about/index": "../index.html", + "0.1/": "../specifications/0.1/index.html", + "0.2/": "../specifications/0.2/index.html", + "0.3/": "../specifications/0.3/index.html", + "0.4/": "../specifications/0.4/index.html", + "0.5/": "../specifications/0.5/index.html", + "latest/index": "../specifications/0.5/index.html", + "latest/": "../specifications/0.5/index.html", + "dev/index": "../specifications/dev/index.html", + "dev/": "../specifications/dev/index.html" } # -- Options for HTML output ------------------------------------------------- @@ -77,151 +90,46 @@ ] html_extra_path = [ - "_bikeshed", + "_html_extra", ] -# #################################### -# Post-process all versions -# #################################### - - - -from pathlib import Path - -from json_schema_for_humans.generate import ( - generate_from_filename, - GenerationConfiguration, -) - - -def get_version_index_html(*, version: str, schmea_fnames: list[Path]) -> str: - schemas_list = "\n".join( - [f"
  • {p.stem}
  • " for p in schmea_fnames] - ) - return f""" - - - - - - - - - - - - - - OME-zarr version {version} - - - -

    Version {version}


    - - - -""" - - -def get_index_html(*, versions: list[str]) -> str: - versions_list = "\n".join( - [f"
  • {v}
  • " for v in versions] - ) - return f""" - - - - - - - - - - - - - - OME-zarr JSON schema specifications - - - -

    OME-zarr JSON schema specifications


    -

    Nicely rendered JSON schemas generated directly from the OME-zarr specifications.

    -

    Generated using json-schema-for-humans.

    - - - -""" - - -def gen_version(version): - version_path = Path(version) - schema_path = version_path / "schemas" - for schema_file in sorted(schema_path.glob("*.schema")): - print(schema_file) - generate_from_filename( - schema_file, - result_file_name=schema_path / schema_file.with_suffix(".html").name, - config=GenerationConfiguration(template_name="js", with_footer=False), - ) - - schema_fnames = [ - p - for p in sorted(schema_path.glob("*.html")) - if p.name != "index.html" - ] - with open(schema_path / "index.html", "w") as f: - f.write( - get_version_index_html(version=version, schmea_fnames=schema_fnames) - ) - - -def post_process(): +def build_served_html(): import glob + import subprocess + import sys import os import shutil - import subprocess + from pathlib import Path - versions = ["latest"] + glob.glob("[0-9]*") - for version in versions: - - # Run bikeshed - index_file = f"{version}/index.bs" - output_file = index_file.replace("bs", "html") - output_dir = os.path.dirname(output_file) - target_dir = os.path.join("_bikeshed", output_dir) + os.chdir(Path(__file__).parent) + versions = [d for d in os.listdir("specifications") if os.path.isdir(os.path.join("specifications", d))] - run_bikeshed = True + for version in versions: - # Give the loop a chance to skip files if no build is needed/requested - if "BIKESHED" not in os.environ and os.path.exists(output_file): - src_time = os.path.getmtime(index_file) - out_time = os.path.getmtime(output_file) - if src_time < out_time: - print(f"{index_file} unchanged") - run_bikeshed = False + # copy schemas to _html_extra + os.makedirs(f'_html_extra/{version}/schemas', exist_ok=True) + schemas = glob.glob(f'specifications/{version}/**/*.schema', recursive=True) + for schema in schemas: + shutil.copy2(schema, f'_html_extra/{version}/schemas/') + print(f'✅ Copied schemas for version {version}') + + # find 'pre_build.py' in 'specifications' subdirectories + script = glob.glob(f'specifications/{version}/**/pre_build.py', recursive=True)[0] - if run_bikeshed: - subprocess.check_call( - f"bikeshed spec {index_file} {output_file}", shell=True, - ) + subprocess.check_call([sys.executable, script]) + print('✅ Built rendered examples/schemas for version', version) - if os.path.exists(target_dir): - shutil.rmtree(target_dir) - shutil.copytree(output_dir, target_dir) + # build jupyter-book docs in specification submodules + myst_file = glob.glob(f'specifications/{version}/**/myst.yml', recursive=True)[0] + bikeshed_output = f'specifications/{version}/index.html' - # Run json-schema-for-humans + # copy built html files to _html_extra try: - d = os.getcwd() - os.chdir("_bikeshed") - gen_version(version) - finally: - os.chdir(d) - - -post_process() -del post_process + if os.path.exists(bikeshed_output): + shutil.copy2(bikeshed_output, f'_html_extra/{version}/index.html') + print(f'✅ Found legacy bikeshed, serving as extra html for {version}') + except Exception as e: + print(f'⚠️ Could not copy served html for version {version}: {e}') + +build_served_html() + \ No newline at end of file diff --git a/latest b/latest deleted file mode 160000 index 8cbba216..00000000 --- a/latest +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 8cbba216e37407bd2d4bd5c7128ab13bd0a6404e diff --git a/.readthedocs.yaml b/readthedocs.yml similarity index 75% rename from .readthedocs.yaml rename to readthedocs.yml index b23558fa..d73b0d3b 100644 --- a/.readthedocs.yaml +++ b/readthedocs.yml @@ -4,6 +4,7 @@ build: os: ubuntu-24.04 tools: python: "3.10" + nodejs: "22" submodules: include: all @@ -15,3 +16,5 @@ sphinx: python: install: - requirements: requirements.txt + - method: pip + path: specifications/dev \ No newline at end of file diff --git a/references.bib b/references.bib new file mode 100644 index 00000000..25e054af --- /dev/null +++ b/references.bib @@ -0,0 +1,121 @@ +@article{moore2021ome, + title={OME-NGFF: a next-generation file format for expanding bioimaging data-access strategies}, + author={Moore, Josh and Allan, Chris and Besson, S{\'e}bastien and Burel, Jean-Marie and Diel, Erin and Gault, David and Kozlowski, Kevin and Lindner, Dominik and Linkert, Melissa and Manz, Trevor and others}, + journal={Nature methods}, + volume={18}, + number={12}, + pages={1496--1498}, + year={2021}, + publisher={Nature Publishing Group US New York} +} + +@software{ngff_spec_latest, + author = {Josh Moore}, + title = {ome/ngff: Next-generation file format (NGFF) + specifications for storing bioimaging data in the + cloud. + }, + month = nov, + year = 2020, + publisher = {Zenodo}, + version = {0.0.1}, + doi = {10.5281/zenodo.4282107}, + url = {https://ngff.openmicroscopy.org/latest/}, +} + +@software{zarr, + author = {Alistair Miles and + jakirkham and + Martin Durant and + Matthias Bussonnier and + James Bourbeau and + Tarik Onalan and + Joe Hamman and + Zain Patel and + Matthew Rocklin and + shikharsg and + Ryan Abernathey and + Josh Moore and + Vincent Schut and + raphael dussin and + Elliott Sales de Andrade and + Charles Noyes and + Aleksandar Jelenak and + Anderson Banihirwe and + Chris Barnes and + George Sakkis and + Jan Funke and + Jerome Kelleher and + Joe Jevnik and + Justin Swaney and + Poruri Sai Rahul and + Stephan Saalfeld and + john and + Tommy Tran and + pyup.io bot and + sbalmer}, + title = {zarr-developers/zarr-python: v2.5.0}, + month = oct, + year = 2020, + publisher = {Zenodo}, + version = {v2.5.0}, + doi = {10.5281/zenodo.4069231}, + url = {https://doi.org/10.5281/zenodo.4069231}, +} + +@software{n5, + author = {Stephan Saalfeld and + Igor Pisarev and + Philipp Hanslovsky and + Andrew Champion and + Curtis Rueden and + John Bogovic and + Mark Kittisopikul and + jakirkham}, + title = {saalfeldlab/n5: n5-2.5.1}, + month = may, + year = 2022, + publisher = {Zenodo}, + version = {n5-2.5.1}, + doi = {10.5281/zenodo.6578232}, + url = {https://doi.org/10.5281/zenodo.6578232}, +} + +@software{ome-zarr-py, + author = {Josh Moore and + Will Moore and + Sébastien Besson and + jean-marie burel and + Constantin Pape and + Dimitri Papadopoulos Orfanos and + David Stansby and + toloudis and + Giovanni Palla and + Guillaume Gay and + Evan Lyall and + Satrajit Ghosh and + Simon Li and + Benjamin Rombaut and + Minh Nhat Nguyen and + Juan Nunez-Iglesias and + aeisenbarth and + Albert Dominguez Mantes and + Yaroslav Halchenko and + Joshua Gould and + Camilo Laiton and + Tommaso Comparin and + LucaMarconato and + Heath Patterson and + Wouter-Michiel Vierdag and + Talley Lambert and + Sean Martin and + Peter Sobolewski and + M Bussonnier}, + title = {ome/ome-zarr-py: v0.12.2}, + month = aug, + year = 2025, + publisher = {Zenodo}, + version = {v0.12.2}, + doi = {10.5281/zenodo.16925672}, + url = {https://doi.org/10.5281/zenodo.16925672}, +} \ No newline at end of file diff --git a/requirements.txt b/requirements.txt index 5409e6d9..3479fbfd 100644 --- a/requirements.txt +++ b/requirements.txt @@ -4,5 +4,5 @@ pydata-sphinx-theme json-schema-for-humans testresources sphinx-reredirects -sphinx-reredirects -sphinx-design \ No newline at end of file +sphinxcontrib-bibtex +sphinx-design diff --git a/specifications/0.1 b/specifications/0.1 new file mode 160000 index 00000000..4affd105 --- /dev/null +++ b/specifications/0.1 @@ -0,0 +1 @@ +Subproject commit 4affd105cc2ef4ef3ecd299763866db2297ec6e5 diff --git a/specifications/0.2 b/specifications/0.2 new file mode 160000 index 00000000..8eb58c16 --- /dev/null +++ b/specifications/0.2 @@ -0,0 +1 @@ +Subproject commit 8eb58c1665156fe20cc7f1323d0e0e782711b64f diff --git a/specifications/0.3 b/specifications/0.3 new file mode 160000 index 00000000..4a7efee6 --- /dev/null +++ b/specifications/0.3 @@ -0,0 +1 @@ +Subproject commit 4a7efee679a761ba8b8123dc11d9da537ae81541 diff --git a/specifications/0.4 b/specifications/0.4 new file mode 160000 index 00000000..fd39e070 --- /dev/null +++ b/specifications/0.4 @@ -0,0 +1 @@ +Subproject commit fd39e0708b0b99dcc3c8fb0c277ead06a413282d diff --git a/specifications/0.5 b/specifications/0.5 new file mode 160000 index 00000000..acb23fba --- /dev/null +++ b/specifications/0.5 @@ -0,0 +1 @@ +Subproject commit acb23fbac1d937b944932b7a46bc30817ace9819 diff --git a/specifications/dev b/specifications/dev new file mode 160000 index 00000000..f7da49b3 --- /dev/null +++ b/specifications/dev @@ -0,0 +1 @@ +Subproject commit f7da49b3dd4f89b9019cde7bb8911ac97bb4933e diff --git a/specifications/index.md b/specifications/index.md index abfe2e8d..4b228c14 100644 --- a/specifications/index.md +++ b/specifications/index.md @@ -3,13 +3,17 @@ Specifications OME-Zarr files have standardized metadata (that is the OME portion of "OME-Zarr") - each new version of OME-Zarr files has its own specification. Those specifications are listed below. -The current released version of the OME-Zarr specification is 0.5. - - +The current released version of the OME-Zarr specification is [0.5](0.5/ngff_spec/index.md). + +```{toctree} +:maxdepth: 1 +:caption: available specifications + +dev/index.md +0.5/index.md +0.4/index.md +0.3/index.md +0.2/index.md +0.1/index.md + +``` \ No newline at end of file