docs: reorganize toctree into basic→advanced sections, rewrite user-guide landing#681
Open
FBumann wants to merge 26 commits into
Open
docs: reorganize toctree into basic→advanced sections, rewrite user-guide landing#681FBumann wants to merge 26 commits into
FBumann wants to merge 26 commits into
Conversation
HiGHS prints a banner + progress lines to the Python REPL on every m.solve() call by default. In a tutorial that calls solve many times, this drowns the actual lesson in solver chatter. Pass output_flag=False (a HiGHS solver option forwarded via **solver_options) to suppress it. Touches the four notebooks where solver_name="highs" is the only solver invoked: - create-a-model.ipynb - create-a-model-with-coordinates.ipynb - manipulating-models.ipynb (9 solves) - transport-tutorial.ipynb Left alone: - infeasible-model.ipynb (uses Gurobi, kwarg is OutputFlag there; also showing solver feedback may be pedagogically relevant for infeasibility detection). - solve-on-remote.ipynb / solve-on-oetc.ipynb (remote handler manages its own logging). - piecewise-*.ipynb (already addressed in #677). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Extends the log-silencing scope to the two piecewise tutorials, which together call m.solve() nine times. Same transformation as the other notebooks — output_flag=False as a HiGHS-specific kwarg forwarded via **solver_options. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…-logs # Conflicts: # examples/piecewise-inequality-bounds.ipynb # examples/piecewise-linear-constraints.ipynb
- Add doc/coordinate-alignment.nblink so the index.rst toctree entry resolves to examples/coordinate-alignment.ipynb. - Update api.rst to match the current public API: add the missing solver classes (COPT, Knitro, MindOpt, PIPS, cuPDLPx), expose top-level helpers (align, merge, options, EvolvingAPIWarning, PerformanceWarning), add the missing Model methods (add_sos_constraints, reformulate_sos_constraints, compute_infeasibilities, format_infeasibilities), add Variable methods (to_linexpr, fix/unfix, relax/unrelax), add sections for QuadraticExpression, Objective, and RemoteHandler, remove the duplicate Variables.integers, and fix the "hook" -> "hood" typo. - contributing.rst: replace stale Black reference with ruff, correct the nblink example (proper JSON, right path, fixed RST indentation that was breaking pygments), and use pre-commit run --all-files. - benchmark.rst: fix the rendered objective, which read as a product of two variables; corrected to the actual linear benchmark (2x + y with x - y >= i-1, matching benchmark_linopy.py). - prerequisites.rst: add SCIP, give MOSEK a description, drop the dangling "-" after MindOpt, remove the outdated HiGHS-platforms claim, and clarify what the [solvers] extra actually pulls in. - conf.py + index.rst: bump copyright to 2026 and fix the "contnuous" typo on the landing page. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…r-guide landing page Split the previously flat 16-item User Guide bag into focused sections so users move from install to advanced features in a clear order: Getting Started → User Guide (core building blocks) → Advanced Features → Tutorials → Solving → Troubleshooting → Benchmarking → Reference Rewrite user-guide.rst from a one-paragraph stub into a roadmap landing page: it groups the core notebooks (variables, expressions, constraints, coordinate alignment, manipulating models) into a recommended reading order and points outward to advanced topics, tutorials, remote/GPU solving, and troubleshooting. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Three RST admonitions in notebook markdown cells had a blank line
between the directive and a tab-indented body. CommonMark then ate
the indented block as a code block, so nbsphinx saw an empty
directive ("Content block expected for the …" build errors). Fix by
removing the blank line and using a 3-space indent — the convention
already used by the working admonitions in the same notebooks
(e.g. creating-variables cell `..note::\n Since we did not …`).
- creating-expressions.ipynb cell 13: restored `.. important::` on
coordinate-determination semantics.
- creating-expressions.ipynb cell 17: restored `.. tip::` pointing
at `.add/.sub/.mul/.div` with the `join` parameter and the
coordinate-alignment guide.
- creating-variables.ipynb cell 42: re-added a corrected `.. note::`
on `coords=` being ignored when supplied alongside pandas objects.
Dropped the stale "New in version 0.3.6" framing and the broken
"is ignored is passed" wording from the original.
conf.py: configure intersphinx_mapping for python, numpy, pandas,
xarray, scipy, and dask. The intersphinx extension was already
loaded but had no mapping, so cross-references like
:class:`xarray.DataArray` or :func:`numpy.ndarray` were silently
unresolved.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
… note The coordinate-determination behaviour is regular alignment semantics, not a sharp pitfall — note is the right level. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…rtant to note" This reverts commit e44cbd3. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- Benchmarking → Comparisons. The two children (performance and syntax) both compare linopy with JuMP and Pyomo, not "benchmark" in the regression-tracking sense. - benchmark.rst H1: Benchmarks → Performance comparison, so the page title matches the section framing (syntax.rst was already "Syntax comparison"). - Tutorials → Examples. The contents are end-to-end worked problems and a migration guide; "Tutorials" overloads with the rest of the docs (every notebook is tutorial-style). - Move Examples below Solving so the section flow is Getting Started → User Guide → Advanced Features → Solving → Examples → Troubleshooting → Comparisons → Reference. The user now knows how to both build and run a model before being handed a full worked problem. Update the user-guide.rst cross-reference accordingly. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Sit Examples right after the core building blocks so users move from "I learned the mechanics" to "show me a complete worked problem" before tackling Advanced Features and Solving. Final sidebar order: Getting Started → User Guide → Examples → Advanced Features → Solving → Troubleshooting → Comparisons → Reference Reorder the corresponding bullets in user-guide.rst so the prose matches the sidebar. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Three small fixes that tighten the boundary between the two top sections without changing what each one covers: - Append a "Where to next" cell to create-a-model-with-coordinates, pointing into the five User Guide notebooks. The coordinates notebook is deliberately a shallow tour, so the handoff is now explicit rather than implied by toctree order. - Rewrite the user-guide.rst opening to acknowledge what the reader just did in Getting Started, framing the User Guide as the depth pass on the same surface. - Rename the user-guide.rst H1 from "User Guide" to "Overview" so the sidebar entry under the "User Guide" caption no longer duplicates the caption name. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Cell 0 had two lines that contained literal "\n" sequences as text (plus a stray trailing double-quote), so the markdown rendered as one long line and Sphinx emitted four warnings about "SSH:nbsphinx-math" file-not-found and inline interpreted text. Rewrite the cell with proper newline-separated lines and turn the inline reference to solve-on-oetc.ipynb into a :doc: cross-reference. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
:doc: only resolves inside RST contexts (rst files and the body of RST directives like .. tip::). In plain markdown cells nbsphinx needs markdown links to the .ipynb files, which it then rewrites to the rendered .html targets. - create-a-model-with-coordinates: the new "Where to next" cell now uses [text](other.ipynb) for the five User Guide notebooks. - solve-on-remote: the inline :doc:`solve-on-oetc` introduced in the previous fix is now a markdown link too. Verified the build rewrites all five links to .html targets. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…overview Listing the five User Guide notebooks at the end of the coordinates notebook duplicated the bullet list the overview page already maintains. Single forward pointer keeps the User Guide overview as the source of truth and pushes the reader through the deliberate intro on that page. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…, advanced bottom Replace the flat alphabetic per-class dump with a layered structure that puts the surface 90% of users reach for at the top, the supporting classes in the middle, and the genuinely rare-use surface at the bottom. Task-oriented top sections (Model methods grouped by what the user is doing): Creating a model Inspecting a model Modifying a model Solving Post-solve access (Model post-solve accessors + status enums) Diagnostics IO Top-level helpers (align, options) Classes under the hood: Variable / Variables / LinearExpression / Constraint / Constraints / Objective / Piecewise Each gets a small thematic split inside (Attributes / Operations / Conversion / Post-solve / etc.) rather than an alphabetic dump. Advanced section at the bottom for surface that most users will not reach for: QuadraticExpression CSRConstraint Bulk variable operations (Variables.fix/unfix/relax/unrelax) Auto-reformulation (Model.reformulate_sos_constraints) Remote solving (RemoteHandler) Warnings (EvolvingAPIWarning, PerformanceWarning) Curated to drop internal escape hatches and helpers: - Model.to_gurobipy/to_highspy/to_mosek/to_cupdlpx (power-user escape hatches) - Model.linexpr (arithmetic on Variables is the natural path) - Constraints.format_labels, .coefficientrange (internal diagnostics) - LinearExpression.from_rule, .from_constant (niche constructors) - Constraint.freeze / .mutable, CSRConstraint.freeze / .mutable (CSR backend plumbing) - ScalarVariable, ScalarLinearExpression (internal types) - solvers.PIPS (stub that raises NotImplementedError) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ables The new api.rst structure exposed 14 properties whose autosummary table cell was blank because they had no docstring. Add a single-line description to each: - Model.is_linear / is_quadratic / type - BaseExpression.vars / coeffs / const (fixes both LinearExpression and QuadraticExpression entries) - Objective.is_linear / is_quadratic - PiecewiseFormulation.method / convexity (added as inline attribute docstrings on the dataclass fields) - OptionSettings class docstring (so the top-level `options` instance picks up a description) PiecewiseFormulation: also dropped the duplicated literal value lists from the class-level Attributes block and from the new attribute docstrings, referencing the PWL_METHOD / PWL_CONVEXITY type aliases instead so there is a single source of truth for the allowed values. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The :data:`PWL_METHOD` and :data:`PWL_CONVEXITY` references added in the previous commit rendered as plain <code> rather than as hyperlinks: their docs target didn't exist yet, and the role was being looked up in the wrong module. - Add docstrings to PWL_METHOD, PWL_METHODS, PWL_CONVEXITY, and PWL_CONVEXITIES in linopy/constants.py. - List all four in api.rst under the Piecewise subsection so autosummary generates dedicated pages. - Switch the cross-references in PiecewiseFormulation.method / .convexity and in constants.py to the fully-qualified form (:data:`~linopy.constants.PWL_METHOD`) so they resolve from whichever module they're rendered in. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
3 tasks
…l home The Advanced section was a subjective bucket. Each entry now sits where it belongs: - QuadraticExpression moves into Classes under the hood alongside LinearExpression — it's a class with its own surface, not a power-user appendix. - CSRConstraint moves into Classes under the hood next to Constraint — alternative storage backend, but a regular documented class. - Variables.fix / unfix / relax / unrelax return as a Bulk modify subgroup under the Variables container. - Model.reformulate_sos_constraints joins Modifying a model — it transforms the model in place. - Remote solving and Warnings become small top-level sections of their own at the end of the page rather than nested under Advanced. Preamble updated to drop the now-stale "Advanced section at the bottom" reference and to signal the actual top-level structure (task-oriented top, supporting classes below). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Inline ``.. contents::`` directive on api.rst stays at depth 2 — the page-top TOC is the executive summary, not a complete map. For navigation into a section, bump sphinx-book-theme's ``show_toc_level`` to 2 in ``html_theme_options``. The right-side "On this page" panel now shows H3 entries by default rather than only expanding the section the user has scrolled into. Applies site-wide; the other pages have shallow H3 structures so this is a usability win across the board. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Makes the structural role explicit: these are the classes and types not already covered by the task-oriented top sections. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Align the subgroup names that appear in multiple class sections so a reader who learns the scheme once can scan across classes. Six shared labels emerge — Structure, Construction, Modification, Operations, Conversion, Post-solve access — used wherever they fit. - Variable: "Modifying state" → "Modification" (match Variables, Constraints). - LinearExpression: "Building blocks" → "Structure" (match Constraint, QuadraticExpression below); "Manipulation" → "Operations" (match Variable). - QuadraticExpression: replace the flat list with the same subgroup shape as LinearExpression — Structure, Conversion, Post-solve access. - CSRConstraint: replace the flat list with the same subgroup shape as Constraint — Structure, Post-solve access, Conversion. Also move the solver-status enums out of Post-solve access into their own subsection (Solver status and result types) under Other classes and types: SolverStatus / TerminationCondition / Status / Solution / Result are types you compare Model.status against, not accessors. Model keeps its own task vocabulary (Building / Inspecting / Modifying / Solving / Diagnostics / IO / etc.) because it's structurally different from the data-type classes. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Roll back to the default (1). The right-side page TOC will only expand the section the reader has scrolled into, not all H3 entries across the page. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Two changes in one pass:
(1) Make api.rst per-class throughout. Drop the artificial split
between task-oriented top sections and "Other classes and types".
Model becomes the first H2 (with its task labels — Building /
Inspecting / Modifying / Solving / Post-solve / Diagnostics / IO —
as H3 subsections), and every supporting class becomes a sibling
H2 of Model. Preamble rewritten to frame the page: Model is the
entry point; supporting classes document the types reached via
``model.<attr>`` accessors.
(2) Tighten the surface further. Drop entries that are internal,
implicit-by-arithmetic, or trivial:
- Variables.add / .remove, Constraints.add / .remove — internal
mechanisms used by model.add_*; users never call them.
- Variable.sanitize, Constraints.sanitize_missings — internal
cleanup helpers in the solver pipeline.
- LinearExpression.to_constraint, QuadraticExpression.to_constraint
— almost always implicit via <=, >=, == on expressions.
- LinearExpression.to_quadexpr — niche conversion only meaningful
if you're already deep in quadratic forms.
- Model.get_problem_file / .get_solution_file — debugging-only
temp-file accessors.
- solvers.Solver (abstract base, never instantiated) and
solvers.quadratic_solvers (trivial list).
With Solver and quadratic_solvers removed, the "Solver interface"
section only contained available_solvers, so collapse it into a
single "Solvers" section with the implementation classes.
Also reordered the H3 subgroups inside each class so the most-used
entries appear first. Post-solve access leads on the expression /
constraint classes (the .solution and .dual readers are typically
what a reader is looking for); Aggregate access + Bulk modify lead
on the Variables container.
Top-level helpers moved to the bottom as "Utilities" (align,
options) — they're stragglers, not entry points.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The piecewise construction helpers (breakpoints, segments, Slopes) were previously listed under Model > Building a model because they are used alongside Model.add_piecewise_formulation. Move them into the Piecewise section instead — they live in linopy.piecewise and a reader looking for "how do I build a piecewise formulation" expects everything piecewise in one place. Split the Piecewise section into four small subsections (Construction helpers / PiecewiseFormulation / Low-level helper / Type aliases) so the helper functions, the return type, the standalone tangent_lines, and the PWL_METHOD / PWL_CONVEXITY type aliases all sit under clearly labelled groups instead of one mixed flat list. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…e cross-refs
- Rename Variables container subgroups so they match Variable's
vocabulary where the role is the same:
"Aggregate access" → "Attributes"
"Bulk modify" → "Modification" (the "Bulk" qualifier is
clear from context — the
methods live on the
container)
"Inventory by type" → "Inventory" (matches Constraints'
equivalent subsection)
- Drop the redundant prose note "Container-wide analogues of
Variable.fix, etc." — same reason; clear from context.
Also fix the preamble cross-references. The autosummary entries
register the documented entities under their full module paths
(linopy.model.Model, linopy.variables.Variable, …), so the bare
``:class:`Model``` refs were rendering as plain styled code rather
than hyperlinks. Use the qualified ``~linopy.<module>.<name>`` form
for class refs (display stays "Model" / "Variable" / "Constraint" /
"Objective") and the ``Target <full.path>`` form for methods and
attributes so the link text reads "Model.add_variables" etc.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Stacked on top of #680.
What this PR does
A second pass on the docs that reorganizes the top-level structure for a basic→advanced flow, tightens the boundary between Getting Started and the User Guide, restructures the API reference, and cleans up a handful of latent rendering issues that were dragging the build.
Toctree reorganization
index.rsthad a 16-item flat User Guide bag mixing core mechanics, advanced features, troubleshooting, remote solving, migration, and FAQ-style pages. Split into focused sections with a clear reading order:benchmark.rstH1 became Performance comparison so the page title matches the section framing —syntax.rstwas already titled Syntax comparison.Getting Started → User Guide bridge
Three small but real gaps before this PR:
user-guide.rstwas a one-paragraph stub.Fixed by:
create-a-model-with-coordinatesthat links forward to the User Guide overview. (Initially tried:doc:cross-refs — those only resolve inside RST contexts; switched to markdown links pointing at.ipynbfiles, which nbsphinx rewrites to the rendered.htmltargets.)user-guide.rstas a roadmap that explicitly references the Getting Started content and frames the User Guide as the depth pass on the same surface.API reference restructure (
api.rst)Replaced the alphabetic flat dump per class with a layered structure that puts the surface 90% of users reach for at the top, supporting classes in the middle, and genuinely rare-use surface at the bottom.
Top sections are task-oriented (Model methods grouped by what the user is doing):
Classes under the hood keeps the supporting types together (Variable, Variables, LinearExpression, Constraint, Constraints, Objective, Piecewise), each with thematic subgroups (Attributes / Operations / Conversion / Post-solve etc.) rather than alphabetic dumps.
autosummaryrenders each subgroup as a name + first-line-of-docstring table, so the page becomes scannable.A new Advanced umbrella at the bottom for surface most users don't reach for:
QuadraticExpression,CSRConstraint, bulk variable operations (Variables.fix/unfix/relax/unrelax), auto-reformulation (Model.reformulate_sos_constraints), remote solving (RemoteHandler), warning classes.Curated to drop internal escape hatches and helpers:
Model.to_gurobipy / to_highspy / to_mosek / to_cupdlpx— power-user escape hatches.Model.linexpr— arithmetic onVariableis the natural path.Constraints.format_labels,Constraints.coefficientrange— internal diagnostics.LinearExpression.from_rule,LinearExpression.from_constant— niche constructors.Constraint.freeze / .mutable,CSRConstraint.freeze / .mutable— CSR backend plumbing.ScalarVariable,ScalarLinearExpression— internal types.solvers.PIPS— stub that raisesNotImplementedError.Kept:
Objective(with the post-solve fields a reader cares about:value,sense,expression,is_linear,is_quadratic),EvolvingAPIWarning/PerformanceWarning(called out under Warnings asfilterwarningstargets).PiecewiseFormulationis the return type ofadd_piecewise_formulation, not a construction helper — moved out of Creating a model into its own Piecewise subsection under Classes under the hood, grouped with the lower-leveltangent_lineshelper.Source-side fixes that fell out of the restructure
The new api.rst structure exposed 14 properties whose autosummary table cell was blank because they had no docstring. Added a single-line description to each:
Model.is_linear/is_quadratic/typeBaseExpression.vars/coeffs/const(fixes bothLinearExpressionandQuadraticExpressionentries through inheritance)Objective.is_linear/is_quadraticPiecewiseFormulation.method/convexity(inline attribute docstrings on the dataclass fields)OptionSettingsclass docstring (so the top-leveloptionsinstance picks up a description)While in
piecewise.py, also dropped the duplicated literal value lists from the class-levelAttributesblock — now refers to thePWL_METHOD/PWL_CONVEXITYtype aliases so there's a single source of truth for the allowed values.To make those references resolve as actual links (rather than rendering as plain
<code>):PWL_METHOD,PWL_METHODS,PWL_CONVEXITY,PWL_CONVEXITIESinlinopy/constants.py.api.rstunder the Piecewise subsection soautosummarygenerates dedicated pages.PiecewiseFormulation.method/.convexityand inconstants.pyto the fully-qualified form (:data:\~linopy.constants.PWL_METHOD``) so they resolve from whichever module they're rendered in.Notebook rendering fixes
creating-expressionscells 13 + 17,creating-variablescell 41) had a blank line between the directive and a tab-indented body. CommonMark ate the indented block as a code block, so nbsphinx saw an empty directive and Sphinx emitted "Content block expected for the … directive" build errors. Fixed by using the convention already working elsewhere in the same notebooks (no blank line, 3-space indent).solve-on-remote.ipynbhad literal\nsequences in its source instead of real newlines (plus a stray trailing quote). The markdown rendered as one run-on line, Sphinx emitted four "SSH:nbsphinx-math" file-not-found and inline-interpreted-text warnings. Cell rewritten with proper line breaks.intersphinx
The
sphinx.ext.intersphinxextension was loaded inconf.pybut had nointersphinx_mapping— cross-refs toxarray,numpy,pandas, etc. were silently unresolved. Added mappings for python, numpy, pandas, xarray, scipy, dask.Build
sphinx-buildruns clean. The remaining warnings are pre-existing docstring formatting issues inlinopy/source (CSRConstraint,Model.solve) — separate cleanup.🤖 Generated with Claude Code