Repository navigation
v0.13.0
erdify 0.13.0 — one ERD generator for every Python schema in your repository.
Warning
Breaking: a run that finds no tables now exits 1 instead of 0 and writes nothing. Pass --allow-empty (or set allow_empty = true under [tool.erdify]) to restore the previous behavior. Details below.
Changed — breaking
-
A run that finds no tables now exits
1instead of0, and writes
nothing. Up to 0.12.3 it warned, wrote a structurally valid but empty
diagram, and exited0— so a CI job that commits the regenerated ERD
silently replaced a good diagram with an empty one whenever--include
stopped matching, which a rename or a moved package is enough to cause. The
overwhelmingly likely cause of zero entities is a misconfiguration, so that
is now an error.Failing before generation means an existing output file is left untouched.
If an empty schema is a legitimate outcome for your project — everything
filtered out by--exclude, a--sourcesfilter that matches nothing, a
schema mid-migration — pass--allow-emptyor setallow_empty = trueunder
[tool.erdify]. That restores the previous behavior exactly.
Added
- New documentation page Comparison — erdify next to eralchemy,
sqlalchemy-schemadisplay, erdantic,django-extensions graph_modelsand
DBML/dbdiagram, on the axes that actually differ (live connection, importing
your code, frameworks covered, runtime dependencies, output formats, CI drift
gate), including where each alternative is the better choice. - New documentation page Python Parsing Limitations — the Python-side
counterpart to the SQL frontend's "Deferred / Not Supported" table: what the
AST parser cannot see (runtime-constructed models, non-literal
__tablename__,__table_args__, composite foreign keys, foreign keys inside
sa_column, unannotatedrelationship()assignments) and what to do instead. - New documentation page Troubleshooting — symptom-first fixes for models
not being found, too many entities, missing relationships and missing keys on
Pydantic/dataclass models. - Every documentation page now carries its own
descriptionfrontmatter, so
each page gets its own search-engine snippet and social-card subtitle instead
of repeatingsite_description. --allow-empty(andallow_emptyin[tool.erdify]) opts back in to the
pre-0.13.0 behavior for an empty result: warn, write the empty diagram, exit
0. See the breaking change below.- erdify now ships
.pre-commit-hooks.yaml, so it can be used as a pre-commit
repository instead of arepo: local/language: systemhook that requires
erdify to be installed in the consumer's environment first. Two ids are
provided:erdifyregenerates the diagram (pre-commit fails the commit when
the file changed), anderdify-checknever writes and exits non-zero when the
committed diagram has drifted.--checkis part of the latter's entry point,
so overridingargscannot drop it. SQL DDL projects add
additional_dependencies: ['sqlglot>=25']rather than using a separate id. - The documentation site now renders a social card (
og:image) for every page,
so links shared on chat, social and link-preview surfaces show a real card
instead of a bare text entry. This enables mkdocs-material'ssocialplugin,
which pulls in themkdocs-material[imaging]dependencies and their system
libraries in the docs workflow. - The changelog is published as a page on the documentation site. It includes
the repository'sCHANGELOG.mdverbatim viapymdownx.snippets, so there is
still a single source of truth. - Every documentation page now has an edit link back to its source on GitHub
(content.action.edit;edit_uriwas already configured but Material never
rendered the button without the feature) and previous/next navigation in the
footer (navigation.footer).
Changed
-
The "No tables found" message now ends with a link to the troubleshooting
page, which did not exist when the message was written. -
The Datadog coverage upload is now also skipped for Dependabot. The existing
fork check covers pull requests from forks, but a Dependabot pull request's
head branch lives in this repository, and GitHub runs those with Dependabot
secrets rather than Actions secrets — so the step would have run with an
empty key and failed the requiredTests passedcheck on every dependency
bump. The condition matches on the actor: secrets cannot be referenced in an
if:conditional, and the documented job-level-env workaround would put the
API key in the environment of every step in the job. -
SECURITY.mdscopes its absolute claims to the core install. "Does not
execute / import / connect / send" holds for the stdlib-only core; the
erdify[sql]extra runs third-party code (sqlglot) in your process and is now
described as its own trust boundary. Added:--output/--injectdo write to
the paths you name, and the rendering step (PlantUML server, Mermaid, browser)
is outside erdify's control. The response times are stated as what a small
team aims for rather than a service-level guarantee. -
docs/usage/ci.mdleads with the--checkdrift gate and presents the
auto-commit workflow as the alternative, with its trade-off stated. The
workflow examples keep floating action tags for readability, and a note now
says so explicitly and tells readers to pin to a SHA in their own repository —
as erdify's own workflows do. -
Reduced decorative emoji in
SECURITY.mdandCONTRIBUTING.md, which people
reach when something is wrong or when they are trying to get set up. -
The "No tables found" warning is now actionable: it names the active
--includepatterns, reports how many.py/.sqlfiles were scanned and how
many matched, and distinguishes "nothing matched the patterns" (the usual
cause —--includedefaults tomodels.py, so models in e.g.schema.pyare
never seen) from "files matched but held no recognized models". -
The README now answers "why erdify and not X" right after the feature list,
with a condensed comparison table and a link to the full one. -
The README shows its example ERD as a live Mermaid diagram injected with
erdify --injectinstead of a committed PNG — the format the README itself
advertises as rendering natively on GitHub. Areadme-erdpre-commit hook
runs the same command with--check, so the embedded diagram cannot go stale
(and it dogfoods both flags on the project's own front page). -
The README badge row is down from ten to six: PyPI version, Python versions,
License, Tests, Coverage and a new docs badge. The Linting, Ruff, mypy and
download badges added rows without adding information a reader acts on. -
The PyPI project page now links to the documentation site
(https://erdify.devsuit.io/) instead of the README anchor on GitHub, and
gainsChangelogandIssueslinks. -
[tool.ruff] target-versionispy311, matchingrequires-python = ">=3.11"
instead of contradicting it withpy310. -
The documentation home page now leads with what erdify is, the
framework-comparison diagram and a three-line install-and-run, instead of
restating the sidebar. TheComparison,Python Parsing Limitationsand
Troubleshootingpages are in the nav. -
docs/frameworks/index.mdloads its second example image from the repository
instead ofraw.githubusercontent.com, matching the first one on the page. -
The Mermaid section of
docs/usage/output-formats.mdshows the.mmdsource
and the rendered diagram in side-by-side tabs; the rendered-only fence never
showed readers what the file actually contains. -
The required
Tests passedcheck now fails for a pull request from the
machine-writtenbadgesbranch intomain(the only base the test workflow
runs for). GitHub cannot bar a branch from being a pull-request source, and
such a pull request would otherwise look mergeable while replacing the README
onmainwith the branch's own. -
Test coverage is now uploaded to Datadog Code Coverage from the Linux /
Python 3.13 matrix leg, withcode-coverage.datadog.yamldefining the
service mapping and 90% total/patch PR gates (matching the existing
fail_under), andservice.datadog.yamlregistering erdify in the Datadog
Software Catalog. The upload is skipped on pull requests from forks, which
have no access to repository secrets; the workflow deliberately stays on the
pull_requesttrigger. -
The README now carries a coverage badge. Datadog exposes no public badge
endpoint, so pushes tomainpublish the percentage as a shields.io endpoint
payload on the orphanbadgesbranch of this repository, committed by
github-actions[bot]with the workflow's built-inGITHUB_TOKEN. Pull
requests never update it. Keeping the payload in the repository rather than in
a Gist or a third-party badge service means no personal credential is involved
and the badge survives any contributor leaving. -
CI now resolves
uvtolatest-knowninstead oflatest, so the version
installed in every workflow (including the PyPI publish job) is one whose
checksum ships with the pinnedsetup-uvrelease. Newuvversions reach CI
only through asetup-uvbump, which arrives as a reviewed, cooldown-gated
Dependabot PR. -
Dependabot's
github-actionsversion-update group now includesmajor, so
major action bumps arrive as a single grouped PR instead of one PR each. The
uventry deliberately keeps majors separate, and security updates are
unaffected in both.
Install: pip install erdify · Docs: https://erdify.devsuit.io/ · Full diff: v0.12.3...v0.13.0