Diagram Specification¶
Schema visualization as directed acyclic graphs.
Overview¶
dj.Diagram visualizes DataJoint schemas as directed graphs showing tables and their foreign key relationships. It provides multiple output formats including SVG, PNG, and Mermaid syntax.
Design Principles¶
- Multiple output formats: Graphviz (SVG/PNG) and Mermaid for different use cases
- Graph algebra: Combine and filter diagrams with set operators
- Visual encoding: Table tiers distinguished by shape and color
- Flexible layout: Configurable direction and schema grouping
API Reference¶
Constructor¶
dj.Diagram(source, context=None)
| Parameter | Type | Default | Description |
|---|---|---|---|
source |
Table, Schema, module | — | Source to visualize |
context |
dict | None | Namespace for class name resolution |
Layout Direction¶
New in 2.1
Configurable layout direction was added in DataJoint 2.1.
Layout direction is controlled via configuration:
# Check current direction
dj.config.display.diagram_direction # "TB" or "LR"
# Set globally
dj.config.display.diagram_direction = "LR"
# Override temporarily
with dj.config.override(display__diagram_direction="LR"):
dj.Diagram(schema).draw()
| Value | Description |
|---|---|
"TB" |
Top to bottom (default) |
"LR" |
Left to right |
Class Method¶
dj.Diagram.from_sequence(sequence)
Create a combined diagram from multiple sources. Equivalent to Diagram(a) + Diagram(b) + ....
Operators¶
Diagrams support set algebra for combining and filtering:
| Operator | Description | Example |
|---|---|---|
diag + n |
Expand n levels downstream (children) | dj.Diagram(Mouse) + 2 |
diag - n |
Expand n levels upstream (parents) | dj.Diagram(Neuron) - 2 |
diag1 + diag2 |
Union of two diagrams | dj.Diagram(Mouse) + dj.Diagram(Session) |
diag1 - diag2 |
Difference (remove nodes) | dj.Diagram(schema) - dj.Diagram(Lookup) |
diag1 * diag2 |
Intersection | dj.Diagram(schema1) * dj.Diagram(schema2) |
Common Patterns¶
# Show table with immediate parents and children
dj.Diagram(MyTable) + 1 - 1
# Show entire schema
dj.Diagram(schema)
# Show all tables downstream of a source
dj.Diagram(SourceTable) + 10
# Show ancestry of a computed table
dj.Diagram(ComputedTable) - 10
Note: Order matters. diagram + 1 - 1 may differ from diagram - 1 + 1.
Collapsing Schemas¶
New in 2.1
The collapse() method was added in DataJoint 2.1.
diag.collapse()
Mark a diagram for collapsing when combined with other diagrams. Collapsed schemas appear as single nodes showing the table count.
# Show schema1 expanded, schema2 as a single collapsed node
dj.Diagram(schema1) + dj.Diagram(schema2).collapse()
"Expanded wins" rule: If a node appears in both a collapsed and non-collapsed diagram, it stays expanded. This allows you to show specific tables from a schema while collapsing the rest.
# Subject is expanded, rest of analysis schema is collapsed
dj.Diagram(Subject) + dj.Diagram(analysis).collapse()
Output Methods¶
Graphviz Output¶
| Method | Returns | Description |
|---|---|---|
make_svg() |
IPython.SVG |
SVG for Jupyter display |
make_png() |
BytesIO |
PNG image bytes |
make_image() |
ndarray |
NumPy array (matplotlib) |
make_dot() |
pydot.Dot |
Graphviz DOT object |
Mermaid Output¶
New in 2.1
Mermaid output was added in DataJoint 2.1.
make_mermaid() -> str
Generates Mermaid flowchart syntax for embedding in Markdown, GitHub, or web documentation. Tables are grouped into subgraphs by schema.
Display Methods¶
| Method | Description |
|---|---|
draw() |
Display with matplotlib |
_repr_svg_() |
Jupyter notebook auto-display |
File Output¶
save(filename, format=None)
| Parameter | Type | Description |
|---|---|---|
filename |
str | Output file path |
format |
str | "png", "svg", or "mermaid". Inferred from extension if None. |
Supported extensions: .png, .svg, .mmd, .mermaid
Visual Encoding¶
Table Tiers¶
Each table tier has a distinct visual style:
| Tier | Shape | Fill Color | Font Color |
|---|---|---|---|
| Manual | rectangle | green | dark green |
| Lookup | plain text | gray | black |
| Computed | ellipse | red | dark red |
| Imported | ellipse | blue | dark blue |
| Part | plain text | transparent | black |
Edge Styles¶
| Style | Meaning |
|---|---|
| Solid line | Primary foreign key |
| Dashed line | Non-primary foreign key |
| Thick line | Master-Part relationship |
| Thin line | Multi-valued foreign key |
Node Labels¶
- Underlined: Table introduces new primary key attributes
- Plain: Table inherits all primary key attributes from parents
Schema Grouping¶
New in 2.1
Automatic schema grouping was added in DataJoint 2.1.
Tables are automatically grouped into visual clusters by their database schema. The cluster label shows the Python module name when available (following the DataJoint convention of one module per schema), otherwise the database schema name.
# Multi-schema diagram - tables automatically grouped
combined = dj.Diagram(schema1) + dj.Diagram(schema2)
combined.draw()
# Save with grouping
combined.save("pipeline.svg")
This is useful when visualizing multi-schema pipelines to see which tables belong to which module.
Examples¶
Basic Usage¶
import datajoint as dj
# Diagram from a single table
dj.Diagram(Mouse)
# Diagram from entire schema
dj.Diagram(schema)
# Diagram from module
dj.Diagram(my_pipeline_module)
Layout Direction¶
# Horizontal layout using config override
with dj.config.override(display__diagram_direction="LR"):
dj.Diagram(schema).draw()
# Or set globally
dj.config.display.diagram_direction = "LR"
dj.Diagram(schema).save("pipeline.svg")
Saving Diagrams¶
diag = dj.Diagram(schema)
# Save as SVG
diag.save("pipeline.svg")
# Save as PNG
diag.save("pipeline.png")
# Save as Mermaid
diag.save("pipeline.mmd")
# Explicit format
diag.save("output.txt", format="mermaid")
Mermaid Output¶
print(dj.Diagram(schema).make_mermaid())
Output:
flowchart TB
classDef manual fill:#90EE90,stroke:#006400
classDef lookup fill:#D3D3D3,stroke:#696969
classDef computed fill:#FFB6C1,stroke:#8B0000
classDef imported fill:#ADD8E6,stroke:#00008B
classDef part fill:#FFFFFF,stroke:#000000
subgraph my_pipeline
Mouse[Mouse]:::manual
Session[Session]:::manual
Neuron([Neuron]):::computed
end
Mouse --> Session
Session --> Neuron
Combining Diagrams¶
# Union of schemas
combined = dj.Diagram(schema1) + dj.Diagram(schema2)
# Intersection
common = dj.Diagram(schema1) * dj.Diagram(schema2)
# From sequence
combined = dj.Diagram.from_sequence([schema1, schema2, schema3])
Dependencies¶
Diagram visualization requires optional dependencies:
pip install matplotlib pygraphviz
If dependencies are missing, dj.Diagram displays a warning and provides a stub class.