Skip to content

feat: converting documentation to mkdocs #5276

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 39 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
9fa8326
add swarm plot to the scatter documentation
rl-utility-man Apr 20, 2025
e563804
ending with fig.show()
rl-utility-man Apr 20, 2025
15b7580
collision avoidance
rl-utility-man Apr 21, 2025
1e4d6b9
replaced a work around with a bug fix.
rl-utility-man May 3, 2025
5469864
maintain collision avoidance while arranging points in c-curves
rl-utility-man May 4, 2025
6d27e9f
Update line-and-scatter.md
rl-utility-man Jun 4, 2025
83d158a
update header
rl-utility-man Jun 4, 2025
7fa86a6
Update line-and-scatter.md
rl-utility-man Jun 4, 2025
f4d8464
Merge pull request #5252 from plotly/merge-docs-to-make-live
LiamConnors Jun 26, 2025
aff4e97
restoring an accidently deleted figure creation line
rl-utility-man Jun 27, 2025
558016f
Merge pull request #5255 from rl-utility-man/patch-18
LiamConnors Jun 30, 2025
d1c1b85
Merge branch 'doc-prod' into swarm-plot
LiamConnors Jul 3, 2025
c6cb0f5
Update static-image-export.md
LiamConnors Jul 7, 2025
b8dfc84
Merge pull request #5149 from rl-utility-man/swarm-plot
LiamConnors Jul 7, 2025
8574401
corrected an incorrect description entry
rl-utility-man Jul 8, 2025
6d39a52
Merge pull request #5271 from rl-utility-man/patch-19
LiamConnors Jul 8, 2025
dc31ccd
Update static-image-export.md
LiamConnors Jul 8, 2025
faa1ee3
Update static-image-export.md
LiamConnors Jul 8, 2025
73e4588
Merge pull request #5270 from plotly/plotly-js-info
LiamConnors Jul 8, 2025
7c2b5a6
Merge pull request #5273 from plotly/fix-command
LiamConnors Jul 8, 2025
a2787a0
- Move contents of `commands.py` to scripts in new `bin` directory an…
gvwilson Jul 10, 2025
ec4b6cd
Update figurewidget.md
LiamConnors Jul 17, 2025
6952aad
Merge pull request #5284 from plotly/LiamConnors-patch-3
LiamConnors Jul 21, 2025
3dced44
preload _plotly_utils
LiamConnors Jul 22, 2025
bc32c86
add docstrings directly to px functions
LiamConnors Dec 2, 2024
174b0e9
change docstring style
LiamConnors Jul 22, 2025
badb199
Merge pull request #5292 from plotly/plotly.express-docstrings
gvwilson Jul 22, 2025
86f69f1
Merge branch 'mkdocs-conversion' into preload-plotly-utils
gvwilson Jul 22, 2025
c0237f6
Merge pull request #5290 from plotly/preload-plotly-utils
gvwilson Jul 22, 2025
76b36dd
feat: numpy documentation style
gvwilson Jul 22, 2025
96af9f6
feat: regenerating Python code with .js fixes
gvwilson Jul 22, 2025
9525f6a
feat: converting doc/python/*.md using bin/run_markdown.py
gvwilson Jul 23, 2025
80792d8
better verbosity
gvwilson Jul 26, 2025
9386750
feat: conditionalize Makefile target for testing
gvwilson Jul 29, 2025
36b21ab
add missing imports and variable definitions
LiamConnors Jul 29, 2025
1e54e0c
add missing imports and variable definitions
LiamConnors Jul 29, 2025
6d1e5c8
Merge remote-tracking branch 'origin/fix-docs' into mkdocs-conversion
gvwilson Jul 30, 2025
20c60ef
Merge remote-tracking branch 'origin/add-missing-imports' into mkdocs…
gvwilson Jul 30, 2025
a07ea45
feat: script to check all examples in doc/python.
gvwilson Jul 30, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,10 @@ tests/test_orca/images/linux/failed/

doc/python/raw.githubusercontent.com/

docs/
docs_tmp/
pages/examples/

# Don't ignore dataset files
!*.csv.gz
!*.geojson.gz
Expand Down
23 changes: 13 additions & 10 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ then explains the technical aspects of preparing your contribution.

## Code of Conduct

Please note that all contributos are required to abide by our [Code of Conduct](CODE_OF_CONDUCT.md).
Please note that all contributos are required to abide by our Code of Conduct.

## Different Ways to Contribute

Expand All @@ -19,7 +19,7 @@ it is important to understand the structure of the code and the repository.
- The [`plotly.graph_objects`](https://plotly.com/python/graph-objects/) module (usually imported as `go`)
is [generated from the plotly.js schema](https://plotly.com/python/figure-structure/),
so changes to be made in this package need to be contributed to [plotly.js](https://github.com/plotly/plotly.js)
or to the code generation system in `./codegen/`.
or to the code generation system in `./bin/codegen/`.
Code generation creates traces and layout classes that have a direct correspondence to their JavaScript counterparts,
while higher-level methods that work on figures regardless of the current schema (e.g., `BaseFigure.for_each_trace`)
are defined in `plotly/basedatatypes.py`.
Expand All @@ -38,16 +38,17 @@ it is important to understand the structure of the code and the repository.
These are organized in subdirectories according to what they test:
see the "Setup" section below for more details.

- Documentation is found in `doc/`, and its structure is described in [its README file](doc/README.md).
- Documentation is found in `doc/`, and its structure is described in its README file.
The documentation is a great place to start contributing,
since you can add or modify examples without setting up a full environment.

Code and documentation are not the only way to contribute:
you can also help by:
Code and documentation are not the only way to contribute.
You can also help by:

- Reporting bugs at <https://github.com/plotly/plotly.py/issues>.
Please take a moment to see if your problem has already been reported, and if so, add a comment to the existing issue;
we will try to prioritize those that affect the most people.
we will try to prioritize those that affect the most people
and that are accompanied by small, runnable examples.

- Submitting feature requests (also at <https://github.com/plotly/plotly.py/issues>).
Again, please add a comment to an existing issue if the feature you want has already been requested.
Expand Down Expand Up @@ -219,11 +220,11 @@ Once you have done that,
run the `updateplotlyjs` command:

```bash
python commands.py updateplotlyjs
python bin/updatejs.py
```

This downloads new versions of `plot-schema.json` and `plotly.min.js` from the `plotly/plotly.js` GitHub repository
and places them in `plotly/package_data`.
and places them in `resources` and `plotly/package_data` respectively.
It then regenerates all of the `graph_objs` classes based on the new schema.

### Using a Development Branch of Plotly.js
Expand All @@ -232,7 +233,8 @@ If your development branch is in [the plotly.js repository](https://github.com/p
you can update to development versions of `plotly.js` with this command:

```bash
python commands.py updateplotlyjsdev --devrepo reponame --devbranch branchname
# FIXME commands.py didn't provide --devrepo or --devbranch
python bin/updatejs.py --dev --devrepo reponame --devbranch branchname
```

This fetches the `plotly.js` in the CircleCI artifact of the branch `branchname` of the repo `reponame`.
Expand All @@ -255,5 +257,6 @@ You can then run the following command
*in your local plotly.py repository*:

```bash
python commands.py updateplotlyjsdev --local /path/to/your/plotly.js/
# FIXME: commands.py didn't provide --local
python bin/updatejs.py --dev --local /path/to/your/plotly.js/
```
78 changes: 78 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
# Manage plotly.py project.

RUN = uv run
PACKAGE_DIRS = _plotly_utils plotly
CODE_DIRS = ${PACKAGE_DIRS} scripts

ifdef MKDOCS_ALL
EXAMPLE_SRC = $(wildcard doc/python/*.md)
else
EXAMPLE_SRC = doc/python/cone-plot.md doc/python/strip-charts.md
endif

EXAMPLE_DST = $(patsubst doc/python/%.md,pages/examples/%.md,${EXAMPLE_SRC})

## commands: show available commands
commands:
@grep -h -E '^##' ${MAKEFILE_LIST} | sed -e 's/## //g' | column -t -s ':'

## docs: rebuild documentation
.PHONY: docs
docs:
${RUN} mkdocs build

## docs-lint: check documentation
docs-lint:
${RUN} pydoclint ${PACKAGE_DIRS}

## docs-tmp: rebuild documentation saving Markdown in ./tmp
docs-tmp:
MKDOCS_TEMP_DIR=./docs_tmp ${RUN} mkdocs build

## examples-batch: generate Markdown for all doc/python
examples-batch:
${RUN} bin/run_markdown.py --outdir pages/examples --inline --verbose 1 ${EXAMPLE_SRC}

## examples: generate Markdown for individual doc/python
examples: ${EXAMPLE_DST}

pages/examples/%.md: doc/python/%.md
${RUN} bin/run_markdown.py --outdir pages/examples --inline --verbose 2 $<

## format: reformat code
format:
${RUN} ruff format ${CODE_DIRS}

## generate: generate code
generate:
${RUN} bin/generate_code.py --codedir plotly
${RUN} ruff format plotly

## lint: check the code
lint:
${RUN} ruff check ${CODE_DIRS}

## test: run tests
test:
${RUN} pytest tests

## updatejs: update JavaScript bundle
updatejs:
${RUN} bin/updatejs.py --codedir plotly

## --: --

## clean: clean up repository
clean:
@find . -name '*~' -delete
@find . -name '.DS_Store' -delete
@rm -rf .coverage
@rm -rf .pytest_cache
@rm -rf .ruff_cache
@rm -rf dist
@rm -rf docs
@rm -rf pages/examples

## sync: update Python packages
sync:
uv sync --extra dev
19 changes: 9 additions & 10 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -76,22 +76,21 @@ Built on top of [plotly.js](https://github.com/plotly/plotly.js), `plotly.py` is

## Installation

plotly.py may be installed using pip
plotly.py may be installed using pip:

```
pip install plotly
```

or conda.
or conda:

```
conda install -c conda-forge plotly
```

### Jupyter Widget Support

For use as a Jupyter widget, install `jupyter` and `anywidget`
packages using `pip`:
For use as a Jupyter widget, install the `jupyter` and `anywidget` packages using `pip`:

```
pip install jupyter anywidget
Expand All @@ -112,14 +111,14 @@ command line utility (legacy as of `plotly` version 4.9).

#### Kaleido

The [`kaleido`](https://github.com/plotly/Kaleido) package has no dependencies and can be installed
using pip
The [`kaleido`](https://github.com/plotly/Kaleido) package has no dependencies
and can be installed using pip:

```
pip install -U kaleido
```

or conda
or conda:

```
conda install -c conda-forge python-kaleido
Expand All @@ -129,13 +128,13 @@ conda install -c conda-forge python-kaleido

Some plotly.py features rely on fairly large geographic shape files. The county
choropleth figure factory is one such example. These shape files are distributed as a
separate `plotly-geo` package. This package can be installed using pip...
separate `plotly-geo` package. This package can be installed using pip:

```
pip install plotly-geo==1.0.0
```

or conda
or conda:

```
conda install -c plotly plotly-geo=1.0.0
Expand All @@ -145,7 +144,7 @@ conda install -c plotly plotly-geo=1.0.0

## Copyright and Licenses

Code and documentation copyright 2019 Plotly, Inc.
Code and documentation copyright Plotly, Inc.

Code released under the [MIT license](https://github.com/plotly/plotly.py/blob/main/LICENSE.txt).

Expand Down
18 changes: 18 additions & 0 deletions bin/check-all-md.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
from pathlib import Path
import os
import re
import sys

PAT = re.compile(r"^```python\n(.+?)\n```", re.MULTILINE | re.DOTALL)
TMP_FILE = "tmp.py"

for filename in sys.argv[1:]:
content = Path(filename).read_text()
blocks = PAT.findall(content)
for i, b in enumerate(blocks):
Path(TMP_FILE).write_text(b.strip())
sys.stdout.write(f"\n{'=' * 40}\n{filename}: {i}\n")
sys.stdout.flush()
sys.stdout.write(f"{'-' * 40}\n")
sys.stdout.flush()
os.system(f"python {TMP_FILE} > /dev/null")
67 changes: 23 additions & 44 deletions codegen/__init__.py → bin/codegen/__init__.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
import json
import os
import os.path as opath
import shutil
import subprocess
import sys

from codegen.datatypes import build_datatype_py, write_datatype_py # noqa: F401
Expand Down Expand Up @@ -87,45 +85,30 @@ def preprocess_schema(plotly_schema):
items["colorscale"] = items.pop("concentrationscales")


def make_paths(outdir):
"""Make various paths needed for formatting and linting."""
def make_paths(codedir):
"""Make various paths needed for code generation."""

validators_dir = opath.join(outdir, "validators")
graph_objs_dir = opath.join(outdir, "graph_objs")
graph_objects_path = opath.join(outdir, "graph_objects", "__init__.py")
validators_dir = codedir / "validators"
graph_objs_dir = codedir / "graph_objs"
graph_objects_path = codedir / "graph_objects" / "__init__.py"
return validators_dir, graph_objs_dir, graph_objects_path


def lint_code(outdir):
"""Check Python code using settings in pyproject.toml."""

subprocess.call(["ruff", "check", *make_paths(outdir)])


def reformat_code(outdir):
"""Reformat Python code using settings in pyproject.toml."""

subprocess.call(["ruff", "format", *make_paths(outdir)])


def perform_codegen(outdir, noformat=False):
"""Generate code (and possibly reformat)."""
def perform_codegen(codedir, noformat=False):
"""Generate code."""

# Get paths
validators_dir, graph_objs_dir, graph_objects_path = make_paths(outdir)
validators_dir, graph_objs_dir, graph_objects_path = make_paths(codedir)

# Delete prior codegen output
if opath.exists(validators_dir):
if validators_dir.exists():
shutil.rmtree(validators_dir)
if opath.exists(graph_objs_dir):
if graph_objs_dir.exists():
shutil.rmtree(graph_objs_dir)

# Load plotly schema
project_root = opath.dirname(outdir)
plot_schema_path = opath.join(
project_root, "codegen", "resources", "plot-schema.json"
)

project_root = codedir.parent
plot_schema_path = project_root / "resources" / "plot-schema.json"
with open(plot_schema_path, "r") as f:
plotly_schema = json.load(f)

Expand Down Expand Up @@ -193,26 +176,26 @@ def perform_codegen(outdir, noformat=False):

# Write out the JSON data for the validators
os.makedirs(validators_dir, exist_ok=True)
write_validator_json(outdir, validator_params)
write_validator_json(codedir, validator_params)

# Alls
alls = {}

# Write out datatypes
for node in all_compound_nodes:
write_datatype_py(outdir, node)
write_datatype_py(codedir, node)

# Deprecated
# These are deprecated legacy datatypes like graph_objs.Marker
write_deprecated_datatypes(outdir)
write_deprecated_datatypes(codedir)

# Write figure class to graph_objs
data_validator = get_data_validator_instance(base_traces_node)
layout_validator = layout_node.get_validator_instance()
frame_validator = frame_node.get_validator_instance()

write_figure_classes(
outdir,
codedir,
base_traces_node,
data_validator,
layout_validator,
Expand Down Expand Up @@ -242,7 +225,7 @@ def perform_codegen(outdir, noformat=False):
# Write plotly/graph_objs/graph_objs.py
# This is for backward compatibility. It just imports everything from
# graph_objs/__init__.py
write_graph_objs_graph_objs(outdir)
write_graph_objs_graph_objs(codedir)

# Add Figure and FigureWidget
root_datatype_imports = datatype_rel_class_imports[()]
Expand Down Expand Up @@ -287,12 +270,13 @@ def __getattr__(import_name):
# __all__
for path_parts, class_names in alls.items():
if path_parts and class_names:
filepath = opath.join(outdir, "graph_objs", *path_parts, "__init__.py")
filepath = codedir / "graph_objs"
filepath = filepath.joinpath(*path_parts) / "__init__.py"
with open(filepath, "at") as f:
f.write(f"\n__all__ = {class_names}")

# Output datatype __init__.py files
graph_objs_pkg = opath.join(outdir, "graph_objs")
graph_objs_pkg = codedir / "graph_objs"
for path_parts in datatype_rel_class_imports:
rel_classes = sorted(datatype_rel_class_imports[path_parts])
rel_modules = sorted(datatype_rel_module_imports.get(path_parts, []))
Expand All @@ -317,18 +301,13 @@ def __getattr__(import_name):
graph_objects_rel_classes,
init_extra=optional_figure_widget_import,
)
graph_objects_path = opath.join(outdir, "graph_objects", "__init__.py")
os.makedirs(opath.join(outdir, "graph_objects"), exist_ok=True)
graph_objects_path = codedir / "graph_objects"
graph_objects_path.mkdir(parents=True, exist_ok=True)
graph_objects_path /= "__init__.py"
with open(graph_objects_path, "wt") as f:
f.write("# ruff: noqa: F401\n")
f.write(graph_objects_init_source)

# Run code formatter on output directories
if noformat:
print("skipping reformatting")
else:
reformat_code(outdir)


if __name__ == "__main__":
if len(sys.argv) != 2:
Expand Down
Loading