A Sphinx extension that builds an HTML gallery of examples from any set of Python scripts.
Flexible sorting system for organizing galleries and examples within galleries. Sphinx-Gallery provides built-in sorting functions and supports custom sorting logic for complete control over gallery organization.
Sort key class for explicit ordering of gallery subsections.
class ExplicitOrder:
"""
Sorting key for explicit ordering of gallery subsections.
Allows you to specify the exact order of gallery subsections
by providing a list of subsection names. Subsections not in
the list appear after ordered ones in alphabetical order.
"""
def __init__(self, ordered_list):
"""
Parameters:
- ordered_list: list, explicit order of subsection names
"""
def __call__(self, item):
"""
Sorting key function.
Parameters:
- item: str, subsection name to sort
Returns:
tuple: Sort key for the item
"""from sphinx_gallery.sorting import ExplicitOrder
sphinx_gallery_conf = {
'subsection_order': ExplicitOrder([
'basic_examples',
'intermediate_examples',
'advanced_examples',
'expert_examples'
]),
}def FileSizeKey(filename):
"""
Sort examples by file size.
Parameters:
- filename: str, path to the example file
Returns:
int: File size in bytes for sorting
"""def NumberOfCodeLinesSortKey(filename):
"""
Sort examples by number of lines of code.
Parameters:
- filename: str, path to the example file
Returns:
int: Number of lines of code for sorting
"""def FileNameSortKey(filename):
"""
Sort examples alphabetically by filename.
Parameters:
- filename: str, path to the example file
Returns:
str: Filename for alphabetical sorting
"""def ExampleTitleSortKey(filename):
"""
Sort examples by title extracted from docstring.
Parameters:
- filename: str, path to the example file
Returns:
str: Example title for sorting
"""Control the order of gallery subsections (directories):
from sphinx_gallery.sorting import ExplicitOrder
sphinx_gallery_conf = {
# Use explicit ordering
'subsection_order': ExplicitOrder(['basic', 'advanced', 'expert']),
# Or use a custom function
'subsection_order': lambda x: x.lower(), # Alphabetical, case-insensitive
}Control the order of examples within each subsection:
from sphinx_gallery.sorting import NumberOfCodeLinesSortKey, FileSizeKey
sphinx_gallery_conf = {
# Sort by number of code lines (default)
'within_subsection_order': NumberOfCodeLinesSortKey,
# Sort by file size
'within_subsection_order': FileSizeKey,
# Sort alphabetically by filename
'within_subsection_order': lambda filename: os.path.basename(filename),
}def custom_sort_key(filename):
"""
Custom sorting function example.
Sort by complexity level indicated in filename prefix.
"""
basename = os.path.basename(filename)
# Extract complexity level from filename
if basename.startswith('beginner_'):
return (1, basename)
elif basename.startswith('intermediate_'):
return (2, basename)
elif basename.startswith('advanced_'):
return (3, basename)
else:
return (4, basename) # Unknown complexity last
# Usage
sphinx_gallery_conf = {
'within_subsection_order': custom_sort_key,
}def multi_level_sort(filename):
"""
Multi-level sorting by category and then alphabetically.
"""
import os
import re
basename = os.path.basename(filename)
# Primary sort by category prefix
category_order = {
'plot_': 1,
'example_': 2,
'tutorial_': 3,
}
category = 999 # Default for unknown categories
for prefix, order in category_order.items():
if basename.startswith(prefix):
category = order
break
# Secondary sort alphabetically
return (category, basename.lower())
sphinx_gallery_conf = {
'within_subsection_order': multi_level_sort,
}def modification_time_sort(filename):
"""
Sort by file modification time (newest first).
"""
import os
return -os.path.getmtime(filename) # Negative for reverse order
sphinx_gallery_conf = {
'within_subsection_order': modification_time_sort,
}def directory_priority_sort(subsection_dir):
"""
Sort subsections by directory name with priorities.
"""
priority_dirs = {
'getting_started': 1,
'basic_usage': 2,
'advanced_features': 3,
'tutorials': 4,
'examples': 5,
}
dir_name = os.path.basename(subsection_dir)
return priority_dirs.get(dir_name, 999), dir_name
sphinx_gallery_conf = {
'subsection_order': directory_priority_sort,
}def docstring_complexity_sort(filename):
"""
Sort by complexity indicated in docstring.
"""
try:
with open(filename, 'r') as f:
content = f.read()
# Extract docstring
import ast
tree = ast.parse(content)
docstring = ast.get_docstring(tree)
if docstring:
# Look for complexity indicators
complexity_words = ['basic', 'simple', 'introduction']
advanced_words = ['advanced', 'complex', 'expert']
docstring_lower = docstring.lower()
if any(word in docstring_lower for word in complexity_words):
return (1, filename)
elif any(word in docstring_lower for word in advanced_words):
return (3, filename)
else:
return (2, filename)
except:
pass
return (2, filename) # Default to middle complexity
sphinx_gallery_conf = {
'within_subsection_order': docstring_complexity_sort,
}from sphinx_gallery.sorting import ExplicitOrder, NumberOfCodeLinesSortKey
# Custom subsection order
tutorial_order = ExplicitOrder([
'01_introduction',
'02_basic_usage',
'03_advanced_features',
'04_customization',
'05_integration',
])
# Custom example sorting within subsections
def example_sort(filename):
"""Sort examples by number in filename, then alphabetically."""
import re
basename = os.path.basename(filename)
# Extract number from filename like "plot_001_example.py"
match = re.search(r'(\d+)', basename)
if match:
number = int(match.group(1))
return (number, basename)
return (999, basename) # Files without numbers last
sphinx_gallery_conf = {
'subsection_order': tutorial_order,
'within_subsection_order': example_sort,
}def conditional_sort(filename):
"""
Apply different sorting logic based on directory.
"""
dir_name = os.path.dirname(filename)
basename = os.path.basename(filename)
if 'tutorials' in dir_name:
# Sort tutorials by number prefix
import re
match = re.search(r'(\d+)', basename)
return int(match.group(1)) if match else 999
elif 'examples' in dir_name:
# Sort examples by complexity
if 'simple' in basename or 'basic' in basename:
return (1, basename)
elif 'advanced' in basename:
return (3, basename)
else:
return (2, basename)
else:
# Default alphabetical
return basename
sphinx_gallery_conf = {
'within_subsection_order': conditional_sort,
}Use consistent filename prefixes for easier sorting:
basic_examples/
├── plot_001_simple_line.py
├── plot_002_bar_chart.py
└── plot_003_scatter_plot.py
advanced_examples/
├── plot_101_custom_colors.py
├── plot_102_animations.py
└── plot_103_interactive.pyOrganize examples from simple to complex:
complexity_order = ExplicitOrder([
'getting_started', # Basic concepts
'common_tasks', # Everyday usage
'advanced_features', # Power user features
'customization', # Theming and styling
'integration', # With other tools
])Group related functionality:
topic_order = ExplicitOrder([
'data_visualization', # Core plotting
'statistical_plots', # Stats and analysis
'geographic_maps', # Geospatial data
'time_series', # Temporal data
'interactive_plots', # User interaction
])def debug_sort(filename):
"""Sort function with debugging output."""
key = NumberOfCodeLinesSortKey(filename)
print(f"Sorting {filename}: key={key}")
return key
sphinx_gallery_conf = {
'within_subsection_order': debug_sort,
'log_level': {'examples_log_level': 'DEBUG'},
}Install with Tessl CLI
npx tessl i tessl/pypi-sphinx-gallery