Installation
See the
packages.ddev.com). Your existing Gemfury (pkg.ddev.com) setup keeps working, but please re-run the ; you can run it for install or upgrade.
ddev delete images or ddev delete images --all after upgrading to free up disk space used by previous Docker image versions. This does no harm.ddev config --auto to update your projects to current configuration.Highlights
- Database seeding and reset:
ddev start --seed-snapshot=<name-or-path>fills a new database from any snapshot, andddev start --reset-databasedeletes the current database and starts fresh, see Snapshots and Database Seeding below - MySQL 9.7 LTS support, and MySQL 8.0/8.4 now build from
- Set things once for every project: global Dockerfiles in
~/.ddev/web-build/and~/.ddev/db-build/, and global env files in~/.ddev/.env*, see Global Configuration below - apt/rpm packages are now published to Cloudsmith (
packages.ddev.com) as well as Gemfury, and the yum repo now verifies package signatures, which the Gemfury one never did. Gemfury (pkg.ddev.com) is still supported but will be retired eventually; see the Linux note above to switch over
Snapshots and Database Seeding
- A snapshot named
seedis automatically loaded when you start a project with an empty database. So if you delete your db or project and thenddev start, you'll have the database from theseedsnapshot. - deletes the database and starts fresh. It takes a snapshot first, using the database version that created the data, so this also works when you already changed
database:in your config.ddev config --database=now warns instead of failing, andddev deleteno longer refuses to work on a project whose data came from a different database server ddev snapshot restore --forcerestores a snapshot made by a different version of the same database serverddev snapshot --listshows each snapshot's size and database versionddev snapshot restoreandddev snapshot --listalso see snapshots from other Git worktrees of the same repository, so a database doesn't have to be copied between worktrees by hand- Snapshots and the database seed can skip compression with
--uncompressed: more disk space, faster restore. Thebase_dbseed also reads zstd now, not only gzip, which is much faster for a customdbimagewith a large database built into it, thanks to in~/.ddev/web-build/and~/.ddev/db-build/add the same image changes to every project - CA certificates, system tools, extra apt packages. If a project has a file with the same name in its own.ddev/web-build/, the project file is used, thanks to~/.ddev/.envand~/.ddev/.env.<service>set variables for every project. This is the only way to set a variable globally for a container other thanweb, sinceweb_environmentonly reachesweb. If a project sets the same variable, the project value is used. Write these files with 2.x/3.x, thanks to , thanks to add-on isn't needed, thanks to checks installed add-ons against their latest GitHub release and updates the outdated ones, with--dry-runto see what would change - New removes one of the project's Docker volumes by name or from an interactive list, for add-ons like ddev-solr that create their own
- New
- New
- The
ddev sshandddev execpass yourTERMandCOLORTERMinto interactive sessions, so you get more than 16 colors, thanks to- The
Bug Fixes for Regressions from v1.25.3
- Project image builds are fast again. Permissions on the Node.js directory were being changed recursively on every build, and now they are set once when the image is built
- Add-ons and apps that write log files straight into
/var/logcan do that again, after the directory was locked down to root only - A site that generates
/robots.txtitself works again, including Drupal's RobotsTxt module. An nginx rule was answering/robots.txtbefore your site could, and it is now removed - Projects that pin the web service to a specific platform, like
platform: linux/amd64on an Apple Silicon Mac, start again - Orphan containers get removed again, so Docker Compose stops warning about them
Bug Fixes
ddev wpuses the path from your project's ownwp-cli.ymlagain, and only falls back to the docroot when that file doesn't set one, which is what the docs always said. Since v1.24.5 it always added--path=$DDEV_DOCROOT, which broke Bedrock and any layout where WordPress isn't in the docroot- Running
ddevin a subdirectory that has its own.ddev/config.yaml, like a Drupal contrib module or a Git submodule, keeps using the outer project and tells you which one it chose. Before, it switched to the nested project silently, and the outer project's custom commands stopped working.ddev startthere asks whether you want the nested project - DDEV stops writing database connection settings into your CMS config when there's no db container or you configured a different database. That fixes TYPO3 projects using
omit_containers: [db], which failed to install withgetaddrinfo for db failed, and a TYPO3 SQLite setup that got switched back to MySQL on every restart. thanks to - Your
pre-/post-import-dbandpre-/post-import-fileshooks now run when a provider does its own importing withdb_import_command/files_import_command, and those pulls no longer print a "skipping database pull" warning that wasn't true - When port 80 or 443 is already taken and DDEV uses a different port instead,
ddev-routerremembers that. Before, after the program using that port stopped, starting another project rebuilt the router for no reason - Drupal 10, 11, and 12 projects handle a page with unusually large HTTP headers instead of failing with a 502 error. Drupal test runs hit this, since they report deprecation notices in the response headers, thanks to
Breaking Changes
xdebug_enabledis gone fromddev describe -j. It reported project config, not live Xdebug status, so useddev xdebug statusfor that. This only affects a custom GUI or script that read the field, thanks to . thanks to- A
docrootorupload_dirsvalue in.ddev/config.yaml, or a path you pass toddev dotenv, now gives a clear error when it points outside the project, instead of DDEV silently reading and writing files there
Internal Changes
ddev-webserverexplains the 403s and 404s it generates itself instead of serving a bare error page, since those usually mean a wrongdocrootor a project that isn't installed yet, andddev-routerdoes the same for a hostname that matches no project. A 403 or 404 from your own application is passed through unchanged. This replaces the "docroot may be wrong" warning onddev start, which you couldn't see in a browser and which warned wrongly when.htaccessrewrites into a subdirectoryddev-php-baseis consolidated intoddev-webserveras local build stages, so a new base image no longer has to be pushed to Docker Hub beforeddev-webservercan reference it.ddev/ddev-php-baseandddev/ddev-php-prodare no longer published and stay at their last-pushed tag; theddev-webserverimage itself behaves the same- Per-project certificates no longer carry a shared
*.<TLD>wildcard SAN, which Traefik 3.7.6+ would use to serve one project's certificate for every hostname on a shared custom TLD. v1.25.3 shipped Traefik 3.6.13, which isn't affected. The obsolete*.ddev.localSAN is also gone from the global default certificate - Under rootless Docker or Podman, the host's
usr.sbin.mysqldAppArmor profile attaches to the container's mysqld and left it unable to read/etc/my.cnf. That profile is loaded on any Linux machine withmysql-serverinstalled, and the newdhi.io/mysqlbase puts mysqld at the path it matches. MySQL 8.0, 8.4, and 9.7 now load their config with an explicit--defaults-fileinstead - A nightly performance benchmark harness feeding a tracking per test type across GitHub Actions and Buildkite
- Rootless Podman CI setup reworked,
podman-rootCI dropped DDEV_DOCKER_ORGpoints a binary at a different Docker Hub organization, so a release built outsideddev/ddevcan be pull-tested end to endlast_started_versionis recorded by every command that starts containers, not onlyddev start/ddev restart, so you stop being asked for addev poweroffthat isn't needed.ddev start -yrecords it too- Three fixes toward Apple Container and socktainer support ( ( in ( in ( in ) [skip ci] by
- fix(mysql): build mysql 8.0/8.4 from Docker Hardened Images, fixes in in ) [skip ci] by
- docs(commands): add precision about
launchwhich start project, fixes in by - fix(router): remove obsolete *.ddev.local from generated certs, fixes in ) [skip ci] by
- feat(commands): add
ddev tableproglobal host command by - fix(build): honor service platform override when building images, fixes in by
- chore: Updates to the settings.php for the drupal11 and drupal12 project types by
- docs(quickstart): update Shopware 6 references to up-to-date information by
- fix(buildkite): run orb start/stop synchronously so orbstack reliably ends up running ( in by
- chore: replace github.com/sponsors/ddev with ddev.com/sponsor by
- docs: expand CLAUDE.md language rules to curb AI-nonsense words and ego-stroking [skip ci] by
- docs(quickstart): work around Drush/Guzzle 8 conflict in Drupal 12 install ( in in in ) [skip ci] by
- feat: add support for global Dockerfiles, fixes ) [skip ci] by
- fix(nodejs): stop recursively chgrp/chmod'ing /usr/local/n on every project build, fixes in ) [skip ci] by
- fix(describe): omit xdebug_enabled from describe output, fixes ) [skip ci] by
- fix: don't write CMS db connection settings when db container is omitted or another driver is configured, for ) [skip ci] by
- feat(maho): add Maho project type by
- docs(quickstart): pin quickstart to Symfony LTS, fixes symfony.bats failures [skip ci] by
- fix: reject symlinks with rooted/absolute targets in Untar, for ) [skip ci] by
- perf(router): update network aliases in place instead of recreating on start, for ) [skip ci] by
- build(docker): consolidate ddev-php-base into ddev-webserver, fixes in ) [skip ci] by
- ci(podman): force nftables firewall backend to avoid intermittent netavark failure [skip ci] by
- test(macos-docker-desktop): skip tests hitting a Docker Desktop connection reset by
- feat: add MySQL 9.7 LTS support, fixes in in ( in ( in ) [skip ci] by
- fix(compose): remove BuildKit snapshot race retry logic, for in by
- docs: Remove obsolete Lullabot nodejs link ( in ) [skip ci] by
- fix(docker): restore /usr/local/n and make /var/log group-0-writable, fixes by
- fix(router): skip TestRouterNotRebuiltOnHostnameChange on Windows, fixes ) [skip ci] by
- docs(webserver): condense the 404 explanation comments, for ) [skip ci] by
- feat(webserver): explain webserver-level 403s, fixes ( in in ) [skip ci] by
- fix(webserver): don't let a failing global-cache chown kill the container by
- feat(dbserver): support zstd-compressed base_db for faster first-boot restore by
- test(db): fix filepath formatting in test [skip github] by
- ci(github): pin setup-homebrew, drop dead setup-sandbox input ( in ) [skip ci] by
- feat(perf): add nightly performance benchmark harness by
- fix(perf): fix bugs found validating the nightly benchmark harness end-to-end ( in in in ) [skip ci] by
- test(quickstart): statamic output changed, fix assertion by
- build: bump the actions group with 4 updates by
- docs: update config.md for minor typos, for ) [skip ci] by
- fix(modx): add missing 403 in nginx, use
ddev php, for in ) [skip ci] by - test(quickstart): derive URLs from
ddev describe -jinstead of hardcoding ddev.site [skip buildkite] by - feat(snapshot): show size and DB version in
ddev snapshot --listby - fix(dockerutil): fall back to NetworkSettings.Ports in GetBoundHostPorts ( in ) [skip ci] by
- feat: forward TERM and COLORTERM to ddev ssh/exec sessions, fixes ) [skip ci] by
- fix: record last_started_version from every command that starts containers, fixes in ) [skip ci] by
- ci(podman): rework the rootless setup script and docs, drop podman-root CI by
- docs: reorganize README to put getting started first ( in ( in ) [skip ci] by
- fix(ddevapp): attach command output to failing provider and hook commands ( in ) [skip ci] by
- feat(images): record image tag in a com.ddev.image-tag label and warn when a pinned image is stale by
- docs(readme): add in-kind sponsors section ( in ( in by
- feat(containers): auto-detect content changes and tag/rebuild docker base images locally, for ) [skip ci] by
- fix(acquia): broken db import with long application names by
- ci: add placeholder image-build/image-push workflows for ) [skip ci] by
- fix(ci): quote placeholder workflow strings so ) [skip ci] by
- build: bump 1password/load-secrets-action from 4 to 5 by
- build(public-variables): Add DOCKER_ORG [skip ci] by
- feat(images): Automatically push and then test new images when changes made, fixes in in ) [skip ci] by
- docs(comments): Clean up comments missed in ) [skip ci] by
- feat: publish apt/rpm packages to Cloudsmith to replace (gradually) Gemfury, fixes in by
- test(mutagen): Minor test cleaup [skip ci] by
- fix(images): gate fork image builds on approval earlier, skip it for authorized authors ( in ) [skip ci] by
- fix(addon): tolerate numeric default_branch in add-on registry JSON ( in ) [skip ci] by
- feat(amplitude): report add-on repository to Amplitude, fixes in in ) [skip ci] by
- ci(perf): track total CI runtime per test type across GitHub Actions and Buildkite ( in ( in ( in , fixes in ) [skip ci] by
- test(mutagen): we don't need some mutagen testing [skip buildkite] ( in in by
- ci: comment on PRs included in a release ( in in ( in ) [skip ci] by
- fix(wordpress): let wp-cli.yml override the docroot, fixes in ( in ) [skip ci] by
- fix: reject path traversal in docroot, upload_dirs, and dotenv path validation by
- build(go): bump all go.mod dependencies ( in ) [skip ci] by
- fix(compose): always use RemoveOrphans option, fixes in by
- fix(buildx): skip sha verification on macOS for versions before v0.36.0, for in by
- build: bump actions/upload-artifact from 4 to 7 in the actions group ([bot] in ( in ( in ) [skip ci] by
- feat: add gitignored .env.local, labeled, and global .env files, fixes by
- feat: add ddev launch --print-url flag and DDEV_LAUNCH_PRINT_URL env var, fixes ) [skip ci] by
- feat(drupal): support symfony_mailer_lite in settings.ddev.php, fixes ) [skip ci] by
- fix: don't use nested project unless it's registered, fixes in ) [skip ci] by
- feat: add nodejs_root so Node.js version auto-detection can read a subdirectory, fixes ) [skip ci] by
- fix(dbserver): pin secure_file_priv for mysql 8.0, 8.4, and 9.7 by
- ci(debug): replace tmate with upterm [skip ci] by
- fix: update TestCmdVersion for release-tag image resolution ( in in in by
New Contributors
Full Changelog: v1.25.3...v1.25.4
SOCIAL SHARE CARD GENERATOR