Skip to content

[TASK] Consolidate documentation into README and docs/ - #596

Merged
Kanti merged 15 commits into
webdevops:masterfrom
andersundsehr:docs/consolidate-documentation
Nov 7, 2026
Merged

Kanti merged 15 commits into
webdevops:masterfrom
andersundsehr:docs/consolidate-documentation

Conversation

@Kanti

@Kanti Kanti commented Nov 7, 2026

Copy link
Copy Markdown
Collaborator

Summary

One documentation for the images, checked against the current images:

  • Removed: the Sphinx/readthedocs and GitBook docs (documentation/, .gitbook.yaml, Makefile target documentation), the per-image docker/*/README.md files and provisioning/README.md. They described images, tags and options that no longer exist.
  • New docs/: one page per image family; every environment variable with its default; customization (commands, start and build scripts, tools for your Dockerfile, services, cron jobs, configuration files, supervisord, locales, application user); guides for file permissions and UID, Xdebug with an IDE, mail, platforms and nightly updates, production, more PHP extensions, Debian or Alpine, uploads and long requests, cron time zone, healthcheck.
  • docs/known-issues.md: options and tools that do not work, with affected images and workaround; build tools that need Python 2; migration notes.
  • README.md: changed only where needed: docker compose quick start, links to docs/, GitHub Actions badge, building locally.
  • AGENTS.md (new): documentation is updated in the same PR and checked in a running container.
  • conf/console.yml: imagePath pointed into the removed documentation/; it now points to graph/.

The images themselves are not changed.

How it was verified

Every documented statement was tried in a running container (images published on 2026-11-05 and 2026-11-07), on Debian and Alpine, and on PHP 8.2 and 8.5 where it can differ. Scripts check that no option name was missed, that the tag lists in the README match .github/workflows/build.yaml, that all links and anchors resolve, and that make provision leaves the tree unchanged.

The checks for each commit and a checklist with one line per option are in andersundsehr#4.

Not run: a full ./build-local.sh and make structure-test. Xdebug was checked with Docker Engine on Linux, not with Docker Desktop.

Kanti added 15 commits November 6, 2026 11:49
Remove the Sphinx/readthedocs and GitBook documentation, .gitbook.yaml, the per-image READMEs under docker/ and provisioning/README.md. All of them describe images, tags and options that no longer exist. Also drop the Makefile target that served the Sphinx documentation.
Add docs/ with one page per published image family, all environment variables with their defaults, and the customization hooks (commands, start and build scripts, services, cron, application user). Every option was checked in the published images on Debian and Alpine; options that do not work are left out.
Add a docker compose quick start and links to docs/, replace the GitLab badge with the GitHub Actions badge, and drop the readthedocs/GitBook links, the GitLab CI note and the image that lived in documentation/. Correct statements that no longer hold: the CI is a GitHub Actions workflow generated by 'ci/console github:generate-ci', the Debian images are based on bookworm, and the Dockerfile.jinja2 files in docker/ are hand-maintained sources.
Add AGENTS.md: changes that affect image users must update README.md and docs/ in the same pull request, verified in a running container on Debian and Alpine, with the checks listed in the pull request description.
- FTP_PATH has no effect; uploads go to /home/<FTP_USER>. Fix the vsftp example.
- Cron jobs need absolute paths (PATH lacks /usr/local/bin); fix the example.
- Apache appends WEB_DOCUMENT_INDEX after its own index files.
- The cli command only works in base-app and php-* images.
- Document configuration file locations, including the TLS certificate.
- PHP_DISMOD matches by substring, VIRTUAL_HOST keeps one wildcard, the FPM pool section is [www].
- README: CI runs the tests defined for each image.
- AGENTS.md: check every image a statement names.
…se-app tools

- PHP_DEBUGGER=blackfire: the blackfire-agent service restarts in a loop
- LOG_STDOUT: Apache and vsftpd also write to /docker.stdout
- nginx and apache pages: the bundled certificate expired on 2025-05-01
- base-app: list the tools it adds
imagePath still pointed to documentation/docs/resources/images/, which
was removed with the old documentation. make graph would recreate it.
- docs/known-issues.md: options and tools that do not work, with
  affected images, workaround and issue; build tools; migration notes
- docs/README.md: webdevops/toolbox and webdevops/dockerfile-build-env,
  dashed COPY --from edges in the diagram, link to known issues
- environment-variables.md: link to known issues, ini order,
  PHP_SENDMAIL_PATH in the FPM pool, COMPOSER_VERSION at start only
- Configuration files: shipped Nginx, Apache, PHP and supervisord files,
  placeholders and what they mean for :ro and read-write mounts
- Tools for your Dockerfile: apt-install, apk-install,
  docker-image-cleanup, go-replace, gosu, docker-service,
  docker-cronjob, docker-run-bootstrap, per image
- Locales per image, supervisorctl program names
- php.md: Composer in Dockerfiles, session upload progress for apps
- README: building single images and build-local.sh, what no longer
  works, reworded support intro with a link to known issues
- AGENTS.md: repository map, build and test commands, rule that
  known issues are never documented as working
- known-issues.md: drop the empty issue lines, keep links to existing
  upstream issues; own entry for the latest and alpine tags of the PHP
  images (last built 2020/2019)
- AGENTS.md: list non-working options in known-issues.md instead of
  opening an issue
- nginx, php-nginx: Nginx restart loop without IPv6
- php-nginx-dev, php-apache-dev: SSH without passwords
- vsftp: FTP_PATH has no effect
- nginx, apache, base: Alpine 3.11
- php: latest/alpine tags, Xdebug variables, Blackfire agent
- environment-variables: XDEBUG_* variables write into php.ini
- AGENTS.md: list all topics of customization.md
PHP-FPM listens on [::]:9000 in php, php-dev, php-nginx-dev and
php-apache-dev and does not start in a container without IPv6.
php-nginx and php-apache listen on 127.0.0.1:9000 and are not
affected. The start script now also changes the PHP-FPM listen
address, and the image pages link to the entry.
- customization.md: run commands as application, change UID/GID in
  an own image, cron time zone (TZ), healthcheck examples
- php.md: installing more extensions (docker-php-ext-install, PIE),
  Debian or Alpine, production defaults, mail with and without -dev
  (Mailpit), Xdebug with an IDE
- environment-variables.md: uploads and long requests
- docs/README.md, README.md: platforms, nightly rebuild, digest pinning
- known-issues.md: images on ghcr.io cannot be pulled without login
- AGENTS.md: documentation table lists the new topics
- environment-variables.md: add TZ; link APPLICATION_GID to the UID
  section; POSTFIX_RELAYHOST example without login (port 25)
- Apache: LimitRequestBody (1 GiB default) applies to static files,
  not to requests passed to PHP-FPM
- Xdebug CLI example runs as application
- customization.md: SSH paragraph back under "Application user"
- php.md: download size only in the Debian/Alpine table
- ghcr.io is internal: removed from docs/README.md and known-issues.md,
  README says so in "Building in CI"
- README: links to known issues and the PHP guides
@sonarqubecloud

sonarqubecloud Bot commented Nov 7, 2026

Copy link
Copy Markdown

@Kanti
Kanti merged commit c1acb53 into webdevops:master Nov 7, 2026
183 checks passed
@Kanti
Kanti deleted the docs/consolidate-documentation branch November 7, 2026 15:06
Kanti added a commit to andersundsehr/Dockerfile that referenced this pull request Nov 8, 2026
Since webdevops#596 the documentation shows how the images build on each other
as a Mermaid diagram; nothing uses the Graphviz image anymore.

Removed: conf/diagram.yml, the generate:graph command and its
registration in bin/console, the Makefile targets graph and graph-full,
imagePath and graph.label in conf/console.yml (and imagePath in the path
list of bin/console and the defaults of Configuration.py), graphviz in
bin/requirements.txt and in the dockerfile-build-env image, and /graph
in .gitignore. README, AGENTS.md and the build tools known issue name
make provision as the only Python 2 target.
Kanti added a commit that referenced this pull request Nov 9, 2026
…ftovers (#599)

* [TASK] Move checks from unused tests into the tests the CI runs

The CI picks structure-test suites per built tag, so the suites for
old tags no longer ran, and some serverspec examples were never
included. Their checks that still apply now run for every tag:

- base-app: bzip2 for all tags; sponge (moreutils) for ubuntu-22.04
- base: netstat and sed for all tags
- bootstrap: PATH for all tags
- serverspec: docker-image-info dist-codename matches os-release on
  Debian and Ubuntu (the templates use it at build time)
- serverspec: syslog-ng is installed in all PHP images

The alpine suites of base and base-app are now covered by the common
test.yaml. build.yaml is regenerated for the new suite paths.

* [TASK] Remove tests that never run

- serverspec: apache-dev_spec.rb (no such image), php-official_spec.rb
  (copy of php_spec.rb; the php job publishes php-official), and the
  unused examples base-app::packages, php::pear, python::toolchain,
  misc::graphviz, misc::letsencrypt, collection::bootstrap::upstream-image
- testinfra: the only test was for webdevops/liquibase; also remove
  conftest.py and tests/__init__.py

* [TASK] Remove unused template macros

docker.add, docker.volume, environment.mailbox, provision.registerRole
and provision.runRoleInline are not called anywhere. Generated
Dockerfiles are unchanged.

* [TASK] Remove Makefile targets that do not work

Keep provision, graph and graph-full (Python 2, inside
dockerfile-build-env), structure-test and setup, which the
dockerfile-build-env image runs while it is built. Remove list, full,
all, build, push, test and the image groups, which point to images
that no longer exist. Drop webdevops/ansible from conf/diagram.yml.
README, AGENTS.md and the build-tools known issue describe the
remaining targets.

* [TASK] Fix review findings in the moved tests

- Move the sponge check from the ubuntu-22.04 structure-test suite to
  serverspec, conditional on Ubuntu, so it does not depend on the tag
  name. build.yaml is regenerated.
- Remove the PATH check from the bootstrap alpine suite; the common
  test.yaml has it.
- tests/structure-test/run.sh: test every directory with a test.yaml
  (php-dev and php-nginx were missing) and exit non-zero if any image
  fails, not only the last one.

* [TASK] Remove more PHP 5 leftovers from provisioning

- 20-php-module-blackfire.sh only deleted files under /etc/php5.
- logrotate.d/php5-fpm rotated /var/log/php5-fpm/*, which does not
  exist.
- 10-php.sh (dev) and 20-setup-php-fpm.sh: drop the branches for PHP
  older than 5.6; the [::]:9000 listen line now runs unconditionally,
  as it already did for every built image.

* [TASK] Restore make list and describe the Makefile precisely

- Keep list as the first target, so a bare make lists the targets
  instead of running setup.
- README, AGENTS.md and the build-tools known issue name graph-full,
  AGENTS.md says which images make structure-test and the CI test.

* [TASK] Remove dead PHP-FPM and opcache settings

- 20-setup-php-fpm.sh removed the literal file "PHP_MAIN_CONF" instead
  of $PHP_MAIN_CONF.
- clear_env exists in all supported PHP versions, so the workaround for
  PHP-FPM without it (PHP_CLEAR_ENV_AVAILABLE, 11-clear-env.sh) is gone.
- PHP_VERSION in 10-php-init.sh was not used; 30-setup-ioncube.sh sets
  its own.
- opcache.fast_shutdown no longer exists since PHP 7.2; it is removed
  from php.webdevops.ini and from the development settings.
- The structure tests name what 10-php-init.sh and 11-php-conf.sh do.
- .editorconfig no longer has sections for DOCKER_REPOSITORY and
  DOCKER_TAG_LATEST, which do not exist.
- `make` no longer prints "No rule to make target 'no_targets__'".

* [BUGFIX] Start Nginx and PHP-FPM without IPv6

Nginx listens on [::]:80 and [::]:443, PHP-FPM in php, php-dev,
php-nginx-dev and php-apache-dev on [::]:9000. Without IPv6 in the
container both failed with "Address family not supported by protocol"
and supervisord restarted them over and over.

If /proc/net/if_inet6 does not exist, the start scripts now remove the
listen [::] lines from the Nginx files and let PHP-FPM listen on
0.0.0.0 instead of [::]. With IPv6 nothing changes. A file that cannot
be changed, for example one mounted read-only, gets a warning instead
of stopping the container.

The known issue is removed; the image pages say how Nginx and PHP-FPM
listen, and the configuration file section mentions read-only Nginx
files with listen [::].

* [TASK] Make make structure-test strict and check sponge on Debian

- tests/structure-test/run.sh tests only the tags that the CI builds
  (the -t "webdevops/..." lines in build.yaml), so old local tags no
  longer fail the run. It fails if docker cannot list the images or if
  no image was tested, instead of exiting 0.
- base-app::moreutils also runs on Debian, so the PHP images on Debian
  check sponge as well.
- The build tools known issue names which images the CI tests and shows
  make structure-test as the local check; AGENTS.md describes the new
  behaviour.

* [BUGFIX] Rewrite mounted files in place in the IPv6 fallback

sed -i writes a temporary file and renames it over the original. For a
single file mounted read-write, for example ./vhost.conf mounted to
/opt/docker/etc/nginx/vhost.conf, the rename fails with "Device or
resource busy", so Nginx still did not start without IPv6. A file in a
mounted directory was replaced by a new file.

The start scripts now write the result back into the same file, as
go-replace does for the placeholders. In a read-write mount the listen
lines change on the host as well; a file mounted :ro still gets the
warning, and Nginx or PHP-FPM does not start.

* [BUGFIX] Leave mounted Nginx files alone, let PHP-FPM fall back to IPv4

PHP-FPM listens on the port only (listen = 9000) instead of [::]:9000.
PHP-FPM then binds to :: itself and falls back to 0.0.0.0 if the
container has no IPv6, so the rewrite at start is gone. With IPv6 the
socket is the same as before: neither form sets IPV6_V6ONLY.

Without IPv6, the Nginx start script now changes only files in the
container's own file system, such as the image's vhost.conf and files
added with COPY. Mounted files (bind mounts, volumes, ConfigMaps) are
never changed, so a developer without IPv6 does not lose the listen [::]
lines in the project; a warning names the file instead. Warnings go to
stderr, because the provisioning output is discarded unless the
container runs supervisord or noop.

The loop reads find -print0 with its own variable names instead of
overwriting FILE of includeScriptDir, follows symlinks (ConfigMaps), and
skips hidden directories such as ..data, so every file is handled once.

* [TASK] Test identical images once in make structure-test

latest and ubuntu-22.04 of bootstrap, base and base-app are the same
image; run.sh tested them twice when both tags existed locally. A tag
whose image and suites were already tested is now skipped with a note.

The error message for "no image tested" lists the suites from an array
instead of an unquoted $(ls ...) (shellcheck SC2046).

* [TASK] Remove the image graph generation

Since #596 the documentation shows how the images build on each other
as a Mermaid diagram; nothing uses the Graphviz image anymore.

Removed: conf/diagram.yml, the generate:graph command and its
registration in bin/console, the Makefile targets graph and graph-full,
imagePath and graph.label in conf/console.yml (and imagePath in the path
list of bin/console and the defaults of Configuration.py), graphviz in
bin/requirements.txt and in the dockerfile-build-env image, and /graph
in .gitignore. README, AGENTS.md and the build tools known issue name
make provision as the only Python 2 target.

* [TASK] Keep the Nginx IPv6 listen directives in their own files

Nginx has no fallback like PHP-FPM: listen [::] fails without IPv6, also
with ipv6only=off. Instead of searching all configuration files and
leaving mounted ones alone, the two listen [::] directives of the
default vhost now live in vhost.ipv6/listen-80.conf and listen-443.conf.
vhost.conf includes them with a wildcard, so missing files are fine,
and the start script only deletes these files if the container has no
IPv6. No other file is changed; a file of one's own with listen [::]
keeps nginx from starting without IPv6, as before.

* [TASK] Check the IPv6 listen files in nginx::layout

serverspec now checks the vhost.ipv6 directory, that vhost.conf
includes listen-80.conf and listen-443.conf, and the two files with
their listen [::] directives, so the CI notices if they are missing in
an image. The start script deletes the files if the kernel has no IPv6;
serverspec runs on the Docker host, which shares its kernel with the
container, so without IPv6 the test expects the files to be gone.

* [TASK] Stop run.sh with a clear message on Bash 3

run.sh uses declare -A and mapfile, which need Bash 4. With the Bash
3.2 of macOS, make structure-test failed with "declare: -A: invalid
option" and "mapfile: command not found". The script now checks the
version first and points to webdevops/dockerfile-build-env, and it runs
the first bash in PATH instead of /bin/bash.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant